diff options
Diffstat (limited to 'clang/lib')
-rw-r--r-- | clang/lib/StaticAnalyzer/Checkers/OSAtomicChecker.cpp | 7 | ||||
-rw-r--r-- | clang/lib/StaticAnalyzer/Core/Environment.cpp | 12 |
2 files changed, 17 insertions, 2 deletions
diff --git a/clang/lib/StaticAnalyzer/Checkers/OSAtomicChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/OSAtomicChecker.cpp index 6a4f1926f01..7262bc36404 100644 --- a/clang/lib/StaticAnalyzer/Checkers/OSAtomicChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/OSAtomicChecker.cpp @@ -127,7 +127,12 @@ bool OSAtomicChecker::evalOSAtomicCompareAndSwap(CheckerContext &C, ExplodedNode *N = *I; const GRState *stateLoad = N->getState(); - SVal theValueVal_untested = stateLoad->getSVal(theValueExpr); + + // Use direct bindings from the environment since we are forcing a load + // from a location that the Environment would typically not be used + // to bind a value. + SVal theValueVal_untested = stateLoad->getSVal(theValueExpr, true); + SVal oldValueVal_untested = stateLoad->getSVal(oldValueExpr); // FIXME: Issue an error. diff --git a/clang/lib/StaticAnalyzer/Core/Environment.cpp b/clang/lib/StaticAnalyzer/Core/Environment.cpp index 0d43c37587b..a00f9dc10b6 100644 --- a/clang/lib/StaticAnalyzer/Core/Environment.cpp +++ b/clang/lib/StaticAnalyzer/Core/Environment.cpp @@ -27,7 +27,17 @@ SVal Environment::lookupExpr(const Stmt* E) const { return UnknownVal(); } -SVal Environment::getSVal(const Stmt *E, SValBuilder& svalBuilder) const { +SVal Environment::getSVal(const Stmt *E, SValBuilder& svalBuilder, + bool useOnlyDirectBindings) const { + + if (useOnlyDirectBindings) { + // This branch is rarely taken, but can be exercised by + // checkers that explicitly bind values to arbitrary + // expressions. It is crucial that we do not ignore any + // expression here, and do a direct lookup. + return lookupExpr(E); + } + for (;;) { switch (E->getStmtClass()) { case Stmt::AddrLabelExprClass: |