diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/Analysis/GRExprEngine.cpp | 6 | ||||
-rw-r--r-- | lib/Analysis/RegionStore.cpp | 32 | ||||
-rw-r--r-- | lib/Analysis/Store.cpp | 9 |
3 files changed, 43 insertions, 4 deletions
diff --git a/lib/Analysis/GRExprEngine.cpp b/lib/Analysis/GRExprEngine.cpp index 6bc70d5925..31ee3fc323 100644 --- a/lib/Analysis/GRExprEngine.cpp +++ b/lib/Analysis/GRExprEngine.cpp @@ -1119,9 +1119,9 @@ void GRExprEngine::EvalLoad(NodeSet& Dst, Expr* Ex, NodeTy* Pred, // invalidate(y); // 'x' now binds to a symbolic region // int z = *y; // - if (isa<Loc>(V) && !Loc::IsLocType(Ex->getType())) { - V = EvalCast(V, Ex->getType()); - } + //if (isa<Loc>(V) && !Loc::IsLocType(Ex->getType())) { + // V = EvalCast(V, Ex->getType()); + //} MakeNode(Dst, Ex, Pred, state->bindExpr(Ex, V), K, tag); } diff --git a/lib/Analysis/RegionStore.cpp b/lib/Analysis/RegionStore.cpp index c59d935c3d..577ace306b 100644 --- a/lib/Analysis/RegionStore.cpp +++ b/lib/Analysis/RegionStore.cpp @@ -327,6 +327,10 @@ public: const GRState *setCastType(const GRState *state, const MemRegion* R, QualType T); + const QualType *getCastType(const GRState *state, const MemRegion *R) { + return state->get<RegionCasts>(R); + } + static inline RegionBindingsTy GetRegionBindings(Store store) { return RegionBindingsTy(static_cast<const RegionBindingsTy::TreeTy*>(store)); } @@ -349,6 +353,27 @@ public: } // end anonymous namespace +static bool isGenericPtr(ASTContext &Ctx, QualType Ty) { + if (Ty->isObjCIdType() || Ty->isObjCQualifiedIdType()) + return true; + + while (true) { + Ty = Ctx.getCanonicalType(Ty); + + if (Ty->isVoidType()) + return true; + + if (const PointerType *PT = Ty->getAsPointerType()) { + Ty = PT->getPointeeType(); + continue; + } + + break; + } + + return false; +} + //===----------------------------------------------------------------------===// // RegionStore creation. //===----------------------------------------------------------------------===// @@ -1251,6 +1276,13 @@ const GRState *RegionStoreManager::RemoveRegionView(const GRState *state, const GRState *RegionStoreManager::setCastType(const GRState *state, const MemRegion* R, QualType T) { + // We do not record generic cast type, since we are using cast type to + // invlidate regions, and generic type is meaningless for invalidating + // regions. + // If the region already has a cast type before, that type is preserved. + // FIXME: is this the right thing to do? + if (isGenericPtr(getContext(), T)) + return state; return state->set<RegionCasts>(R, T); } diff --git a/lib/Analysis/Store.cpp b/lib/Analysis/Store.cpp index 7101b34477..50d0767f61 100644 --- a/lib/Analysis/Store.cpp +++ b/lib/Analysis/Store.cpp @@ -235,7 +235,14 @@ const GRState *StoreManager::InvalidateRegion(const GRState *state, const TypedRegion *TR = cast<TypedRegion>(R); - QualType T = TR->getValueType(Ctx); + QualType T; + + // If the region is cast to another type, use that type. + if (const QualType *CastTy = getCastType(state, R)) { + assert(!(*CastTy)->isObjCObjectPointerType()); + T = (*CastTy)->getAsPointerType()->getPointeeType(); + } else + T = TR->getValueType(Ctx); if (Loc::IsLocType(T) || (T->isIntegerType() && T->isScalarType())) { SVal V = ValMgr.getConjuredSymbolVal(E, T, Count); |