1616// ===----------------------------------------------------------------------===//
1717
1818#include " llvm/ADT/DenseSet.h"
19+ #include " llvm/ADT/MapVector.h"
1920#include " llvm/ADT/PointerIntPair.h"
2021#include " llvm/ADT/SetVector.h"
2122#include " llvm/ADT/SmallSet.h"
@@ -566,9 +567,10 @@ void MachineSinking::ProcessDbgInst(MachineInstr &MI) {
566567 MI.getDebugLoc ()->getInlinedAt ());
567568 bool SeenBefore = SeenDbgVars.contains (Var);
568569
569- MachineOperand &MO = MI.getDebugOperand (0 );
570- if (MO.isReg () && MO.getReg ().isVirtual ())
571- SeenDbgUsers[MO.getReg ()].push_back (SeenDbgUser (&MI, SeenBefore));
570+ for (MachineOperand &MO : MI.debug_operands ()) {
571+ if (MO.isReg () && MO.getReg ().isVirtual ())
572+ SeenDbgUsers[MO.getReg ()].push_back (SeenDbgUser (&MI, SeenBefore));
573+ }
572574
573575 // Record the variable for any DBG_VALUE, to avoid re-ordering any of them.
574576 SeenDbgVars.insert (Var);
@@ -1028,14 +1030,14 @@ static bool SinkingPreventsImplicitNullCheck(MachineInstr &MI,
10281030// / leaving an 'undef' DBG_VALUE in the original location. Don't do this if
10291031// / there's any subregister weirdness involved. Returns true if copy
10301032// / propagation occurred.
1031- static bool attemptDebugCopyProp (MachineInstr &SinkInst, MachineInstr &DbgMI) {
1033+ static bool attemptDebugCopyProp (MachineInstr &SinkInst, MachineInstr &DbgMI,
1034+ Register Reg) {
10321035 const MachineRegisterInfo &MRI = SinkInst.getMF ()->getRegInfo ();
10331036 const TargetInstrInfo &TII = *SinkInst.getMF ()->getSubtarget ().getInstrInfo ();
10341037
10351038 // Copy DBG_VALUE operand and set the original to undef. We then check to
10361039 // see whether this is something that can be copy-forwarded. If it isn't,
10371040 // continue around the loop.
1038- MachineOperand &DbgMO = DbgMI.getDebugOperand (0 );
10391041
10401042 const MachineOperand *SrcMO = nullptr , *DstMO = nullptr ;
10411043 auto CopyOperands = TII.isCopyInstr (SinkInst);
@@ -1048,36 +1050,41 @@ static bool attemptDebugCopyProp(MachineInstr &SinkInst, MachineInstr &DbgMI) {
10481050 bool PostRA = MRI.getNumVirtRegs () == 0 ;
10491051
10501052 // Trying to forward between physical and virtual registers is too hard.
1051- if (DbgMO. getReg () .isVirtual () != SrcMO->getReg ().isVirtual ())
1053+ if (Reg .isVirtual () != SrcMO->getReg ().isVirtual ())
10521054 return false ;
10531055
10541056 // Only try virtual register copy-forwarding before regalloc, and physical
10551057 // register copy-forwarding after regalloc.
1056- bool arePhysRegs = !DbgMO. getReg () .isVirtual ();
1058+ bool arePhysRegs = !Reg .isVirtual ();
10571059 if (arePhysRegs != PostRA)
10581060 return false ;
10591061
10601062 // Pre-regalloc, only forward if all subregisters agree (or there are no
10611063 // subregs at all). More analysis might recover some forwardable copies.
1062- if (!PostRA && (DbgMO.getSubReg () != SrcMO->getSubReg () ||
1063- DbgMO.getSubReg () != DstMO->getSubReg ()))
1064- return false ;
1064+ if (!PostRA)
1065+ for (auto &DbgMO : DbgMI.getDebugOperandsForReg (Reg))
1066+ if (DbgMO.getSubReg () != SrcMO->getSubReg () ||
1067+ DbgMO.getSubReg () != DstMO->getSubReg ())
1068+ return false ;
10651069
10661070 // Post-regalloc, we may be sinking a DBG_VALUE of a sub or super-register
10671071 // of this copy. Only forward the copy if the DBG_VALUE operand exactly
10681072 // matches the copy destination.
1069- if (PostRA && DbgMO. getReg () != DstMO->getReg ())
1073+ if (PostRA && Reg != DstMO->getReg ())
10701074 return false ;
10711075
1072- DbgMO.setReg (SrcMO->getReg ());
1073- DbgMO.setSubReg (SrcMO->getSubReg ());
1076+ for (auto &DbgMO : DbgMI.getDebugOperandsForReg (Reg)) {
1077+ DbgMO.setReg (SrcMO->getReg ());
1078+ DbgMO.setSubReg (SrcMO->getSubReg ());
1079+ }
10741080 return true ;
10751081}
10761082
1083+ using MIRegs = std::pair<MachineInstr *, SmallVector<unsigned , 2 >>;
10771084// / Sink an instruction and its associated debug instructions.
10781085static void performSink (MachineInstr &MI, MachineBasicBlock &SuccToSinkTo,
10791086 MachineBasicBlock::iterator InsertPos,
1080- SmallVectorImpl<MachineInstr * > &DbgValuesToSink) {
1087+ SmallVectorImpl<MIRegs > &DbgValuesToSink) {
10811088
10821089 // If we cannot find a location to use (merge with), then we erase the debug
10831090 // location to prevent debug-info driven tools from potentially reporting
@@ -1097,11 +1104,21 @@ static void performSink(MachineInstr &MI, MachineBasicBlock &SuccToSinkTo,
10971104 // DBG_VALUE location as 'undef', indicating that any earlier variable
10981105 // location should be terminated as we've optimised away the value at this
10991106 // point.
1100- for (MachineInstr *DbgMI : DbgValuesToSink) {
1107+ for (auto DbgValueToSink : DbgValuesToSink) {
1108+ MachineInstr *DbgMI = DbgValueToSink.first ;
11011109 MachineInstr *NewDbgMI = DbgMI->getMF ()->CloneMachineInstr (DbgMI);
11021110 SuccToSinkTo.insert (InsertPos, NewDbgMI);
11031111
1104- if (!attemptDebugCopyProp (MI, *DbgMI))
1112+ bool PropagatedAllSunkOps = true ;
1113+ for (unsigned Reg : DbgValueToSink.second ) {
1114+ if (DbgMI->hasDebugOperandForReg (Reg)) {
1115+ if (!attemptDebugCopyProp (MI, *DbgMI, Reg)) {
1116+ PropagatedAllSunkOps = false ;
1117+ break ;
1118+ }
1119+ }
1120+ }
1121+ if (!PropagatedAllSunkOps)
11051122 DbgMI->setDebugValueUndef ();
11061123 }
11071124}
@@ -1384,7 +1401,7 @@ bool MachineSinking::SinkInstruction(MachineInstr &MI, bool &SawStore,
13841401 ++InsertPos;
13851402
13861403 // Collect debug users of any vreg that this inst defines.
1387- SmallVector<MachineInstr * , 4 > DbgUsersToSink;
1404+ SmallVector<MIRegs , 4 > DbgUsersToSink;
13881405 for (auto &MO : MI.operands ()) {
13891406 if (!MO.isReg () || !MO.isDef () || !MO.getReg ().isVirtual ())
13901407 continue ;
@@ -1398,10 +1415,11 @@ bool MachineSinking::SinkInstruction(MachineInstr &MI, bool &SawStore,
13981415 if (User.getInt ()) {
13991416 // This DBG_VALUE would re-order assignments. If we can't copy-propagate
14001417 // it, it can't be recovered. Set it undef.
1401- if (!attemptDebugCopyProp (MI, *DbgMI))
1418+ if (!attemptDebugCopyProp (MI, *DbgMI, MO. getReg () ))
14021419 DbgMI->setDebugValueUndef ();
14031420 } else {
1404- DbgUsersToSink.push_back (DbgMI);
1421+ DbgUsersToSink.push_back (
1422+ {DbgMI, SmallVector<unsigned , 2 >(1 , MO.getReg ())});
14051423 }
14061424 }
14071425 }
@@ -1436,10 +1454,12 @@ void MachineSinking::SalvageUnsunkDebugUsersOfCopy(
14361454 // be sunk. For the rest, if they are not dominated by the block we will sink
14371455 // MI into, propagate the copy source to them.
14381456 SmallVector<MachineInstr *, 4 > DbgDefUsers;
1457+ SmallVector<Register, 4 > DbgUseRegs;
14391458 const MachineRegisterInfo &MRI = MI.getMF ()->getRegInfo ();
14401459 for (auto &MO : MI.operands ()) {
14411460 if (!MO.isReg () || !MO.isDef () || !MO.getReg ().isVirtual ())
14421461 continue ;
1462+ DbgUseRegs.push_back (MO.getReg ());
14431463 for (auto &User : MRI.use_instructions (MO.getReg ())) {
14441464 if (!User.isDebugValue () || DT->dominates (TargetBlock, User.getParent ()))
14451465 continue ;
@@ -1448,17 +1468,21 @@ void MachineSinking::SalvageUnsunkDebugUsersOfCopy(
14481468 if (User.getParent () == MI.getParent ())
14491469 continue ;
14501470
1451- assert (User.getDebugOperand ( 0 ). isReg ( ) &&
1452- " DBG_VALUE user of vreg, but non reg operand?" );
1471+ assert (User.hasDebugOperandForReg (MO. getReg () ) &&
1472+ " DBG_VALUE user of vreg, but has no operand for it ?" );
14531473 DbgDefUsers.push_back (&User);
14541474 }
14551475 }
14561476
14571477 // Point the users of this copy that are no longer dominated, at the source
14581478 // of the copy.
14591479 for (auto *User : DbgDefUsers) {
1460- User->getDebugOperand (0 ).setReg (MI.getOperand (1 ).getReg ());
1461- User->getDebugOperand (0 ).setSubReg (MI.getOperand (1 ).getSubReg ());
1480+ for (auto &Reg : DbgUseRegs) {
1481+ for (auto &DbgOp : User->getDebugOperandsForReg (Reg)) {
1482+ DbgOp.setReg (MI.getOperand (1 ).getReg ());
1483+ DbgOp.setSubReg (MI.getOperand (1 ).getSubReg ());
1484+ }
1485+ }
14621486 }
14631487}
14641488
@@ -1521,8 +1545,10 @@ class PostRAMachineSinking : public MachineFunctionPass {
15211545 LiveRegUnits ModifiedRegUnits, UsedRegUnits;
15221546
15231547 // / Track DBG_VALUEs of (unmodified) register units. Each DBG_VALUE has an
1524- // / entry in this map for each unit it touches.
1525- DenseMap<unsigned , TinyPtrVector<MachineInstr *>> SeenDbgInstrs;
1548+ // / entry in this map for each unit it touches. The DBG_VALUE's entry
1549+ // / consists of a pointer to the instruction itself, and a vector of registers
1550+ // / referred to by the instruction that overlap the key register unit.
1551+ DenseMap<unsigned , SmallVector<MIRegs, 2 >> SeenDbgInstrs;
15261552
15271553 // / Sink Copy instructions unused in the same block close to their uses in
15281554 // / successors.
@@ -1704,18 +1730,27 @@ bool PostRAMachineSinking::tryToSinkCopy(MachineBasicBlock &CurBB,
17041730 // We must sink this DBG_VALUE if its operand is sunk. To avoid searching
17051731 // for DBG_VALUEs later, record them when they're encountered.
17061732 if (MI->isDebugValue ()) {
1707- auto &MO = MI->getDebugOperand (0 );
1708- if (MO.isReg () && Register::isPhysicalRegister (MO.getReg ())) {
1709- // Bail if we can already tell the sink would be rejected, rather
1710- // than needlessly accumulating lots of DBG_VALUEs.
1711- if (hasRegisterDependency (MI, UsedOpsInCopy, DefedRegsInCopy,
1712- ModifiedRegUnits, UsedRegUnits))
1713- continue ;
1714-
1715- // Record debug use of each reg unit.
1716- SmallSet<MCRegister, 4 > Units = getRegUnits (MO.getReg (), TRI);
1717- for (MCRegister Reg : Units)
1718- SeenDbgInstrs[Reg].push_back (MI);
1733+ SmallDenseMap<MCRegister, SmallVector<unsigned , 2 >, 4 > MIUnits;
1734+ bool IsValid = true ;
1735+ for (MachineOperand &MO : MI->debug_operands ()) {
1736+ if (MO.isReg () && Register::isPhysicalRegister (MO.getReg ())) {
1737+ // Bail if we can already tell the sink would be rejected, rather
1738+ // than needlessly accumulating lots of DBG_VALUEs.
1739+ if (hasRegisterDependency (MI, UsedOpsInCopy, DefedRegsInCopy,
1740+ ModifiedRegUnits, UsedRegUnits)) {
1741+ IsValid = false ;
1742+ break ;
1743+ }
1744+
1745+ // Record debug use of each reg unit.
1746+ SmallSet<MCRegister, 4 > RegUnits = getRegUnits (MO.getReg (), TRI);
1747+ for (MCRegister Reg : RegUnits)
1748+ MIUnits[Reg].push_back (MO.getReg ());
1749+ }
1750+ }
1751+ if (IsValid) {
1752+ for (auto RegOps : MIUnits)
1753+ SeenDbgInstrs[RegOps.first ].push_back ({MI, RegOps.second });
17191754 }
17201755 continue ;
17211756 }
@@ -1757,18 +1792,22 @@ bool PostRAMachineSinking::tryToSinkCopy(MachineBasicBlock &CurBB,
17571792 // Collect DBG_VALUEs that must sink with this copy. We've previously
17581793 // recorded which reg units that DBG_VALUEs read, if this instruction
17591794 // writes any of those units then the corresponding DBG_VALUEs must sink.
1760- SetVector <MachineInstr *> DbgValsToSinkSet ;
1795+ MapVector <MachineInstr *, MIRegs::second_type> DbgValsToSinkMap ;
17611796 for (auto &MO : MI->operands ()) {
17621797 if (!MO.isReg () || !MO.isDef ())
17631798 continue ;
17641799
17651800 SmallSet<MCRegister, 4 > Units = getRegUnits (MO.getReg (), TRI);
1766- for (MCRegister Reg : Units)
1767- for (auto *MI : SeenDbgInstrs.lookup (Reg))
1768- DbgValsToSinkSet.insert (MI);
1801+ for (MCRegister Reg : Units) {
1802+ for (auto MIRegs : SeenDbgInstrs.lookup (Reg)) {
1803+ auto &Regs = DbgValsToSinkMap[MIRegs.first ];
1804+ for (unsigned Reg : MIRegs.second )
1805+ Regs.push_back (Reg);
1806+ }
1807+ }
17691808 }
1770- SmallVector<MachineInstr * , 4 > DbgValsToSink (DbgValsToSinkSet .begin (),
1771- DbgValsToSinkSet .end ());
1809+ SmallVector<MIRegs , 4 > DbgValsToSink (DbgValsToSinkMap .begin (),
1810+ DbgValsToSinkMap .end ());
17721811
17731812 // Clear the kill flag if SrcReg is killed between MI and the end of the
17741813 // block.
0 commit comments