]> granicus.if.org Git - clang/commitdiff
Fix broken CFG when an initializer is a statement expression that starts with a while...
authorTed Kremenek <kremenek@apple.com>
Thu, 22 Mar 2012 05:57:43 +0000 (05:57 +0000)
committerTed Kremenek <kremenek@apple.com>
Thu, 22 Mar 2012 05:57:43 +0000 (05:57 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@153242 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Analysis/CFG.cpp
test/SemaCXX/uninitialized.cpp

index 24ca95882710c04c76c87694dfc8935454222393..d0ccef68901acd30c08f2b0718568cbcb553b22d 100644 (file)
@@ -1464,14 +1464,24 @@ CFGBlock *CFGBuilder::VisitDeclSubExpr(DeclStmt *DS) {
 
   autoCreateBlock();
   appendStmt(Block, DS);
+  
+  // Keep track of the last non-null block, as 'Block' can be nulled out
+  // if the initializer expression is something like a 'while' in a
+  // statement-expression.
+  CFGBlock *LastBlock = Block;
 
   if (Init) {
-    if (HasTemporaries)
+    if (HasTemporaries) {
       // For expression with temporaries go directly to subexpression to omit
       // generating destructors for the second time.
-      Visit(cast<ExprWithCleanups>(Init)->getSubExpr());
-    else
-      Visit(Init);
+      ExprWithCleanups *EC = cast<ExprWithCleanups>(Init);
+      if (CFGBlock *newBlock = Visit(EC->getSubExpr()))
+        LastBlock = newBlock;
+    }
+    else {
+      if (CFGBlock *newBlock = Visit(Init))
+        LastBlock = newBlock;
+    }
   }
 
   // If the type of VD is a VLA, then we must process its size expressions.
@@ -1483,7 +1493,7 @@ CFGBlock *CFGBuilder::VisitDeclSubExpr(DeclStmt *DS) {
   if (ScopePos && VD == *ScopePos)
     ++ScopePos;
 
-  return Block;
+  return Block ? Block : LastBlock;
 }
 
 CFGBlock *CFGBuilder::VisitIfStmt(IfStmt *I) {
index 955068291806161d6944dbc258b4378a1f7cc5b5..15c06eb421ee409d1ea3f1603ff8ae0f80ae9d5c 100644 (file)
@@ -147,3 +147,18 @@ namespace rdar10398199 {
     (void)y;
   };
 }
+
+// PR 12325 - this was a false uninitialized value warning due to
+// a broken CFG.
+int pr12325(int params) {
+  int x = ({
+    while (false)
+      ;
+    int _v = params;
+    if (false)
+      ;
+    _v; // no-warning
+  });
+  return x;
+}
+