This is safe to do because the physreg has been marked UsedInInstr and the kill flag will be set on the last operand using the virtreg if there are more then one.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@103933
91177308-0d34-0410-b5e6-
96231b3b80d8
bool New;
tie(LRI, New) = LiveVirtRegs.insert(std::make_pair(VirtReg, LiveReg()));
LiveReg &LR = LRI->second;
bool New;
tie(LRI, New) = LiveVirtRegs.insert(std::make_pair(VirtReg, LiveReg()));
LiveReg &LR = LRI->second;
+ MachineOperand &MO = MI->getOperand(OpNum);
if (New) {
allocVirtReg(MI, *LRI, Hint);
const TargetRegisterClass *RC = MRI->getRegClass(VirtReg);
if (New) {
allocVirtReg(MI, *LRI, Hint);
const TargetRegisterClass *RC = MRI->getRegClass(VirtReg);
TII->loadRegFromStackSlot(*MBB, MI, LR.PhysReg, FrameIndex, RC, TRI);
++NumLoads;
} else if (LR.Dirty) {
TII->loadRegFromStackSlot(*MBB, MI, LR.PhysReg, FrameIndex, RC, TRI);
++NumLoads;
} else if (LR.Dirty) {
- MachineOperand &MO = MI->getOperand(OpNum);
if (isLastUseOfLocalReg(MO)) {
DEBUG(dbgs() << "Killing last use: " << MO << "\n");
MO.setIsKill();
if (isLastUseOfLocalReg(MO)) {
DEBUG(dbgs() << "Killing last use: " << MO << "\n");
MO.setIsKill();
DEBUG(dbgs() << "Clearing dubious kill: " << MO << "\n");
MO.setIsKill(false);
}
DEBUG(dbgs() << "Clearing dubious kill: " << MO << "\n");
MO.setIsKill(false);
}
+ } else if (MO.isKill()) {
+ // We must remove kill flags from uses of reloaded registers because the
+ // register would be killed immediately, and there might be a second use:
+ // %foo = OR %x<kill>, %x
+ // This would cause a second reload of %x into a different register.
+ DEBUG(dbgs() << "Clearing clean kill: " << MO << "\n");
+ MO.setIsKill(false);
}
assert(LR.PhysReg && "Register not assigned");
LR.LastUse = MI;
}
assert(LR.PhysReg && "Register not assigned");
LR.LastUse = MI;
E = MBB->livein_end(); I != E; ++I)
definePhysReg(MII, *I, regReserved);
E = MBB->livein_end(); I != E; ++I)
definePhysReg(MII, *I, regReserved);
- SmallVector<unsigned, 8> VirtKills, PhysDefs;
+ SmallVector<unsigned, 8> PhysECs;
SmallVector<MachineInstr*, 32> Coalesced;
// Otherwise, sequentially allocate each instruction in the MBB.
SmallVector<MachineInstr*, 32> Coalesced;
// Otherwise, sequentially allocate each instruction in the MBB.
// Track registers used by instruction.
UsedInInstr.reset();
// Track registers used by instruction.
UsedInInstr.reset();
// First scan.
// Mark physreg uses and early clobbers as used.
// First scan.
// Mark physreg uses and early clobbers as used.
usePhysReg(MO);
} else if (MO.isEarlyClobber()) {
definePhysReg(MI, Reg, MO.isDead() ? regFree : regReserved);
usePhysReg(MO);
} else if (MO.isEarlyClobber()) {
definePhysReg(MI, Reg, MO.isDead() ? regFree : regReserved);
- PhysDefs.push_back(Reg);
+ PhysECs.push_back(Reg);
unsigned PhysReg = reloadVirtReg(MI, i, Reg, CopyDst);
CopySrc = (CopySrc == Reg || CopySrc == PhysReg) ? PhysReg : 0;
if (setPhysReg(MO, PhysReg))
unsigned PhysReg = reloadVirtReg(MI, i, Reg, CopyDst);
CopySrc = (CopySrc == Reg || CopySrc == PhysReg) ? PhysReg : 0;
if (setPhysReg(MO, PhysReg))
- VirtKills.push_back(Reg);
} else if (MO.isEarlyClobber()) {
unsigned PhysReg = defineVirtReg(MI, i, Reg, 0);
setPhysReg(MO, PhysReg);
} else if (MO.isEarlyClobber()) {
unsigned PhysReg = defineVirtReg(MI, i, Reg, 0);
setPhysReg(MO, PhysReg);
- PhysDefs.push_back(PhysReg);
+ PhysECs.push_back(PhysReg);
- // Process virtreg kills
- for (unsigned i = 0, e = VirtKills.size(); i != e; ++i)
- killVirtReg(VirtKills[i]);
- VirtKills.clear();
-
MRI->addPhysRegsUsed(UsedInInstr);
// Track registers defined by instruction - early clobbers at this point.
UsedInInstr.reset();
MRI->addPhysRegsUsed(UsedInInstr);
// Track registers defined by instruction - early clobbers at this point.
UsedInInstr.reset();
- for (unsigned i = 0, e = PhysDefs.size(); i != e; ++i) {
- unsigned PhysReg = PhysDefs[i];
+ for (unsigned i = 0, e = PhysECs.size(); i != e; ++i) {
+ unsigned PhysReg = PhysECs[i];
UsedInInstr.set(PhysReg);
for (const unsigned *AS = TRI->getAliasSet(PhysReg);
unsigned Alias = *AS; ++AS)
UsedInInstr.set(PhysReg);
for (const unsigned *AS = TRI->getAliasSet(PhysReg);
unsigned Alias = *AS; ++AS)
}
unsigned PhysReg = defineVirtReg(MI, i, Reg, CopySrc);
if (setPhysReg(MO, PhysReg)) {
}
unsigned PhysReg = defineVirtReg(MI, i, Reg, CopySrc);
if (setPhysReg(MO, PhysReg)) {
- VirtKills.push_back(Reg);
CopyDst = 0; // cancel coalescing;
} else
CopyDst = (CopyDst == Reg || CopyDst == PhysReg) ? PhysReg : 0;
}
CopyDst = 0; // cancel coalescing;
} else
CopyDst = (CopyDst == Reg || CopyDst == PhysReg) ? PhysReg : 0;
}
- // Process virtreg deads.
- for (unsigned i = 0, e = VirtKills.size(); i != e; ++i)
- killVirtReg(VirtKills[i]);
- VirtKills.clear();
-
MRI->addPhysRegsUsed(UsedInInstr);
if (CopyDst && CopyDst == CopySrc && CopyDstSub == CopySrcSub) {
MRI->addPhysRegsUsed(UsedInInstr);
if (CopyDst && CopyDst == CopySrc && CopyDstSub == CopySrcSub) {