Add StoreManager::getSubRegionMap(). This method returns an opaque mapping for clients of StoreManagers from MemRegions to their subregions.

llvm-svn: 65914
This commit is contained in:
Ted Kremenek 2009-03-03 01:35:36 +00:00
parent a458c4ff65
commit 8dc671cdc9
3 changed files with 84 additions and 1 deletions

View File

@ -31,7 +31,8 @@ class GRStateManager;
class Stmt; class Stmt;
class Expr; class Expr;
class ObjCIvarDecl; class ObjCIvarDecl;
class SubRegionMap;
class StoreManager { class StoreManager {
protected: protected:
/// MRMgr - Manages region objects associated with this StoreManager. /// MRMgr - Manages region objects associated with this StoreManager.
@ -71,8 +72,17 @@ public:
const CompoundLiteralExpr* CL, const CompoundLiteralExpr* CL,
SVal V) = 0; SVal V) = 0;
/// getInitialStore - Returns the initial "empty" store representing the
/// value bindings upon entry to an analyzed function.
virtual Store getInitialStore() = 0; virtual Store getInitialStore() = 0;
/// getRegionManager - Returns the internal RegionManager object that is
/// used to query and manipulate MemRegion objects.
MemRegionManager& getRegionManager() { return MRMgr; } MemRegionManager& getRegionManager() { return MRMgr; }
/// getSubRegionMap - Returns an opaque map object that clients can query
/// to get the subregions of a given MemRegion object.
virtual std::auto_ptr<SubRegionMap> getSubRegionMap(const GRState *state) = 0;
virtual SVal getLValueVar(const GRState* St, const VarDecl* VD) = 0; virtual SVal getLValueVar(const GRState* St, const VarDecl* VD) = 0;
@ -151,6 +161,21 @@ public:
/// iterBindings - Iterate over the bindings in the Store. /// iterBindings - Iterate over the bindings in the Store.
virtual void iterBindings(Store store, BindingsHandler& f) = 0; virtual void iterBindings(Store store, BindingsHandler& f) = 0;
}; };
/// SubRegionMap - An abstract interface that represents a queryable map
/// between MemRegion objects and their subregions.
class SubRegionMap {
public:
virtual ~SubRegionMap() {}
class Visitor {
public:
virtual ~Visitor() {}
virtual bool Visit(const MemRegion* Parent, const MemRegion* SubRegion);
};
virtual void iterSubRegions(const MemRegion* R, Visitor& V) const = 0;
};
StoreManager* CreateBasicStoreManager(GRStateManager& StMgr); StoreManager* CreateBasicStoreManager(GRStateManager& StMgr);
StoreManager* CreateRegionStoreManager(GRStateManager& StMgr); StoreManager* CreateRegionStoreManager(GRStateManager& StMgr);

View File

@ -23,6 +23,15 @@ typedef llvm::ImmutableMap<const VarDecl*,SVal> VarBindingsTy;
namespace { namespace {
class VISIBILITY_HIDDEN BasicStoreSubRegionMap : public SubRegionMap {
public:
BasicStoreSubRegionMap() {}
void iterSubRegions(const MemRegion* R, Visitor& V) const {
// Do nothing. No subregions.
}
};
class VISIBILITY_HIDDEN BasicStoreManager : public StoreManager { class VISIBILITY_HIDDEN BasicStoreManager : public StoreManager {
VarBindingsTy::Factory VBFactory; VarBindingsTy::Factory VBFactory;
GRStateManager& StateMgr; GRStateManager& StateMgr;
@ -37,6 +46,10 @@ public:
~BasicStoreManager() {} ~BasicStoreManager() {}
std::auto_ptr<SubRegionMap> getSubRegionMap(const GRState *state) {
return std::auto_ptr<SubRegionMap>(new BasicStoreSubRegionMap());
}
SVal Retrieve(const GRState *state, Loc loc, QualType T = QualType()); SVal Retrieve(const GRState *state, Loc loc, QualType T = QualType());
const GRState* Bind(const GRState* St, Loc L, SVal V) { const GRState* Bind(const GRState* St, Loc L, SVal V) {

View File

@ -105,6 +105,37 @@ namespace clang {
namespace { namespace {
class VISIBILITY_HIDDEN RegionStoreSubRegionMap : public SubRegionMap {
typedef llvm::DenseMap<const MemRegion*,
llvm::ImmutableSet<const MemRegion*> > Map;
llvm::ImmutableSet<const MemRegion*>::Factory F;
Map M;
public:
void add(const MemRegion* Parent, const MemRegion* SubRegion) {
Map::iterator I = M.find(Parent);
M.insert(std::make_pair(Parent,
F.Add(I == M.end() ? F.GetEmptySet() : I->second, SubRegion)));
}
~RegionStoreSubRegionMap() {}
void iterSubRegions(const MemRegion* Parent, Visitor& V) const {
Map::iterator I = M.find(Parent);
if (I == M.end())
return;
llvm::ImmutableSet<const MemRegion*> S = I->second;
for (llvm::ImmutableSet<const MemRegion*>::iterator SI=S.begin(),SE=S.end();
SI != SE; ++SI) {
if (!V.Visit(Parent, *SI))
return;
}
}
};
class VISIBILITY_HIDDEN RegionStoreManager : public StoreManager { class VISIBILITY_HIDDEN RegionStoreManager : public StoreManager {
RegionBindingsTy::Factory RBFactory; RegionBindingsTy::Factory RBFactory;
RegionViews::Factory RVFactory; RegionViews::Factory RVFactory;
@ -128,6 +159,8 @@ public:
MemRegionManager& getRegionManager() { return MRMgr; } MemRegionManager& getRegionManager() { return MRMgr; }
std::auto_ptr<SubRegionMap> getSubRegionMap(const GRState *state);
const GRState* BindCompoundLiteral(const GRState* St, const GRState* BindCompoundLiteral(const GRState* St,
const CompoundLiteralExpr* CL, SVal V); const CompoundLiteralExpr* CL, SVal V);
@ -268,6 +301,18 @@ StoreManager* clang::CreateRegionStoreManager(GRStateManager& StMgr) {
return new RegionStoreManager(StMgr); return new RegionStoreManager(StMgr);
} }
std::auto_ptr<SubRegionMap>
RegionStoreManager::getSubRegionMap(const GRState *state) {
RegionBindingsTy B = GetRegionBindings(state->getStore());
RegionStoreSubRegionMap *M = new RegionStoreSubRegionMap();
for (RegionBindingsTy::iterator I=B.begin(), E=B.end(); I!=E; ++I) {
if (const SubRegion* R = dyn_cast<SubRegion>(I.getKey()))
M->add(R->getSuperRegion(), R);
}
return std::auto_ptr<SubRegionMap>(M);
}
/// getLValueString - Returns an SVal representing the lvalue of a /// getLValueString - Returns an SVal representing the lvalue of a
/// StringLiteral. Within RegionStore a StringLiteral has an /// StringLiteral. Within RegionStore a StringLiteral has an