Home | History | Annotate | Line # | Download | only in midgard
      1 /* Copyright (c) 2018-2019 Alyssa Rosenzweig (alyssa (at) rosenzweig.io)
      2  * Copyright (C) 2019-2020 Collabora, Ltd.
      3  *
      4  * Permission is hereby granted, free of charge, to any person obtaining a copy
      5  * of this software and associated documentation files (the "Software"), to deal
      6  * in the Software without restriction, including without limitation the rights
      7  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
      8  * copies of the Software, and to permit persons to whom the Software is
      9  * furnished to do so, subject to the following conditions:
     10  *
     11  * The above copyright notice and this permission notice shall be included in
     12  * all copies or substantial portions of the Software.
     13  *
     14  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
     15  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
     16  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
     17  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
     18  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
     19  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
     20  * THE SOFTWARE.
     21  */
     22 
     23 #include "midgard.h"
     24 
     25 /* Include the definitions of the macros and such */
     26 
     27 #define MIDGARD_OPS_TABLE
     28 #include "helpers.h"
     29 #undef MIDGARD_OPS_TABLE
     30 
     31 #include "midgard_ops.h"
     32 
     33 /* Table of mapping opcodes to accompanying properties. This is used for both
     34  * the disassembler and the compiler. It is placed in a .c file like this to
     35  * avoid duplications in the binary */
     36 
     37 struct mir_op_props alu_opcode_props[256] = {
     38         [midgard_alu_op_fadd]            = {"FADD", UNITS_ADD | OP_COMMUTES},
     39         [midgard_alu_op_fadd_rtz]        = {"FADD.rtz", UNITS_ADD | OP_COMMUTES},
     40         [midgard_alu_op_fadd_rtn]        = {"FADD.rtn", UNITS_ADD | OP_COMMUTES},
     41         [midgard_alu_op_fadd_rtp]        = {"FADD.rtp", UNITS_ADD | OP_COMMUTES},
     42         [midgard_alu_op_fmul]            = {"FMUL", UNITS_MUL | UNIT_VLUT | OP_COMMUTES},
     43         [midgard_alu_op_fmul_rtz]        = {"FMUL.rtz", UNITS_MUL | UNIT_VLUT | OP_COMMUTES},
     44         [midgard_alu_op_fmul_rtn]        = {"FMUL.rtn", UNITS_MUL | UNIT_VLUT | OP_COMMUTES},
     45         [midgard_alu_op_fmul_rtp]        = {"FMUL.rtp", UNITS_MUL | UNIT_VLUT | OP_COMMUTES},
     46         [midgard_alu_op_fmin]            = {"FMIN", UNITS_MOST | OP_COMMUTES},
     47         [midgard_alu_op_fmin_nan]        = {"FMIN.nan", UNITS_MOST | OP_COMMUTES},
     48         [midgard_alu_op_fabsmin]         = {"FABSMIN", UNITS_MOST | OP_COMMUTES},
     49         [midgard_alu_op_fabsmin_nan]     = {"FABSMIN.nan", UNITS_MOST | OP_COMMUTES},
     50         [midgard_alu_op_fmax]            = {"FMAX", UNITS_MOST | OP_COMMUTES},
     51         [midgard_alu_op_fmax_nan]        = {"FMAX.nan", UNITS_MOST | OP_COMMUTES},
     52         [midgard_alu_op_fabsmax]         = {"FABSMAX", UNITS_MOST | OP_COMMUTES},
     53         [midgard_alu_op_fabsmax_nan]     = {"FABSMAX.nan", UNITS_MOST | OP_COMMUTES},
     54         [midgard_alu_op_imin]            = {"MIN", UNITS_MOST | OP_COMMUTES},
     55         [midgard_alu_op_imax]            = {"MAX", UNITS_MOST | OP_COMMUTES},
     56         [midgard_alu_op_umin]            = {"MIN", UNITS_MOST | OP_COMMUTES},
     57         [midgard_alu_op_umax]            = {"MAX", UNITS_MOST | OP_COMMUTES},
     58         [midgard_alu_op_iavg]            = {"AVG.rtz", UNITS_ADD | OP_COMMUTES},
     59         [midgard_alu_op_uavg]            = {"AVG.rtz", UNITS_ADD | OP_COMMUTES},
     60         [midgard_alu_op_iravg]           = {"AVG.round", UNITS_ADD | OP_COMMUTES},
     61         [midgard_alu_op_uravg]           = {"AVG.round", UNITS_ADD | OP_COMMUTES},
     62 
     63         [midgard_alu_op_fmov]            = {"FMOV", UNITS_ALL | QUIRK_FLIPPED_R24},
     64         [midgard_alu_op_fmov_rtz]        = {"FMOV.rtz", UNITS_ALL | QUIRK_FLIPPED_R24},
     65         [midgard_alu_op_fmov_rtn]        = {"FMOV.rtn", UNITS_ALL | QUIRK_FLIPPED_R24},
     66         [midgard_alu_op_fmov_rtp]        = {"FMOV.rtp", UNITS_ALL | QUIRK_FLIPPED_R24},
     67         [midgard_alu_op_froundaway]      = {"FROUNDAWAY", UNITS_ADD},
     68         [midgard_alu_op_froundeven]      = {"FROUNDEVEN", UNITS_ADD},
     69         [midgard_alu_op_ftrunc]          = {"FTRUNC", UNITS_ADD},
     70         [midgard_alu_op_ffloor]          = {"FFLOOR", UNITS_ADD},
     71         [midgard_alu_op_fceil]           = {"FCEIL", UNITS_ADD},
     72 
     73         /* Multiplies the X/Y components of the first arg and adds the second
     74          * arg. Like other LUTs, it must be scalarized. */
     75         [midgard_alu_op_ffma]            = {"FMA", UNIT_VLUT},
     76         [midgard_alu_op_ffma_rtz]        = {"FMA.rtz", UNIT_VLUT},
     77         [midgard_alu_op_ffma_rtn]        = {"FMA.rtn", UNIT_VLUT},
     78         [midgard_alu_op_ffma_rtp]        = {"FMA.rtp", UNIT_VLUT},
     79 
     80         /* Though they output a scalar, they need to run on a vector unit
     81          * since they process vectors */
     82         [midgard_alu_op_fdot3]           = {"FDOT3", UNIT_VMUL | OP_CHANNEL_COUNT(3) | OP_COMMUTES},
     83         [midgard_alu_op_fdot3r]          = {"FDOT3R", UNIT_VMUL | OP_CHANNEL_COUNT(3) | OP_COMMUTES},
     84         [midgard_alu_op_fdot4]           = {"FDOT4", UNIT_VMUL | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
     85 
     86         /* Incredibly, iadd can run on vmul, etc */
     87         [midgard_alu_op_iadd]            = {"ADD", UNITS_MOST | OP_COMMUTES},
     88         [midgard_alu_op_ishladd]         = {"ADD", UNITS_MUL},
     89         [midgard_alu_op_iaddsat]         = {"ADDSAT", UNITS_ADD | OP_COMMUTES},
     90         [midgard_alu_op_uaddsat]         = {"ADDSAT", UNITS_ADD | OP_COMMUTES},
     91         [midgard_alu_op_uabsdiff]        = {"ABSDIFF", UNITS_ADD},
     92         [midgard_alu_op_iabsdiff]        = {"ABSDIFF", UNITS_ADD},
     93         [midgard_alu_op_ichoose]         = {"CHOOSE", UNITS_ADD},
     94         [midgard_alu_op_isub]            = {"SUB", UNITS_MOST},
     95         [midgard_alu_op_ishlsub]         = {"SUB", UNITS_MUL},
     96         [midgard_alu_op_isubsat]         = {"SUBSAT", UNITS_ADD},
     97         [midgard_alu_op_usubsat]         = {"SUBSAT", UNITS_ADD},
     98         [midgard_alu_op_imul]            = {"MUL", UNITS_MUL | OP_COMMUTES},
     99         [midgard_alu_op_iwmul]           = {"WMUL.s", UNIT_VMUL | OP_COMMUTES},
    100         [midgard_alu_op_uwmul]           = {"WMUL.u", UNIT_VMUL | OP_COMMUTES},
    101         [midgard_alu_op_iuwmul]          = {"WMUL.su", UNIT_VMUL | OP_COMMUTES},
    102         [midgard_alu_op_imov]            = {"MOV", UNITS_ALL | QUIRK_FLIPPED_R24},
    103 
    104         /* For vector comparisons, use ball etc */
    105         [midgard_alu_op_feq]             = {"FCMP.eq", UNITS_MOST | OP_TYPE_CONVERT | OP_COMMUTES},
    106         [midgard_alu_op_fne]             = {"FCMP.ne", UNITS_MOST | OP_TYPE_CONVERT | OP_COMMUTES},
    107         [midgard_alu_op_fle]             = {"FCMP.le", UNITS_MOST | OP_TYPE_CONVERT},
    108         [midgard_alu_op_flt]             = {"FCMP.lt", UNITS_MOST | OP_TYPE_CONVERT},
    109         [midgard_alu_op_ieq]             = {"CMP.eq", UNITS_MOST | OP_COMMUTES},
    110         [midgard_alu_op_ine]             = {"CMP.ne", UNITS_MOST | OP_COMMUTES},
    111         [midgard_alu_op_ilt]             = {"CMP.lt", UNITS_MOST},
    112         [midgard_alu_op_ile]             = {"CMP.le", UNITS_MOST},
    113         [midgard_alu_op_ult]             = {"CMP.lt", UNITS_MOST},
    114         [midgard_alu_op_ule]             = {"CMP.le", UNITS_MOST},
    115 
    116         /* csel must run in the second pipeline stage (condition written in first) */
    117         [midgard_alu_op_icsel]           = {"CSEL.scalar", UNIT_VADD | UNIT_SMUL},
    118         [midgard_alu_op_icsel_v]         = {"CSEL.vector", UNIT_VADD | UNIT_SMUL}, /* Acts as bitselect() */
    119         [midgard_alu_op_fcsel_v]         = {"FCSEL.vector", UNIT_VADD | UNIT_SMUL},
    120         [midgard_alu_op_fcsel]           = {"FCSEL.scalar", UNIT_VADD | UNIT_SMUL},
    121 
    122         [midgard_alu_op_frcp]            = {"FRCP", UNIT_VLUT},
    123         [midgard_alu_op_frsqrt]          = {"FRSQRT", UNIT_VLUT},
    124         [midgard_alu_op_fsqrt]           = {"FSQRT", UNIT_VLUT},
    125         [midgard_alu_op_fpow_pt1]        = {"FPOW_PT1", UNIT_VLUT},
    126         [midgard_alu_op_fpown_pt1]       = {"FPOWN_PT1", UNIT_VLUT},
    127         [midgard_alu_op_fpowr_pt1]       = {"FPOWR_PT1", UNIT_VLUT},
    128         [midgard_alu_op_fexp2]           = {"FEXP2", UNIT_VLUT},
    129         [midgard_alu_op_flog2]           = {"FLOG2", UNIT_VLUT},
    130 
    131         [midgard_alu_op_f2i_rte]         = {"F2I", UNITS_ADD | OP_TYPE_CONVERT | MIDGARD_ROUNDS},
    132         [midgard_alu_op_f2i_rtz]         = {"F2I.rtz", UNITS_ADD | OP_TYPE_CONVERT},
    133         [midgard_alu_op_f2i_rtn]         = {"F2I.rtn", UNITS_ADD | OP_TYPE_CONVERT},
    134         [midgard_alu_op_f2i_rtp]         = {"F2I.rtp", UNITS_ADD | OP_TYPE_CONVERT},
    135         [midgard_alu_op_f2u_rte]         = {"F2U", UNITS_ADD | OP_TYPE_CONVERT | MIDGARD_ROUNDS},
    136         [midgard_alu_op_f2u_rtz]         = {"F2U.rtz", UNITS_ADD | OP_TYPE_CONVERT},
    137         [midgard_alu_op_f2u_rtn]         = {"F2U.rtn", UNITS_ADD | OP_TYPE_CONVERT},
    138         [midgard_alu_op_f2u_rtp]         = {"F2U.rtp", UNITS_ADD | OP_TYPE_CONVERT},
    139         [midgard_alu_op_i2f_rte]         = {"I2F", UNITS_ADD | OP_TYPE_CONVERT},
    140         [midgard_alu_op_i2f_rtz]         = {"I2F.rtz", UNITS_ADD | OP_TYPE_CONVERT},
    141         [midgard_alu_op_i2f_rtn]         = {"I2F.rtn", UNITS_ADD | OP_TYPE_CONVERT},
    142         [midgard_alu_op_i2f_rtp]         = {"I2F.rtp", UNITS_ADD | OP_TYPE_CONVERT},
    143         [midgard_alu_op_u2f_rte]         = {"U2F", UNITS_ADD | OP_TYPE_CONVERT},
    144         [midgard_alu_op_u2f_rtz]         = {"U2F.rtz", UNITS_ADD | OP_TYPE_CONVERT},
    145         [midgard_alu_op_u2f_rtn]         = {"U2F.rtn", UNITS_ADD | OP_TYPE_CONVERT},
    146         [midgard_alu_op_u2f_rtp]         = {"U2F.rtp", UNITS_ADD | OP_TYPE_CONVERT},
    147 
    148         [midgard_alu_op_fsinpi]          = {"FSINPI", UNIT_VLUT},
    149         [midgard_alu_op_fcospi]          = {"FCOSPI", UNIT_VLUT},
    150 
    151         [midgard_alu_op_iand]            = {"AND", UNITS_MOST | OP_COMMUTES},
    152         [midgard_alu_op_iandnot]         = {"ANDNOT", UNITS_MOST},
    153 
    154         [midgard_alu_op_ior]             = {"OR", UNITS_MOST | OP_COMMUTES},
    155         [midgard_alu_op_iornot]          = {"ORNOT", UNITS_MOST | OP_COMMUTES},
    156         [midgard_alu_op_inor]            = {"NOR", UNITS_MOST | OP_COMMUTES},
    157         [midgard_alu_op_ixor]            = {"XOR", UNITS_MOST | OP_COMMUTES},
    158         [midgard_alu_op_inxor]           = {"NXOR", UNITS_MOST | OP_COMMUTES},
    159         [midgard_alu_op_iclz]            = {"CLZ", UNITS_ADD},
    160         [midgard_alu_op_ipopcnt]         = {"POPCNT", UNIT_VADD},
    161         [midgard_alu_op_inand]           = {"NAND", UNITS_MOST},
    162         [midgard_alu_op_ishl]            = {"SHL", UNITS_ADD},
    163         [midgard_alu_op_ishlsat]         = {"SHL.sat", UNITS_ADD},
    164         [midgard_alu_op_ushlsat]         = {"SHL.sat", UNITS_ADD},
    165         [midgard_alu_op_iasr]            = {"ASR", UNITS_ADD},
    166         [midgard_alu_op_ilsr]            = {"LSR", UNITS_ADD},
    167 
    168         [midgard_alu_op_fball_eq]        = {"FCMP.all.eq",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES | OP_TYPE_CONVERT},
    169         [midgard_alu_op_fball_neq]       = {"FCMP.all.ne", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES | OP_TYPE_CONVERT},
    170         [midgard_alu_op_fball_lt]        = {"FCMP.all.lt",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES | OP_TYPE_CONVERT},
    171         [midgard_alu_op_fball_lte]       = {"FCMP.all.le", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES | OP_TYPE_CONVERT},
    172 
    173         [midgard_alu_op_fbany_eq]        = {"FCMP.any.eq",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES | OP_TYPE_CONVERT},
    174         [midgard_alu_op_fbany_neq]       = {"FCMP.any.ne", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES | OP_TYPE_CONVERT},
    175         [midgard_alu_op_fbany_lt]        = {"FCMP.any.lt",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES | OP_TYPE_CONVERT},
    176         [midgard_alu_op_fbany_lte]       = {"FCMP.any.le", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES | OP_TYPE_CONVERT},
    177 
    178         [midgard_alu_op_iball_eq]        = {"CMP.all.eq",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    179         [midgard_alu_op_iball_neq]       = {"CMP.all.ne", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    180         [midgard_alu_op_iball_lt]        = {"CMP.all.lt",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    181         [midgard_alu_op_iball_lte]       = {"CMP.all.le", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    182         [midgard_alu_op_uball_lt]        = {"CMP.all.lt",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    183         [midgard_alu_op_uball_lte]       = {"CMP.all.le", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    184 
    185         [midgard_alu_op_ibany_eq]        = {"CMP.any.eq",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    186         [midgard_alu_op_ibany_neq]       = {"CMP.any.ne", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    187         [midgard_alu_op_ibany_lt]        = {"CMP.any.lt",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    188         [midgard_alu_op_ibany_lte]       = {"CMP.any.le", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    189         [midgard_alu_op_ubany_lt]        = {"CMP.any.lt",  UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    190         [midgard_alu_op_ubany_lte]       = {"CMP.any.le", UNITS_VECTOR | OP_CHANNEL_COUNT(4) | OP_COMMUTES},
    191 
    192         [midgard_alu_op_fatan2_pt1]      = {"FATAN2_PT1", UNIT_VLUT},
    193         [midgard_alu_op_fatan2_pt2]      = {"FATAN2_PT2", UNIT_VLUT},
    194 
    195         /* Haven't seen in a while */
    196         [midgard_alu_op_freduce]         = {"FREDUCE", 0},
    197 };
    198 
    199 /* Define shorthands */
    200 
    201 #define M8  midgard_reg_mode_8
    202 #define M16 midgard_reg_mode_16
    203 #define M32 midgard_reg_mode_32
    204 #define M64 midgard_reg_mode_64
    205 
    206 struct mir_ldst_op_props load_store_opcode_props[256] = {
    207         [midgard_op_unpack_colour_f32] = {"UNPACK.f32", M32},
    208         [midgard_op_unpack_colour_f16] = {"UNPACK.f16", M32},
    209         [midgard_op_unpack_colour_u32] = {"UNPACK.u32", M32},
    210         [midgard_op_unpack_colour_s32] = {"UNPACK.s32", M32},
    211         [midgard_op_pack_colour_f32] = {"PACK.f32", M32},
    212         [midgard_op_pack_colour_f16] = {"PACK.f16", M32},
    213         [midgard_op_pack_colour_u32] = {"PACK.u32", M32},
    214         [midgard_op_pack_colour_s32] = {"PACK.s32", M32},
    215         [midgard_op_lea] = {"LEA", M32 | LDST_ADDRESS },
    216         [midgard_op_lea_image] = {"LEA_IMAGE", M32 | LDST_ATTRIB },
    217         [midgard_op_ld_cubemap_coords] = {"CUBEMAP", M32},
    218         [midgard_op_ldst_mov] = {"LDST_MOV", M32},
    219         [midgard_op_ldst_perspective_div_y] = {"LDST_PERSPECTIVE_DIV_Y", M32},
    220         [midgard_op_ldst_perspective_div_z] = {"LDST_PERSPECTIVE_DIV_Z", M32},
    221         [midgard_op_ldst_perspective_div_w] = {"LDST_PERSPECTIVE_DIV_W", M32},
    222 
    223         [midgard_op_atomic_add]     = {"AADD.32",    M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    224         [midgard_op_atomic_and]     = {"AAND.32",    M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    225         [midgard_op_atomic_or]      = {"AOR.32",     M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    226         [midgard_op_atomic_xor]     = {"AXOR.32",    M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    227         [midgard_op_atomic_imin]    = {"AMIN.s32",   M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    228         [midgard_op_atomic_umin]    = {"AMIN.u32",   M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    229         [midgard_op_atomic_imax]    = {"AMAX.s32",   M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    230         [midgard_op_atomic_umax]    = {"AMAX.u32",   M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    231         [midgard_op_atomic_xchg]    = {"XCHG.32",    M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    232         [midgard_op_atomic_cmpxchg] = {"CMPXCHG.32", M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    233 
    234         [midgard_op_atomic_add64]     = {"AADD.64",    M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    235         [midgard_op_atomic_and64]     = {"AAND.64",    M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    236         [midgard_op_atomic_or64]      = {"AOR.64",     M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    237         [midgard_op_atomic_xor64]     = {"AXOR.64",    M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    238         [midgard_op_atomic_imin64]    = {"AMIN.s64",   M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    239         [midgard_op_atomic_umin64]    = {"AMIN.u64",   M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    240         [midgard_op_atomic_imax64]    = {"AMAX.s64",   M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    241         [midgard_op_atomic_umax64]    = {"AMAX.u64",   M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    242         [midgard_op_atomic_xchg64]    = {"XCHG.64",    M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    243         [midgard_op_atomic_cmpxchg64] = {"CMPXCHG.64", M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    244 
    245         [midgard_op_atomic_add_be]     = {"AADD.32.be",    M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    246         [midgard_op_atomic_and_be]     = {"AAND.32.be",    M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    247         [midgard_op_atomic_or_be]      = {"AOR.32.be",     M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    248         [midgard_op_atomic_xor_be]     = {"AXOR.32.be",    M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    249         [midgard_op_atomic_imin_be]    = {"AMIN.s32.be",   M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    250         [midgard_op_atomic_umin_be]    = {"AMIN.u32.be",   M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    251         [midgard_op_atomic_imax_be]    = {"AMAX.s32.be",   M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    252         [midgard_op_atomic_umax_be]    = {"AMAX.u32.be",   M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    253         [midgard_op_atomic_xchg_be]    = {"XCHG.32.be",    M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    254         [midgard_op_atomic_cmpxchg_be] = {"CMPXCHG.32.be", M32 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    255 
    256         [midgard_op_atomic_add64]     = {"AADD.64.be",    M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    257         [midgard_op_atomic_and64]     = {"AAND.64.be",    M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    258         [midgard_op_atomic_or64]      = {"AOR.64.be",     M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    259         [midgard_op_atomic_xor64]     = {"AXOR.64.be",    M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    260         [midgard_op_atomic_imin64]    = {"AMIN.s64.be",   M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    261         [midgard_op_atomic_umin64]    = {"AMIN.u64.be",   M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    262         [midgard_op_atomic_imax64]    = {"AMAX.s64.be",   M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    263         [midgard_op_atomic_umax64]    = {"AMAX.u64.be",   M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    264         [midgard_op_atomic_xchg64]    = {"XCHG.64.be",    M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    265         [midgard_op_atomic_cmpxchg64] = {"CMPXCHG.64.be", M64 | LDST_SIDE_FX | LDST_ADDRESS | LDST_ATOMIC},
    266 
    267         [midgard_op_ld_u8]         = {"LD.u8",         M32 | LDST_ADDRESS},
    268         [midgard_op_ld_i8]         = {"LD.s8",         M32 | LDST_ADDRESS},
    269         [midgard_op_ld_u16]        = {"LD.u16",        M32 | LDST_ADDRESS},
    270         [midgard_op_ld_i16]        = {"LD.s16",        M32 | LDST_ADDRESS},
    271         [midgard_op_ld_u16_be]     = {"LD.u16.be",     M32 | LDST_ADDRESS},
    272         [midgard_op_ld_i16_be]     = {"LD.s16.be",     M32 | LDST_ADDRESS},
    273         [midgard_op_ld_32]         = {"LD.32",         M32 | LDST_ADDRESS},
    274         [midgard_op_ld_32_bswap2]  = {"LD.32.bswap2",  M32 | LDST_ADDRESS},
    275         [midgard_op_ld_32_bswap4]  = {"LD.32.bswap4",  M32 | LDST_ADDRESS},
    276         [midgard_op_ld_64]         = {"LD.64",         M32 | LDST_ADDRESS},
    277         [midgard_op_ld_64_bswap2]  = {"LD.64.bswap2",  M32 | LDST_ADDRESS},
    278         [midgard_op_ld_64_bswap4]  = {"LD.64.bswap4",  M32 | LDST_ADDRESS},
    279         [midgard_op_ld_64_bswap8]  = {"LD.64.bswap8",  M32 | LDST_ADDRESS},
    280         [midgard_op_ld_128]        = {"LD.128",        M32 | LDST_ADDRESS},
    281         [midgard_op_ld_128_bswap2] = {"LD.128.bswap2", M32 | LDST_ADDRESS},
    282         [midgard_op_ld_128_bswap4] = {"LD.128.bswap4", M32 | LDST_ADDRESS},
    283         [midgard_op_ld_128_bswap8] = {"LD.128.bswap8", M32 | LDST_ADDRESS},
    284 
    285         [midgard_op_ld_attr_32]  = {"LD_ATTR.f32", M32 | LDST_ATTRIB},
    286         [midgard_op_ld_attr_32i] = {"LD_ATTR.s32", M32 | LDST_ATTRIB},
    287         [midgard_op_ld_attr_32u] = {"LD_ATTR.u32", M32 | LDST_ATTRIB},
    288         [midgard_op_ld_attr_16]  = {"LD_ATTR.f16", M32 | LDST_ATTRIB},
    289 
    290         [midgard_op_ld_vary_32]  = {"LD_VARY.f32", M32 | LDST_ATTRIB},
    291         [midgard_op_ld_vary_16]  = {"LD_VARY.f16", M32 | LDST_ATTRIB},
    292         [midgard_op_ld_vary_32i] = {"LD_VARY.s32", M32 | LDST_ATTRIB},
    293         [midgard_op_ld_vary_32u] = {"LD_VARY.u32", M32 | LDST_ATTRIB},
    294 
    295         [midgard_op_ld_special_32f] = {"LD_SPECIAL.f32", M32 | LDST_SPECIAL_MASK},
    296         [midgard_op_ld_special_16f] = {"LD_SPECIAL.f16", M16 | LDST_SPECIAL_MASK},
    297         [midgard_op_ld_special_32u] = {"LD_SPECIAL.u32", M32},
    298         [midgard_op_ld_special_32i] = {"LD_SPECIAL.s32", M32},
    299 
    300         [midgard_op_ld_tilebuffer_32f] = {"LD_TILEBUFFER.f32", M32},
    301         [midgard_op_ld_tilebuffer_16f] = {"LD_TILEBUFFER.f16", M16},
    302         [midgard_op_ld_tilebuffer_raw] = {"LD_TILEBUFFER.raw", M32},
    303 
    304         [midgard_op_ld_ubo_u8]         = {"LD_UBO.u8",         M32},
    305         [midgard_op_ld_ubo_i8]         = {"LD_UBO.s8",         M32},
    306         [midgard_op_ld_ubo_u16]        = {"LD_UBO.u16",        M16},
    307         [midgard_op_ld_ubo_i16]        = {"LD_UBO.s16",        M16},
    308         [midgard_op_ld_ubo_u16_be]     = {"LD_UBO.u16.be",     M16},
    309         [midgard_op_ld_ubo_i16_be]     = {"LD_UBO.s16.be",     M16},
    310         [midgard_op_ld_ubo_32]         = {"LD_UBO.32",         M32},
    311         [midgard_op_ld_ubo_32_bswap2]  = {"LD_UBO.32.bswap2",  M32},
    312         [midgard_op_ld_ubo_32_bswap4]  = {"LD_UBO.32.bswap4",  M32},
    313         [midgard_op_ld_ubo_64]         = {"LD_UBO.64",         M32},
    314         [midgard_op_ld_ubo_64_bswap2]  = {"LD_UBO.64.bswap2",  M32},
    315         [midgard_op_ld_ubo_64_bswap4]  = {"LD_UBO.64.bswap4",  M32},
    316         [midgard_op_ld_ubo_64_bswap8]  = {"LD_UBO.64.bswap8",  M32},
    317         [midgard_op_ld_ubo_128]        = {"LD_UBO.128",        M32},
    318         [midgard_op_ld_ubo_128_bswap2] = {"LD_UBO.128.bswap2", M32},
    319         [midgard_op_ld_ubo_128_bswap4] = {"LD_UBO.128.bswap4", M32},
    320         [midgard_op_ld_ubo_128_bswap8] = {"LD_UBO.128.bswap8", M32},
    321 
    322         [midgard_op_ld_image_32f] = {"LD_IMAGE.f32", M32 | LDST_ATTRIB},
    323         [midgard_op_ld_image_16f] = {"LD_IMAGE.f16", M16 | LDST_ATTRIB},
    324         [midgard_op_ld_image_32i] = {"LD_IMAGE.s32", M32 | LDST_ATTRIB},
    325         [midgard_op_ld_image_32u] = {"LD_IMAGE.u32", M32 | LDST_ATTRIB},
    326 
    327         [midgard_op_st_u8]         = {"ST.u8",         M32 | LDST_STORE | LDST_ADDRESS},
    328         [midgard_op_st_i8]         = {"ST.s8",         M32 | LDST_STORE | LDST_ADDRESS},
    329         [midgard_op_st_u16]        = {"ST.u16",        M32 | LDST_STORE | LDST_ADDRESS},
    330         [midgard_op_st_i16]        = {"ST.s16",        M32 | LDST_STORE | LDST_ADDRESS},
    331         [midgard_op_st_u16_be]     = {"ST.u16.be",     M32 | LDST_STORE | LDST_ADDRESS},
    332         [midgard_op_st_i16_be]     = {"ST.s16.be",     M32 | LDST_STORE | LDST_ADDRESS},
    333         [midgard_op_st_32]         = {"ST.32",         M32 | LDST_STORE | LDST_ADDRESS},
    334         [midgard_op_st_32_bswap2]  = {"ST.32.bswap2",  M32 | LDST_STORE | LDST_ADDRESS},
    335         [midgard_op_st_32_bswap4]  = {"ST.32.bswap4",  M32 | LDST_STORE | LDST_ADDRESS},
    336         [midgard_op_st_64]         = {"ST.64",         M32 | LDST_STORE | LDST_ADDRESS},
    337         [midgard_op_st_64_bswap2]  = {"ST.64.bswap2",  M32 | LDST_STORE | LDST_ADDRESS},
    338         [midgard_op_st_64_bswap4]  = {"ST.64.bswap4",  M32 | LDST_STORE | LDST_ADDRESS},
    339         [midgard_op_st_64_bswap8]  = {"ST.64.bswap8",  M32 | LDST_STORE | LDST_ADDRESS},
    340         [midgard_op_st_128]        = {"ST.128",        M32 | LDST_STORE | LDST_ADDRESS},
    341         [midgard_op_st_128_bswap2] = {"ST.128.bswap2", M32 | LDST_STORE | LDST_ADDRESS},
    342         [midgard_op_st_128_bswap4] = {"ST.128.bswap4", M32 | LDST_STORE | LDST_ADDRESS},
    343         [midgard_op_st_128_bswap8] = {"ST.128.bswap8", M32 | LDST_STORE | LDST_ADDRESS},
    344 
    345         [midgard_op_st_vary_32]  = {"ST_VARY.f32", M32 | LDST_STORE | LDST_ATTRIB},
    346         [midgard_op_st_vary_32i] = {"ST_VARY.s32", M32 | LDST_STORE | LDST_ATTRIB},
    347         [midgard_op_st_vary_32u] = {"ST_VARY.u32", M32 | LDST_STORE | LDST_ATTRIB},
    348         [midgard_op_st_vary_16]  = {"ST_VARY.f16", M16 | LDST_STORE | LDST_ATTRIB},
    349 
    350         [midgard_op_st_image_32f] = {"ST_IMAGE.f32", M32 | LDST_STORE | LDST_ATTRIB},
    351         [midgard_op_st_image_16f] = {"ST_IMAGE.f16", M16 | LDST_STORE | LDST_ATTRIB},
    352         [midgard_op_st_image_32i] = {"ST_IMAGE.u32", M32 | LDST_STORE | LDST_ATTRIB},
    353         [midgard_op_st_image_32u] = {"ST_IMAGE.s32", M32 | LDST_STORE | LDST_ATTRIB},
    354 
    355         [midgard_op_st_special_32f] = {"ST_SPECIAL.f32", M32},
    356         [midgard_op_st_special_16f] = {"ST_SPECIAL.f16", M16},
    357         [midgard_op_st_special_32u] = {"ST_SPECIAL.u32", M32},
    358         [midgard_op_st_special_32i] = {"ST_SPECIAL.s32", M32},
    359 
    360         [midgard_op_st_tilebuffer_32f] = {"ST_TILEBUFFER.f32", M32},
    361         [midgard_op_st_tilebuffer_16f] = {"ST_TILEBUFFER.f16", M16},
    362         [midgard_op_st_tilebuffer_raw] = {"ST_TILEBUFFER.raw", M32},
    363 };
    364 
    365 struct mir_tex_op_props tex_opcode_props[16] = {
    366         [midgard_tex_op_normal] = {"TEX", M32},
    367         [midgard_tex_op_gradient] = {"TEX_GRAD", M32},
    368         [midgard_tex_op_fetch] = {"TEX_FETCH", M32},
    369         [midgard_tex_op_grad_from_derivative] = {"DER_TO_GRAD", M32},
    370         [midgard_tex_op_grad_from_coords] = {"COORDS_TO_GRAD", M32},
    371         [midgard_tex_op_mov] = {"MOV", M32},
    372         [midgard_tex_op_barrier] = {"BARRIER", M32},
    373         [midgard_tex_op_derivative] = {"DERIVATIVE", M32}
    374 };
    375 
    376 #undef M8
    377 #undef M16
    378 #undef M32
    379 #undef M64
    380 
    381 struct mir_tag_props midgard_tag_props[16] = {
    382         [TAG_INVALID]           = {"invalid", 0},
    383         [TAG_BREAK]             = {"break", 0},
    384         [TAG_TEXTURE_4_VTX]     = {"tex/vt", 1},
    385         [TAG_TEXTURE_4]         = {"tex", 1},
    386         [TAG_TEXTURE_4_BARRIER] = {"tex/bar", 1},
    387         [TAG_LOAD_STORE_4]      = {"ldst", 1},
    388         [TAG_UNKNOWN_1]         = {"unk1", 1},
    389         [TAG_UNKNOWN_2]         = {"unk2", 1},
    390         [TAG_ALU_4]             = {"alu/4", 1},
    391         [TAG_ALU_8]             = {"alu/8", 2},
    392         [TAG_ALU_12]            = {"alu/12", 3},
    393         [TAG_ALU_16]            = {"alu/16", 4},
    394         [TAG_ALU_4_WRITEOUT]    = {"aluw/4", 1},
    395         [TAG_ALU_8_WRITEOUT]    = {"aluw/8", 2},
    396         [TAG_ALU_12_WRITEOUT]   = {"aluw/12", 3},
    397         [TAG_ALU_16_WRITEOUT]   = {"aluw/16", 4}
    398 };
    399