Revert rL251061 [SimplifyCFG] Extend SimplifyResume to handle phi of trivial landing pad.

llvm-svn: 251149
This commit is contained in:
Chen Li 2015-10-23 21:13:01 +00:00
parent b621d1ae58
commit 7009cd3554
2 changed files with 11 additions and 107 deletions

View File

@ -2905,80 +2905,26 @@ bool SimplifyCFGOpt::SimplifyResume(ResumeInst *RI, IRBuilder<> &Builder) {
// exception then zap the landing pad, turning its invokes into calls.
BasicBlock *BB = RI->getParent();
LandingPadInst *LPInst = dyn_cast<LandingPadInst>(BB->getFirstNonPHI());
// If RI->getValue() is a landing pad, check if the first instruction is
// the same landing pad that caused control to branch here. If RI->getValue
// is a phi of landing pad, check its predecessor blocks to see if any of
// them contains a trivial landing pad.
if (RI->getValue() != LPInst && !isa<PHINode>(RI->getValue()))
if (RI->getValue() != LPInst)
// Not a landing pad, or the resume is not unwinding the exception that
// caused control to branch here.
return false;
// Check that there are no other instructions except for debug intrinsics
// between the landing pad (or phi of landing pad) and resume instruction.
BasicBlock::iterator I = cast<Instruction>(RI->getValue()), E = RI;
// Check that there are no other instructions except for debug intrinsics.
BasicBlock::iterator I = LPInst->getIterator(), E = RI->getIterator();
while (++I != E)
if (!isa<DbgInfoIntrinsic>(I))
return false;
SmallVector<BasicBlock *, 4> TrivialUnwindBlocks;
if (RI->getValue() == LPInst) {
// Landing pad is in current block, which has already been checked.
TrivialUnwindBlocks.push_back(BB);
} else {
// Check incoming blocks to see if any of them are trivial.
auto *PhiLPInst = cast<PHINode>(RI->getValue());
for (unsigned i = 0; i < PhiLPInst->getNumIncomingValues(); i++) {
auto *IncomingBB = PhiLPInst->getIncomingBlock(i);
auto *IncomingValue = PhiLPInst->getIncomingValue(i);
auto *LandingPad =
dyn_cast<LandingPadInst>(IncomingBB->getFirstNonPHI());
// Not the landing pad that caused the control to branch here.
if (IncomingValue != LandingPad)
continue;
bool isTrivial = true;
I = IncomingBB->getFirstNonPHI();
E = IncomingBB->getTerminator();
while (++I != E)
if (!isa<DbgInfoIntrinsic>(I)) {
isTrivial = false;
break;
}
if (isTrivial)
TrivialUnwindBlocks.push_back(IncomingBB);
}
}
// Turn all invokes that unwind here into calls and delete the basic block.
for (auto *TrivialBB : TrivialUnwindBlocks) {
if (isa<PHINode>(RI->getValue())) {
// Blocks that will be deleted should also be removed
// from the phi node.
BB->removePredecessor(TrivialBB, true);
}
for (pred_iterator PI = pred_begin(TrivialBB), PE = pred_end(TrivialBB);
PI != PE;) {
BasicBlock *Pred = *PI++;
removeUnwindEdge(Pred);
}
// The landingpad is now unreachable. Zap it.
if (TrivialBB == BB)
BB = nullptr;
TrivialBB->eraseFromParent();
for (pred_iterator PI = pred_begin(BB), PE = pred_end(BB); PI != PE;) {
BasicBlock *Pred = *PI++;
removeUnwindEdge(Pred);
}
// Delete the resume block if all its predecessors have been deleted, and we
// haven't already deleted it above when deleting the landing pad blocks.
if (BB && pred_begin(BB) == pred_end(BB)) {
BB->eraseFromParent();
}
return TrivialUnwindBlocks.size() != 0;
// The landingpad is now unreachable. Zap it.
BB->eraseFromParent();
return true;
}
bool SimplifyCFGOpt::SimplifyCleanupReturn(CleanupReturnInst *RI) {

View File

@ -17,46 +17,4 @@ Rethrow:
resume { i8*, i32 } %exn
}
declare i64 @dummy1()
declare i64 @dummy2()
; This testcase checks to see if simplifycfg pass can convert two invoke
; instructions to call instructions if they share a common trivial unwind
; block.
define i64 @test2(i1 %cond) personality i32 (...)* @__gxx_personality_v0 {
entry:
; CHECK-LABEL: @test2(
; CHECK: %call1 = call i64 @dummy1()
; CHECK: %call2 = call i64 @dummy2()
; CHECK-NOT: resume { i8*, i32 } %lp
br i1 %cond, label %br1, label %br2
br1:
%call1 = invoke i64 @dummy1()
to label %invoke.cont unwind label %lpad1
br2:
%call2 = invoke i64 @dummy2()
to label %invoke.cont unwind label %lpad2
invoke.cont:
%c = phi i64 [%call1, %br1], [%call2, %br2]
ret i64 %c
lpad1:
%0 = landingpad { i8*, i32 }
cleanup
br label %rethrow
lpad2:
%1 = landingpad { i8*, i32 }
cleanup
br label %rethrow
rethrow:
%lp = phi { i8*, i32 } [%0, %lpad1], [%1, %lpad2]
resume { i8*, i32 } %lp
}
declare i32 @__gxx_personality_v0(...)