Home | History | Annotate | Download | only in R600
      1 //===-- SIInstrInfo.td - SI Instruction Infos -------------*- tablegen -*--===//
      2 //
      3 //                     The LLVM Compiler Infrastructure
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 
     10 //===----------------------------------------------------------------------===//
     11 // SI DAG Nodes
     12 //===----------------------------------------------------------------------===//
     13 
     14 // SMRD takes a 64bit memory address and can only add an 32bit offset
     15 def SIadd64bit32bit : SDNode<"ISD::ADD",
     16   SDTypeProfile<1, 2, [SDTCisSameAs<0, 1>, SDTCisVT<0, i64>, SDTCisVT<2, i32>]>
     17 >;
     18 
     19 // Transformation function, extract the lower 32bit of a 64bit immediate
     20 def LO32 : SDNodeXForm<imm, [{
     21   return CurDAG->getTargetConstant(N->getZExtValue() & 0xffffffff, MVT::i32);
     22 }]>;
     23 
     24 // Transformation function, extract the upper 32bit of a 64bit immediate
     25 def HI32 : SDNodeXForm<imm, [{
     26   return CurDAG->getTargetConstant(N->getZExtValue() >> 32, MVT::i32);
     27 }]>;
     28 
     29 def IMM8bitDWORD : ImmLeaf <
     30   i32, [{
     31     return (Imm & ~0x3FC) == 0;
     32   }], SDNodeXForm<imm, [{
     33     return CurDAG->getTargetConstant(
     34       N->getZExtValue() >> 2, MVT::i32);
     35   }]>
     36 >;
     37 
     38 def IMM12bit : ImmLeaf <
     39   i16,
     40   [{return isUInt<12>(Imm);}]
     41 >;
     42 
     43 class InlineImm <ValueType vt> : PatLeaf <(vt imm), [{
     44   return ((const SITargetLowering &)TLI).analyzeImmediate(N) == 0;
     45 }]>;
     46 
     47 //===----------------------------------------------------------------------===//
     48 // SI assembler operands
     49 //===----------------------------------------------------------------------===//
     50 
     51 def SIOperand {
     52   int ZERO = 0x80;
     53   int VCC = 0x6A;
     54 }
     55 
     56 include "SIInstrFormats.td"
     57 
     58 //===----------------------------------------------------------------------===//
     59 //
     60 // SI Instruction multiclass helpers.
     61 //
     62 // Instructions with _32 take 32-bit operands.
     63 // Instructions with _64 take 64-bit operands.
     64 //
     65 // VOP_* instructions can use either a 32-bit or 64-bit encoding.  The 32-bit
     66 // encoding is the standard encoding, but instruction that make use of
     67 // any of the instruction modifiers must use the 64-bit encoding.
     68 //
     69 // Instructions with _e32 use the 32-bit encoding.
     70 // Instructions with _e64 use the 64-bit encoding.
     71 //
     72 //===----------------------------------------------------------------------===//
     73 
     74 //===----------------------------------------------------------------------===//
     75 // Scalar classes
     76 //===----------------------------------------------------------------------===//
     77 
     78 class SOP1_32 <bits<8> op, string opName, list<dag> pattern> : SOP1 <
     79   op, (outs SReg_32:$dst), (ins SSrc_32:$src0),
     80   opName#" $dst, $src0", pattern
     81 >;
     82 
     83 class SOP1_64 <bits<8> op, string opName, list<dag> pattern> : SOP1 <
     84   op, (outs SReg_64:$dst), (ins SSrc_64:$src0),
     85   opName#" $dst, $src0", pattern
     86 >;
     87 
     88 class SOP2_32 <bits<7> op, string opName, list<dag> pattern> : SOP2 <
     89   op, (outs SReg_32:$dst), (ins SSrc_32:$src0, SSrc_32:$src1),
     90   opName#" $dst, $src0, $src1", pattern
     91 >;
     92 
     93 class SOP2_64 <bits<7> op, string opName, list<dag> pattern> : SOP2 <
     94   op, (outs SReg_64:$dst), (ins SSrc_64:$src0, SSrc_64:$src1),
     95   opName#" $dst, $src0, $src1", pattern
     96 >;
     97 
     98 class SOPC_32 <bits<7> op, string opName, list<dag> pattern> : SOPC <
     99   op, (outs SCCReg:$dst), (ins SSrc_32:$src0, SSrc_32:$src1),
    100   opName#" $dst, $src0, $src1", pattern
    101 >;
    102 
    103 class SOPC_64 <bits<7> op, string opName, list<dag> pattern> : SOPC <
    104   op, (outs SCCReg:$dst), (ins SSrc_64:$src0, SSrc_64:$src1),
    105   opName#" $dst, $src0, $src1", pattern
    106 >;
    107 
    108 class SOPK_32 <bits<5> op, string opName, list<dag> pattern> : SOPK <
    109   op, (outs SReg_32:$dst), (ins i16imm:$src0),
    110   opName#" $dst, $src0", pattern
    111 >;
    112 
    113 class SOPK_64 <bits<5> op, string opName, list<dag> pattern> : SOPK <
    114   op, (outs SReg_64:$dst), (ins i16imm:$src0),
    115   opName#" $dst, $src0", pattern
    116 >;
    117 
    118 multiclass SMRD_Helper <bits<5> op, string asm, RegisterClass baseClass,
    119                         RegisterClass dstClass> {
    120   def _IMM : SMRD <
    121     op, 1, (outs dstClass:$dst),
    122     (ins baseClass:$sbase, i32imm:$offset),
    123     asm#" $dst, $sbase, $offset", []
    124   >;
    125 
    126   def _SGPR : SMRD <
    127     op, 0, (outs dstClass:$dst),
    128     (ins baseClass:$sbase, SReg_32:$soff),
    129     asm#" $dst, $sbase, $soff", []
    130   >;
    131 }
    132 
    133 //===----------------------------------------------------------------------===//
    134 // Vector ALU classes
    135 //===----------------------------------------------------------------------===//
    136 
    137 class VOP <string opName> {
    138   string OpName = opName;
    139 }
    140 
    141 multiclass VOP1_Helper <bits<8> op, RegisterClass drc, RegisterClass src,
    142                         string opName, list<dag> pattern> {
    143 
    144   def _e32 : VOP1 <
    145     op, (outs drc:$dst), (ins src:$src0),
    146     opName#"_e32 $dst, $src0", pattern
    147   >, VOP <opName>;
    148 
    149   def _e64 : VOP3 <
    150     {1, 1, op{6}, op{5}, op{4}, op{3}, op{2}, op{1}, op{0}},
    151     (outs drc:$dst),
    152     (ins src:$src0,
    153          i32imm:$abs, i32imm:$clamp,
    154          i32imm:$omod, i32imm:$neg),
    155     opName#"_e64 $dst, $src0, $abs, $clamp, $omod, $neg", []
    156   >, VOP <opName> {
    157     let SRC1 = SIOperand.ZERO;
    158     let SRC2 = SIOperand.ZERO;
    159   }
    160 }
    161 
    162 multiclass VOP1_32 <bits<8> op, string opName, list<dag> pattern>
    163   : VOP1_Helper <op, VReg_32, VSrc_32, opName, pattern>;
    164 
    165 multiclass VOP1_64 <bits<8> op, string opName, list<dag> pattern>
    166   : VOP1_Helper <op, VReg_64, VSrc_64, opName, pattern>;
    167 
    168 multiclass VOP2_Helper <bits<6> op, RegisterClass vrc, RegisterClass arc,
    169                         string opName, list<dag> pattern> {
    170   def _e32 : VOP2 <
    171     op, (outs vrc:$dst), (ins arc:$src0, vrc:$src1),
    172     opName#"_e32 $dst, $src0, $src1", pattern
    173   >, VOP <opName>;
    174 
    175   def _e64 : VOP3 <
    176     {1, 0, 0, op{5}, op{4}, op{3}, op{2}, op{1}, op{0}},
    177     (outs vrc:$dst),
    178     (ins arc:$src0, arc:$src1,
    179          i32imm:$abs, i32imm:$clamp,
    180          i32imm:$omod, i32imm:$neg),
    181     opName#"_e64 $dst, $src0, $src1, $abs, $clamp, $omod, $neg", []
    182   >, VOP <opName> {
    183     let SRC2 = SIOperand.ZERO;
    184   }
    185 }
    186 
    187 multiclass VOP2_32 <bits<6> op, string opName, list<dag> pattern>
    188   : VOP2_Helper <op, VReg_32, VSrc_32, opName, pattern>;
    189 
    190 multiclass VOP2_64 <bits<6> op, string opName, list<dag> pattern>
    191   : VOP2_Helper <op, VReg_64, VSrc_64, opName, pattern>;
    192 
    193 multiclass VOP2b_32 <bits<6> op, string opName, list<dag> pattern> {
    194 
    195   def _e32 : VOP2 <
    196     op, (outs VReg_32:$dst), (ins VSrc_32:$src0, VReg_32:$src1),
    197     opName#"_e32 $dst, $src0, $src1", pattern
    198   >, VOP <opName>;
    199 
    200   def _e64 : VOP3b <
    201     {1, 0, 0, op{5}, op{4}, op{3}, op{2}, op{1}, op{0}},
    202     (outs VReg_32:$dst),
    203     (ins VSrc_32:$src0, VSrc_32:$src1,
    204          i32imm:$abs, i32imm:$clamp,
    205          i32imm:$omod, i32imm:$neg),
    206     opName#"_e64 $dst, $src0, $src1, $abs, $clamp, $omod, $neg", []
    207   >, VOP <opName> {
    208     let SRC2 = SIOperand.ZERO;
    209     /* the VOP2 variant puts the carry out into VCC, the VOP3 variant
    210        can write it into any SGPR. We currently don't use the carry out,
    211        so for now hardcode it to VCC as well */
    212     let SDST = SIOperand.VCC;
    213   }
    214 }
    215 
    216 multiclass VOPC_Helper <bits<8> op, RegisterClass vrc, RegisterClass arc,
    217                         string opName, ValueType vt, PatLeaf cond> {
    218 
    219   def _e32 : VOPC <
    220     op, (ins arc:$src0, vrc:$src1),
    221     opName#"_e32 $dst, $src0, $src1", []
    222   >, VOP <opName>;
    223 
    224   def _e64 : VOP3 <
    225     {0, op{7}, op{6}, op{5}, op{4}, op{3}, op{2}, op{1}, op{0}},
    226     (outs SReg_64:$dst),
    227     (ins arc:$src0, arc:$src1,
    228          InstFlag:$abs, InstFlag:$clamp,
    229          InstFlag:$omod, InstFlag:$neg),
    230     opName#"_e64 $dst, $src0, $src1, $abs, $clamp, $omod, $neg",
    231     !if(!eq(!cast<string>(cond), "COND_NULL"), []<dag>,
    232       [(set SReg_64:$dst, (i1 (setcc (vt arc:$src0), arc:$src1, cond)))]
    233     )
    234   >, VOP <opName> {
    235     let SRC2 = SIOperand.ZERO;
    236   }
    237 }
    238 
    239 multiclass VOPC_32 <bits<8> op, string opName,
    240   ValueType vt = untyped, PatLeaf cond = COND_NULL>
    241   : VOPC_Helper <op, VReg_32, VSrc_32, opName, vt, cond>;
    242 
    243 multiclass VOPC_64 <bits<8> op, string opName,
    244   ValueType vt = untyped, PatLeaf cond = COND_NULL>
    245   : VOPC_Helper <op, VReg_64, VSrc_64, opName, vt, cond>;
    246 
    247 class VOP3_32 <bits<9> op, string opName, list<dag> pattern> : VOP3 <
    248   op, (outs VReg_32:$dst),
    249   (ins VSrc_32:$src0, VSrc_32:$src1, VSrc_32:$src2,
    250    i32imm:$abs, i32imm:$clamp, i32imm:$omod, i32imm:$neg),
    251   opName#" $dst, $src0, $src1, $src2, $abs, $clamp, $omod, $neg", pattern
    252 >, VOP <opName>;
    253 
    254 class VOP3_64 <bits<9> op, string opName, list<dag> pattern> : VOP3 <
    255   op, (outs VReg_64:$dst),
    256   (ins VSrc_64:$src0, VSrc_64:$src1, VSrc_64:$src2,
    257    i32imm:$abs, i32imm:$clamp, i32imm:$omod, i32imm:$neg),
    258   opName#" $dst, $src0, $src1, $src2, $abs, $clamp, $omod, $neg", pattern
    259 >, VOP <opName>;
    260 
    261 //===----------------------------------------------------------------------===//
    262 // Vector I/O classes
    263 //===----------------------------------------------------------------------===//
    264 
    265 class MTBUF_Store_Helper <bits<3> op, string asm, RegisterClass regClass> : MTBUF <
    266   op,
    267   (outs),
    268   (ins regClass:$vdata, i16imm:$offset, i1imm:$offen, i1imm:$idxen, i1imm:$glc,
    269    i1imm:$addr64, i8imm:$dfmt, i8imm:$nfmt, VReg_32:$vaddr,
    270    SReg_128:$srsrc, i1imm:$slc, i1imm:$tfe, SSrc_32:$soffset),
    271   asm#" $vdata, $offset, $offen, $idxen, $glc, $addr64, $dfmt,"
    272      #" $nfmt, $vaddr, $srsrc, $slc, $tfe, $soffset",
    273   []> {
    274   let mayStore = 1;
    275   let mayLoad = 0;
    276 }
    277 
    278 class MUBUF_Load_Helper <bits<7> op, string asm, RegisterClass regClass> : MUBUF <
    279   op,
    280   (outs regClass:$dst),
    281   (ins i16imm:$offset, i1imm:$offen, i1imm:$idxen, i1imm:$glc, i1imm:$addr64,
    282        i1imm:$lds, VReg_32:$vaddr, SReg_128:$srsrc, i1imm:$slc,
    283        i1imm:$tfe, SSrc_32:$soffset),
    284   asm#" $dst, $offset, $offen, $idxen, $glc, $addr64, "
    285      #"$lds, $vaddr, $srsrc, $slc, $tfe, $soffset",
    286   []> {
    287   let mayLoad = 1;
    288   let mayStore = 0;
    289 }
    290 
    291 class MTBUF_Load_Helper <bits<3> op, string asm, RegisterClass regClass> : MTBUF <
    292   op,
    293   (outs regClass:$dst),
    294   (ins i16imm:$offset, i1imm:$offen, i1imm:$idxen, i1imm:$glc, i1imm:$addr64,
    295        i8imm:$dfmt, i8imm:$nfmt, VReg_32:$vaddr, SReg_128:$srsrc,
    296        i1imm:$slc, i1imm:$tfe, SSrc_32:$soffset),
    297   asm#" $dst, $offset, $offen, $idxen, $glc, $addr64, $dfmt,"
    298      #" $nfmt, $vaddr, $srsrc, $slc, $tfe, $soffset",
    299   []> {
    300   let mayLoad = 1;
    301   let mayStore = 0;
    302 }
    303 
    304 class MIMG_Load_Helper <bits<7> op, string asm> : MIMG <
    305   op,
    306   (outs VReg_128:$vdata),
    307   (ins i32imm:$dmask, i1imm:$unorm, i1imm:$glc, i1imm:$da, i1imm:$r128,
    308        i1imm:$tfe, i1imm:$lwe, i1imm:$slc, VReg_32:$vaddr,
    309        SReg_256:$srsrc, SReg_128:$ssamp),
    310   asm#" $vdata, $dmask, $unorm, $glc, $da, $r128,"
    311      #" $tfe, $lwe, $slc, $vaddr, $srsrc, $ssamp",
    312   []> {
    313   let mayLoad = 1;
    314   let mayStore = 0;
    315 }
    316 
    317 //===----------------------------------------------------------------------===//
    318 // Vector instruction mappings
    319 //===----------------------------------------------------------------------===//
    320 
    321 // Maps an opcode in e32 form to its e64 equivalent
    322 def getVOPe64 : InstrMapping {
    323   let FilterClass = "VOP";
    324   let RowFields = ["OpName"];
    325   let ColFields = ["Size"];
    326   let KeyCol = ["4"];
    327   let ValueCols = [["8"]];
    328 }
    329 
    330 include "SIInstructions.td"
    331