aboutsummaryrefslogtreecommitdiff
path: root/lib/Analysis/CFG.cpp
diff options
context:
space:
mode:
authorTed Kremenek <kremenek@apple.com>2012-03-22 05:57:43 +0000
committerTed Kremenek <kremenek@apple.com>2012-03-22 05:57:43 +0000
commit550f2234fc9218914c325041067052342dfce553 (patch)
tree5d84efc1c581f31ab583cff96013c6f53fe632f4 /lib/Analysis/CFG.cpp
parent564f4c5664f552becbd05407611a92754c40e641 (diff)
Fix broken CFG when an initializer is a statement expression that starts with a while loop (PR 12325).
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@153242 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Analysis/CFG.cpp')
-rw-r--r--lib/Analysis/CFG.cpp20
1 files changed, 15 insertions, 5 deletions
diff --git a/lib/Analysis/CFG.cpp b/lib/Analysis/CFG.cpp
index 24ca958827..d0ccef6890 100644
--- a/lib/Analysis/CFG.cpp
+++ b/lib/Analysis/CFG.cpp
@@ -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) {