aboutsummaryrefslogtreecommitdiff
path: root/lib/Transforms/Utils/LoopSimplify.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/Transforms/Utils/LoopSimplify.cpp')
-rw-r--r--lib/Transforms/Utils/LoopSimplify.cpp82
1 files changed, 53 insertions, 29 deletions
diff --git a/lib/Transforms/Utils/LoopSimplify.cpp b/lib/Transforms/Utils/LoopSimplify.cpp
index dcad43fc2b..7289f2261a 100644
--- a/lib/Transforms/Utils/LoopSimplify.cpp
+++ b/lib/Transforms/Utils/LoopSimplify.cpp
@@ -105,6 +105,58 @@ bool LoopSimplify::runOnFunction(Function &F) {
LI = &getAnalysis<LoopInfo>();
AA = getAnalysisToUpdate<AliasAnalysis>();
+ // Check to see that no blocks (other than the header) in loops have
+ // predecessors that are not in loops. This is not valid for natural loops,
+ // but can occur if the blocks are unreachable. Since they are unreachable we
+ // can just shamelessly destroy their terminators to make them not branch into
+ // the loop!
+ for (Function::iterator BB = F.begin(), E = F.end(); BB != E; ++BB) {
+ // This case can only occur for unreachable blocks. Blocks that are
+ // unreachable can't be in loops, so filter those blocks out.
+ if (LI->getLoopFor(BB)) continue;
+
+ bool BlockUnreachable = false;
+ TerminatorInst *TI = BB->getTerminator();
+
+ // Check to see if any successors of this block are non-loop-header loops
+ // that are not the header.
+ for (unsigned i = 0, e = TI->getNumSuccessors(); i != e; ++i) {
+ // If this successor is not in a loop, BB is clearly ok.
+ Loop *L = LI->getLoopFor(TI->getSuccessor(i));
+ if (!L) continue;
+
+ // If the succ is the loop header, and if L is a top-level loop, then this
+ // is an entrance into a loop through the header, which is also ok.
+ if (L->getHeader() == TI->getSuccessor(i) && L->getParentLoop() == 0)
+ continue;
+
+ // Otherwise, this is an entrance into a loop from some place invalid.
+ // Either the loop structure is invalid and this is not a natural loop (in
+ // which case the compiler is buggy somewhere else) or BB is unreachable.
+ BlockUnreachable = true;
+ break;
+ }
+
+ // If this block is ok, check the next one.
+ if (!BlockUnreachable) continue;
+
+ // Otherwise, this block is dead. To clean up the CFG and to allow later
+ // loop transformations to ignore this case, we delete the edges into the
+ // loop by replacing the terminator.
+
+ // Remove PHI entries from the successors.
+ for (unsigned i = 0, e = TI->getNumSuccessors(); i != e; ++i)
+ TI->getSuccessor(i)->removePredecessor(BB);
+
+ // Add a new unreachable instruction.
+ new UnreachableInst(TI);
+
+ // Delete the dead terminator.
+ if (AA) AA->deleteValue(&BB->back());
+ BB->getInstList().pop_back();
+ Changed |= true;
+ }
+
for (LoopInfo::iterator I = LI->begin(), E = LI->end(); I != E; ++I)
Changed |= ProcessLoop(*I);
@@ -121,38 +173,10 @@ bool LoopSimplify::ProcessLoop(Loop *L) {
for (Loop::iterator I = L->begin(), E = L->end(); I != E; ++I)
Changed |= ProcessLoop(*I);
- // Check to see that no blocks (other than the header) in the loop have
- // predecessors that are not in the loop. This is not valid for natural
- // loops, but can occur if the blocks are unreachable. Since they are
- // unreachable we can just shamelessly destroy their terminators to make them
- // not branch into the loop!
assert(L->getBlocks()[0] == L->getHeader() &&
"Header isn't first block in loop?");
- for (unsigned i = 1, e = L->getBlocks().size(); i != e; ++i) {
- BasicBlock *LoopBB = L->getBlocks()[i];
- Retry:
- for (pred_iterator PI = pred_begin(LoopBB), E = pred_end(LoopBB);
- PI != E; ++PI)
- if (!L->contains(*PI)) {
- // This predecessor is not in the loop. Kill its terminator!
- BasicBlock *DeadBlock = *PI;
- for (succ_iterator SI = succ_begin(DeadBlock), E = succ_end(DeadBlock);
- SI != E; ++SI)
- (*SI)->removePredecessor(DeadBlock); // Remove PHI node entries
-
- // Delete the dead terminator.
- if (AA) AA->deleteValue(&DeadBlock->back());
- DeadBlock->getInstList().pop_back();
-
- Value *RetVal = 0;
- if (LoopBB->getParent()->getReturnType() != Type::VoidTy)
- RetVal = Constant::getNullValue(LoopBB->getParent()->getReturnType());
- new ReturnInst(RetVal, DeadBlock);
- goto Retry; // We just invalidated the pred_iterator. Retry.
- }
- }
- // Does the loop already have a preheader? If so, don't modify the loop...
+ // Does the loop already have a preheader? If so, don't insert one.
if (L->getLoopPreheader() == 0) {
InsertPreheaderForLoop(L);
NumInserted++;