#include "clang/AST/Decl.h"
#include "clang/AST/DeclObjC.h"
#include "clang/Analysis/PathSensitive/SymbolManager.h"
+#include "clang/Analysis/PathSensitive/RValues.h"
#include "llvm/Support/Casting.h"
#include "llvm/ADT/FoldingSet.h"
#include "llvm/Support/Allocator.h"
enum Kind { MemSpaceRegionKind, SymbolicRegionKind,
// Typed regions.
BEG_TYPED_REGIONS,
- VarRegionKind, FieldRegionKind, ObjCIvarRegionKind,
+ VarRegionKind, FieldRegionKind, ElementRegionKind,
+ ObjCIvarRegionKind,
AnonTypedRegionKind, AnonPointeeRegionKind,
END_TYPED_REGIONS };
private:
return R->getKind() == ObjCIvarRegionKind;
}
};
-
+
+class ElementRegion : public SubRegion {
+ friend class MemRegionManager;
+
+ SVal Index;
+
+ ElementRegion(SVal Idx, const MemRegion* sReg)
+ : SubRegion(sReg, ElementRegionKind), Index(Idx) {}
+
+ static void ProfileRegion(llvm::FoldingSetNodeID& ID, SVal Idx,
+ const MemRegion* superRegion);
+
+public:
+
+ void Profile(llvm::FoldingSetNodeID& ID) const;
+
+ static bool classof(const MemRegion* R) {
+ return R->getKind() == ElementRegionKind;
+ }
+};
+
//===----------------------------------------------------------------------===//
// MemRegionManager - Factory object for creating regions.
//===----------------------------------------------------------------------===//
return getVarRegion(vd, vd->hasLocalStorage() ? getStackRegion()
: getGlobalsRegion());
}
-
+
+ ElementRegion* getElementRegion(SVal Idx, const MemRegion* superRegion);
+
/// getFieldRegion - Retrieve or create the memory region associated with
/// a specified FieldDecl. 'superRegion' corresponds to the containing
/// memory region (which typically represents the memory representing
SymbolicRegion::ProfileRegion(ID, sym);
}
+void ElementRegion::ProfileRegion(llvm::FoldingSetNodeID& ID, SVal Idx,
+ const MemRegion* superRegion) {
+ ID.AddInteger(MemRegion::ElementRegionKind);
+ ID.AddPointer(superRegion);
+ Idx.Profile(ID);
+}
+
+void ElementRegion::Profile(llvm::FoldingSetNodeID& ID) const {
+ ElementRegion::ProfileRegion(ID, Index, superRegion);
+}
//===----------------------------------------------------------------------===//
// Region pretty-printing.
//===----------------------------------------------------------------------===//
return R;
}
+ElementRegion* MemRegionManager::getElementRegion(SVal Idx,
+ const MemRegion* superRegion){
+ llvm::FoldingSetNodeID ID;
+ ElementRegion::ProfileRegion(ID, Idx, superRegion);
+
+ void* InsertPos;
+ MemRegion* data = Regions.FindNodeOrInsertPos(ID, InsertPos);
+ ElementRegion* R = cast_or_null<ElementRegion>(data);
+
+ if (!R) {
+ R = (ElementRegion*) A.Allocate<ElementRegion>();
+ new (R) ElementRegion(Idx, superRegion);
+ Regions.InsertNode(R, InsertPos);
+ }
+
+ return R;
+}
+
/// getSymbolicRegion - Retrieve or create a "symbolic" memory region.
SymbolicRegion* MemRegionManager::getSymbolicRegion(const SymbolID sym) {