Index: llvm/lib/CodeGen/TwoAddressInstructionPass.cpp =================================================================== --- llvm/lib/CodeGen/TwoAddressInstructionPass.cpp +++ llvm/lib/CodeGen/TwoAddressInstructionPass.cpp @@ -751,6 +751,24 @@ // then one instruction. Sunk = sink3AddrInstruction(NewMI, RegB, mi); + // If the old instruction is debug value tracked, an update is required. + if (auto OldInstrNum = mi->peekDebugInstrNum()) { + // Sanity check. + assert(mi->getNumExplicitDefs() == 1); + assert(NewMI->getNumExplicitDefs() == 1); + + // Find the old and new def location. + auto OldIt = mi->defs().begin(); + auto NewIt = NewMI->defs().begin(); + unsigned OldIdx = mi->getOperandNo(OldIt); + unsigned NewIdx = NewMI->getOperandNo(NewIt); + + // Record that one def has been replaced by the other. + unsigned NewInstrNum = NewMI->getDebugInstrNum(); + MF->makeDebugValueSubstitution(std::make_pair(OldInstrNum, OldIdx), + std::make_pair(NewInstrNum, NewIdx)); + } + MBB->erase(mi); // Nuke the old inst. if (!Sunk) { Index: llvm/lib/Target/X86/X86FixupLEAs.cpp =================================================================== --- llvm/lib/Target/X86/X86FixupLEAs.cpp +++ llvm/lib/Target/X86/X86FixupLEAs.cpp @@ -434,6 +434,7 @@ } else return false; + MBB.getParent()->substituteDebugValuesForInst(*I, *NewMI); MBB.erase(I); I = NewMI; return true; @@ -469,6 +470,7 @@ LLVM_DEBUG(dbgs() << "FixLEA: Candidate to replace:"; MBI->dump();); // now to replace with an equivalent LEA... LLVM_DEBUG(dbgs() << "FixLEA: Replaced by: "; NewMI->dump();); + MBB.getParent()->substituteDebugValuesForInst(*MBI, *NewMI); MBB.erase(MBI); MachineBasicBlock::iterator J = static_cast(NewMI); @@ -521,6 +523,7 @@ LLVM_DEBUG(NewMI->dump();); } if (NewMI) { + MBB.getParent()->substituteDebugValuesForInst(*I, *NewMI); MBB.erase(I); I = NewMI; } @@ -626,6 +629,7 @@ } } + MBB.getParent()->substituteDebugValuesForInst(*I, *NewMI); MBB.erase(I); I = NewMI; return; @@ -651,6 +655,7 @@ .add(Index); LLVM_DEBUG(NewMI->dump();); + MBB.getParent()->substituteDebugValuesForInst(*I, *NewMI); MBB.erase(I); I = NewMI; return; @@ -673,6 +678,7 @@ .add(Base); LLVM_DEBUG(NewMI->dump();); + MBB.getParent()->substituteDebugValuesForInst(*I, *NewMI); MBB.erase(I); I = NewMI; } Index: llvm/test/DebugInfo/MIR/InstrRef/twoaddr-to-threeaddr-sub.mir =================================================================== --- /dev/null +++ llvm/test/DebugInfo/MIR/InstrRef/twoaddr-to-threeaddr-sub.mir @@ -0,0 +1,40 @@ +# RUN: llc -run-pass=twoaddressinstruction -mtriple=x86_64-- -o - %s -experimental-debug-variable-locations | FileCheck %s +# +# Test that a new instruction (LEA) is created when the two-addr add below is +# converted to three address; and that an appropriate substitution is created. +# Maybe at some point we'll normalise DBG_INSTR_REFs on output, but until then, +# lets not. +# +# CHECK: debugValueSubstitutions: +# CHECK-NEXT: - { srcinst: 1, srcop: 0, dstinst: 2, dstop: 0 } +# +# CHECK: LEA64_32r +# CHECK-SAME: debug-instr-number 2 +# +# CHECK: DBG_INSTR_REF 1, 0 +--- +name: test1 +alignment: 16 +tracksRegLiveness: true +registers: + - { id: 0, class: gr32 } + - { id: 1, class: gr32 } + - { id: 2, class: gr32 } +liveins: + - { reg: '$edi', virtual-reg: '%0' } +frameInfo: + maxAlignment: 1 +machineFunctionInfo: {} +body: | + bb.0: + liveins: $edi + + %0:gr32 = COPY killed $edi + %1:gr32 = SHL32ri killed %0, 5, implicit-def dead $eflags + %2:gr32 = ADD32ri8_DB killed %1, 3, implicit-def dead $eflags, debug-instr-number 1 + DBG_INSTR_REF 1, 0 + $eax = COPY killed %2 + RET 0, killed $eax + +... +