make tail merging more aggressive. If two blocks share a common tail, but the

tail is not an entire block for either of them, pick one, split it, then
merge the common part.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@31336 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Chris Lattner 2006-11-01 01:16:12 +00:00
parent d8ccff0c3e
commit 1d08d83230

View File

@ -44,6 +44,8 @@ namespace {
bool TailMergeBlocks(MachineFunction &MF);
void ReplaceTailWithBranchTo(MachineBasicBlock::iterator OldInst,
MachineBasicBlock *NewDest);
MachineBasicBlock *SplitMBBAt(MachineBasicBlock &CurMBB,
MachineBasicBlock::iterator BBI1);
// Branch optzn.
bool OptimizeBranches(MachineFunction &MF);
@ -256,6 +258,31 @@ void BranchFolder::ReplaceTailWithBranchTo(MachineBasicBlock::iterator OldInst,
++NumTailMerge;
}
/// SplitMBBAt - Given a machine basic block and an iterator into it, split the
/// MBB so that the part before the iterator falls into the part starting at the
/// iterator. This returns the new MBB.
MachineBasicBlock *BranchFolder::SplitMBBAt(MachineBasicBlock &CurMBB,
MachineBasicBlock::iterator BBI1) {
// Create the fall-through block.
MachineFunction::iterator MBBI = &CurMBB;
MachineBasicBlock *NewMBB = new MachineBasicBlock(CurMBB.getBasicBlock());
CurMBB.getParent()->getBasicBlockList().insert(++MBBI, NewMBB);
// Move all the successors of this block to the specified block.
while (!CurMBB.succ_empty()) {
MachineBasicBlock *S = *(CurMBB.succ_end()-1);
NewMBB->addSuccessor(S);
CurMBB.removeSuccessor(S);
}
// Add an edge from CurMBB to NewMBB for the fall-through.
CurMBB.addSuccessor(NewMBB);
// Splice the code over.
NewMBB->splice(NewMBB->end(), &CurMBB, BBI1, CurMBB.end());
return NewMBB;
}
bool BranchFolder::TailMergeBlocks(MachineFunction &MF) {
MadeChange = false;
@ -319,26 +346,36 @@ bool BranchFolder::TailMergeBlocks(MachineFunction &MF) {
std::swap(MergePotentials[FoundMatch], *(MergePotentials.end()-2));
}
// If either block is the entire common tail, make the longer one branch to
// the shorter one.
MachineBasicBlock *MBB2 = (MergePotentials.end()-2)->second;
if (CurMBB->begin() == BBI1) {
// Hack the end off MBB2, making it jump to CurMBB instead.
ReplaceTailWithBranchTo(BBI2, CurMBB);
// This modifies MBB2, so remove it from the worklist.
MergePotentials.erase(MergePotentials.end()-2);
MadeChange = true;
continue;
} else if (MBB2->begin() == BBI2) {
// If neither block is the entire common tail, split the tail of one block
// to make it redundant with the other tail.
if (CurMBB->begin() != BBI1 && MBB2->begin() != BBI2) {
if (0) { // Enable this to disable partial tail merges.
MergePotentials.pop_back();
continue;
}
// TODO: if we had some notion of which block was hotter, we could split
// the hot block, so it is the fall-through. For now, just split the
// second block.
MBB2 = SplitMBBAt(*MBB2, BBI2);
BBI2 = MBB2->begin();
(MergePotentials.end()-2)->second = MBB2;
}
if (MBB2->begin() == BBI2) {
// Hack the end off CurMBB, making it jump to MBBI@ instead.
ReplaceTailWithBranchTo(BBI1, MBB2);
// This modifies CurMBB, so remove it from the worklist.
MergePotentials.pop_back();
MadeChange = true;
continue;
} else {
assert(CurMBB->begin() == BBI1 && "Didn't split block correctly?");
// Hack the end off MBB2, making it jump to CurMBB instead.
ReplaceTailWithBranchTo(BBI2, CurMBB);
// This modifies MBB2, so remove it from the worklist.
MergePotentials.erase(MergePotentials.end()-2);
}
MergePotentials.pop_back();
MadeChange = true;
}
return MadeChange;