X-Git-Url: http://plrg.eecs.uci.edu/git/?a=blobdiff_plain;f=lib%2FTarget%2FAArch64%2FAArch64InstrInfo.td;h=562a7f60bbd9b09e2037214b41528d871b762b40;hb=2878b7d7ab8dc4bf424690b58088e0b7d3ada49f;hp=673e05155d542e4b553d039c73456224e2357531;hpb=dfe076af9879eb68a7b8331f9c02eecf563d85be;p=oota-llvm.git diff --git a/lib/Target/AArch64/AArch64InstrInfo.td b/lib/Target/AArch64/AArch64InstrInfo.td index 673e05155d5..562a7f60bbd 100644 --- a/lib/Target/AArch64/AArch64InstrInfo.td +++ b/lib/Target/AArch64/AArch64InstrInfo.td @@ -1,3 +1,16 @@ +//===----- AArch64InstrInfo.td - AArch64 Instruction Info ----*- tablegen -*-=// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// This file describes the AArch64 scalar instructions in TableGen format. +// +//===----------------------------------------------------------------------===// + include "AArch64InstrFormats.td" //===----------------------------------------------------------------------===// @@ -6,7 +19,8 @@ include "AArch64InstrFormats.td" def SDT_A64ret : SDTypeProfile<0, 0, []>; def A64ret : SDNode<"AArch64ISD::Ret", SDT_A64ret, [SDNPHasChain, - SDNPOptInGlue]>; + SDNPOptInGlue, + SDNPVariadic]>; // (ins NZCV, Condition, Dest) def SDT_A64br_cc : SDTypeProfile<0, 3, [SDTCisVT<0, i32>]>; @@ -204,11 +218,12 @@ def ATOMIC_CMP_SWAP_I64 // is not optional in that case (but can explicitly be 0), and the // entire suffix can be skipped (e.g. "add sp, x3, x2"). -multiclass extend_operands { +multiclass extend_operands { def _asmoperand : AsmOperandClass { let Name = PREFIX; let RenderMethod = "addRegExtendOperands"; let PredicateMethod = "isRegExtend"; + let DiagnosticType = "AddSubRegExtend" # Diag; } def _operand : Operand, @@ -219,18 +234,19 @@ multiclass extend_operands { } } -defm UXTB : extend_operands<"UXTB">; -defm UXTH : extend_operands<"UXTH">; -defm UXTW : extend_operands<"UXTW">; -defm UXTX : extend_operands<"UXTX">; -defm SXTB : extend_operands<"SXTB">; -defm SXTH : extend_operands<"SXTH">; -defm SXTW : extend_operands<"SXTW">; -defm SXTX : extend_operands<"SXTX">; +defm UXTB : extend_operands<"UXTB", "Small">; +defm UXTH : extend_operands<"UXTH", "Small">; +defm UXTW : extend_operands<"UXTW", "Small">; +defm UXTX : extend_operands<"UXTX", "Large">; +defm SXTB : extend_operands<"SXTB", "Small">; +defm SXTH : extend_operands<"SXTH", "Small">; +defm SXTW : extend_operands<"SXTW", "Small">; +defm SXTX : extend_operands<"SXTX", "Large">; def LSL_extasmoperand : AsmOperandClass { let Name = "RegExtendLSL"; let RenderMethod = "addRegExtendOperands"; + let DiagnosticType = "AddSubRegExtendLarge"; } def LSL_extoperand : Operand { @@ -539,10 +555,14 @@ let ParserMethod = "ParseImmWithLSLOperand", // Derived PredicateMethod fields are different for each def addsubimm_lsl0_asmoperand : AsmOperandClass { let Name = "AddSubImmLSL0"; + // If an error is reported against this operand, instruction could also be a + // register variant. + let DiagnosticType = "AddSubSecondSource"; } def addsubimm_lsl12_asmoperand : AsmOperandClass { let Name = "AddSubImmLSL12"; + let DiagnosticType = "AddSubSecondSource"; } } @@ -688,8 +708,8 @@ multiclass shift_operands { def _asmoperand_i32 : AsmOperandClass { let Name = "Shift" # form # "i32"; let RenderMethod = "addShiftOperands"; - let PredicateMethod - = "isShift"; + let PredicateMethod = "isShift"; + let DiagnosticType = "AddSubRegShift32"; } // Note that the operand type is intentionally i64 because the DAGCombiner @@ -704,8 +724,8 @@ multiclass shift_operands { def _asmoperand_i64 : AsmOperandClass { let Name = "Shift" # form # "i64"; let RenderMethod = "addShiftOperands"; - let PredicateMethod - = "isShift"; + let PredicateMethod = "isShift"; + let DiagnosticType = "AddSubRegShift64"; } def _i64 : Operand, ImmLeaf= 0 && Imm <= 63; }]> { @@ -956,12 +976,14 @@ def uimm5_asmoperand : AsmOperandClass { let Name = "UImm5"; let PredicateMethod = "isUImm<5>"; let RenderMethod = "addImmOperands"; + let DiagnosticType = "UImm5"; } def uimm6_asmoperand : AsmOperandClass { let Name = "UImm6"; let PredicateMethod = "isUImm<6>"; let RenderMethod = "addImmOperands"; + let DiagnosticType = "UImm6"; } def bitfield32_imm : Operand, @@ -1156,6 +1178,7 @@ def bfx32_width_asmoperand : AsmOperandClass { let Name = "BFX32Width"; let PredicateMethod = "isBitfieldWidth<32>"; let RenderMethod = "addBFXWidthOperands"; + let DiagnosticType = "Width32"; } def bfx32_width : Operand, ImmLeaf { @@ -1167,6 +1190,7 @@ def bfx64_width_asmoperand : AsmOperandClass { let Name = "BFX64Width"; let PredicateMethod = "isBitfieldWidth<64>"; let RenderMethod = "addBFXWidthOperands"; + let DiagnosticType = "Width64"; } def bfx64_width : Operand { @@ -1234,6 +1258,7 @@ def bfi32_lsb_asmoperand : AsmOperandClass { let Name = "BFI32LSB"; let PredicateMethod = "isUImm<5>"; let RenderMethod = "addBFILSBOperands<32>"; + let DiagnosticType = "UImm5"; } def bfi32_lsb : Operand, @@ -1246,6 +1271,7 @@ def bfi64_lsb_asmoperand : AsmOperandClass { let Name = "BFI64LSB"; let PredicateMethod = "isUImm<6>"; let RenderMethod = "addBFILSBOperands<64>"; + let DiagnosticType = "UImm6"; } def bfi64_lsb : Operand, @@ -1261,6 +1287,7 @@ def bfi32_width_asmoperand : AsmOperandClass { let Name = "BFI32Width"; let PredicateMethod = "isBitfieldWidth<32>"; let RenderMethod = "addBFIWidthOperands"; + let DiagnosticType = "Width32"; } def bfi32_width : Operand, @@ -1273,6 +1300,7 @@ def bfi64_width_asmoperand : AsmOperandClass { let Name = "BFI64Width"; let PredicateMethod = "isBitfieldWidth<64>"; let RenderMethod = "addBFIWidthOperands"; + let DiagnosticType = "Width64"; } def bfi64_width : Operand, @@ -1328,6 +1356,7 @@ class label_asmoperand : AsmOperandClass { let Name = "Label" # width # "_" # scale; let PredicateMethod = "isLabel<" # width # "," # scale # ">"; let RenderMethod = "addLabelOperands<" # width # ", " # scale # ">"; + let DiagnosticType = "Label"; } def label_wid19_scal4_asmoperand : label_asmoperand<19, 4>; @@ -1374,6 +1403,7 @@ defm CBNZ : cmpbr_sizes<0b1, "cbnz", ImmLeaf, ImmLeaf { @@ -1419,6 +1450,7 @@ def cond_code_op_asmoperand : AsmOperandClass { let RenderMethod = "addCondCodeOperands"; let PredicateMethod = "isCondCode"; let ParserMethod = "ParseCondCodeOperand"; + let DiagnosticType = "CondCode"; } def cond_code_op : Operand { @@ -1470,6 +1502,7 @@ def inv_cond_code_op_asmoperand : AsmOperandClass { let RenderMethod = "addInvCondCodeOperands"; let PredicateMethod = "isCondCode"; let ParserMethod = "ParseCondCodeOperand"; + let DiagnosticType = "CondCode"; } def inv_cond_code_op : Operand { @@ -1618,7 +1651,7 @@ class A64I_dp_1src_impl opcode, string asmop, itin>; multiclass A64I_dp_1src opcode, string asmop> { - let neverHasSideEffects = 1 in { + let hasSideEffects = 0 in { def ww : A64I_dp_1src_impl<0b0, opcode, asmop, [], GPR32, NoItinerary>; def xx : A64I_dp_1src_impl<0b1, opcode, asmop, [], GPR64, NoItinerary>; } @@ -1657,7 +1690,9 @@ def REV16xx : A64I_dp_1src_impl<0b1, 0b000001, "rev16", [], GPR64, NoItinerary>; //===----------------------------------------------------------------------===// // Data Processing (2 sources) instructions //===----------------------------------------------------------------------===// -// Contains: UDIV, SDIV, LSLV, LSRV, ASRV, RORV + aliases LSL, LSR, ASR, ROR +// Contains: CRC32C?[BHWX], UDIV, SDIV, LSLV, LSRV, ASRV, RORV + aliases LSL, +// LSR, ASR, ROR + class dp_2src_impl opcode, string asmop, list patterns, RegisterClass GPRsp, @@ -1671,6 +1706,19 @@ class dp_2src_impl opcode, string asmop, list patterns, patterns, itin>; +multiclass dp_2src_crc { + def B_www : dp_2src_impl<0b0, {0, 1, 0, c, 0, 0}, + !strconcat(asmop, "b"), [], GPR32, NoItinerary>; + def H_www : dp_2src_impl<0b0, {0, 1, 0, c, 0, 1}, + !strconcat(asmop, "h"), [], GPR32, NoItinerary>; + def W_www : dp_2src_impl<0b0, {0, 1, 0, c, 1, 0}, + !strconcat(asmop, "w"), [], GPR32, NoItinerary>; + def X_wwx : A64I_dp_2src<0b1, {0, 1, 0, c, 1, 1}, 0b0, + !strconcat(asmop, "x\t$Rd, $Rn, $Rm"), + (outs GPR32:$Rd), (ins GPR32:$Rn, GPR64:$Rm), [], + NoItinerary>; +} + multiclass dp_2src_zext opcode, string asmop, SDPatternOperator op> { def www : dp_2src_impl<0b0, opcode, @@ -1704,6 +1752,9 @@ multiclass dp_2src opcode, string asmop, SDPatternOperator op> { } // Here we define the data processing 2 source instructions. +defm CRC32 : dp_2src_crc<0b0, "crc32">; +defm CRC32C : dp_2src_crc<0b1, "crc32c">; + defm UDIV : dp_2src<0b000010, "udiv", udiv>; defm SDIV : dp_2src<0b000011, "sdiv", sdiv>; @@ -1817,6 +1868,7 @@ def uimm16_asmoperand : AsmOperandClass { let Name = "UImm16"; let PredicateMethod = "isUImm<16>"; let RenderMethod = "addImmOperands"; + let DiagnosticType = "UImm16"; } def uimm16 : Operand { @@ -1883,6 +1935,7 @@ def : Pat<(rotr GPR64:$Rn, bitfield64_imm:$LSB), def fpzero_asmoperand : AsmOperandClass { let Name = "FPZero"; let ParserMethod = "ParseFPImmOperand"; + let DiagnosticType = "FPZero"; } def fpz32 : Operand, @@ -2120,6 +2173,7 @@ def fixedpos_asmoperand_i32 : AsmOperandClass { let Name = "CVTFixedPos32"; let RenderMethod = "addCVTFixedPosOperands"; let PredicateMethod = "isCVTFixedPos<32>"; + let DiagnosticType = "CVTFixedPos32"; } // Also encoded as "64 - " but #1-#64 allowed. @@ -2127,6 +2181,7 @@ def fixedpos_asmoperand_i64 : AsmOperandClass { let Name = "CVTFixedPos64"; let RenderMethod = "addCVTFixedPosOperands"; let PredicateMethod = "isCVTFixedPos<64>"; + let DiagnosticType = "CVTFixedPos64"; } // We need the cartesian product of f32/f64 i32/i64 operands for @@ -2282,6 +2337,7 @@ def : Pat<(f64 (bitconvert (i64 GPR64:$Rn))), (FMOVdx GPR64:$Rn)>; def lane1_asmoperand : AsmOperandClass { let Name = "Lane1"; let RenderMethod = "addImmOperands"; + let DiagnosticType = "Lane1"; } def lane1 : Operand { @@ -2313,6 +2369,7 @@ def : InstAlias<"fmov $Rd.2d[$Lane], $Rn", def fpimm_asmoperand : AsmOperandClass { let Name = "FMOVImm"; let ParserMethod = "ParseFPImmOperand"; + let DiagnosticType = "FPImm"; } // The MCOperand for these instructions are the encoded 8-bit values. @@ -2353,6 +2410,7 @@ def FMOVdi : A64I_fpimm_impl<0b01, FPR64, f64, fmov64_operand>; def ldrlit_label_asmoperand : AsmOperandClass { let Name = "LoadLitLabel"; let RenderMethod = "addLabelOperands<19, 4>"; + let DiagnosticType = "Label"; } def ldrlit_label : Operand { @@ -2373,6 +2431,7 @@ multiclass namedimm { let PredicateMethod = "isUImm"; let RenderMethod = "addImmOperands"; let ParserMethod = "ParseNamedImmOperand<" # mapper # ">"; + let DiagnosticType = "NamedImm_" # prefix; } def _op : Operand { @@ -2394,10 +2453,8 @@ let mayLoad = 1 in { def LDRx_lit : A64I_LDRlitSimple<0b01, 0b0, GPR64>; } -def LDRs_lit : A64I_LDRlitSimple<0b00, 0b1, FPR32, - [(set (f32 FPR32:$Rt), (load constpool:$Imm19))]>; -def LDRd_lit : A64I_LDRlitSimple<0b01, 0b1, FPR64, - [(set (f64 FPR64:$Rt), (load constpool:$Imm19))]>; +def LDRs_lit : A64I_LDRlitSimple<0b00, 0b1, FPR32>; +def LDRd_lit : A64I_LDRlitSimple<0b01, 0b1, FPR64>; let mayLoad = 1 in { def LDRq_lit : A64I_LDRlitSimple<0b10, 0b1, FPR128>; @@ -2440,6 +2497,7 @@ def GPR64xsp0_asmoperand : AsmOperandClass { let PredicateMethod = "isWrappedReg"; let RenderMethod = "addRegOperands"; let ParserMethod = "ParseLSXAddressOperand"; + // Diagnostics are provided by ParserMethod } def GPR64xsp0 : RegisterOperand { @@ -2717,6 +2775,7 @@ multiclass offsets_uimm12 { let Name = "OffsetUImm12_" # MemSize; let PredicateMethod = "isOffsetUImm12<" # MemSize # ">"; let RenderMethod = "addOffsetUImm12Operands<" # MemSize # ">"; + let DiagnosticType = "LoadStoreUImm12_" # MemSize; } // Pattern is really no more than an ImmLeaf, but predicated on MemSize which @@ -2751,6 +2810,7 @@ def simm9_asmoperand : AsmOperandClass { let Name = "SImm9"; let PredicateMethod = "isSImm<9>"; let RenderMethod = "addSImmOperands<9>"; + let DiagnosticType = "LoadStoreSImm9"; } def simm9 : Operand, @@ -2783,6 +2843,7 @@ multiclass regexts"; let RenderMethod = "addAddrRegExtendOperands<" # MemSize # ">"; + let DiagnosticType = "LoadStoreExtend" # RmSize # "_" # MemSize; } def regext : Operand { @@ -3356,6 +3417,7 @@ multiclass offsets_simm7 { let Name = "SImm7_Scaled" # MemSize; let PredicateMethod = "isSImm7Scaled<" # MemSize # ">"; let RenderMethod = "addSImm7ScaledOperands<" # MemSize # ">"; + let DiagnosticType = "LoadStoreSImm7_" # MemSize; } def simm7 : Operand { @@ -3507,6 +3569,7 @@ multiclass logical_imm_operands"; let RenderMethod = "addLogicalImmOperands<" # size # ">"; + let DiagnosticType = "LogicalSecondSource"; } def _operand @@ -3798,8 +3861,8 @@ multiclass movw_operands { let Name = instname # width # "Shifted" # shift; let PredicateMethod = "is" # instname # width # "Imm"; let RenderMethod = "addMoveWideImmOperands"; - let ParserMethod = "ParseImmWithLSLOperand"; + let DiagnosticType = "MOVWUImm16"; } def _imm : Operand { @@ -3840,7 +3903,7 @@ multiclass A64I_movwSizes opc, string asmop, dag ins32bit, } let isMoveImm = 1, isReMaterializable = 1, - isAsCheapAsAMove = 1, neverHasSideEffects = 1 in { + isAsCheapAsAMove = 1, hasSideEffects = 0 in { defm MOVN : A64I_movwSizes<0b00, "movn", (ins movn32_imm:$FullImm), (ins movn64_imm:$FullImm)>; @@ -3914,6 +3977,7 @@ def adr_label : Operand { def adrp_label_asmoperand : AsmOperandClass { let Name = "AdrpLabel"; let RenderMethod = "addLabelOperands<21, 4096>"; + let DiagnosticType = "Label"; } def adrp_label : Operand { @@ -3925,7 +3989,7 @@ def adrp_label : Operand { let OperandType = "OPERAND_PCREL"; } -let neverHasSideEffects = 1 in { +let hasSideEffects = 0 in { def ADRxi : A64I_PCADR<0b0, (outs GPR64:$Rd), (ins adr_label:$Label), "adr\t$Rd, $Label", [], NoItinerary>; @@ -3944,6 +4008,7 @@ def uimm3_asmoperand : AsmOperandClass { let Name = "UImm3"; let PredicateMethod = "isUImm<3>"; let RenderMethod = "addImmOperands"; + let DiagnosticType = "UImm3"; } def uimm3 : Operand { @@ -3955,6 +4020,7 @@ def uimm7_asmoperand : AsmOperandClass { let Name = "UImm7"; let PredicateMethod = "isUImm<7>"; let RenderMethod = "addImmOperands"; + let DiagnosticType = "UImm7"; } def uimm7 : Operand { @@ -3990,6 +4056,7 @@ defm tlbi : namedimm<"tlbi", "A64TLBI::TLBIMapper">; def mrs_asmoperand : AsmOperandClass { let Name = "MRS"; let ParserMethod = "ParseSysRegOperand"; + let DiagnosticType = "MRS"; } def mrs_op : Operand { @@ -4006,6 +4073,7 @@ def msr_asmoperand : AsmOperandClass { // AArch64Operand rather than an immediate. The overlap is small enough that // it could be resolved with hackery now, but who can say in future? let ParserMethod = "ParseSysRegOperand"; + let DiagnosticType = "MSR"; } def msr_op : Operand { @@ -4018,6 +4086,7 @@ def pstate_asmoperand : AsmOperandClass { let Name = "MSRPState"; // See comment above about parser. let ParserMethod = "ParseSysRegOperand"; + let DiagnosticType = "MSR"; } def pstate_op : Operand { @@ -4033,6 +4102,7 @@ def CRx_asmoperand : AsmOperandClass { let PredicateMethod = "isUImm<4>"; let RenderMethod = "addImmOperands"; let ParserMethod = "ParseCRxOperand"; + // Diagnostics are handled in all cases by ParseCRxOperand. } def CRx : Operand { @@ -4490,22 +4560,6 @@ def : Pat<(and (A64Bfi GPR64:$src, GPR64:$Rn, imm:$ImmR, imm:$ImmS), } -//===----------------------------------------------------------------------===// -// Constant island entries -//===----------------------------------------------------------------------===// - -// The constant island pass needs to create "instructions" in the middle of the -// instruction stream to reresent its constants. - -def cpinst_operand : Operand; - -def CONSTPOOL_ENTRY : PseudoInst<(outs), (ins cpinst_operand:$instid, - cpinst_operand:$cpidx, - i32imm:$size), []> { - let neverHasSideEffects = 1; - let isNotDuplicable = 1; -} - //===----------------------------------------------------------------------===// // Miscellaneous patterns //===----------------------------------------------------------------------===// @@ -4824,6 +4878,8 @@ defm : uimm12_pats<(A64WrapperSmall texternalsym:$Hi, texternalsym:$Lo12, ALIGN), (ADRPxi texternalsym:$Hi), (i64 texternalsym:$Lo12)>; +defm : uimm12_pats<(A64WrapperSmall tconstpool:$Hi, tconstpool:$Lo12, ALIGN), + (ADRPxi tconstpool:$Hi), (i64 tconstpool:$Lo12)>; // We also want to use uimm12 instructions for local variables at the moment. def tframeindex_XFORM : SDNodeXForm