summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJordan Rose <jordan_rose@apple.com>2012-08-03 23:31:15 +0000
committerJordan Rose <jordan_rose@apple.com>2012-08-03 23:31:15 +0000
commit17a8757a46ede9028024211d293bb473ae3de5ff (patch)
treef14a0647de38d870bda7b3bf4eaccefda15e0d64
parent874886cd66261b7e5039a975769503f53cdd42db (diff)
downloadbcm5719-llvm-17a8757a46ede9028024211d293bb473ae3de5ff.tar.gz
bcm5719-llvm-17a8757a46ede9028024211d293bb473ae3de5ff.zip
[analyzer] Update initializer assertion for delegating constructors.
Like base constructors, delegating constructors require no further processing in the CFGInitializer node. Also, add PrettyStackTraceLoc to the initializer and destructor logic so we can get better stack traces in the future. llvm-svn: 161283
-rw-r--r--clang/lib/StaticAnalyzer/Core/ExprEngine.cpp9
-rw-r--r--clang/lib/StaticAnalyzer/Core/ExprEngineCXX.cpp5
-rw-r--r--clang/test/Analysis/initializer.cpp14
3 files changed, 25 insertions, 3 deletions
diff --git a/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp b/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp
index b46dc49a1bf..b0435fb562e 100644
--- a/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp
+++ b/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp
@@ -360,8 +360,13 @@ void ExprEngine::ProcessInitializer(const CFGInitializer Init,
ProgramStateRef State = Pred->getState();
- // We don't set EntryNode and currentStmt. And we don't clean up state.
const CXXCtorInitializer *BMI = Init.getInitializer();
+
+ PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
+ BMI->getSourceLocation(),
+ "Error evaluating initializer");
+
+ // We don't set EntryNode and currentStmt. And we don't clean up state.
const StackFrameContext *stackFrame =
cast<StackFrameContext>(Pred->getLocationContext());
const CXXConstructorDecl *decl =
@@ -383,7 +388,7 @@ void ExprEngine::ProcessInitializer(const CFGInitializer Init,
State = State->bindLoc(FieldLoc, InitVal);
}
} else {
- assert(BMI->isBaseInitializer());
+ assert(BMI->isBaseInitializer() || BMI->isDelegatingInitializer());
// We already did all the work when visiting the CXXConstructExpr.
}
diff --git a/clang/lib/StaticAnalyzer/Core/ExprEngineCXX.cpp b/clang/lib/StaticAnalyzer/Core/ExprEngineCXX.cpp
index d0a0e32f74d..44a860f689d 100644
--- a/clang/lib/StaticAnalyzer/Core/ExprEngineCXX.cpp
+++ b/clang/lib/StaticAnalyzer/Core/ExprEngineCXX.cpp
@@ -17,6 +17,7 @@
#include "clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h"
#include "clang/AST/DeclCXX.h"
#include "clang/AST/StmtCXX.h"
+#include "clang/Basic/PrettyStackTrace.h"
using namespace clang;
using namespace ento;
@@ -172,6 +173,10 @@ void ExprEngine::VisitCXXDestructor(QualType ObjectType,
CallEventRef<CXXDestructorCall> Call =
CEMgr.getCXXDestructorCall(DtorDecl, S, Dest, State, LCtx);
+ PrettyStackTraceLoc CrashInfo(getContext().getSourceManager(),
+ Call->getSourceRange().getBegin(),
+ "Error evaluating destructor");
+
ExplodedNodeSet DstPreCall;
getCheckerManager().runCheckersForPreCall(DstPreCall, Pred,
*Call, *this);
diff --git a/clang/test/Analysis/initializer.cpp b/clang/test/Analysis/initializer.cpp
index f7a6fd7bea9..d43c8cfd9a0 100644
--- a/clang/test/Analysis/initializer.cpp
+++ b/clang/test/Analysis/initializer.cpp
@@ -1,4 +1,4 @@
-// RUN: %clang_cc1 -analyze -analyzer-checker=core,debug.ExprInspection -analyzer-store region -cfg-add-implicit-dtors -verify %s
+// RUN: %clang_cc1 -analyze -analyzer-checker=core,debug.ExprInspection -analyzer-store region -cfg-add-implicit-dtors -std=c++11 -verify %s
// We don't inline constructors unless we have destructors turned on.
@@ -45,6 +45,18 @@ void testIndirectMember() {
}
+struct DelegatingConstructor {
+ int x;
+ DelegatingConstructor(int y) { x = y; }
+ DelegatingConstructor() : DelegatingConstructor(42) {}
+};
+
+void testDelegatingConstructor() {
+ DelegatingConstructor obj;
+ clang_analyzer_eval(obj.x == 42); // expected-warning{{TRUE}}
+}
+
+
// ------------------------------------
// False negatives
// ------------------------------------
OpenPOWER on IntegriCloud