X-Git-Url: http://demsky.eecs.uci.edu/git/?a=blobdiff_plain;f=lib%2FTarget%2FAMDGPU%2FSIInstrInfo.td;h=61e9022c47ba58ced2b713e7d3f1321f63e43a1c;hb=08e1ec066dc01294e34e7adbe877a7e06d4f00a7;hp=7ecb25a52df49abf412064ca11ac4d85ea4d6995;hpb=e8ad273f980490245ac8c20b7ac691856c4c518f;p=oota-llvm.git diff --git a/lib/Target/AMDGPU/SIInstrInfo.td b/lib/Target/AMDGPU/SIInstrInfo.td index 7ecb25a52df..61e9022c47b 100644 --- a/lib/Target/AMDGPU/SIInstrInfo.td +++ b/lib/Target/AMDGPU/SIInstrInfo.td @@ -72,6 +72,15 @@ class sopk si, bits<5> vi = si> { field bits<5> VI = vi; } +// Specify an SMRD opcode for SI and SMEM opcode for VI + +// FIXME: This should really be bits<5> si, Tablegen crashes if +// parameter default value is other parameter with different bit size +class smrd si, bits<8> vi = si> { + field bits<5> SI = si{4-0}; + field bits<8> VI = vi; +} + // Execpt for the NONE field, this must be kept in sync with the SISubtarget enum // in AMDGPUInstrInfo.cpp def SISubtarget { @@ -331,9 +340,9 @@ class SGPRImm : PatLeaf(Subtarget->getRegisterInfo()); for (SDNode::use_iterator U = N->use_begin(), E = SDNode::use_end(); U != E; ++U) { - if (SIRI->isSGPRClass(getOperandRegClass(*U, U.getOperandNo()))) { + const TargetRegisterClass *RC = getOperandRegClass(*U, U.getOperandNo()); + if (RC && SIRI->isSGPRClass(RC)) return true; - } } return false; }]>; @@ -893,28 +902,55 @@ class SMRD_Real_si op, string opName, bit imm, dag outs, dag ins, } class SMRD_Real_vi op, string opName, bit imm, dag outs, dag ins, - string asm> : - SMRD , + string asm, list pattern = []> : + SMRD , SMEMe_vi , SIMCInstr { let AssemblerPredicates = [isVI]; } -multiclass SMRD_m op, string opName, bit imm, dag outs, dag ins, +multiclass SMRD_m pattern> { def "" : SMRD_Pseudo ; - def _si : SMRD_Real_si ; + def _si : SMRD_Real_si ; // glc is only applicable to scalar stores, which are not yet // implemented. let glc = 0 in { - def _vi : SMRD_Real_vi <{0, 0, 0, op}, opName, imm, outs, ins, asm>; + def _vi : SMRD_Real_vi ; + } +} + +multiclass SMRD_Inval { + let hasSideEffects = 1, mayStore = 1 in { + def "" : SMRD_Pseudo ; + + let sbase = 0, offset = 0 in { + let sdst = 0 in { + def _si : SMRD_Real_si ; + } + + let glc = 0, sdata = 0 in { + def _vi : SMRD_Real_vi ; + } + } } } -multiclass SMRD_Helper op, string opName, RegisterClass baseClass, +class SMEM_Inval op, string opName, SDPatternOperator node> : + SMRD_Real_vi { + let hasSideEffects = 1; + let mayStore = 1; + let sbase = 0; + let sdata = 0; + let glc = 0; + let offset = 0; +} + +multiclass SMRD_Helper { defm _IMM : SMRD_m < op, opName#"_IMM", 1, (outs dstClass:$dst), @@ -924,7 +960,7 @@ multiclass SMRD_Helper op, string opName, RegisterClass baseClass, def _IMM_ci : SMRD < (outs dstClass:$dst), (ins baseClass:$sbase, smrd_literal_offset:$offset), - opName#" $dst, $sbase, $offset", []>, SMRD_IMMe_ci { + opName#" $dst, $sbase, $offset", []>, SMRD_IMMe_ci { let AssemblerPredicates = [isCIOnly]; } @@ -953,11 +989,12 @@ def InputModsNoDefault : Operand { let ParserMatchClass = InputModsMatchClass; } -class getNumSrcArgs { +class getNumSrcArgs { int ret = - !if (!eq(Src1.Value, untyped.Value), 1, // VOP1 + !if (!eq(Src0.Value, untyped.Value), 0, + !if (!eq(Src1.Value, untyped.Value), 1, // VOP1 !if (!eq(Src2.Value, untyped.Value), 2, // VOP2 - 3)); // VOP3 + 3))); // VOP3 } // Returns the register class to use for the destination of VOP[123C] @@ -965,28 +1002,37 @@ class getNumSrcArgs { class getVALUDstForVT { RegisterOperand ret = !if(!eq(VT.Size, 32), VOPDstOperand, !if(!eq(VT.Size, 64), VOPDstOperand, - VOPDstOperand)); // else VT == i1 + !if(!eq(VT.Size, 16), VOPDstOperand, + VOPDstOperand))); // else VT == i1 } // Returns the register class to use for source 0 of VOP[12C] // instructions for the given VT. class getVOPSrc0ForVT { - RegisterOperand ret = !if(!eq(VT.Size, 32), VSrc_32, VSrc_64); + RegisterOperand ret = !if(!eq(VT.Size, 64), VSrc_64, VSrc_32); } // Returns the register class to use for source 1 of VOP[12C] for the // given VT. class getVOPSrc1ForVT { - RegisterClass ret = !if(!eq(VT.Size, 32), VGPR_32, VReg_64); + RegisterClass ret = !if(!eq(VT.Size, 64), VReg_64, VGPR_32); } // Returns the register class to use for sources of VOP3 instructions for the // given VT. class getVOP3SrcForVT { - RegisterOperand ret = !if(!eq(VT.Size, 32), VCSrc_32, VCSrc_64); + RegisterOperand ret = + !if(!eq(VT.Size, 64), + VCSrc_64, + !if(!eq(VT.Value, i1.Value), + SCSrc_64, + VCSrc_32 + ) + ); } // Returns 1 if the source arguments have modifiers, 0 if they do not. +// XXX - do f16 instructions? class hasModifiers { bit ret = !if(!eq(SrcVT.Value, f32.Value), 1, !if(!eq(SrcVT.Value, f64.Value), 1, 0)); @@ -1040,17 +1086,20 @@ class getIns64 { +class getAsm32 { + string dst = "$dst"; + string src0 = ", $src0"; string src1 = ", $src1"; string src2 = ", $src2"; - string ret = "$dst, $src0"# - !if(!eq(NumSrcArgs, 1), "", src1)# - !if(!eq(NumSrcArgs, 3), src2, ""); + string ret = !if(HasDst, dst, "") # + !if(!eq(NumSrcArgs, 1), src0, "") # + !if(!eq(NumSrcArgs, 2), src0#src1, "") # + !if(!eq(NumSrcArgs, 3), src0#src1#src2, ""); } // Returns the assembly string for the inputs and outputs of a VOP3 // instruction. -class getAsm64 { +class getAsm64 { string src0 = !if(!eq(NumSrcArgs, 1), "$src0_modifiers", "$src0_modifiers,"); string src1 = !if(!eq(NumSrcArgs, 1), "", !if(!eq(NumSrcArgs, 2), " $src1_modifiers", @@ -1058,11 +1107,10 @@ class getAsm64 { string src2 = !if(!eq(NumSrcArgs, 3), " $src2_modifiers", ""); string ret = !if(!eq(HasModifiers, 0), - getAsm32.ret, + getAsm32.ret, "$dst, "#src0#src1#src2#"$clamp"#"$omod"); } - class VOPProfile _ArgVT> { field list ArgVT = _ArgVT; @@ -1078,29 +1126,38 @@ class VOPProfile _ArgVT> { field RegisterOperand Src1RC64 = getVOP3SrcForVT.ret; field RegisterOperand Src2RC64 = getVOP3SrcForVT.ret; - field int NumSrcArgs = getNumSrcArgs.ret; + field bit HasDst = !if(!eq(DstVT.Value, untyped.Value), 0, 1); + field bit HasDst32 = HasDst; + field int NumSrcArgs = getNumSrcArgs.ret; field bit HasModifiers = hasModifiers.ret; - field dag Outs = (outs DstRC:$dst); + field dag Outs = !if(HasDst,(outs DstRC:$dst),(outs)); + + // VOP3b instructions are a special case with a second explicit + // output. This is manually overridden for them. + field dag Outs32 = Outs; + field dag Outs64 = Outs; field dag Ins32 = getIns32.ret; field dag Ins64 = getIns64.ret; - field string Asm32 = getAsm32.ret; - field string Asm64 = getAsm64.ret; + field string Asm32 = getAsm32.ret; + field string Asm64 = getAsm64.ret; } // FIXME: I think these F16/I16 profiles will need to use f16/i16 types in order // for the instruction patterns to work. -def VOP_F16_F16 : VOPProfile <[f32, f32, untyped, untyped]>; -def VOP_F16_I16 : VOPProfile <[f32, i32, untyped, untyped]>; -def VOP_I16_F16 : VOPProfile <[i32, f32, untyped, untyped]>; +def VOP_F16_F16 : VOPProfile <[f16, f16, untyped, untyped]>; +def VOP_F16_I16 : VOPProfile <[f16, i32, untyped, untyped]>; +def VOP_I16_F16 : VOPProfile <[i32, f16, untyped, untyped]>; -def VOP_F16_F16_F16 : VOPProfile <[f32, f32, f32, untyped]>; -def VOP_F16_F16_I16 : VOPProfile <[f32, f32, i32, untyped]>; +def VOP_F16_F16_F16 : VOPProfile <[f16, f16, f16, untyped]>; +def VOP_F16_F16_I16 : VOPProfile <[f16, f16, i32, untyped]>; def VOP_I16_I16_I16 : VOPProfile <[i32, i32, i32, untyped]>; +def VOP_NONE : VOPProfile <[untyped, untyped, untyped, untyped]>; + def VOP_F32_F32 : VOPProfile <[f32, f32, untyped, untyped]>; def VOP_F32_F64 : VOPProfile <[f32, f64, untyped, untyped]>; def VOP_F32_I32 : VOPProfile <[f32, i32, untyped, untyped]>; @@ -1118,25 +1175,76 @@ def VOP_F64_F64_I32 : VOPProfile <[f64, f64, i32, untyped]>; def VOP_I32_F32_F32 : VOPProfile <[i32, f32, f32, untyped]>; def VOP_I32_F32_I32 : VOPProfile <[i32, f32, i32, untyped]>; def VOP_I32_I32_I32 : VOPProfile <[i32, i32, i32, untyped]>; -def VOP_I32_I32_I32_VCC : VOPProfile <[i32, i32, i32, untyped]> { + +// Write out to vcc or arbitrary SGPR. +def VOP2b_I32_I1_I32_I32 : VOPProfile<[i32, i32, i32, untyped]> { + let Asm32 = "$dst, vcc, $src0, $src1"; + let Asm64 = "$dst, $sdst, $src0, $src1"; + let Outs32 = (outs DstRC:$dst); + let Outs64 = (outs DstRC:$dst, SReg_64:$sdst); +} + +// Write out to vcc or arbitrary SGPR and read in from vcc or +// arbitrary SGPR. +def VOP2b_I32_I1_I32_I32_I1 : VOPProfile<[i32, i32, i32, i1]> { + // We use VCSrc_32 to exclude literal constants, even though the + // encoding normally allows them since the implicit VCC use means + // using one would always violate the constant bus + // restriction. SGPRs are still allowed because it should + // technically be possible to use VCC again as src0. let Src0RC32 = VCSrc_32; + let Asm32 = "$dst, vcc, $src0, $src1, vcc"; + let Asm64 = "$dst, $sdst, $src0, $src1, $src2"; + let Outs32 = (outs DstRC:$dst); + let Outs64 = (outs DstRC:$dst, SReg_64:$sdst); + + // Suppress src2 implied by type since the 32-bit encoding uses an + // implicit VCC use. + let Ins32 = (ins Src0RC32:$src0, Src1RC32:$src1); } -def VOP_I1_F32_I32 : VOPProfile <[i1, f32, i32, untyped]> { - let Ins64 = (ins InputModsNoDefault:$src0_modifiers, Src0RC64:$src0, Src1RC64:$src1); - let Asm64 = "$dst, $src0_modifiers, $src1"; +class VOP3b_Profile : VOPProfile<[vt, vt, vt, vt]> { + let Outs64 = (outs DstRC:$vdst, SReg_64:$sdst); + let Asm64 = "$vdst, $sdst, $src0_modifiers, $src1_modifiers, $src2_modifiers"#"$clamp"#"$omod"; } -def VOP_I1_F64_I32 : VOPProfile <[i1, f64, i32, untyped]> { +def VOP3b_F32_I1_F32_F32_F32 : VOP3b_Profile { + // FIXME: Hack to stop printing _e64 + let DstRC = RegisterOperand; +} + +def VOP3b_F64_I1_F64_F64_F64 : VOP3b_Profile { + // FIXME: Hack to stop printing _e64 + let DstRC = RegisterOperand; +} + +// VOPC instructions are a special case because for the 32-bit +// encoding, we want to display the implicit vcc write as if it were +// an explicit $dst. +class VOPC_Profile : VOPProfile <[i1, vt0, vt1, untyped]> { + let Asm32 = "vcc, $src0, $src1"; + // The destination for 32-bit encoding is implicit. + let HasDst32 = 0; +} + +class VOPC_Class_Profile : VOPC_Profile { let Ins64 = (ins InputModsNoDefault:$src0_modifiers, Src0RC64:$src0, Src1RC64:$src1); let Asm64 = "$dst, $src0_modifiers, $src1"; } +def VOPC_I1_F32_F32 : VOPC_Profile; +def VOPC_I1_F64_F64 : VOPC_Profile; +def VOPC_I1_I32_I32 : VOPC_Profile; +def VOPC_I1_I64_I64 : VOPC_Profile; + +def VOPC_I1_F32_I32 : VOPC_Class_Profile; +def VOPC_I1_F64_I32 : VOPC_Class_Profile; + def VOP_I64_I64_I32 : VOPProfile <[i64, i64, i32, untyped]>; def VOP_I64_I32_I64 : VOPProfile <[i64, i32, i64, untyped]>; def VOP_I64_I64_I64 : VOPProfile <[i64, i64, i64, untyped]>; def VOP_CNDMASK : VOPProfile <[i32, i32, i32, untyped]> { - let Ins32 = (ins Src0RC32:$src0, Src1RC32:$src1, VCCReg:$src2); + let Ins32 = (ins Src0RC32:$src0, Src1RC32:$src1); let Ins64 = (ins Src0RC64:$src0, Src1RC64:$src1, SSrc_64:$src2); let Asm64 = "$dst, $src0, $src1, $src2"; } @@ -1150,13 +1258,60 @@ def VOP_MAC : VOPProfile <[f32, f32, f32, f32]> { let Ins32 = (ins Src0RC32:$src0, Src1RC32:$src1, VGPR_32:$src2); let Ins64 = getIns64, 3, HasModifiers>.ret; - let Asm32 = getAsm32<2>.ret; - let Asm64 = getAsm64<2, HasModifiers>.ret; + let Asm32 = getAsm32<1, 2>.ret; + let Asm64 = getAsm64<1, 2, HasModifiers>.ret; } def VOP_F64_F64_F64_F64 : VOPProfile <[f64, f64, f64, f64]>; def VOP_I32_I32_I32_I32 : VOPProfile <[i32, i32, i32, i32]>; def VOP_I64_I32_I32_I64 : VOPProfile <[i64, i32, i32, i64]>; +class SIInstAlias : + InstAlias , PredicateControl { + + field bit isCompare; + field bit isCommutable; + + let ResultInst = + !if (p.HasDst32, + !if (!eq(p.NumSrcArgs, 0), + // 1 dst, 0 src + (inst p.DstRC:$dst), + !if (!eq(p.NumSrcArgs, 1), + // 1 dst, 1 src + (inst p.DstRC:$dst, p.Src0RC32:$src0), + !if (!eq(p.NumSrcArgs, 2), + // 1 dst, 2 src + (inst p.DstRC:$dst, p.Src0RC32:$src0, p.Src1RC32:$src1), + // else - unreachable + (inst)))), + // else + !if (!eq(p.NumSrcArgs, 2), + // 0 dst, 2 src + (inst p.Src0RC32:$src0, p.Src1RC32:$src1), + !if (!eq(p.NumSrcArgs, 1), + // 0 dst, 1 src + (inst p.Src0RC32:$src1), + // else + // 0 dst, 0 src + (inst)))); +} + +class SIInstAliasSI : + SIInstAlias (op_name#"_e32_si"), p> { + let AssemblerPredicate = SIAssemblerPredicate; +} + +class SIInstAliasVI : + SIInstAlias (op_name#"_e32_vi"), p> { + let AssemblerPredicates = [isVI]; +} + +multiclass SIInstAliasBuilder { + + def : SIInstAliasSI ; + + def : SIInstAliasVI ; +} class VOP { string OpName = opName; @@ -1281,6 +1436,9 @@ class VOP3_Pseudo pattern, string opName> : MnemonicAlias { let isPseudo = 1; let isCodeGenOnly = 1; + + field bit vdst; + field bit src0; } class VOP3_Real_si op, dag outs, dag ins, string asm, string opName> : @@ -1326,22 +1484,6 @@ multiclass VOP3_m pattern, HasMods>; } -// VOP3_m without source modifiers -multiclass VOP3_m_nomods pattern, - string opName, int NumSrcArgs, bit HasMods = 1> { - - def "" : VOP3_Pseudo ; - - let src0_modifiers = 0, - src1_modifiers = 0, - src2_modifiers = 0, - clamp = 0, - omod = 0 in { - def _si : VOP3_Real_si ; - def _vi : VOP3_Real_vi ; - } -} - multiclass VOP3_1_m pattern, string opName, bit HasMods = 1> { @@ -1366,7 +1508,7 @@ multiclass VOP3SI_1_m pattern, string opName, string revOp, - bit HasMods = 1, bit UseFullOp = 0> { + bit HasMods = 1> { def "" : VOP3_Pseudo , VOP2_REV; @@ -1380,7 +1522,7 @@ multiclass VOP3_2_m pattern, string opName, string revOp, - bit HasMods = 1, bit UseFullOp = 0> { + bit HasMods = 1> { def "" : VOP3_Pseudo , VOP2_REV; @@ -1391,54 +1533,41 @@ multiclass VOP3SI_2_m pattern, string opName, string revOp, - bit HasMods = 1, bit UseFullOp = 0> { - def "" : VOP3_Pseudo , - VOP2_REV; - - // The VOP2 variant puts the carry out into VCC, the VOP3 variant - // can write it into any SGPR. We currently don't use the carry out, - // so for now hardcode it to VCC as well. - let sdst = SIOperand.VCC, Defs = [VCC] in { - def _si : VOP3b_Real_si , - VOP3DisableFields<1, 0, HasMods>; - - def _vi : VOP3b_Real_vi , - VOP3DisableFields<1, 0, HasMods>; - } // End sdst = SIOperand.VCC, Defs = [VCC] -} - -multiclass VOP3b_3_m pattern, string opName, string revOp, - bit HasMods = 1, bit UseFullOp = 0> { +// Two operand VOP3b instruction that may have a 3rd SGPR bool operand +// instead of an implicit VCC as in the VOP2b format. +multiclass VOP3b_2_3_m pattern, string opName, string revOp, + bit HasMods = 1, bit useSrc2Input = 0> { def "" : VOP3_Pseudo ; - def _si : VOP3b_Real_si , - VOP3DisableFields<1, 1, HasMods>; + VOP3DisableFields<1, useSrc2Input, HasMods>; def _vi : VOP3b_Real_vi , - VOP3DisableFields<1, 1, HasMods>; + VOP3DisableFields<1, useSrc2Input, HasMods>; } multiclass VOP3_C_m pattern, string opName, - bit HasMods, bit defExec, string revOp> { + bit HasMods, bit defExec, + string revOp, list sched> { def "" : VOP3_Pseudo , - VOP2_REV; + VOP2_REV { + let Defs = !if(defExec, [EXEC], []); + let SchedRW = sched; + } def _si : VOP3_Real_si , VOP3DisableFields<1, 0, HasMods> { let Defs = !if(defExec, [EXEC], []); + let SchedRW = sched; } def _vi : VOP3_Real_vi , VOP3DisableFields<1, 0, HasMods> { let Defs = !if(defExec, [EXEC], []); + let SchedRW = sched; } } @@ -1539,22 +1668,25 @@ multiclass VOP2InstSI ; } -multiclass VOP2b_Helper pat32, dag ins64, string asm64, list pat64, - string revOp, bit HasMods> { - - defm _e32 : VOP2_m ; + string revOp, bit HasMods, bit useSGPRInput> { + let SchedRW = [Write32Bit, WriteSALU] in { + let Uses = !if(useSGPRInput, [VCC, EXEC], [EXEC]), Defs = [VCC] in { + defm _e32 : VOP2_m ; + } - defm _e64 : VOP3b_2_m ; + defm _e64 : VOP3b_2_3_m ; + } } multiclass VOP2bInst : VOP2b_Helper < - op, opName, P.Outs, + op, opName, P.Outs32, P.Outs64, P.Ins32, P.Asm32, [], P.Ins64, P.Asm64, !if(P.HasModifiers, @@ -1563,7 +1695,7 @@ multiclass VOP2bInst ; // A VOP2 instruction that is VOP3-only on VI. @@ -1617,39 +1749,55 @@ let isCodeGenOnly = 0 in { class VOPC_Pseudo pattern, string opName> : VOPCCommon , VOP , - SIMCInstr, - MnemonicAlias { + SIMCInstr { let isPseudo = 1; let isCodeGenOnly = 1; } -multiclass VOPC_m pattern, - string opName, bit DefExec, string revOpName = ""> { - def "" : VOPC_Pseudo ; - - def _si : VOPC, - SIMCInstr { - let Defs = !if(DefExec, [EXEC], []); - let hasSideEffects = DefExec; - let AssemblerPredicates = [isSICI]; +multiclass VOPC_m pattern, + string opName, bit DefExec, VOPProfile p, + list sched, + string revOpName = "", string asm = opName#"_e32 "#op_asm, + string alias_asm = opName#" "#op_asm> { + def "" : VOPC_Pseudo { + let Defs = !if(DefExec, [VCC, EXEC], [VCC]); + let SchedRW = sched; } - def _vi : VOPC, - SIMCInstr { - let Defs = !if(DefExec, [EXEC], []); - let hasSideEffects = DefExec; - let AssemblerPredicates = [isVI]; - } + let AssemblerPredicates = [isSICI] in { + def _si : VOPC, + SIMCInstr { + let Defs = !if(DefExec, [VCC, EXEC], [VCC]); + let hasSideEffects = DefExec; + let SchedRW = sched; + } + + } // End AssemblerPredicates = [isSICI] + + let AssemblerPredicates = [isVI] in { + def _vi : VOPC, + SIMCInstr { + let Defs = !if(DefExec, [VCC, EXEC], [VCC]); + let hasSideEffects = DefExec; + let SchedRW = sched; + } + + } // End AssemblerPredicates = [isVI] + + defm : SIInstAliasBuilder; } multiclass VOPC_Helper pat32, dag out64, dag ins64, string asm64, list pat64, - bit HasMods, bit DefExec, string revOp> { - defm _e32 : VOPC_m ; + bit HasMods, bit DefExec, string revOp, + VOPProfile p, + list sched> { + defm _e32 : VOPC_m ; defm _e64 : VOP3_C_m ; + opName, HasMods, DefExec, revOp, + sched>; } // Special case for class instructions which only have modifiers on @@ -1657,18 +1805,22 @@ multiclass VOPC_Helper pat32, dag out64, dag ins64, string asm64, list pat64, - bit HasMods, bit DefExec, string revOp> { - defm _e32 : VOPC_m ; + bit HasMods, bit DefExec, string revOp, + VOPProfile p, + list sched> { + defm _e32 : VOPC_m ; defm _e64 : VOP3_C_m , + opName, HasMods, DefExec, revOp, sched>, VOP3DisableModFields<1, 0, 0>; } multiclass VOPCInst : VOPC_Helper < + bit DefExec = 0, + list sched = [Write32Bit]> : + VOPC_Helper < op, opName, P.Ins32, P.Asm32, [], (outs VOPDstS64:$dst), P.Ins64, P.Asm64, @@ -1679,11 +1831,12 @@ multiclass VOPCInst ; multiclass VOPCClassInst : VOPC_Class_Helper < + bit DefExec = 0, + list sched> : VOPC_Class_Helper < op, opName, P.Ins32, P.Asm32, [], (outs VOPDstS64:$dst), P.Ins64, P.Asm64, @@ -1691,39 +1844,40 @@ multiclass VOPCClassInst ; multiclass VOPC_F32 : - VOPCInst ; + VOPCInst ; multiclass VOPC_F64 : - VOPCInst ; + VOPCInst ; multiclass VOPC_I32 : - VOPCInst ; + VOPCInst ; multiclass VOPC_I64 : - VOPCInst ; + VOPCInst ; multiclass VOPCX sched, string revOp = ""> - : VOPCInst ; + : VOPCInst ; multiclass VOPCX_F32 : - VOPCX ; + VOPCX ; multiclass VOPCX_F64 : - VOPCX ; + VOPCX ; multiclass VOPCX_I32 : - VOPCX ; + VOPCX ; multiclass VOPCX_I64 : - VOPCX ; + VOPCX ; multiclass VOP3_Helper pat, int NumSrcArgs, bit HasMods> : VOP3_m < @@ -1731,16 +1885,16 @@ multiclass VOP3_Helper ; multiclass VOPC_CLASS_F32 : - VOPCClassInst ; + VOPCClassInst ; multiclass VOPCX_CLASS_F32 : - VOPCClassInst ; + VOPCClassInst ; multiclass VOPC_CLASS_F64 : - VOPCClassInst ; + VOPCClassInst ; multiclass VOPCX_CLASS_F64 : - VOPCClassInst ; + VOPCClassInst ; multiclass VOP3Inst : VOP3_Helper < @@ -1792,25 +1946,13 @@ multiclass VOP3_VCC_Inst ; -multiclass VOP3b_Helper pattern> : - VOP3b_3_m < - op, (outs vrc:$vdst, SReg_64:$sdst), - (ins InputModsNoDefault:$src0_modifiers, arc:$src0, - InputModsNoDefault:$src1_modifiers, arc:$src1, - InputModsNoDefault:$src2_modifiers, arc:$src2, - ClampMod:$clamp, omod:$omod), - opName#" $vdst, $sdst, $src0_modifiers, $src1_modifiers, $src2_modifiers"#"$clamp"#"$omod", pattern, - opName, opName, 1, 1 +multiclass VOP3bInst pattern = []> : + VOP3b_2_3_m < + op, P.Outs64, P.Ins64, + opName#" "#P.Asm64, pattern, + opName, "", 1, 1 >; -multiclass VOP3b_64 pattern> : - VOP3b_Helper ; - -multiclass VOP3b_32 pattern> : - VOP3b_Helper ; - - class Vop3ModPat : Pat< (node (P.Src0VT (VOP3Mods0 P.Src0VT:$src0, i32:$src0_modifiers, i1:$clamp, i32:$omod)), (P.Src1VT (VOP3Mods P.Src1VT:$src1, i32:$src1_modifiers)), @@ -1956,12 +2098,14 @@ multiclass DS_1A1D_RET op, string opName, RegisterClass rc, dag ins = (ins VGPR_32:$addr, rc:$data0, ds_offset:$offset, gds:$gds), string asm = opName#" $vdst, $addr, $data0"#"$offset$gds"> { - def "" : DS_Pseudo , - AtomicNoRet; + let hasPostISelHook = 1 in { + def "" : DS_Pseudo , + AtomicNoRet; - let data1 = 0 in { - def _si : DS_Off16_Real_si ; - def _vi : DS_Off16_Real_vi ; + let data1 = 0 in { + def _si : DS_Off16_Real_si ; + def _vi : DS_Off16_Real_vi ; + } } } @@ -1970,11 +2114,13 @@ multiclass DS_1A2D_RET_m op, string opName, RegisterClass rc, dag outs = (outs rc:$vdst), string asm = opName#" $vdst, $addr, $data0, $data1"#"$offset"#"$gds"> { - def "" : DS_Pseudo , - AtomicNoRet; + let hasPostISelHook = 1 in { + def "" : DS_Pseudo , + AtomicNoRet; - def _si : DS_Off16_Real_si ; - def _vi : DS_Off16_Real_vi ; + def _si : DS_Off16_Real_si ; + def _vi : DS_Off16_Real_vi ; + } } multiclass DS_1A2D_RET op, string asm, RegisterClass rc, @@ -2276,7 +2422,7 @@ multiclass MUBUF_Atomic { + let hasSideEffects = 1, mayStore = 1, AsmMatchConverter = "" in { + def "" : MUBUF_Pseudo ; + + // Set everything to 0. + let offset = 0, offen = 0, idxen = 0, glc = 0, vaddr = 0, + vdata = 0, srsrc = 0, slc = 0, tfe = 0, soffset = 0 in { + let addr64 = 0 in { + def _si : MUBUF_Real_si ; + } + + def _vi : MUBUF_Real_vi ; + } + } // End hasSideEffects = 1, mayStore = 1, AsmMatchConverter = "" +} + class FLAT_Load_Helper op, string asm, RegisterClass regClass> : FLAT op, string name, RegisterClass vdst_rc, name#" $vdst, $addr, $data glc"#"$slc"#"$tfe", []>, AtomicNoRet { let glc = 1; + let hasPostISelHook = 1; } } }