diff --git a/llvm/lib/Target/ARM/ARMInstrCDE.td b/llvm/lib/Target/ARM/ARMInstrCDE.td index f4326de5ed667..5d4e3acf5b581 100644 --- a/llvm/lib/Target/ARM/ARMInstrCDE.td +++ b/llvm/lib/Target/ARM/ARMInstrCDE.td @@ -115,6 +115,7 @@ class CDE_CX1_Instr !con(params.Iops1, (ins imm_13b:$imm), params.PredOp), !strconcat(iname, params.PAsm, "\t$coproc, $Rd, $imm"), params.Cstr> { + bits<0> p; bits<13> imm; bits<4> Rd; @@ -131,6 +132,7 @@ class CDE_CX2_Instr !con(params.Iops2, (ins imm_9b:$imm), params.PredOp), !strconcat(iname, params.PAsm, "\t$coproc, $Rd, $Rn, $imm"), params.Cstr> { + bits<0> p; bits<9> imm; bits<4> Rd; bits<4> Rn; @@ -149,6 +151,7 @@ class CDE_CX3_Instr !con(params.Iops3, (ins imm_6b:$imm), params.PredOp), !strconcat(iname, params.PAsm, "\t$coproc, $Rd, $Rn, $Rm, $imm"), params.Cstr> { + bits<0> p; bits<6> imm; bits<4> Rd; bits<4> Rn; diff --git a/llvm/lib/Target/ARM/ARMInstrFormats.td b/llvm/lib/Target/ARM/ARMInstrFormats.td index 1ad2485dce17f..1cd1a9a0f7331 100644 --- a/llvm/lib/Target/ARM/ARMInstrFormats.td +++ b/llvm/lib/Target/ARM/ARMInstrFormats.td @@ -1220,6 +1220,7 @@ class Thumb1sI pattern> : InstThumb { bits<0> s; + bits<0> p; let OutOperandList = !con(oops, (outs s_cc_out:$s)); let InOperandList = !con(iops, (ins pred:$p)); let AsmString = !strconcat(opc, "${s}${p}", asm); @@ -1244,6 +1245,7 @@ class Thumb1pI pattern> : InstThumb { + bits<0> p; let OutOperandList = oops; let InOperandList = !con(iops, (ins pred:$p)); let AsmString = !strconcat(opc, "${p}", asm); @@ -1343,6 +1345,7 @@ class Thumb2I pattern> : InstARM { + bits<0> p; let OutOperandList = oops; let InOperandList = !con(iops, (ins pred:$p)); let AsmString = !strconcat(opc, "${p}", asm); @@ -1361,6 +1364,7 @@ class Thumb2sI pattern> : InstARM { + bits<0> p; bits<1> s; // condition-code set flag ('1' if the insn should set the flags) let Inst{20} = s; @@ -2221,6 +2225,7 @@ class NeonI pattern> : InstARM { + bits<0> p; let OutOperandList = oops; let InOperandList = !con(iops, (ins pred:$p)); let AsmString = !strconcat(opc, "${p}", ".", dt, "\t", asm); @@ -2234,6 +2239,7 @@ class NeonXI pattern> : InstARM { + bits<0> p; let OutOperandList = oops; let InOperandList = !con(iops, (ins pred:$p)); let AsmString = !strconcat(opc, "${p}", "\t", asm); diff --git a/llvm/lib/Target/ARM/ARMInstrThumb.td b/llvm/lib/Target/ARM/ARMInstrThumb.td index 0c5ea3e0fa8d5..bc1b34c691e39 100644 --- a/llvm/lib/Target/ARM/ARMInstrThumb.td +++ b/llvm/lib/Target/ARM/ARMInstrThumb.td @@ -483,6 +483,7 @@ let isBranch = 1, isTerminator = 1, isBarrier = 1, isIndirectBranch = 1 in { def tBX : TI<(outs), (ins GPR:$Rm, pred:$p), IIC_Br, "bx${p}\t$Rm", []>, T1Special<{1,1,0,?}>, Sched<[WriteBr]> { // A6.2.3 & A8.6.25 + bits<0> p; bits<4> Rm; let Inst{6-3} = Rm; let Inst{2-0} = 0b000; @@ -491,6 +492,7 @@ let isBranch = 1, isTerminator = 1, isBarrier = 1, isIndirectBranch = 1 in { def tBXNS : TI<(outs), (ins GPR:$Rm, pred:$p), IIC_Br, "bxns${p}\t$Rm", []>, Requires<[IsThumb, Has8MSecExt]>, T1Special<{1,1,0,?}>, Sched<[WriteBr]> { + bits<0> p; bits<4> Rm; let Inst{6-3} = Rm; let Inst{2-0} = 0b100; @@ -523,6 +525,7 @@ let isCall = 1, "bl${p}\t$func", [(ARMcall tglobaladdr:$func)]>, Requires<[IsThumb]>, Sched<[WriteBrL]> { + bits<0> p; bits<24> func; let Inst{26} = func{23}; let Inst{25-16} = func{20-11}; @@ -536,6 +539,7 @@ let isCall = 1, (outs), (ins pred:$p, thumb_blx_target:$func), IIC_Br, "blx${p}\t$func", []>, Requires<[IsThumb, HasV5T, IsNotMClass]>, Sched<[WriteBrL]> { + bits<0> p; bits<24> func; let Inst{26} = func{23}; let Inst{25-16} = func{20-11}; @@ -550,6 +554,7 @@ let isCall = 1, "blx${p}\t$func", []>, Requires<[IsThumb, HasV5T]>, T1Special<{1,1,1,?}>, Sched<[WriteBrL]> { // A6.2.3 & A8.6.24; + bits<0> p; bits<4> func; let Inst{6-3} = func; let Inst{2-0} = 0b000; @@ -565,6 +570,7 @@ let isCall = 1, "blxns${p}\t$func", []>, Requires<[IsThumb, Has8MSecExt]>, T1Special<{1,1,1,?}>, Sched<[WriteBrL]> { + bits<0> p; bits<4> func; let Inst{6-3} = func; let Inst{2-0} = 0b100; @@ -824,6 +830,7 @@ let hasSideEffects = 0 in { let mayLoad = 1, hasExtraDefRegAllocReq = 1, variadicOpsAreDefs = 1 in def tLDMIA : T1I<(outs), (ins tGPR:$Rn, pred:$p, reglist:$regs, variable_ops), IIC_iLoad_m, "ldm${p}\t$Rn, $regs", []>, T1Encoding<{1,1,0,0,1,?}> { + bits<0> p; bits<3> Rn; bits<8> regs; let Inst{10-8} = Rn; @@ -854,6 +861,7 @@ def tSTMIA_UPD : Thumb1I<(outs tGPR:$wb), AddrModeNone, 2, IIC_iStore_mu, "stm${p}\t$Rn!, $regs", "$Rn = $wb", []>, T1Encoding<{1,1,0,0,0,?}> { + bits<0> p; bits<3> Rn; bits<8> regs; let Inst{10-8} = Rn; @@ -872,6 +880,7 @@ def tPOP : T1I<(outs), (ins pred:$p, reglist:$regs, variable_ops), IIC_iPop, "pop${p}\t$regs", []>, T1Misc<{1,1,0,?,?,?,?}>, Sched<[WriteLd]> { + bits<0> p; bits<16> regs; let Inst{8} = regs{15}; let Inst{7-0} = regs{7-0}; @@ -882,6 +891,7 @@ def tPUSH : T1I<(outs), (ins pred:$p, reglist:$regs, variable_ops), IIC_iStore_m, "push${p}\t$regs", []>, T1Misc<{0,1,0,?,?,?,?}>, Sched<[WriteST]> { + bits<0> p; bits<16> regs; let Inst{8} = regs{14}; let Inst{7-0} = regs{7-0}; diff --git a/llvm/lib/Target/ARM/ARMInstrThumb2.td b/llvm/lib/Target/ARM/ARMInstrThumb2.td index c229c8e4491df..290dd05fc84cb 100644 --- a/llvm/lib/Target/ARM/ARMInstrThumb2.td +++ b/llvm/lib/Target/ARM/ARMInstrThumb2.td @@ -2059,6 +2059,7 @@ multiclass thumb2_ld_mult { + bits<0> p; bits<4> Rn; bits<16> regs; @@ -2074,6 +2075,7 @@ multiclass thumb2_ld_mult { + bits<0> p; bits<4> Rn; bits<16> regs; @@ -2089,6 +2091,7 @@ multiclass thumb2_ld_mult { + bits<0> p; bits<4> Rn; bits<16> regs; @@ -2104,6 +2107,7 @@ multiclass thumb2_ld_mult { + bits<0> p; bits<4> Rn; bits<16> regs; @@ -2128,6 +2132,7 @@ multiclass thumb2_st_mult { + bits<0> p; bits<4> Rn; bits<16> regs; @@ -2146,6 +2151,7 @@ multiclass thumb2_st_mult { + bits<0> p; bits<4> Rn; bits<16> regs; @@ -2164,6 +2170,7 @@ multiclass thumb2_st_mult { + bits<0> p; bits<4> Rn; bits<16> regs; @@ -2182,6 +2189,7 @@ multiclass thumb2_st_mult { + bits<0> p; bits<4> Rn; bits<16> regs; @@ -4030,9 +4038,11 @@ def t2TBH : T2I<(outs), (ins (addrmode_tbh $Rn, $Rm):$addr), IIC_Br, // FIXME: should be able to write a pattern for ARMBrcond, but can't use // a two-value operand where a dag node expects ", "two operands. :( let isBranch = 1, isTerminator = 1 in -def t2Bcc : T2I<(outs), (ins brtarget:$target), IIC_Br, - "b", ".w\t$target", - [/*(ARMbrcond bb:$target, imm:$cc)*/]>, Sched<[WriteBr]> { +def t2Bcc : Thumb2XI<(outs), (ins brtarget:$target, pred:$p), + AddrModeNone, 4, IIC_Br, + "b${p}.w\t$target", "", + [/*(ARMbrcond bb:$target, imm:$cc)*/]>, + Sched<[WriteBr]> { let Inst{31-27} = 0b11110; let Inst{15-14} = 0b10; let Inst{12} = 0; @@ -5481,6 +5491,7 @@ class V8_1MI { + bits<0> p; bits<16> regs; let Inst{31-16} = 0b1110100010011111; @@ -5509,6 +5520,7 @@ def t2BF_LabelPseudo def t2BFi : t2BF<(ins bflabel_u4:$b_label, bflabel_s16:$label, pred:$p), !strconcat("bf", "${p}"), "$b_label, $label"> { + bits<0> p; bits<4> b_label; bits<16> label; @@ -5540,6 +5552,7 @@ def t2BFic : t2BF<(ins bflabel_u4:$b_label, bflabel_s12:$label, def t2BFr : t2BF<(ins bflabel_u4:$b_label, rGPR:$Rn, pred:$p), !strconcat("bfx", "${p}"), "$b_label, $Rn"> { + bits<0> p; bits<4> b_label; bits<4> Rn; @@ -5551,6 +5564,7 @@ def t2BFr : t2BF<(ins bflabel_u4:$b_label, rGPR:$Rn, pred:$p), def t2BFLi : t2BF<(ins bflabel_u4:$b_label, bflabel_s18:$label, pred:$p), !strconcat("bfl", "${p}"), "$b_label, $label"> { + bits<0> p; bits<4> b_label; bits<18> label; @@ -5563,6 +5577,7 @@ def t2BFLi : t2BF<(ins bflabel_u4:$b_label, bflabel_s18:$label, pred:$p), def t2BFLr : t2BF<(ins bflabel_u4:$b_label, rGPR:$Rn, pred:$p), !strconcat("bflx", "${p}"), "$b_label, $Rn"> { + bits<0> p; bits<4> b_label; bits<4> Rn; @@ -5803,6 +5818,7 @@ let Predicates = [IsThumb2, HasV8_1MMainline, HasPACBTI] in { def t2PACG : V8_1MI<(outs rGPR:$Rd), (ins pred:$p, GPRnopc:$Rn, GPRnopc:$Rm), AddrModeNone, NoItinerary, "pacg${p}", "$Rd, $Rn, $Rm", "", []> { + bits<0> p; bits<4> Rd; bits<4> Rn; bits<4> Rm; @@ -5818,6 +5834,7 @@ let hasSideEffects = 1 in { class PACBTIAut : V8_1MI<(outs), iops, AddrModeNone, NoItinerary, asm, "$Ra, $Rn, $Rm", "", []> { + bits<0> p; bits<4> Ra; bits<4> Rn; bits<4> Rm; diff --git a/llvm/lib/Target/ARM/CMakeLists.txt b/llvm/lib/Target/ARM/CMakeLists.txt index fa778cad4af8e..a39629bd8aeb0 100644 --- a/llvm/lib/Target/ARM/CMakeLists.txt +++ b/llvm/lib/Target/ARM/CMakeLists.txt @@ -6,8 +6,7 @@ tablegen(LLVM ARMGenAsmMatcher.inc -gen-asm-matcher) tablegen(LLVM ARMGenAsmWriter.inc -gen-asm-writer) tablegen(LLVM ARMGenCallingConv.inc -gen-callingconv) tablegen(LLVM ARMGenDAGISel.inc -gen-dag-isel) -tablegen(LLVM ARMGenDisassemblerTables.inc -gen-disassembler - -ignore-non-decodable-operands) +tablegen(LLVM ARMGenDisassemblerTables.inc -gen-disassembler) tablegen(LLVM ARMGenFastISel.inc -gen-fast-isel) tablegen(LLVM ARMGenGlobalISel.inc -gen-global-isel) tablegen(LLVM ARMGenInstrInfo.inc -gen-instr-info) diff --git a/llvm/lib/Target/ARM/Disassembler/ARMDisassembler.cpp b/llvm/lib/Target/ARM/Disassembler/ARMDisassembler.cpp index e67db8e3159c0..d5c23f1e837dd 100644 --- a/llvm/lib/Target/ARM/Disassembler/ARMDisassembler.cpp +++ b/llvm/lib/Target/ARM/Disassembler/ARMDisassembler.cpp @@ -618,6 +618,23 @@ static DecodeStatus DecodePredicateOperand(MCInst &Inst, unsigned Val, return S; } +// This overload is called when decoding a `pred` operand that is not encoded +// into instruction. For Thumb instructions, this means we should get the +// condition from the enclosing IT block. +// There are some Thumb instructions equivalent to ARM instructions, but with +// slightly different encoding. (NEONData, NEONLoadStore). +static DecodeStatus DecodePredicateOperand(MCInst &Inst, + const MCDisassembler *Decoder) { + const auto *D = static_cast(Decoder); + unsigned CC = ARMCC::AL; + if (D->getSubtargetInfo().hasFeature(ARM::ModeThumb)) + CC = D->ITBlock.getITCC(); + MCRegister CondReg = CC == ARMCC::AL ? ARM::NoRegister : ARM::CPSR; + Inst.addOperand(MCOperand::createImm(CC)); + Inst.addOperand(MCOperand::createReg(CondReg)); + return MCDisassembler::Success; +} + static DecodeStatus DecodeCCOutOperand(MCInst &Inst, unsigned Val, uint64_t Address, const MCDisassembler *Decoder) { @@ -1050,6 +1067,40 @@ static DecodeStatus DecodeCopMemInstruction(MCInst &Inst, unsigned Insn, if (!Check(S, DecodePredicateOperand(Inst, pred, Address, Decoder))) return MCDisassembler::Fail; break; + case ARM::t2LDC2L_OFFSET: + case ARM::t2LDC2L_OPTION: + case ARM::t2LDC2L_POST: + case ARM::t2LDC2L_PRE: + case ARM::t2LDC2_OFFSET: + case ARM::t2LDC2_OPTION: + case ARM::t2LDC2_POST: + case ARM::t2LDC2_PRE: + case ARM::t2LDCL_OFFSET: + case ARM::t2LDCL_OPTION: + case ARM::t2LDCL_POST: + case ARM::t2LDCL_PRE: + case ARM::t2LDC_OFFSET: + case ARM::t2LDC_OPTION: + case ARM::t2LDC_POST: + case ARM::t2LDC_PRE: + case ARM::t2STC2L_OFFSET: + case ARM::t2STC2L_OPTION: + case ARM::t2STC2L_POST: + case ARM::t2STC2L_PRE: + case ARM::t2STC2_OFFSET: + case ARM::t2STC2_OPTION: + case ARM::t2STC2_POST: + case ARM::t2STC2_PRE: + case ARM::t2STCL_OFFSET: + case ARM::t2STCL_OPTION: + case ARM::t2STCL_POST: + case ARM::t2STCL_PRE: + case ARM::t2STC_OFFSET: + case ARM::t2STC_OPTION: + case ARM::t2STC_POST: + case ARM::t2STC_PRE: + DecodePredicateOperand(Inst, Decoder); + break; default: break; } @@ -1217,6 +1268,8 @@ static DecodeStatus DecodeTSBInstruction(MCInst &Inst, unsigned Insn, // the only available operand), but LLVM expects the instruction to have one // operand, so we need to add the csync when decoding. Inst.addOperand(MCOperand::createImm(ARM_TSB::CSYNC)); + if (Inst.getOpcode() == ARM::t2TSB) + DecodePredicateOperand(Inst, Decoder); return MCDisassembler::Success; } @@ -1650,6 +1703,7 @@ static DecodeStatus DecodeT2CPSInstruction(MCInst &Inst, unsigned Insn, if(imm > 4) return MCDisassembler::Fail; Inst.setOpcode(ARM::t2HINT); Inst.addOperand(MCOperand::createImm(imm)); + DecodePredicateOperand(Inst, Decoder); } return S; @@ -1675,6 +1729,7 @@ DecodeT2HintSpaceInstruction(MCInst &Inst, unsigned Insn, uint64_t Address, Inst.setOpcode(Opcode); if (Opcode == ARM::t2HINT) { Inst.addOperand(MCOperand::createImm(imm)); + DecodePredicateOperand(Inst, Decoder); } return MCDisassembler::Success; @@ -1702,6 +1757,7 @@ static DecodeStatus DecodeT2MOVTWInstruction(MCInst &Inst, unsigned Insn, if (!tryAddingSymbolicOperand(Address, imm, false, 4, Inst, Decoder)) Inst.addOperand(MCOperand::createImm(imm)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -1906,6 +1962,7 @@ static DecodeStatus DecodeT2BInstruction(MCInst &Inst, unsigned Insn, true, 4, Inst, Decoder)) Inst.addOperand(MCOperand::createImm(imm32)); + DecodePredicateOperand(Inst, Decoder); return Status; } @@ -2231,6 +2288,7 @@ static DecodeStatus DecodeVLDInstruction(MCInst &Inst, unsigned Insn, break; } + DecodePredicateOperand(Inst, Decoder); return S; } @@ -2502,6 +2560,7 @@ static DecodeStatus DecodeVSTInstruction(MCInst &Inst, unsigned Insn, break; } + DecodePredicateOperand(Inst, Decoder); return S; } @@ -2605,6 +2664,7 @@ static DecodeStatus DecodeVLD1DupInstruction(MCInst &Inst, unsigned Insn, !Check(S, DecodeGPRRegisterClass(Inst, Rm, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -2654,6 +2714,7 @@ static DecodeStatus DecodeVLD2DupInstruction(MCInst &Inst, unsigned Insn, return MCDisassembler::Fail; } + DecodePredicateOperand(Inst, Decoder); return S; } @@ -2690,6 +2751,7 @@ static DecodeStatus DecodeVLD3DupInstruction(MCInst &Inst, unsigned Insn, return MCDisassembler::Fail; } + DecodePredicateOperand(Inst, Decoder); return S; } @@ -2743,6 +2805,7 @@ static DecodeStatus DecodeVLD4DupInstruction(MCInst &Inst, unsigned Insn, return MCDisassembler::Fail; } + DecodePredicateOperand(Inst, Decoder); return S; } @@ -2789,6 +2852,7 @@ static DecodeStatus DecodeVMOVModImmInstruction(MCInst &Inst, unsigned Insn, break; } + DecodePredicateOperand(Inst, Decoder); return S; } @@ -2861,6 +2925,7 @@ static DecodeStatus DecodeVSHLMaxInstruction(MCInst &Inst, unsigned Insn, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(8 << size)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -2926,6 +2991,7 @@ static DecodeStatus DecodeTBLInstruction(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeDPRRegisterClass(Inst, Rm, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -2951,6 +3017,7 @@ static DecodeStatus DecodeThumbAddSpecialReg(MCInst &Inst, uint16_t Insn, } Inst.addOperand(MCOperand::createImm(imm)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -3113,6 +3180,7 @@ static DecodeStatus DecodeT2LoadLabel(MCInst &Inst, unsigned Insn, } Inst.addOperand(MCOperand::createImm(imm)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -3197,6 +3265,7 @@ static DecodeStatus DecodeT2LoadShift(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeT2AddrModeSOReg(Inst, addrmode, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -3341,6 +3410,7 @@ static DecodeStatus DecodeT2LoadImm8(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeT2AddrModeImm8(Inst, imm, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -3449,6 +3519,7 @@ static DecodeStatus DecodeT2LoadImm12(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeT2AddrModeImm12(Inst, imm, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -3488,6 +3559,7 @@ static DecodeStatus DecodeT2LoadT(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; if (!Check(S, DecodeT2AddrModeImm8(Inst, imm, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -3678,6 +3750,7 @@ static DecodeStatus DecodeT2LdStPre(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeT2AddrModeImm8(Inst, addr, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -3690,6 +3763,7 @@ static DecodeStatus DecodeThumbAddSPImm(MCInst &Inst, uint16_t Insn, Inst.addOperand(MCOperand::createReg(ARM::SP)); Inst.addOperand(MCOperand::createImm(imm)); + DecodePredicateOperand(Inst, Decoder); return MCDisassembler::Success; } @@ -3716,6 +3790,7 @@ static DecodeStatus DecodeThumbAddSPReg(MCInst &Inst, uint16_t Insn, return MCDisassembler::Fail; } + DecodePredicateOperand(Inst, Decoder); return S; } @@ -3840,6 +3915,7 @@ static DecodeStatus DecodeThumbTableBranch(MCInst &Inst, unsigned Insn, return MCDisassembler::Fail; if (!Check(S, DecoderGPRRegisterClass(Inst, Rm, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4305,6 +4381,7 @@ static DecodeStatus DecodeVLD1LN(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(index)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4370,6 +4447,7 @@ static DecodeStatus DecodeVST1LN(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(index)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4437,6 +4515,7 @@ static DecodeStatus DecodeVLD2LN(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(index)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4500,6 +4579,7 @@ static DecodeStatus DecodeVST2LN(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(index)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4570,6 +4650,7 @@ static DecodeStatus DecodeVLD3LN(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(index)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4633,6 +4714,7 @@ static DecodeStatus DecodeVST3LN(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(index)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4714,6 +4796,7 @@ static DecodeStatus DecodeVLD4LN(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(index)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4786,6 +4869,7 @@ static DecodeStatus DecodeVST4LN(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(index)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4904,6 +4988,7 @@ static DecodeStatus DecodeT2LDRDPreInstruction(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeT2AddrModeImm8s4(Inst, addr, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4939,6 +5024,7 @@ static DecodeStatus DecodeT2STRDPreInstruction(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeT2AddrModeImm8s4(Inst, addr, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -4965,6 +5051,7 @@ static DecodeStatus DecodeT2Adr(MCInst &Inst, uint32_t Insn, uint64_t Address, Val = -Val; } Inst.addOperand(MCOperand::createImm(Val)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -5062,6 +5149,7 @@ static DecodeStatus DecodeVCVTD(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(64 - imm)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -5121,6 +5209,7 @@ static DecodeStatus DecodeVCVTQ(MCInst &Inst, unsigned Insn, uint64_t Address, return MCDisassembler::Fail; Inst.addOperand(MCOperand::createImm(64 - imm)); + DecodePredicateOperand(Inst, Decoder); return S; } @@ -5326,8 +5415,10 @@ static DecodeStatus DecodeLOLoop(MCInst &Inst, unsigned Insn, uint64_t Address, const MCDisassembler *Decoder) { DecodeStatus S = MCDisassembler::Success; - if (Inst.getOpcode() == ARM::MVE_LCTP) + if (Inst.getOpcode() == ARM::MVE_LCTP) { + DecodePredicateOperand(Inst, Decoder); return S; + } unsigned Imm = fieldFromInstruction(Insn, 11, 1) | fieldFromInstruction(Insn, 1, 10) << 1; @@ -5372,6 +5463,7 @@ static DecodeStatus DecodeLOLoop(MCInst &Inst, unsigned Insn, uint64_t Address, Check(S, MCDisassembler::SoftFail); // an SBZ bit is wrong: soft fail Inst.setOpcode(ARM::MVE_LCTP); + DecodePredicateOperand(Inst, Decoder); } else { Inst.addOperand(MCOperand::createReg(ARM::LR)); if (!Check(S, DecoderGPRRegisterClass(Inst, @@ -5762,6 +5854,7 @@ static DecodeStatus DecodeMVEVMOVQtoDReg(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeMVEPairVectorIndexOperand<0>(Inst, index, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -5788,6 +5881,7 @@ static DecodeStatus DecodeMVEVMOVDRegtoQ(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeMVEPairVectorIndexOperand<0>(Inst, index, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); return S; } @@ -5833,6 +5927,8 @@ DecodeMVEOverlappingLongShift(MCInst &Inst, unsigned Insn, uint64_t Address, if (!Check(S, DecoderGPRRegisterClass(Inst, Rm, Address, Decoder))) return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); + if (fieldFromInstruction (Insn, 6, 3) != 4) return MCDisassembler::SoftFail; @@ -5868,6 +5964,7 @@ DecodeMVEOverlappingLongShift(MCInst &Inst, unsigned Insn, uint64_t Address, Inst.addOperand(MCOperand::createImm(Saturate)); } + DecodePredicateOperand(Inst, Decoder); return S; } @@ -5971,10 +6068,12 @@ static DecodeStatus DecodeT2AddSubSPImm(MCInst &Inst, unsigned Insn, if (TypeT3) { Inst.setOpcode(sign1 ? ARM::t2SUBspImm12 : ARM::t2ADDspImm12); Inst.addOperand(MCOperand::createImm(Imm12)); // zext imm12 + DecodePredicateOperand(Inst, Decoder); } else { Inst.setOpcode(sign1 ? ARM::t2SUBspImm : ARM::t2ADDspImm); if (!Check(DS, DecodeT2SOImm(Inst, Imm12, Address, Decoder))) // imm12 return MCDisassembler::Fail; + DecodePredicateOperand(Inst, Decoder); if (!Check(DS, DecodeCCOutOperand(Inst, S, Address, Decoder))) // cc_out return MCDisassembler::Fail; } @@ -5994,7 +6093,7 @@ static DecodeStatus DecodeLazyLoadStoreMul(MCInst &Inst, unsigned Insn, if (!Check(S, DecodeGPRRegisterClass(Inst, Rn, Address, Decoder))) return MCDisassembler::Fail; // An optional predicate, '$p' in the assembly. - DecodePredicateOperand(Inst, ARMCC::AL, Address, Decoder); + DecodePredicateOperand(Inst, Decoder); // An immediate that represents a floating point registers list. '$regs' in // the assembly. Inst.addOperand(MCOperand::createImm(0)); // Arbitrary value, has no effect. @@ -6115,28 +6214,17 @@ DecodeStatus ARMDisassembler::getARMInstruction(MCInst &MI, uint64_t &Size, return checkDecodedInstruction(MI, Size, Address, CS, Insn, Result); } - struct DecodeTable { - const uint8_t *P; - bool DecodePred; - }; - - const DecodeTable Tables[] = { - {DecoderTableVFP32, false}, {DecoderTableVFPV832, false}, - {DecoderTableNEONData32, true}, {DecoderTableNEONLoadStore32, true}, - {DecoderTableNEONDup32, false}, {DecoderTablev8NEON32, false}, - {DecoderTablev8Crypto32, false}, + const uint8_t *Tables[] = { + DecoderTableVFP32, DecoderTableVFPV832, + DecoderTableNEONData32, DecoderTableNEONLoadStore32, + DecoderTableNEONDup32, DecoderTablev8NEON32, + DecoderTablev8Crypto32, }; - for (auto Table : Tables) { - Result = decodeInstruction(Table.P, MI, Insn, Address, this, STI); + for (const uint8_t *Table : Tables) { + Result = decodeInstruction(Table, MI, Insn, Address, this, STI); if (Result != MCDisassembler::Fail) { Size = 4; - // Add a fake predicate operand, because we share these instruction - // definitions with Thumb2 where these instructions are predicable. - if (Table.DecodePred && MCII->get(MI.getOpcode()).isPredicable()) { - MI.addOperand(MCOperand::createImm(ARMCC::AL)); - MI.addOperand(MCOperand::createReg(ARM::NoRegister)); - } return Result; } } @@ -6218,34 +6306,10 @@ ARMDisassembler::AddThumbPredicate(MCInst &MI) const { (isVectorPredicable(MI) && ITBlock.instrInITBlock())) S = SoftFail; - // If we're in an IT block, base the predicate on that. Otherwise, - // assume a predicate of AL. - unsigned CC = ARMCC::AL; - if (ITBlock.instrInITBlock()) { - CC = ITBlock.getITCC(); + if (ITBlock.instrInITBlock()) ITBlock.advanceITState(); - } else if (VPTBlock.instrInVPTBlock()) { + else if (VPTBlock.instrInVPTBlock()) VPTBlock.advanceVPTState(); - } - - const MCInstrDesc &MCID = MCII->get(MI.getOpcode()); - - MCInst::iterator CCI = MI.begin(); - for (unsigned i = 0; i < MCID.NumOperands; ++i, ++CCI) { - if (MCID.operands()[i].isPredicate() || CCI == MI.end()) - break; - } - - if (MCID.isPredicable()) { - CCI = MI.insert(CCI, MCOperand::createImm(CC)); - ++CCI; - if (CC == ARMCC::AL) - MI.insert(CCI, MCOperand::createReg(ARM::NoRegister)); - else - MI.insert(CCI, MCOperand::createReg(ARM::CPSR)); - } else if (CC != ARMCC::AL) { - Check(S, SoftFail); - } return S; } diff --git a/llvm/utils/gn/secondary/llvm/lib/Target/ARM/Disassembler/BUILD.gn b/llvm/utils/gn/secondary/llvm/lib/Target/ARM/Disassembler/BUILD.gn index c08304d8a573e..12add5188a9d4 100644 --- a/llvm/utils/gn/secondary/llvm/lib/Target/ARM/Disassembler/BUILD.gn +++ b/llvm/utils/gn/secondary/llvm/lib/Target/ARM/Disassembler/BUILD.gn @@ -2,10 +2,7 @@ import("//llvm/utils/TableGen/tablegen.gni") tablegen("ARMGenDisassemblerTables") { visibility = [ ":Disassembler" ] - args = [ - "-gen-disassembler", - "-ignore-non-decodable-operands", - ] + args = [ "-gen-disassembler" ] td_file = "../ARM.td" } diff --git a/utils/bazel/llvm-project-overlay/llvm/BUILD.bazel b/utils/bazel/llvm-project-overlay/llvm/BUILD.bazel index 8f607c7ce087e..043353790a85e 100644 --- a/utils/bazel/llvm-project-overlay/llvm/BUILD.bazel +++ b/utils/bazel/llvm-project-overlay/llvm/BUILD.bazel @@ -2246,10 +2246,7 @@ llvm_target_lib_list = [lib for lib in [ "lib/Target/ARM/ARMGenGlobalISel.inc": ["-gen-global-isel"], "lib/Target/ARM/ARMGenCallingConv.inc": ["-gen-callingconv"], "lib/Target/ARM/ARMGenSubtargetInfo.inc": ["-gen-subtarget"], - "lib/Target/ARM/ARMGenDisassemblerTables.inc": [ - "-gen-disassembler", - "-ignore-non-decodable-operands", - ], + "lib/Target/ARM/ARMGenDisassemblerTables.inc": ["-gen-disassembler"], }, }, {