Tail merge at any size when there are two potentials blocks and one

can be made to fall through into the other.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@86909 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Dan Gohman 2009-11-12 00:39:10 +00:00
parent 73b5551058
commit ad6af45dc1
2 changed files with 61 additions and 10 deletions

View File

@ -495,6 +495,15 @@ static bool ProfitableToMerge(MachineBasicBlock *MBB1,
return true;
}
// If one of the blocks can be completely merged and happens to be in
// a position where the other could fall through into it, merge any number
// of instructions, because it can be done without a branch.
// TODO: If the blocks are not adjacent, move one of them so that they are?
if (MBB1->isLayoutSuccessor(MBB2) && I2 == MBB2->begin())
return true;
if (MBB2->isLayoutSuccessor(MBB1) && I1 == MBB1->begin())
return true;
// If both blocks have an unconditional branch temporarily stripped out,
// treat that as an additional common instruction.
if (MBB1 != PredBB && MBB2 != PredBB &&
@ -716,16 +725,31 @@ bool BranchFolder::TryTailMergeBlocks(MachineBasicBlock *SuccBB,
MachineBasicBlock *EntryBB = MergePotentials.begin()->getBlock()->
getParent()->begin();
unsigned commonTailIndex = SameTails.size();
for (unsigned i=0; i<SameTails.size(); i++) {
MachineBasicBlock *MBB = SameTails[i].getBlock();
if (MBB == EntryBB)
continue;
if (MBB == PredBB) {
commonTailIndex = i;
break;
// If there are two blocks, check to see if one can be made to fall through
// into the other.
if (SameTails.size() == 2 &&
SameTails[0].getBlock()->isLayoutSuccessor(SameTails[1].getBlock()) &&
SameTails[1].tailIsWholeBlock())
commonTailIndex = 1;
else if (SameTails.size() == 2 &&
SameTails[1].getBlock()->isLayoutSuccessor(
SameTails[0].getBlock()) &&
SameTails[0].tailIsWholeBlock())
commonTailIndex = 0;
else {
// Otherwise just pick one, favoring the fall-through predecessor if
// there is one.
for (unsigned i = 0, e = SameTails.size(); i != e; ++i) {
MachineBasicBlock *MBB = SameTails[i].getBlock();
if (MBB == EntryBB && SameTails[i].tailIsWholeBlock())
continue;
if (MBB == PredBB) {
commonTailIndex = i;
break;
}
if (SameTails[i].tailIsWholeBlock())
commonTailIndex = i;
}
if (MBB->begin() == SameTails[i].getTailStartPos())
commonTailIndex = i;
}
if (commonTailIndex == SameTails.size() ||
@ -1049,7 +1073,7 @@ bool BranchFolder::TailDuplicate(MachineBasicBlock *TailBB,
continue;
// Don't duplicate into a fall-through predecessor unless its the
// only predecessor.
if (&*next(MachineFunction::iterator(PredBB)) == TailBB &&
if (PredBB->isLayoutSuccessor(TailBB) &&
PrevFallsThrough &&
TailBB->pred_size() != 1)
continue;

View File

@ -266,3 +266,30 @@ bb3: ; preds = %bb2, %bb1, %lvalue_
declare fastcc i32 @lvalue_p(%union.tree_node* nocapture) nounwind readonly
declare fastcc %union.tree_node* @default_conversion(%union.tree_node*) nounwind
; If one tail merging candidate falls through into the other,
; tail merging is likely profitable regardless of how few
; instructions are involved. This function should have only
; one ret instruction.
; CHECK: foo:
; CHECK: call func
; CHECK-NEXT: .LBB5_2:
; CHECK-NEXT: addq $8, %rsp
; CHECK-NEXT: ret
define void @foo(i1* %V) nounwind {
entry:
%t0 = icmp eq i1* %V, null
br i1 %t0, label %return, label %bb
bb:
call void @func()
ret void
return:
ret void
}
declare void @func()