From d9ff8c83d137586d8c06f98bdf8adbf0d1fa79ca Mon Sep 17 00:00:00 2001 From: Bill Wendling Date: Thu, 21 Mar 2013 23:30:12 +0000 Subject: Always forward 'resume' instructions to the outter landing pad. How did this ever work? Basically, if you have a function that's inlined into the caller, it may not have any 'call' instructions, but any 'resume' instructions it may have should still be forwarded to the outer (caller's) landing pad. This requires that all of the 'landingpad' instructions in the callee have their clauses merged with the caller's outer 'landingpad' instruction (hence the bit of ugly code in the `forwardResume' method). Testcase in a follow commit to the test-suite repository. & PR15555 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@177680 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Transforms/Utils/InlineFunction.cpp | 55 +++++++++++++++++++++++---------- 1 file changed, 39 insertions(+), 16 deletions(-) (limited to 'lib/Transforms/Utils') diff --git a/lib/Transforms/Utils/InlineFunction.cpp b/lib/Transforms/Utils/InlineFunction.cpp index 0d2598a221..3e1022ef8c 100644 --- a/lib/Transforms/Utils/InlineFunction.cpp +++ b/lib/Transforms/Utils/InlineFunction.cpp @@ -82,7 +82,7 @@ namespace { /// a simple branch. When there is more than one predecessor, we need to /// split the landing pad block after the landingpad instruction and jump /// to there. - void forwardResume(ResumeInst *RI); + void forwardResume(ResumeInst *RI, BasicBlock *FirstNewBlock); /// addIncomingPHIValuesFor - Add incoming-PHI values to the unwind /// destination block for the given basic block, using the values for the @@ -140,8 +140,10 @@ BasicBlock *InvokeInliningInfo::getInnerResumeDest() { /// block. When the landing pad block has only one predecessor, this is a simple /// branch. When there is more than one predecessor, we need to split the /// landing pad block after the landingpad instruction and jump to there. -void InvokeInliningInfo::forwardResume(ResumeInst *RI) { +void InvokeInliningInfo::forwardResume(ResumeInst *RI, + BasicBlock *FirstNewBlock) { BasicBlock *Dest = getInnerResumeDest(); + LandingPadInst *OuterLPad = getLandingPadInst(); BasicBlock *Src = RI->getParent(); BranchInst::Create(Dest, Src); @@ -152,6 +154,36 @@ void InvokeInliningInfo::forwardResume(ResumeInst *RI) { InnerEHValuesPHI->addIncoming(RI->getOperand(0), Src); RI->eraseFromParent(); + + // Get all of the inlined landing pad instructions. + SmallPtrSet InlinedLPads; + Function *Caller = FirstNewBlock->getParent(); + for (Function::iterator I = FirstNewBlock, E = Caller->end(); I != E; ++I) + if (InvokeInst *II = dyn_cast(I->getTerminator())) { + LandingPadInst *LPI = II->getLandingPadInst(); + if (!LPI->hasCatchAll()) + InlinedLPads.insert(LPI); + } + + // Merge the catch clauses from the outer landing pad instruction into the + // inlined landing pad instructions. + for (SmallPtrSet::iterator I = InlinedLPads.begin(), + E = InlinedLPads.end(); I != E; ++I) { + LandingPadInst *InlinedLPad = *I; + for (unsigned OuterIdx = 0, OuterNum = OuterLPad->getNumClauses(); + OuterIdx != OuterNum; ++OuterIdx) { + bool hasClause = false; + if (OuterLPad->isFilter(OuterIdx)) continue; + Value *OuterClause = OuterLPad->getClause(OuterIdx); + for (unsigned Idx = 0, N = InlinedLPad->getNumClauses(); Idx != N; ++Idx) + if (OuterClause == InlinedLPad->getClause(Idx)) { + hasClause = true; + break; + } + if (!hasClause) + InlinedLPad->addClause(OuterClause); + } + } } /// HandleCallsInBlockInlinedThroughInvoke - When we inline a basic block into @@ -229,19 +261,9 @@ static void HandleInlinedInvoke(InvokeInst *II, BasicBlock *FirstNewBlock, // The inlined code is currently at the end of the function, scan from the // start of the inlined code to its end, checking for stuff we need to - // rewrite. If the code doesn't have calls or unwinds, we know there is - // nothing to rewrite. - if (!InlinedCodeInfo.ContainsCalls) { - // Now that everything is happy, we have one final detail. The PHI nodes in - // the exception destination block still have entries due to the original - // invoke instruction. Eliminate these entries (which might even delete the - // PHI node) now. - InvokeDest->removePredecessor(II->getParent()); - return; - } - + // rewrite. InvokeInliningInfo Invoke(II); - + for (Function::iterator BB = FirstNewBlock, E = Caller->end(); BB != E; ++BB){ if (InlinedCodeInfo.ContainsCalls) if (HandleCallsInBlockInlinedThroughInvoke(BB, Invoke)) { @@ -250,13 +272,14 @@ static void HandleInlinedInvoke(InvokeInst *II, BasicBlock *FirstNewBlock, continue; } + // Forward any resumes that are remaining here. if (ResumeInst *RI = dyn_cast(BB->getTerminator())) - Invoke.forwardResume(RI); + Invoke.forwardResume(RI, FirstNewBlock); } // Now that everything is happy, we have one final detail. The PHI nodes in // the exception destination block still have entries due to the original - // invoke instruction. Eliminate these entries (which might even delete the + // invoke instruction. Eliminate these entries (which might even delete the // PHI node) now. InvokeDest->removePredecessor(II->getParent()); } -- cgit v1.2.3-18-g5258 From 7541cd36fdd1bd044e22497838faac7b8f7e48cd Mon Sep 17 00:00:00 2001 From: Evgeniy Stepanov Date: Fri, 22 Mar 2013 08:43:04 +0000 Subject: Fix llvm::removeUnreachableBlocks to handle unreachable loops. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@177713 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Transforms/Utils/Local.cpp | 19 +++++++------------ 1 file changed, 7 insertions(+), 12 deletions(-) (limited to 'lib/Transforms/Utils') diff --git a/lib/Transforms/Utils/Local.cpp b/lib/Transforms/Utils/Local.cpp index a54ee08b67..be80d34d96 100644 --- a/lib/Transforms/Utils/Local.cpp +++ b/lib/Transforms/Utils/Local.cpp @@ -985,22 +985,17 @@ bool llvm::removeUnreachableBlocks(Function &F) { if (Reachable.count(I)) continue; - // Remove the block as predecessor of all its reachable successors. - // Unreachable successors don't matter as they'll soon be removed, too. for (succ_iterator SI = succ_begin(I), SE = succ_end(I); SI != SE; ++SI) if (Reachable.count(*SI)) (*SI)->removePredecessor(I); + I->dropAllReferences(); + } - // Zap all instructions in this basic block. - while (!I->empty()) { - Instruction &Inst = I->back(); - if (!Inst.use_empty()) - Inst.replaceAllUsesWith(UndefValue::get(Inst.getType())); - I->getInstList().pop_back(); - } + for (Function::iterator I = llvm::next(F.begin()), E=F.end(); I != E;) + if (!Reachable.count(I)) + I = F.getBasicBlockList().erase(I); + else + ++I; - --I; - llvm::next(I)->eraseFromParent(); - } return true; } -- cgit v1.2.3-18-g5258 From 63da4062e4ef85fd64a6f5681e61e4bba4c4a076 Mon Sep 17 00:00:00 2001 From: Bill Wendling Date: Fri, 22 Mar 2013 18:49:53 +0000 Subject: Don't use the removed API. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@177749 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Transforms/Utils/InlineFunction.cpp | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) (limited to 'lib/Transforms/Utils') diff --git a/lib/Transforms/Utils/InlineFunction.cpp b/lib/Transforms/Utils/InlineFunction.cpp index 3e1022ef8c..62f101f1e2 100644 --- a/lib/Transforms/Utils/InlineFunction.cpp +++ b/lib/Transforms/Utils/InlineFunction.cpp @@ -159,11 +159,8 @@ void InvokeInliningInfo::forwardResume(ResumeInst *RI, SmallPtrSet InlinedLPads; Function *Caller = FirstNewBlock->getParent(); for (Function::iterator I = FirstNewBlock, E = Caller->end(); I != E; ++I) - if (InvokeInst *II = dyn_cast(I->getTerminator())) { - LandingPadInst *LPI = II->getLandingPadInst(); - if (!LPI->hasCatchAll()) - InlinedLPads.insert(LPI); - } + if (InvokeInst *II = dyn_cast(I->getTerminator())) + InlinedLPads.insert(II->getLandingPadInst()); // Merge the catch clauses from the outer landing pad instruction into the // inlined landing pad instructions. -- cgit v1.2.3-18-g5258 From 4c6250247053810d44119d2e34eb4f07ba56d035 Mon Sep 17 00:00:00 2001 From: Bill Wendling Date: Fri, 22 Mar 2013 20:31:05 +0000 Subject: Add all clauses when merging the landing pads. Duplicates will be handled later on. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@177757 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Transforms/Utils/InlineFunction.cpp | 38 ++++++++++++--------------------- 1 file changed, 14 insertions(+), 24 deletions(-) (limited to 'lib/Transforms/Utils') diff --git a/lib/Transforms/Utils/InlineFunction.cpp b/lib/Transforms/Utils/InlineFunction.cpp index 62f101f1e2..e9828d60cd 100644 --- a/lib/Transforms/Utils/InlineFunction.cpp +++ b/lib/Transforms/Utils/InlineFunction.cpp @@ -82,7 +82,8 @@ namespace { /// a simple branch. When there is more than one predecessor, we need to /// split the landing pad block after the landingpad instruction and jump /// to there. - void forwardResume(ResumeInst *RI, BasicBlock *FirstNewBlock); + void forwardResume(ResumeInst *RI, + SmallPtrSet &InlinedLPads); /// addIncomingPHIValuesFor - Add incoming-PHI values to the unwind /// destination block for the given basic block, using the values for the @@ -141,7 +142,7 @@ BasicBlock *InvokeInliningInfo::getInnerResumeDest() { /// branch. When there is more than one predecessor, we need to split the /// landing pad block after the landingpad instruction and jump to there. void InvokeInliningInfo::forwardResume(ResumeInst *RI, - BasicBlock *FirstNewBlock) { + SmallPtrSet &InlinedLPads) { BasicBlock *Dest = getInnerResumeDest(); LandingPadInst *OuterLPad = getLandingPadInst(); BasicBlock *Src = RI->getParent(); @@ -155,31 +156,14 @@ void InvokeInliningInfo::forwardResume(ResumeInst *RI, InnerEHValuesPHI->addIncoming(RI->getOperand(0), Src); RI->eraseFromParent(); - // Get all of the inlined landing pad instructions. - SmallPtrSet InlinedLPads; - Function *Caller = FirstNewBlock->getParent(); - for (Function::iterator I = FirstNewBlock, E = Caller->end(); I != E; ++I) - if (InvokeInst *II = dyn_cast(I->getTerminator())) - InlinedLPads.insert(II->getLandingPadInst()); - - // Merge the catch clauses from the outer landing pad instruction into the - // inlined landing pad instructions. + // Append the clauses from the outer landing pad instruction into the inlined + // landing pad instructions. for (SmallPtrSet::iterator I = InlinedLPads.begin(), E = InlinedLPads.end(); I != E; ++I) { LandingPadInst *InlinedLPad = *I; for (unsigned OuterIdx = 0, OuterNum = OuterLPad->getNumClauses(); - OuterIdx != OuterNum; ++OuterIdx) { - bool hasClause = false; - if (OuterLPad->isFilter(OuterIdx)) continue; - Value *OuterClause = OuterLPad->getClause(OuterIdx); - for (unsigned Idx = 0, N = InlinedLPad->getNumClauses(); Idx != N; ++Idx) - if (OuterClause == InlinedLPad->getClause(Idx)) { - hasClause = true; - break; - } - if (!hasClause) - InlinedLPad->addClause(OuterClause); - } + OuterIdx != OuterNum; ++OuterIdx) + InlinedLPad->addClause(OuterLPad->getClause(OuterIdx)); } } @@ -261,6 +245,12 @@ static void HandleInlinedInvoke(InvokeInst *II, BasicBlock *FirstNewBlock, // rewrite. InvokeInliningInfo Invoke(II); + // Get all of the inlined landing pad instructions. + SmallPtrSet InlinedLPads; + for (Function::iterator I = FirstNewBlock, E = Caller->end(); I != E; ++I) + if (InvokeInst *II = dyn_cast(I->getTerminator())) + InlinedLPads.insert(II->getLandingPadInst()); + for (Function::iterator BB = FirstNewBlock, E = Caller->end(); BB != E; ++BB){ if (InlinedCodeInfo.ContainsCalls) if (HandleCallsInBlockInlinedThroughInvoke(BB, Invoke)) { @@ -271,7 +261,7 @@ static void HandleInlinedInvoke(InvokeInst *II, BasicBlock *FirstNewBlock, // Forward any resumes that are remaining here. if (ResumeInst *RI = dyn_cast(BB->getTerminator())) - Invoke.forwardResume(RI, FirstNewBlock); + Invoke.forwardResume(RI, InlinedLPads); } // Now that everything is happy, we have one final detail. The PHI nodes in -- cgit v1.2.3-18-g5258