Index: include/llvm/MC/MCInstrDesc.h =================================================================== --- include/llvm/MC/MCInstrDesc.h +++ include/llvm/MC/MCInstrDesc.h @@ -151,7 +151,8 @@ InsertSubreg, Convergent, Add, - Trap + Trap, + VariadicOpsAreDefs, }; } @@ -383,6 +384,11 @@ /// additional values. bool isConvergent() const { return Flags & (1ULL << MCID::Convergent); } + /// Return true if variadic operands of this instruction are definitions. + bool variadicOpsAreDefs() const { + return Flags & (1ULL << MCID::VariadicOpsAreDefs); + } + //===--------------------------------------------------------------------===// // Side Effect Analysis //===--------------------------------------------------------------------===// Index: include/llvm/Target/Target.td =================================================================== --- include/llvm/Target/Target.td +++ include/llvm/Target/Target.td @@ -479,6 +479,7 @@ bit isInsertSubreg = 0; // Is this instruction a kind of insert subreg? // If so, make sure to override // TargetInstrInfo::getInsertSubregLikeInputs. + bit variadicOpsAreDefs = 0; // Are variadic operands definitions? // Does the instruction have side effects that are not captured by any // operands of the instruction or other flags? Index: lib/MC/MCInstrDesc.cpp =================================================================== --- lib/MC/MCInstrDesc.cpp +++ lib/MC/MCInstrDesc.cpp @@ -66,5 +66,10 @@ if (MI.getOperand(i).isReg() && RI.isSubRegisterEq(Reg, MI.getOperand(i).getReg())) return true; + if (variadicOpsAreDefs()) + for (int i = NumOperands - 1, e = MI.getNumOperands(); i != e; ++i) + if (MI.getOperand(i).isReg() && + RI.isSubRegisterEq(Reg, MI.getOperand(i).getReg())) + return true; return hasImplicitDefOfPhysReg(Reg, &RI); } Index: lib/Target/ARM/ARMInstrInfo.td =================================================================== --- lib/Target/ARM/ARMInstrInfo.td +++ lib/Target/ARM/ARMInstrInfo.td @@ -3334,7 +3334,7 @@ let hasSideEffects = 0 in { -let mayLoad = 1, hasExtraDefRegAllocReq = 1 in +let mayLoad = 1, hasExtraDefRegAllocReq = 1, variadicOpsAreDefs = 1 in defm LDM : arm_ldst_mult<"ldm", "", 1, 0, LdStMulFrm, IIC_iLoad_m, IIC_iLoad_mu>, ComplexDeprecationPredicate<"ARMLoad">; Index: lib/Target/ARM/ARMInstrThumb.td =================================================================== --- lib/Target/ARM/ARMInstrThumb.td +++ lib/Target/ARM/ARMInstrThumb.td @@ -781,7 +781,7 @@ // These require base address to be written back or one of the loaded regs. let hasSideEffects = 0 in { -let mayLoad = 1, hasExtraDefRegAllocReq = 1 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<3> Rn; @@ -826,7 +826,8 @@ (tLDMIA tGPR:$Rn, pred:$p, reglist:$regs), 0>, Requires<[IsThumb, IsThumb1Only]>; -let mayLoad = 1, Uses = [SP], Defs = [SP], hasExtraDefRegAllocReq = 1 in +let mayLoad = 1, Uses = [SP], Defs = [SP], hasExtraDefRegAllocReq = 1, + variadicOpsAreDefs = 1 in def tPOP : T1I<(outs), (ins pred:$p, reglist:$regs, variable_ops), IIC_iPop, "pop${p}\t$regs", []>, Index: lib/Target/ARM/ARMInstrThumb2.td =================================================================== --- lib/Target/ARM/ARMInstrThumb2.td +++ lib/Target/ARM/ARMInstrThumb2.td @@ -1775,7 +1775,7 @@ let hasSideEffects = 0 in { -let mayLoad = 1, hasExtraDefRegAllocReq = 1 in +let mayLoad = 1, hasExtraDefRegAllocReq = 1, variadicOpsAreDefs = 1 in defm t2LDM : thumb2_ld_mult<"ldm", IIC_iLoad_m, IIC_iLoad_mu, 1>; multiclass thumb2_st_multgetValueAsBit("isConvergent"); hasNoSchedulingInfo = R->getValueAsBit("hasNoSchedulingInfo"); FastISelShouldIgnore = R->getValueAsBit("FastISelShouldIgnore"); + variadicOpsAreDefs = R->getValueAsBit("variadicOpsAreDefs"); bool Unset; mayLoad = R->getValueAsBitOrUnset("mayLoad", Unset); Index: utils/TableGen/InstrDocsEmitter.cpp =================================================================== --- utils/TableGen/InstrDocsEmitter.cpp +++ utils/TableGen/InstrDocsEmitter.cpp @@ -138,6 +138,7 @@ FLAG(isInsertSubreg) FLAG(isConvergent) FLAG(hasNoSchedulingInfo) + FLAG(variadicOpsAreDefs) if (!FlagStrings.empty()) { OS << "Flags: "; bool IsFirst = true; Index: utils/TableGen/InstrInfoEmitter.cpp =================================================================== --- utils/TableGen/InstrInfoEmitter.cpp +++ utils/TableGen/InstrInfoEmitter.cpp @@ -625,6 +625,7 @@ if (Inst.isExtractSubreg) OS << "|(1ULL<getValueAsBitsInit("TSFlags");