aboutsummaryrefslogtreecommitdiff
path: root/lib/StaticAnalyzer/Core/RegionStore.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/StaticAnalyzer/Core/RegionStore.cpp')
-rw-r--r--lib/StaticAnalyzer/Core/RegionStore.cpp55
1 files changed, 34 insertions, 21 deletions
diff --git a/lib/StaticAnalyzer/Core/RegionStore.cpp b/lib/StaticAnalyzer/Core/RegionStore.cpp
index 9572f64865..354b55119b 100644
--- a/lib/StaticAnalyzer/Core/RegionStore.cpp
+++ b/lib/StaticAnalyzer/Core/RegionStore.cpp
@@ -1497,6 +1497,26 @@ SVal RegionStoreManager::getBindingForObjCIvar(RegionBindingsConstRef B,
return getBindingForLazySymbol(R);
}
+static Optional<SVal> getConstValue(SValBuilder &SVB, const VarDecl *VD) {
+ ASTContext &Ctx = SVB.getContext();
+ if (!VD->getType().isConstQualified())
+ return Optional<SVal>();
+
+ const Expr *Init = VD->getInit();
+ if (!Init)
+ return Optional<SVal>();
+
+ llvm::APSInt Result;
+ if (Init->EvaluateAsInt(Result, Ctx))
+ return SVB.makeIntVal(Result);
+
+ if (Init->isNullPointerConstant(Ctx, Expr::NPC_ValueDependentIsNotNull))
+ return SVB.makeNull();
+
+ // FIXME: Handle other possible constant expressions.
+ return Optional<SVal>();
+}
+
SVal RegionStoreManager::getBindingForVar(RegionBindingsConstRef B,
const VarRegion *R) {
@@ -1506,37 +1526,30 @@ SVal RegionStoreManager::getBindingForVar(RegionBindingsConstRef B,
// Lazily derive a value for the VarRegion.
const VarDecl *VD = R->getDecl();
- QualType T = VD->getType();
const MemSpaceRegion *MS = R->getMemorySpace();
- if (isa<UnknownSpaceRegion>(MS) ||
- isa<StackArgumentsSpaceRegion>(MS))
+ // Arguments are always symbolic.
+ if (isa<StackArgumentsSpaceRegion>(MS))
+ return svalBuilder.getRegionValueSymbolVal(R);
+
+ // Is 'VD' declared constant? If so, retrieve the constant value.
+ if (Optional<SVal> V = getConstValue(svalBuilder, VD))
+ return *V;
+
+ // This must come after the check for constants because closure-captured
+ // constant variables may appear in UnknownSpaceRegion.
+ if (isa<UnknownSpaceRegion>(MS))
return svalBuilder.getRegionValueSymbolVal(R);
if (isa<GlobalsSpaceRegion>(MS)) {
+ QualType T = VD->getType();
+
// Function-scoped static variables are default-initialized to 0; if they
// have an initializer, it would have been processed by now.
if (isa<StaticGlobalSpaceRegion>(MS))
return svalBuilder.makeZeroVal(T);
- // Other globals
- // Is 'VD' declared constant? If so, retrieve the constant value.
- QualType CT = Ctx.getCanonicalType(T);
- if (CT.isConstQualified()) {
- if (const Expr *Init = VD->getInit()) {
- llvm::APSInt Result;
- if (Init->EvaluateAsInt(Result, Ctx))
- return svalBuilder.makeIntVal(Result);
-
- if (Init->isNullPointerConstant(Ctx, Expr::NPC_ValueDependentIsNotNull))
- return svalBuilder.makeNull();
-
- // FIXME: Handle other possible constant expressions.
- }
- }
-
- if (const Optional<SVal> &V
- = getBindingForDerivedDefaultValue(B, MS, R, CT))
+ if (Optional<SVal> V = getBindingForDerivedDefaultValue(B, MS, R, T))
return V.getValue();
return svalBuilder.getRegionValueSymbolVal(R);