diff options
Diffstat (limited to 'include/clang/Analysis/PathSensitive/MemRegion.h')
-rw-r--r-- | include/clang/Analysis/PathSensitive/MemRegion.h | 282 |
1 files changed, 141 insertions, 141 deletions
diff --git a/include/clang/Analysis/PathSensitive/MemRegion.h b/include/clang/Analysis/PathSensitive/MemRegion.h index 54cb872368..ae0580afa4 100644 --- a/include/clang/Analysis/PathSensitive/MemRegion.h +++ b/include/clang/Analysis/PathSensitive/MemRegion.h @@ -31,15 +31,15 @@ namespace llvm { class raw_ostream; } namespace clang { - + class MemRegionManager; class MemSpaceRegion; class LocationContext; - + //===----------------------------------------------------------------------===// // Base region classes. //===----------------------------------------------------------------------===// - + /// MemRegion - The root abstract class for all memory regions. class MemRegion : public llvm::FoldingSetNode { public: @@ -56,52 +56,52 @@ public: VarRegionKind, FieldRegionKind, ObjCIvarRegionKind, ObjCObjectRegionKind, END_DECL_REGIONS, - END_TYPED_REGIONS }; + END_TYPED_REGIONS }; private: const Kind kind; - + protected: MemRegion(Kind k) : kind(k) {} virtual ~MemRegion(); public: ASTContext &getContext() const; - + virtual void Profile(llvm::FoldingSetNodeID& ID) const = 0; virtual MemRegionManager* getMemRegionManager() const = 0; std::string getString() const; - + const MemSpaceRegion *getMemorySpace() const; - + const MemRegion *getBaseRegion() const; - + bool hasStackStorage() const; - + bool hasParametersStorage() const; - + bool hasGlobalsStorage() const; - + bool hasGlobalsOrParametersStorage() const; - + bool hasHeapStorage() const; - + bool hasHeapOrStackStorage() const; virtual void dumpToStream(llvm::raw_ostream& os) const; void dump() const; - - Kind getKind() const { return kind; } - + + Kind getKind() const { return kind; } + template<typename RegionTy> const RegionTy* getAs() const; - + virtual bool isBoundable() const { return false; } static bool classof(const MemRegion*) { return true; } }; - + /// MemSpaceRegion - A memory region that represents and "memory space"; /// for example, the set of global variables, the stack frame, etc. class MemSpaceRegion : public MemRegion { @@ -112,7 +112,7 @@ protected: MemSpaceRegion(MemRegionManager *mgr) : MemRegion(MemSpaceRegionKind), Mgr(mgr) {} - + MemRegionManager* getMemRegionManager() const { return Mgr; } @@ -131,28 +131,28 @@ public: /// are subclasses of SubRegion. class SubRegion : public MemRegion { protected: - const MemRegion* superRegion; + const MemRegion* superRegion; SubRegion(const MemRegion* sReg, Kind k) : MemRegion(k), superRegion(sReg) {} public: const MemRegion* getSuperRegion() const { return superRegion; } - + MemRegionManager* getMemRegionManager() const; - + bool isSubRegionOf(const MemRegion* R) const; - + static bool classof(const MemRegion* R) { return R->getKind() > MemSpaceRegionKind; } }; - + //===----------------------------------------------------------------------===// // Auxillary data classes for use with MemRegions. //===----------------------------------------------------------------------===// class ElementRegion; - + class RegionRawOffset : public std::pair<const MemRegion*, int64_t> { private: friend class ElementRegion; @@ -160,7 +160,7 @@ private: RegionRawOffset(const MemRegion* reg, int64_t offset = 0) : std::pair<const MemRegion*, int64_t>(reg, offset) {} -public: +public: // FIXME: Eventually support symbolic offsets. int64_t getByteOffset() const { return second; } const MemRegion *getRegion() const { return first; } @@ -171,7 +171,7 @@ public: //===----------------------------------------------------------------------===// // MemRegion subclasses. -//===----------------------------------------------------------------------===// +//===----------------------------------------------------------------------===// /// AllocaRegion - A region that represents an untyped blob of bytes created /// by a call to 'alloca'. @@ -184,9 +184,9 @@ protected: AllocaRegion(const Expr* ex, unsigned cnt, const MemRegion *superRegion) : SubRegion(superRegion, AllocaRegionKind), Cnt(cnt), Ex(ex) {} - + public: - + const Expr* getExpr() const { return Ex; } bool isBoundable() const { return true; } @@ -195,32 +195,32 @@ public: static void ProfileRegion(llvm::FoldingSetNodeID& ID, const Expr* Ex, unsigned Cnt, const MemRegion *superRegion); - + void dumpToStream(llvm::raw_ostream& os) const; - + static bool classof(const MemRegion* R) { return R->getKind() == AllocaRegionKind; } -}; - +}; + /// TypedRegion - An abstract class representing regions that are typed. class TypedRegion : public SubRegion { protected: TypedRegion(const MemRegion* sReg, Kind k) : SubRegion(sReg, k) {} - + public: virtual QualType getValueType(ASTContext &C) const = 0; - + virtual QualType getLocationType(ASTContext& C) const { // FIXME: We can possibly optimize this later to cache this value. return C.getPointerType(getValueType(C)); } - + QualType getDesugaredValueType(ASTContext& C) const { QualType T = getValueType(C); return T.getTypePtr() ? T->getDesugaredType() : T; } - + QualType getDesugaredLocationType(ASTContext& C) const { return getLocationType(C)->getDesugaredType(); } @@ -260,9 +260,9 @@ public: const FunctionDecl *getDecl() const { return FD; } - + bool isBoundable() const { return false; } - + virtual void dumpToStream(llvm::raw_ostream& os) const; void Profile(llvm::FoldingSetNodeID& ID) const; @@ -285,9 +285,9 @@ protected: const SymbolRef sym; public: - SymbolicRegion(const SymbolRef s, const MemRegion* sreg) + SymbolicRegion(const SymbolRef s, const MemRegion* sreg) : SubRegion(sreg, SymbolicRegionKind), sym(s) {} - + SymbolRef getSymbol() const { return sym; } @@ -299,13 +299,13 @@ public: static void ProfileRegion(llvm::FoldingSetNodeID& ID, SymbolRef sym, const MemRegion* superRegion); - + void dumpToStream(llvm::raw_ostream& os) const; - + static bool classof(const MemRegion* R) { return R->getKind() == SymbolicRegionKind; } -}; +}; /// StringRegion - Region associated with a StringLiteral. class StringRegion : public TypedRegion { @@ -323,7 +323,7 @@ protected: public: const StringLiteral* getStringLiteral() const { return Str; } - + QualType getValueType(ASTContext& C) const { return Str->getType(); } @@ -351,7 +351,7 @@ private: CompoundLiteralRegion(const CompoundLiteralExpr* cl, const MemRegion* sReg) : TypedRegion(sReg, CompoundLiteralRegionKind), CL(cl) {} - + static void ProfileRegion(llvm::FoldingSetNodeID& ID, const CompoundLiteralExpr* CL, const MemRegion* superRegion); @@ -363,11 +363,11 @@ public: bool isBoundable() const { return !CL->isFileScope(); } void Profile(llvm::FoldingSetNodeID& ID) const; - + void dumpToStream(llvm::raw_ostream& os) const; const CompoundLiteralExpr* getLiteralExpr() const { return CL; } - + static bool classof(const MemRegion* R) { return R->getKind() == CompoundLiteralRegionKind; } @@ -382,23 +382,23 @@ protected: static void ProfileRegion(llvm::FoldingSetNodeID& ID, const Decl* D, const MemRegion* superRegion, Kind k); - + public: const Decl* getDecl() const { return D; } void Profile(llvm::FoldingSetNodeID& ID) const; - + static bool classof(const MemRegion* R) { unsigned k = R->getKind(); return k > BEG_DECL_REGIONS && k < END_DECL_REGIONS; } }; - + class VarRegion : public DeclRegion { friend class MemRegionManager; // Data. const LocationContext *LC; - + // Constructors and private methods. VarRegion(const VarDecl* vd, const LocationContext *lC, const MemRegion* sReg) : DeclRegion(vd, sReg, VarRegionKind), LC(lC) {} @@ -409,24 +409,24 @@ class VarRegion : public DeclRegion { DeclRegion::ProfileRegion(ID, VD, superRegion, VarRegionKind); ID.AddPointer(LC); } - + void Profile(llvm::FoldingSetNodeID& ID) const; - -public: + +public: const VarDecl *getDecl() const { return cast<VarDecl>(D); } - + const LocationContext *getLocationContext() const { return LC; } - - QualType getValueType(ASTContext& C) const { + + QualType getValueType(ASTContext& C) const { // FIXME: We can cache this if needed. return C.getCanonicalType(getDecl()->getType()); - } - + } + void dumpToStream(llvm::raw_ostream& os) const; - + static bool classof(const MemRegion* R) { return R->getKind() == VarRegionKind; - } + } }; class FieldRegion : public DeclRegion { @@ -436,57 +436,57 @@ class FieldRegion : public DeclRegion { : DeclRegion(fd, sReg, FieldRegionKind) {} public: - + void dumpToStream(llvm::raw_ostream& os) const; - + const FieldDecl* getDecl() const { return cast<FieldDecl>(D); } - - QualType getValueType(ASTContext& C) const { + + QualType getValueType(ASTContext& C) const { // FIXME: We can cache this if needed. return C.getCanonicalType(getDecl()->getType()); - } + } static void ProfileRegion(llvm::FoldingSetNodeID& ID, const FieldDecl* FD, const MemRegion* superRegion) { DeclRegion::ProfileRegion(ID, FD, superRegion, FieldRegionKind); } - + static bool classof(const MemRegion* R) { return R->getKind() == FieldRegionKind; } }; - + class ObjCObjectRegion : public DeclRegion { - + friend class MemRegionManager; - + ObjCObjectRegion(const ObjCInterfaceDecl* ivd, const MemRegion* sReg) : DeclRegion(ivd, sReg, ObjCObjectRegionKind) {} - + static void ProfileRegion(llvm::FoldingSetNodeID& ID, const ObjCInterfaceDecl* ivd, const MemRegion* superRegion) { DeclRegion::ProfileRegion(ID, ivd, superRegion, ObjCObjectRegionKind); } - + public: const ObjCInterfaceDecl* getInterface() const { return cast<ObjCInterfaceDecl>(D); } - + QualType getValueType(ASTContext& C) const { return C.getObjCInterfaceType(getInterface()); } - + static bool classof(const MemRegion* R) { return R->getKind() == ObjCObjectRegionKind; } -}; - +}; + class ObjCIvarRegion : public DeclRegion { - + friend class MemRegionManager; - + ObjCIvarRegion(const ObjCIvarDecl* ivd, const MemRegion* sReg) : DeclRegion(ivd, sReg, ObjCIvarRegionKind) {} @@ -494,13 +494,13 @@ class ObjCIvarRegion : public DeclRegion { const MemRegion* superRegion) { DeclRegion::ProfileRegion(ID, ivd, superRegion, ObjCIvarRegionKind); } - + public: const ObjCIvarDecl* getDecl() const { return cast<ObjCIvarDecl>(D); } QualType getValueType(ASTContext&) const { return getDecl()->getType(); } - + void dumpToStream(llvm::raw_ostream& os) const; - + static bool classof(const MemRegion* R) { return R->getKind() == ObjCIvarRegionKind; } @@ -519,7 +519,7 @@ class ElementRegion : public TypedRegion { cast<nonloc::ConcreteInt>(&Idx)->getValue().isSigned()) && "The index must be signed"); } - + static void ProfileRegion(llvm::FoldingSetNodeID& ID, QualType elementType, SVal Idx, const MemRegion* superRegion); @@ -530,13 +530,13 @@ public: QualType getValueType(ASTContext&) const { return ElementType; } - + QualType getElementType() const { return ElementType; } - + RegionRawOffset getAsRawOffset() const; - + void dumpToStream(llvm::raw_ostream& os) const; void Profile(llvm::FoldingSetNodeID& ID) const; @@ -550,7 +550,7 @@ template<typename RegionTy> const RegionTy* MemRegion::getAs() const { if (const RegionTy* RT = dyn_cast<RegionTy>(this)) return RT; - + return NULL; } @@ -562,7 +562,7 @@ class MemRegionManager { ASTContext &C; llvm::BumpPtrAllocator& A; llvm::FoldingSet<MemRegion> Regions; - + MemSpaceRegion *globals; MemSpaceRegion *stack; MemSpaceRegion *stackArguments; @@ -574,11 +574,11 @@ public: MemRegionManager(ASTContext &c, llvm::BumpPtrAllocator& a) : C(c), A(a), globals(0), stack(0), stackArguments(0), heap(0), unknown(0), code(0) {} - + ~MemRegionManager() {} - + ASTContext &getContext() { return C; } - + /// getStackRegion - Retrieve the memory region associated with the /// current stack frame. MemSpaceRegion *getStackRegion(); @@ -586,11 +586,11 @@ public: /// getStackArgumentsRegion - Retrieve the memory region associated with /// function/method arguments of the current stack frame. MemSpaceRegion *getStackArgumentsRegion(); - + /// getGlobalsRegion - Retrieve the memory region associated with /// all global variables. MemSpaceRegion *getGlobalsRegion(); - + /// getHeapRegion - Retrieve the memory region associated with the /// generic "heap". MemSpaceRegion *getHeapRegion(); @@ -603,12 +603,12 @@ public: /// getAllocaRegion - Retrieve a region associated with a call to alloca(). AllocaRegion *getAllocaRegion(const Expr* Ex, unsigned Cnt); - + /// getCompoundLiteralRegion - Retrieve the region associated with a /// given CompoundLiteral. CompoundLiteralRegion* - getCompoundLiteralRegion(const CompoundLiteralExpr* CL); - + getCompoundLiteralRegion(const CompoundLiteralExpr* CL); + /// getSymbolicRegion - Retrieve or create a "symbolic" memory region. SymbolicRegion* getSymbolicRegion(SymbolRef sym); @@ -617,13 +617,13 @@ public: /// getVarRegion - Retrieve or create the memory region associated with /// a specified VarDecl and LocationContext. VarRegion* getVarRegion(const VarDecl *D, const LocationContext *LC); - + /// getElementRegion - Retrieve the memory region associated with the /// associated element type, index, and super region. ElementRegion *getElementRegion(QualType elementType, SVal Idx, const MemRegion *superRegion, ASTContext &Ctx); - + ElementRegion *getElementRegionWithSuper(const ElementRegion *ER, const MemRegion *superRegion) { return getElementRegion(ER->getElementType(), ER->getIndex(), @@ -636,44 +636,44 @@ public: /// a structure or class). FieldRegion *getFieldRegion(const FieldDecl* fd, const MemRegion* superRegion); - + FieldRegion *getFieldRegionWithSuper(const FieldRegion *FR, const MemRegion *superRegion) { return getFieldRegion(FR->getDecl(), superRegion); } - + /// getObjCObjectRegion - Retrieve or create the memory region associated with /// the instance of a specified Objective-C class. ObjCObjectRegion* getObjCObjectRegion(const ObjCInterfaceDecl* ID, const MemRegion* superRegion); - + /// getObjCIvarRegion - Retrieve or create the memory region associated with /// a specified Objective-c instance variable. 'superRegion' corresponds /// to the containing region (which typically represents the Objective-C /// object). ObjCIvarRegion *getObjCIvarRegion(const ObjCIvarDecl* ivd, const MemRegion* superRegion); - + CodeTextRegion *getCodeTextRegion(const FunctionDecl *FD); - + template <typename RegionTy, typename A1> RegionTy* getRegion(const A1 a1); - + template <typename RegionTy, typename A1> RegionTy* getSubRegion(const A1 a1, const MemRegion* superRegion); - + template <typename RegionTy, typename A1, typename A2> RegionTy* getRegion(const A1 a1, const A2 a2); - bool isGlobalsRegion(const MemRegion* R) { + bool isGlobalsRegion(const MemRegion* R) { assert(R); - return R == globals; + return R == globals; } - + private: MemSpaceRegion* LazyAllocate(MemSpaceRegion*& region); }; - + //===----------------------------------------------------------------------===// // Out-of-line member definitions. //===----------------------------------------------------------------------===// @@ -681,69 +681,69 @@ private: inline ASTContext& MemRegion::getContext() const { return getMemRegionManager()->getContext(); } - + template<typename RegionTy> struct MemRegionManagerTrait; - + template <typename RegionTy, typename A1> RegionTy* MemRegionManager::getRegion(const A1 a1) { const typename MemRegionManagerTrait<RegionTy>::SuperRegionTy *superRegion = MemRegionManagerTrait<RegionTy>::getSuperRegion(*this, a1); - - llvm::FoldingSetNodeID ID; - RegionTy::ProfileRegion(ID, a1, superRegion); + + llvm::FoldingSetNodeID ID; + RegionTy::ProfileRegion(ID, a1, superRegion); void* InsertPos; RegionTy* R = cast_or_null<RegionTy>(Regions.FindNodeOrInsertPos(ID, InsertPos)); - + if (!R) { R = (RegionTy*) A.Allocate<RegionTy>(); new (R) RegionTy(a1, superRegion); Regions.InsertNode(R, InsertPos); } - + return R; } template <typename RegionTy, typename A1> RegionTy* MemRegionManager::getSubRegion(const A1 a1, const MemRegion *superRegion) { - llvm::FoldingSetNodeID ID; - RegionTy::ProfileRegion(ID, a1, superRegion); + llvm::FoldingSetNodeID ID; + RegionTy::ProfileRegion(ID, a1, superRegion); void* InsertPos; RegionTy* R = cast_or_null<RegionTy>(Regions.FindNodeOrInsertPos(ID, InsertPos)); - + if (!R) { R = (RegionTy*) A.Allocate<RegionTy>(); new (R) RegionTy(a1, superRegion); Regions.InsertNode(R, InsertPos); } - + return R; } - + template <typename RegionTy, typename A1, typename A2> RegionTy* MemRegionManager::getRegion(const A1 a1, const A2 a2) { - + const typename MemRegionManagerTrait<RegionTy>::SuperRegionTy *superRegion = MemRegionManagerTrait<RegionTy>::getSuperRegion(*this, a1, a2); - - llvm::FoldingSetNodeID ID; - RegionTy::ProfileRegion(ID, a1, a2, superRegion); + + llvm::FoldingSetNodeID ID; + RegionTy::ProfileRegion(ID, a1, a2, superRegion); void* InsertPos; RegionTy* R = cast_or_null<RegionTy>(Regions.FindNodeOrInsertPos(ID, InsertPos)); - + if (!R) { R = (RegionTy*) A.Allocate<RegionTy>(); new (R) RegionTy(a1, a2, superRegion); Regions.InsertNode(R, InsertPos); } - + return R; } - + //===----------------------------------------------------------------------===// // Traits for constructing regions. //===----------------------------------------------------------------------===// @@ -754,18 +754,18 @@ template <> struct MemRegionManagerTrait<AllocaRegion> { const Expr *, unsigned) { return MRMgr.getStackRegion(); } -}; - +}; + template <> struct MemRegionManagerTrait<CompoundLiteralRegion> { typedef MemRegion SuperRegionTy; static const SuperRegionTy* getSuperRegion(MemRegionManager& MRMgr, const CompoundLiteralExpr *CL) { - - return CL->isFileScope() ? MRMgr.getGlobalsRegion() + + return CL->isFileScope() ? MRMgr.getGlobalsRegion() : MRMgr.getStackRegion(); } }; - + template <> struct MemRegionManagerTrait<StringRegion> { typedef MemSpaceRegion SuperRegionTy; static const SuperRegionTy* getSuperRegion(MemRegionManager& MRMgr, @@ -773,24 +773,24 @@ template <> struct MemRegionManagerTrait<StringRegion> { return MRMgr.getGlobalsRegion(); } }; - + template <> struct MemRegionManagerTrait<VarRegion> { typedef MemRegion SuperRegionTy; static const SuperRegionTy* getSuperRegion(MemRegionManager &MRMgr, const VarDecl *D, const LocationContext *LC) { - + // FIXME: Make stack regions have a location context? - + if (D->hasLocalStorage()) { return isa<ParmVarDecl>(D) || isa<ImplicitParamDecl>(D) ? MRMgr.getStackArgumentsRegion() : MRMgr.getStackRegion(); } - + return MRMgr.getGlobalsRegion(); } }; - + template <> struct MemRegionManagerTrait<SymbolicRegion> { typedef MemRegion SuperRegionTy; static const SuperRegionTy* getSuperRegion(MemRegionManager& MRMgr, @@ -810,7 +810,7 @@ template<> struct MemRegionManagerTrait<CodeTextRegion> { return MRMgr.getCodeRegion(); } }; - + } // end clang namespace //===----------------------------------------------------------------------===// @@ -819,7 +819,7 @@ template<> struct MemRegionManagerTrait<CodeTextRegion> { namespace llvm { static inline raw_ostream& operator<<(raw_ostream& os, - const clang::MemRegion* R) { + const clang::MemRegion* R) { R->dumpToStream(os); return os; } |