[cfe-commits] r70274 - in /cfe/trunk: include/clang/AST/CFG.h lib/AST/CFG.cpp

Ted Kremenek kremenek at apple.com
Mon Apr 27 17:51:56 PDT 2009


Author: kremenek
Date: Mon Apr 27 19:51:56 2009
New Revision: 70274

URL: http://llvm.org/viewvc/llvm-project?rev=70274&view=rev
Log:
CFG:
- Add 'LoopTarget' pointer field to CFGBlock. This records if the block is used
  as the 'loop back' path back to the head of a loop.
- For ForStmt, encode the loop back target as the increment code.

Modified:
    cfe/trunk/include/clang/AST/CFG.h
    cfe/trunk/lib/AST/CFG.cpp

Modified: cfe/trunk/include/clang/AST/CFG.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/CFG.h?rev=70274&r1=70273&r2=70274&view=diff

==============================================================================
--- cfe/trunk/include/clang/AST/CFG.h (original)
+++ cfe/trunk/include/clang/AST/CFG.h Mon Apr 27 19:51:56 2009
@@ -61,12 +61,17 @@
   /// Label - An (optional) label that prefixes the executable
   ///  statements in the block.  When this variable is non-NULL, it is
   ///  either an instance of LabelStmt or SwitchCase.
-  Stmt* Label;
+  Stmt *Label;
   
   /// Terminator - The terminator for a basic block that
   ///  indicates the type of control-flow that occurs between a block
   ///  and its successors.
-  Stmt* Terminator;
+  Stmt *Terminator;
+  
+  /// LoopTarget - Some blocks are used to represent the "loop edge" to
+  ///  the start of a loop from within the loop body.  This Stmt* will be
+  ///  refer to the loop statement for such blocks (and be null otherwise).
+  const Stmt *LoopTarget; 
   
   /// BlockID - A numerical ID assigned to a CFGBlock during construction
   ///   of the CFG.
@@ -80,7 +85,7 @@
   
 public:
   explicit CFGBlock(unsigned blockid) : Label(NULL), Terminator(NULL),
-                                        BlockID(blockid) {}
+                                        LoopTarget(NULL), BlockID(blockid) {}
   ~CFGBlock() {};
 
   // Statement iterators
@@ -149,6 +154,7 @@
   void appendStmt(Stmt* Statement) { Stmts.push_back(Statement); }
   void setTerminator(Stmt* Statement) { Terminator = Statement; }
   void setLabel(Stmt* Statement) { Label = Statement; }
+  void setLoopTarget(const Stmt *loopTarget) { LoopTarget = loopTarget; }
 
   Stmt* getTerminator() { return Terminator; }
   const Stmt* getTerminator() const { return Terminator; }
@@ -159,6 +165,8 @@
     return const_cast<CFGBlock*>(this)->getTerminatorCondition();
   }
   
+  const Stmt *getLoopTarget() const { return LoopTarget; }
+  
   bool hasBinaryBranchTerminator() const;
   
   Stmt* getLabel() { return Label; }

Modified: cfe/trunk/lib/AST/CFG.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/CFG.cpp?rev=70274&r1=70273&r2=70274&view=diff

==============================================================================
--- cfe/trunk/lib/AST/CFG.cpp (original)
+++ cfe/trunk/lib/AST/CFG.cpp Mon Apr 27 19:51:56 2009
@@ -752,21 +752,27 @@
       // Generate increment code in its own basic block.  This is the target
       // of continue statements.
       Succ = Visit(I);
-      
-      // Finish up the increment block if it hasn't been already.
-      if (Block) {
-        assert (Block == Succ);
-        FinishBlock(Block);
-        Block = 0;
-      }
-      
-      ContinueTargetBlock = Succ;    
     }
     else {
-      // No increment code.  Continues should go the the entry condition block.
-      ContinueTargetBlock = EntryConditionBlock;
+      // No increment code.  Create a special, empty, block that is used as
+      // the target block for "looping back" to the start of the loop.
+      assert(Succ == EntryConditionBlock);
+      Succ = createBlock();
     }
     
+    // Finish up the increment (or empty) block if it hasn't been already.
+    if (Block) {
+      assert(Block == Succ);
+      FinishBlock(Block);
+      Block = 0;
+    }
+    
+    ContinueTargetBlock = Succ;
+    
+    // The starting block for the loop increment is the block that should
+    // represent the 'loop target' for looping back to the start of the loop.
+    ContinueTargetBlock->setLoopTarget(F);
+
     // All breaks should go to the code following the loop.
     BreakTargetBlock = LoopSuccessor;    
     





More information about the cfe-commits mailing list