Be more clever about calculating live variables through new basic blocks.

When splitting a critical edge, the registers live through the edge are:

- Used in a PHI instruction, or
- Live out from the predecessor, and
- Live in to the successor.

This allows the coalescer to eliminate even more phi joins.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@89530 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Jakob Stoklund Olesen 2009-11-21 02:05:21 +00:00
parent 983c7fe847
commit 323d8c3ed7
4 changed files with 49 additions and 48 deletions

View File

@ -107,6 +107,13 @@ public:
/// findKill - Find a kill instruction in MBB. Return NULL if none is found.
MachineInstr *findKill(const MachineBasicBlock *MBB) const;
/// isLiveIn - Is Reg live in to MBB? This means that Reg is live through
/// MBB, or it is killed in MBB. If Reg is only used by PHI instructions in
/// MBB, it is not considered live in.
bool isLiveIn(const MachineBasicBlock &MBB,
unsigned Reg,
MachineRegisterInfo &MRI);
void dump() const;
};
@ -267,11 +274,17 @@ public:
void HandleVirtRegUse(unsigned reg, MachineBasicBlock *MBB,
MachineInstr *MI);
/// addNewBlock - Add a new basic block BB as an empty succcessor to
/// DomBB. All variables that are live out of DomBB will be marked as passing
/// live through BB. This method assumes that the machine code is still in SSA
/// form.
void addNewBlock(MachineBasicBlock *BB, MachineBasicBlock *DomBB);
bool isLiveIn(unsigned Reg, const MachineBasicBlock &MBB) {
return getVarInfo(Reg).isLiveIn(MBB, Reg, *MRI);
}
/// addNewBlock - Add a new basic block BB between DomBB and SuccBB. All
/// variables that are live out of DomBB and live into SuccBB will be marked
/// as passing live through BB. This method assumes that the machine code is
/// still in SSA form.
void addNewBlock(MachineBasicBlock *BB,
MachineBasicBlock *DomBB,
MachineBasicBlock *SuccBB);
};
} // End llvm namespace

View File

@ -656,35 +656,45 @@ void LiveVariables::analyzePHINodes(const MachineFunction& Fn) {
.push_back(BBI->getOperand(i).getReg());
}
bool LiveVariables::VarInfo::isLiveIn(const MachineBasicBlock &MBB,
unsigned Reg,
MachineRegisterInfo &MRI) {
unsigned Num = MBB.getNumber();
// Reg is live-through.
if (AliveBlocks.test(Num))
return true;
// Registers defined in MBB cannot be live in.
const MachineInstr *Def = MRI.getVRegDef(Reg);
if (Def && Def->getParent() == &MBB)
return false;
// Reg was not defined in MBB, was it killed here?
return findKill(&MBB);
}
/// addNewBlock - Add a new basic block BB as an empty succcessor to DomBB. All
/// variables that are live out of DomBB will be marked as passing live through
/// BB.
void LiveVariables::addNewBlock(MachineBasicBlock *BB,
MachineBasicBlock *DomBB) {
MachineBasicBlock *DomBB,
MachineBasicBlock *SuccBB) {
const unsigned NumNew = BB->getNumber();
const unsigned NumDom = DomBB->getNumber();
// All registers used by PHI nodes in SuccBB must be live through BB.
for (MachineBasicBlock::const_iterator BBI = SuccBB->begin(),
BBE = SuccBB->end();
BBI != BBE && BBI->getOpcode() == TargetInstrInfo::PHI; ++BBI)
for (unsigned i = 1, e = BBI->getNumOperands(); i != e; i += 2)
if (BBI->getOperand(i+1).getMBB() == BB)
getVarInfo(BBI->getOperand(i).getReg()).AliveBlocks.set(NumNew);
// Update info for all live variables
for (unsigned Reg = TargetRegisterInfo::FirstVirtualRegister,
E = MRI->getLastVirtReg()+1; Reg != E; ++Reg) {
VarInfo &VI = getVarInfo(Reg);
// Anything live through DomBB is also live through BB.
if (VI.AliveBlocks.test(NumDom)) {
if (!VI.AliveBlocks.test(NumNew) && VI.isLiveIn(*SuccBB, Reg, *MRI))
VI.AliveBlocks.set(NumNew);
continue;
}
// Variables not defined in DomBB cannot be live out.
const MachineInstr *Def = MRI->getVRegDef(Reg);
if (!Def || Def->getParent() != DomBB)
continue;
// Killed by DomBB?
if (VI.findKill(DomBB))
continue;
// This register is defined in DomBB and live out
VI.AliveBlocks.set(NumNew);
}
}

View File

@ -353,7 +353,7 @@ bool llvm::PHIElimination::SplitPHIEdges(MachineFunction &MF,
// We break edges when registers are live out from the predecessor block
// (not considering PHI nodes). If the register is live in to this block
// anyway, we would gain nothing from splitting.
if (isLiveOut(Reg, *PreMBB, LV) && !isLiveIn(Reg, MBB, LV))
if (!LV.isLiveIn(Reg, MBB) && isLiveOut(Reg, *PreMBB, LV))
SplitCriticalEdge(PreMBB, &MBB);
}
}
@ -406,22 +406,6 @@ bool llvm::PHIElimination::isLiveOut(unsigned Reg, const MachineBasicBlock &MBB,
return false;
}
bool llvm::PHIElimination::isLiveIn(unsigned Reg, const MachineBasicBlock &MBB,
LiveVariables &LV) {
LiveVariables::VarInfo &VI = LV.getVarInfo(Reg);
if (VI.AliveBlocks.test(MBB.getNumber()))
return true;
// defined in MBB?
const MachineInstr *Def = MRI->getVRegDef(Reg);
if (Def && Def->getParent() == &MBB)
return false;
// killed in MBB?
return VI.findKill(&MBB);
}
MachineBasicBlock *PHIElimination::SplitCriticalEdge(MachineBasicBlock *A,
MachineBasicBlock *B) {
assert(A && B && "Missing MBB end point");
@ -463,7 +447,7 @@ MachineBasicBlock *PHIElimination::SplitCriticalEdge(MachineBasicBlock *A,
i->getOperand(ni+1).setMBB(NMBB);
if (LiveVariables *LV=getAnalysisIfAvailable<LiveVariables>())
LV->addNewBlock(NMBB, A);
LV->addNewBlock(NMBB, A, B);
if (MachineDominatorTree *MDT=getAnalysisIfAvailable<MachineDominatorTree>())
MDT->addNewBlock(NMBB, A);

View File

@ -99,12 +99,6 @@ namespace llvm {
bool isLiveOut(unsigned Reg, const MachineBasicBlock &MBB,
LiveVariables &LV);
/// isLiveIn - Determine if Reg is live in to MBB, not considering PHI
/// source registers. This means that Reg is either killed by MBB or passes
/// through it.
bool isLiveIn(unsigned Reg, const MachineBasicBlock &MBB,
LiveVariables &LV);
/// SplitCriticalEdge - Split a critical edge from A to B by
/// inserting a new MBB. Update branches in A and PHI instructions
/// in B. Return the new block.