[llvm-commits] CVS: llvm/lib/Transforms/Utils/LoopSimplify.cpp

Chris Lattner lattner at cs.uiuc.edu
Fri Aug 11 21:51:40 PDT 2006



Changes in directory llvm/lib/Transforms/Utils:

LoopSimplify.cpp updated: 1.70 -> 1.71
---
Log message:

Reimplement the loopsimplify code which deletes edges from unreachable 
blocks that target loop blocks.

Before, the code was run once per loop, and depended on the number of 
predecessors each block in the loop had.  Unfortunately, scanning preds can
be really slow when huge numbers of phis exist or when phis with huge numbers
of inputs exist.

Now, the code is run once per function and scans successors instead of preds,
which is far faster.  In addition, the new code is simpler and is goto free, 
woo.

This change speeds up a nasty testcase Duraid provided me from taking hours to 
taking ~72s with a debug build.  The functionality this implements is already 
tested in the testsuite as Transforms/CodeExtractor/2004-03-13-LoopExtractorCrash.ll.



---
Diffs of the changes:  (+53 -29)

 LoopSimplify.cpp |   82 +++++++++++++++++++++++++++++++++++--------------------
 1 files changed, 53 insertions(+), 29 deletions(-)


Index: llvm/lib/Transforms/Utils/LoopSimplify.cpp
diff -u llvm/lib/Transforms/Utils/LoopSimplify.cpp:1.70 llvm/lib/Transforms/Utils/LoopSimplify.cpp:1.71
--- llvm/lib/Transforms/Utils/LoopSimplify.cpp:1.70	Wed Jun 28 18:17:24 2006
+++ llvm/lib/Transforms/Utils/LoopSimplify.cpp	Fri Aug 11 23:51:20 2006
@@ -105,6 +105,58 @@
   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 @@
   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++;






More information about the llvm-commits mailing list