1178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu//== RegionStore.cpp - Field-sensitive store model --------------*- C++ -*--==// 2178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// 3178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// The LLVM Compiler Infrastructure 4178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// 5178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// This file is distributed under the University of Illinois Open Source 6178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// License. See LICENSE.TXT for details. 7178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// 8178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu//===----------------------------------------------------------------------===// 9178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// 10178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// This file defines a basic region store model. In this model, we do have field 11178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// sensitivity. But we assume nothing about the heap shape. So recursive data 12178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// structures are largely ignored. Basically we do 1-limiting analysis. 13178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// Parameter pointers are assumed with no aliasing. Pointee objects of 14178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// parameters are created lazily. 15178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu// 16178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu//===----------------------------------------------------------------------===// 174967a710c84587c654b56c828382219c3937dacbPirama Arumuga Nainar 182fa67efeaf66a9332c30a026dc1c21bef6c33a6cBenjamin Kramer#include "clang/AST/Attr.h" 193ed04d37573c566205d965d2e91d54ccae898d0aZhongxing Xu#include "clang/AST/CharUnits.h" 2066d5142ab5026aa77ab6f1d7e4d9bdb0b438d55aTed Kremenek#include "clang/Analysis/Analyses/LiveVariables.h" 2166d5142ab5026aa77ab6f1d7e4d9bdb0b438d55aTed Kremenek#include "clang/Analysis/AnalysisContext.h" 2266d5142ab5026aa77ab6f1d7e4d9bdb0b438d55aTed Kremenek#include "clang/Basic/TargetInfo.h" 23258277d5a922e06ef523f7805900689b680ddc7dJordan Rose#include "clang/StaticAnalyzer/Core/PathSensitive/AnalysisManager.h" 24f540c54701e3eeb34cb619a3a4eb18f1ac70ef2dJordan Rose#include "clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h" 252fa67efeaf66a9332c30a026dc1c21bef6c33a6cBenjamin Kramer#include "clang/StaticAnalyzer/Core/PathSensitive/MemRegion.h" 2618c66fdc3c4008d335885695fe36fb5353c5f672Ted Kremenek#include "clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h" 2718c66fdc3c4008d335885695fe36fb5353c5f672Ted Kremenek#include "clang/StaticAnalyzer/Core/PathSensitive/ProgramStateTrait.h" 28258277d5a922e06ef523f7805900689b680ddc7dJordan Rose#include "clang/StaticAnalyzer/Core/PathSensitive/SubEngine.h" 29dc0a25d9bff956cdbe54ea0bfc8fbbe3ceb4eb92Zhongxing Xu#include "llvm/ADT/ImmutableList.h" 3066d5142ab5026aa77ab6f1d7e4d9bdb0b438d55aTed Kremenek#include "llvm/ADT/ImmutableMap.h" 3166d5142ab5026aa77ab6f1d7e4d9bdb0b438d55aTed Kremenek#include "llvm/ADT/Optional.h" 32a071eb053aeeedc1c8128fd309b3a779b6c3152aZhongxing Xu#include "llvm/Support/raw_ostream.h" 334967a710c84587c654b56c828382219c3937dacbPirama Arumuga Nainar#include <utility> 34178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu 35178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xuusing namespace clang; 369ef6537a894c33003359b1f9b9676e9178e028b7Ted Kremenekusing namespace ento; 37178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu 381c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek//===----------------------------------------------------------------------===// 39e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek// Representation of binding keys. 401c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek//===----------------------------------------------------------------------===// 411c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek 4213d50177b13161b209579e1f30a5e3cc72f7e2bdZhongxing Xunamespace { 43e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenekclass BindingKey { 4413d50177b13161b209579e1f30a5e3cc72f7e2bdZhongxing Xupublic: 45824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose enum Kind { Default = 0x0, Direct = 0x1 }; 4613d50177b13161b209579e1f30a5e3cc72f7e2bdZhongxing Xuprivate: 47824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose enum { Symbolic = 0x2 }; 48e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose 49824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose llvm::PointerIntPair<const MemRegion *, 2> P; 50824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose uint64_t Data; 51e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 529d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose /// Create a key for a binding to region \p r, which has a symbolic offset 539d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose /// from region \p Base. 549d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose explicit BindingKey(const SubRegion *r, const SubRegion *Base, Kind k) 55824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose : P(r, k | Symbolic), Data(reinterpret_cast<uintptr_t>(Base)) { 56824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose assert(r && Base && "Must have known regions."); 57824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose assert(getConcreteOffsetRegion() == Base && "Failed to store base region"); 58824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose } 599d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose 609d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose /// Create a key for a binding at \p offset from base region \p r. 61e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek explicit BindingKey(const MemRegion *r, uint64_t offset, Kind k) 62824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose : P(r, k), Data(offset) { 63824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose assert(r && "Must have known regions."); 64824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose assert(getOffset() == offset && "Failed to store offset"); 65d1a4f68a4301d1ee3098cc9db0cd507b96dd1beeBenjamin Kramer assert((r == r->getBaseRegion() || isa<ObjCIvarRegion>(r)) && "Not a base"); 66824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose } 6713d50177b13161b209579e1f30a5e3cc72f7e2bdZhongxing Xupublic: 68e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 69824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose bool isDirect() const { return P.getInt() & Direct; } 70824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose bool hasSymbolicOffset() const { return P.getInt() & Symbolic; } 71e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 72e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek const MemRegion *getRegion() const { return P.getPointer(); } 73e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose uint64_t getOffset() const { 74e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose assert(!hasSymbolicOffset()); 75824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose return Data; 76e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose } 77e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose 789d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose const SubRegion *getConcreteOffsetRegion() const { 79824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose assert(hasSymbolicOffset()); 809d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose return reinterpret_cast<const SubRegion *>(static_cast<uintptr_t>(Data)); 81824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose } 82e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 831e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const MemRegion *getBaseRegion() const { 841e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (hasSymbolicOffset()) 851e934431adba0f459668a59c6059b9596fd627b4Jordan Rose return getConcreteOffsetRegion()->getBaseRegion(); 861e934431adba0f459668a59c6059b9596fd627b4Jordan Rose return getRegion()->getBaseRegion(); 871e934431adba0f459668a59c6059b9596fd627b4Jordan Rose } 881e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 8913d50177b13161b209579e1f30a5e3cc72f7e2bdZhongxing Xu void Profile(llvm::FoldingSetNodeID& ID) const { 90e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek ID.AddPointer(P.getOpaqueValue()); 91824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose ID.AddInteger(Data); 9213d50177b13161b209579e1f30a5e3cc72f7e2bdZhongxing Xu } 93e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 94e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek static BindingKey Make(const MemRegion *R, Kind k); 95e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 96e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek bool operator<(const BindingKey &X) const { 97e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek if (P.getOpaqueValue() < X.P.getOpaqueValue()) 98e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek return true; 99e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek if (P.getOpaqueValue() > X.P.getOpaqueValue()) 100e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek return false; 101824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose return Data < X.Data; 102e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek } 103e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 104e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek bool operator==(const BindingKey &X) const { 105e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek return P.getOpaqueValue() == X.P.getOpaqueValue() && 106824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose Data == X.Data; 1071c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek } 108e701117b21356d3c60133315b5bdd50232ec6ccaJordy Rose 109651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines void dump() const; 110e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek}; 1111c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek} // end anonymous namespace 1121c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek 113dc015e5398d3cdd7baaa5d9a0330aaeafdf1a7c3Zhongxing XuBindingKey BindingKey::Make(const MemRegion *R, Kind k) { 1144213e389d6f8fa96ab30eec0d932e4e3eee32997Ted Kremenek const RegionOffset &RO = R->getAsOffset(); 115824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose if (RO.hasSymbolicOffset()) 1169d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose return BindingKey(cast<SubRegion>(R), cast<SubRegion>(RO.getRegion()), k); 117e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose 118824e07ac8f5c9efdddb4254de0203b9675b1ef0bJordan Rose return BindingKey(RO.getRegion(), RO.getOffset(), k); 119dc015e5398d3cdd7baaa5d9a0330aaeafdf1a7c3Zhongxing Xu} 120dc015e5398d3cdd7baaa5d9a0330aaeafdf1a7c3Zhongxing Xu 1211c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremeneknamespace llvm { 122e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek static inline 1239c378f705405d37f49795d5e915989de774fe11fTed Kremenek raw_ostream &operator<<(raw_ostream &os, BindingKey K) { 124e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose os << '(' << K.getRegion(); 125e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose if (!K.hasSymbolicOffset()) 126e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose os << ',' << K.getOffset(); 127e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose os << ',' << (K.isDirect() ? "direct" : "default") 128e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek << ')'; 1291c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek return os; 1301c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek } 131e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose 132e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose template <typename T> struct isPodLike; 133e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose template <> struct isPodLike<BindingKey> { 134e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose static const bool value = true; 135e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose }; 1361c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek} // end llvm namespace 1371c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek 138651f13cea278ec967336033dd032faef0e9fc2ecStephen HinesLLVM_DUMP_METHOD void BindingKey::dump() const { llvm::errs() << *this; } 1391e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 1401c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek//===----------------------------------------------------------------------===// 141baf03a7c0a846632396f9f5a19f6cd45bbe2b926Zhongxing Xu// Actual Store type. 1421c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek//===----------------------------------------------------------------------===// 1431c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek 14423dca7d88f3e9a7925bfb2c5449499900c906633Ted Kremenektypedef llvm::ImmutableMap<BindingKey, SVal> ClusterBindings; 14523dca7d88f3e9a7925bfb2c5449499900c906633Ted Kremenektypedef llvm::ImmutableMapRef<BindingKey, SVal> ClusterBindingsRef; 146e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rosetypedef std::pair<BindingKey, SVal> BindingPair; 14729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 14829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenektypedef llvm::ImmutableMap<const MemRegion *, ClusterBindings> 14929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindings; 15029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 15129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremeneknamespace { 15229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenekclass RegionBindingsRef : public llvm::ImmutableMapRef<const MemRegion *, 15329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek ClusterBindings> { 15487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar ClusterBindings::Factory *CBFactory; 15587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 15629f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenekpublic: 15729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek typedef llvm::ImmutableMapRef<const MemRegion *, ClusterBindings> 15829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek ParentTy; 15929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 16029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef(ClusterBindings::Factory &CBFactory, 16129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const RegionBindings::TreeTy *T, 16229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindings::TreeTy::Factory *F) 16387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar : llvm::ImmutableMapRef<const MemRegion *, ClusterBindings>(T, F), 16487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar CBFactory(&CBFactory) {} 16529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 16629f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef(const ParentTy &P, ClusterBindings::Factory &CBFactory) 16787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar : llvm::ImmutableMapRef<const MemRegion *, ClusterBindings>(P), 16887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar CBFactory(&CBFactory) {} 16929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 17018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef add(key_type_ref K, data_type_ref D) const { 17187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return RegionBindingsRef(static_cast<const ParentTy *>(this)->add(K, D), 17287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar *CBFactory); 17329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek } 17429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 17518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef remove(key_type_ref K) const { 17687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return RegionBindingsRef(static_cast<const ParentTy *>(this)->remove(K), 17787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar *CBFactory); 17829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek } 17929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 18018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef addBinding(BindingKey K, SVal V) const; 18129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 18229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef addBinding(const MemRegion *R, 18318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek BindingKey::Kind k, SVal V) const; 18429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 18518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const SVal *lookup(BindingKey K) const; 18618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const SVal *lookup(const MemRegion *R, BindingKey::Kind k) const; 18787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar using llvm::ImmutableMapRef<const MemRegion *, ClusterBindings>::lookup; 18829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 18929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef removeBinding(BindingKey K); 19029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 19129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef removeBinding(const MemRegion *R, 19229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek BindingKey::Kind k); 19329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 19429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef removeBinding(const MemRegion *R) { 19529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return removeBinding(R, BindingKey::Direct). 19629f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek removeBinding(R, BindingKey::Default); 19729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek } 19829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 19918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek Optional<SVal> getDirectBinding(const MemRegion *R) const; 20029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 20129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek /// getDefaultBinding - Returns an SVal* representing an optional default 20229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek /// binding associated with a region and its subregions. 20318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek Optional<SVal> getDefaultBinding(const MemRegion *R) const; 2040c312a90c5b9d27e1425bf8d0448e133a97806ceTed Kremenek 2050c312a90c5b9d27e1425bf8d0448e133a97806ceTed Kremenek /// Return the internal tree as a Store. 2060c312a90c5b9d27e1425bf8d0448e133a97806ceTed Kremenek Store asStore() const { 2070c312a90c5b9d27e1425bf8d0448e133a97806ceTed Kremenek return asImmutableMap().getRootWithoutRetain(); 2080c312a90c5b9d27e1425bf8d0448e133a97806ceTed Kremenek } 209b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek 210cfa88f893915ceb8ae4ce2f17c46c24a4d67502fDmitri Gribenko void dump(raw_ostream &OS, const char *nl) const { 211b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek for (iterator I = begin(), E = end(); I != E; ++I) { 212b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek const ClusterBindings &Cluster = I.getData(); 213b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek for (ClusterBindings::iterator CI = Cluster.begin(), CE = Cluster.end(); 214b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek CI != CE; ++CI) { 215b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek OS << ' ' << CI.getKey() << " : " << CI.getData() << nl; 216b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek } 217b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek OS << nl; 218b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek } 219b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek } 220b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek 221651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines LLVM_DUMP_METHOD void dump() const { dump(llvm::errs(), "\n"); } 22229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek}; 22329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek} // end anonymous namespace 22429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 22518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenektypedef const RegionBindingsRef& RegionBindingsConstRef; 22618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek 22718f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekOptional<SVal> RegionBindingsRef::getDirectBinding(const MemRegion *R) const { 228472b0613ff67e8598ef6a69bb478c721b21a9294Jordan Rose return Optional<SVal>::create(lookup(R, BindingKey::Direct)); 22929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek} 23029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 23118f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekOptional<SVal> RegionBindingsRef::getDefaultBinding(const MemRegion *R) const { 23229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (R->isBoundable()) 23329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (const TypedValueRegion *TR = dyn_cast<TypedValueRegion>(R)) 23429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (TR->getValueType()->isUnionType()) 23529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return UnknownVal(); 236472b0613ff67e8598ef6a69bb478c721b21a9294Jordan Rose 237472b0613ff67e8598ef6a69bb478c721b21a9294Jordan Rose return Optional<SVal>::create(lookup(R, BindingKey::Default)); 23829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek} 23929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 24018f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionBindingsRef RegionBindingsRef::addBinding(BindingKey K, SVal V) const { 24129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const MemRegion *Base = K.getBaseRegion(); 24229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 24329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const ClusterBindings *ExistingCluster = lookup(Base); 24487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar ClusterBindings Cluster = 24587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar (ExistingCluster ? *ExistingCluster : CBFactory->getEmptyMap()); 24629f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 24787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar ClusterBindings NewCluster = CBFactory->add(Cluster, K, V); 24829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return add(Base, NewCluster); 24929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek} 25029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 25129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 25229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted KremenekRegionBindingsRef RegionBindingsRef::addBinding(const MemRegion *R, 25329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek BindingKey::Kind k, 25418f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal V) const { 25529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return addBinding(BindingKey::Make(R, k), V); 25629f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek} 25729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 25818f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenekconst SVal *RegionBindingsRef::lookup(BindingKey K) const { 25929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const ClusterBindings *Cluster = lookup(K.getBaseRegion()); 26029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (!Cluster) 2616bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines return nullptr; 26229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return Cluster->lookup(K); 26329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek} 26429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 26529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenekconst SVal *RegionBindingsRef::lookup(const MemRegion *R, 26618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek BindingKey::Kind k) const { 26729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return lookup(BindingKey::Make(R, k)); 26829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek} 26929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 27029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted KremenekRegionBindingsRef RegionBindingsRef::removeBinding(BindingKey K) { 27129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const MemRegion *Base = K.getBaseRegion(); 27229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const ClusterBindings *Cluster = lookup(Base); 27329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (!Cluster) 27429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return *this; 27529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 27687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar ClusterBindings NewCluster = CBFactory->remove(*Cluster, K); 27729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (NewCluster.isEmpty()) 27829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return remove(Base); 27929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return add(Base, NewCluster); 28029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek} 28129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek 28229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted KremenekRegionBindingsRef RegionBindingsRef::removeBinding(const MemRegion *R, 28329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek BindingKey::Kind k){ 28429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return removeBinding(BindingKey::Make(R, k)); 28529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek} 286baf03a7c0a846632396f9f5a19f6cd45bbe2b926Zhongxing Xu 28750dc1b3c851b5700ea32f81ed360586617e2c92fTed Kremenek//===----------------------------------------------------------------------===// 2889af46f59242cfaec74fa491a66724970478263ebTed Kremenek// Fine-grained control of RegionStoreManager. 2899af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 2909af46f59242cfaec74fa491a66724970478263ebTed Kremenek 2919af46f59242cfaec74fa491a66724970478263ebTed Kremeneknamespace { 292ba5fb5a955c896815c439289fc51c03cf0635129Kovarththanan Rajaratnamstruct minimal_features_tag {}; 293ba5fb5a955c896815c439289fc51c03cf0635129Kovarththanan Rajaratnamstruct maximal_features_tag {}; 2941eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 295ba5fb5a955c896815c439289fc51c03cf0635129Kovarththanan Rajaratnamclass RegionStoreFeatures { 2969af46f59242cfaec74fa491a66724970478263ebTed Kremenek bool SupportsFields; 2979af46f59242cfaec74fa491a66724970478263ebTed Kremenekpublic: 2989af46f59242cfaec74fa491a66724970478263ebTed Kremenek RegionStoreFeatures(minimal_features_tag) : 2990752d6d06721c55e5586cd2431d1239c0c8d27aeTed Kremenek SupportsFields(false) {} 3001eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 3019af46f59242cfaec74fa491a66724970478263ebTed Kremenek RegionStoreFeatures(maximal_features_tag) : 3020752d6d06721c55e5586cd2431d1239c0c8d27aeTed Kremenek SupportsFields(true) {} 3031eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 3049af46f59242cfaec74fa491a66724970478263ebTed Kremenek void enableFields(bool t) { SupportsFields = t; } 3051eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 3069af46f59242cfaec74fa491a66724970478263ebTed Kremenek bool supportsFields() const { return SupportsFields; } 3079af46f59242cfaec74fa491a66724970478263ebTed Kremenek}; 3089af46f59242cfaec74fa491a66724970478263ebTed Kremenek} 3099af46f59242cfaec74fa491a66724970478263ebTed Kremenek 3109af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 31150dc1b3c851b5700ea32f81ed360586617e2c92fTed Kremenek// Main RegionStore logic. 31250dc1b3c851b5700ea32f81ed360586617e2c92fTed Kremenek//===----------------------------------------------------------------------===// 313c48ea6e51dd0da0a3def87f148240718ffaaeb0dTed Kremenek 314178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xunamespace { 315658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaksclass invalidateRegionsWorker; 3161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 317ba5fb5a955c896815c439289fc51c03cf0635129Kovarththanan Rajaratnamclass RegionStoreManager : public StoreManager { 31829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenekpublic: 3199af46f59242cfaec74fa491a66724970478263ebTed Kremenek const RegionStoreFeatures Features; 320258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 321451ac091cd1868433985396a25cbbf2092ae8ca9Ted Kremenek RegionBindings::Factory RBFactory; 32229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek mutable ClusterBindings::Factory CBFactory; 323e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 32428743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose typedef std::vector<SVal> SValListTy; 32528743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Roseprivate: 32628743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose typedef llvm::DenseMap<const LazyCompoundValData *, 32728743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose SValListTy> LazyBindingsMapTy; 32828743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose LazyBindingsMapTy LazyBindingsMap; 32928743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose 330258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// The largest number of fields a struct can have and still be 331258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// considered "small". 332258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// 333258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// This is currently used to decide whether or not it is worth "forcing" a 334258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// LazyCompoundVal on bind. 335258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// 336258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// This is controlled by 'region-store-small-struct-limit' option. 337258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// To disable all small-struct-dependent behavior, set the option to "0". 338258277d5a922e06ef523f7805900689b680ddc7dJordan Rose unsigned SmallStructLimit; 339258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 340658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks /// \brief A helper used to populate the work list with the given set of 341658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks /// regions. 342658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks void populateWorkList(invalidateRegionsWorker &W, 343658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks ArrayRef<SVal> Values, 344658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks InvalidatedRegions *TopLevelRegions); 345658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks 34628743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rosepublic: 34718c66fdc3c4008d335885695fe36fb5353c5f672Ted Kremenek RegionStoreManager(ProgramStateManager& mgr, const RegionStoreFeatures &f) 3481e934431adba0f459668a59c6059b9596fd627b4Jordan Rose : StoreManager(mgr), Features(f), 349258277d5a922e06ef523f7805900689b680ddc7dJordan Rose RBFactory(mgr.getAllocator()), CBFactory(mgr.getAllocator()), 350258277d5a922e06ef523f7805900689b680ddc7dJordan Rose SmallStructLimit(0) { 351258277d5a922e06ef523f7805900689b680ddc7dJordan Rose if (SubEngine *Eng = StateMgr.getOwningEngine()) { 352258277d5a922e06ef523f7805900689b680ddc7dJordan Rose AnalyzerOptions &Options = Eng->getAnalysisManager().options; 353258277d5a922e06ef523f7805900689b680ddc7dJordan Rose SmallStructLimit = 354258277d5a922e06ef523f7805900689b680ddc7dJordan Rose Options.getOptionAsInteger("region-store-small-struct-limit", 2); 355258277d5a922e06ef523f7805900689b680ddc7dJordan Rose } 356258277d5a922e06ef523f7805900689b680ddc7dJordan Rose } 357178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu 358e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 359027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek /// setImplicitDefaultValue - Set the default binding for the provided 360027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek /// MemRegion to the value implicitly defined for compound literals when 361e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek /// the value is not specified. 36218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef setImplicitDefaultValue(RegionBindingsConstRef B, 36318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const MemRegion *R, QualType T); 3641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 365869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek /// ArrayToPointer - Emulates the "decay" of an array to a pointer 366869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek /// type. 'Array' represents the lvalue of the array being decayed 367869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek /// to a pointer, and the returned SVal represents the decayed 368869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek /// version of that lvalue (i.e., a pointer to the first element of 369d2592a34a059e7cbb2b11dc53649ac4912422909Argyrios Kyrtzidis /// the array). This is called by ExprEngine when evaluating 370869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek /// casts from arrays to pointers. 371651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines SVal ArrayToPointer(Loc Array, QualType ElementTy) override; 372b1d542a46eb71f23dafb5ce60b68247f280beb41Zhongxing Xu 373651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines StoreRef getInitialStore(const LocationContext *InitLoc) override { 37477a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek return StoreRef(RBFactory.getEmptyMap().getRootWithoutRetain(), *this); 37517fd8632dcda97022a51effc24060eacdad9dbe0Zhongxing Xu } 37682cd37cf1cccde162d1f13eda6cdfe1398216f36Ted Kremenek 37767f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek //===-------------------------------------------------------------------===// 37867f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek // Binding values to regions. 37967f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek //===-------------------------------------------------------------------===// 38029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef invalidateGlobalRegion(MemRegion::Kind K, 38129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const Expr *Ex, 38229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek unsigned Count, 38329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const LocationContext *LCtx, 38429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef B, 38529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek InvalidatedRegions *Invalidated); 3864193eca10ce0cc8b2dae887e935a43b26f492b5bZhongxing Xu 387658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks StoreRef invalidateRegions(Store store, 388658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks ArrayRef<SVal> Values, 38977a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek const Expr *E, unsigned Count, 3903133f79cf451e6302dd05262b4bb53a3e4fd6300Ted Kremenek const LocationContext *LCtx, 391740d490593e0de8732a697c9f77b90ddd463863bJordan Rose const CallEvent *Call, 392658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks InvalidatedSymbols &IS, 393da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev RegionAndSymbolInvalidationTraits &ITraits, 394658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks InvalidatedRegions *Invalidated, 395651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines InvalidatedRegions *InvalidatedTopLevel) override; 3961eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 397e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose bool scanReachableSymbols(Store S, const MemRegion *R, 398651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines ScanReachableSymbols &Callbacks) override; 399e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose 40018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef removeSubRegionBindings(RegionBindingsConstRef B, 40129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const SubRegion *R); 4021e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 403e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenekpublic: // Part of public interface to class. 404e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek 405651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines StoreRef Bind(Store store, Loc LV, SVal V) override { 40618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return StoreRef(bind(getRegionBindings(store), LV, V).asStore(), *this); 40718f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek } 40818f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek 40918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef bind(RegionBindingsConstRef B, Loc LV, SVal V); 41053bcdd4fadc022f4a37a929954a72af98f32e91aZhongxing Xu 41154460091f3987cda47a2604b07a9fb4642068ddaZhongxing Xu // BindDefault is only used to initialize a region with a default value. 412651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines StoreRef BindDefault(Store store, const MemRegion *R, SVal V) override { 41329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef B = getRegionBindings(store); 41429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek assert(!B.lookup(R, BindingKey::Direct)); 415d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose 416d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose BindingKey Key = BindingKey::Make(R, BindingKey::Default); 417d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose if (B.lookup(Key)) { 418d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose const SubRegion *SR = cast<SubRegion>(R); 419d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose assert(SR->getAsOffset().getOffset() == 420d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose SR->getSuperRegion()->getAsOffset().getOffset() && 421d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose "A default value must come from a super-region"); 422d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose B = removeSubRegionBindings(B, SR); 423d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose } else { 424d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose B = B.addBinding(Key, V); 425d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose } 426d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose 427d8dfae602d7b2e42b0eef6b1e7779c96833f83c1Jordan Rose return StoreRef(B.asImmutableMap().getRootWithoutRetain(), *this); 428a5ce966d1a23d84aa5e849cf0ed62494e736ea6aZhongxing Xu } 429a5ce966d1a23d84aa5e849cf0ed62494e736ea6aZhongxing Xu 430258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// Attempt to extract the fields of \p LCV and bind them to the struct region 431258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// \p R. 432258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// 433258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// This path is used when it seems advantageous to "force" loading the values 434258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// within a LazyCompoundVal to bind memberwise to the struct region, rather 435258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// than using a Default binding at the base of the entire region. This is a 436258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// heuristic attempting to avoid building long chains of LazyCompoundVals. 437258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// 438258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// \returns The updated store bindings, or \c None if binding non-lazily 439258277d5a922e06ef523f7805900689b680ddc7dJordan Rose /// would be too expensive. 440258277d5a922e06ef523f7805900689b680ddc7dJordan Rose Optional<RegionBindingsRef> tryBindSmallStruct(RegionBindingsConstRef B, 441258277d5a922e06ef523f7805900689b680ddc7dJordan Rose const TypedValueRegion *R, 442258277d5a922e06ef523f7805900689b680ddc7dJordan Rose const RecordDecl *RD, 443258277d5a922e06ef523f7805900689b680ddc7dJordan Rose nonloc::LazyCompoundVal LCV); 444258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 44567f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// BindStruct - Bind a compound value to a structure. 44618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef bindStruct(RegionBindingsConstRef B, 44718f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const TypedValueRegion* R, SVal V); 4481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4498667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek /// BindVector - Bind a compound value to a vector. 45018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef bindVector(RegionBindingsConstRef B, 45118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const TypedValueRegion* R, SVal V); 4528667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek 45318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef bindArray(RegionBindingsConstRef B, 45418f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const TypedValueRegion* R, 45518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal V); 4561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4575ad76c073e1822d11901a8552c6aa9372038b5f0Jordan Rose /// Clears out all bindings in the given region and assigns a new value 4585ad76c073e1822d11901a8552c6aa9372038b5f0Jordan Rose /// as a Default binding. 45918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef bindAggregate(RegionBindingsConstRef B, 46018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const TypedRegion *R, 46118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal DefaultVal); 46224194ef08ef3816d63686e2cac6d42795a015c68Zhongxing Xu 46356a46b51df691f857f7120aaf2d4deeff0b014deTed Kremenek /// \brief Create a new store with the specified binding removed. 464ad0fe03b897f9486191e75c8d90c3ffa9b4fd6a5Ted Kremenek /// \param ST the original store, that is the basis for the new store. 465ad0fe03b897f9486191e75c8d90c3ffa9b4fd6a5Ted Kremenek /// \param L the location whose binding should be removed. 466651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines StoreRef killBinding(Store ST, Loc L) override; 467e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 468651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines void incrementReferenceCount(Store store) override { 46987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar getRegionBindings(store).manualRetain(); 47077a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek } 47187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 47277a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek /// If the StoreManager supports it, decrement the reference count of 47377a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek /// the specified Store object. If the reference count hits 0, the memory 47477a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek /// associated with the object is recycled. 475651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines void decrementReferenceCount(Store store) override { 47629f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek getRegionBindings(store).manualRelease(); 47777a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek } 478651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines 479651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines bool includedInBindings(Store store, const MemRegion *region) const override; 48067f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek 4811437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks /// \brief Return the value bound to specified location in a given state. 4821437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks /// 48367f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// The high level logic for this method is this: 4841437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks /// getBinding (L) 48567f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// if L has binding 48667f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// return L's binding 48767f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// else if L is in killset 48867f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// return unknown 48967f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// else 49067f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// if L is on stack or heap 49167f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// return undefined 49267f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// else 49367f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// return symbolic 494651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines SVal getBinding(Store S, Loc L, QualType T) override { 49518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return getBinding(getRegionBindings(S), L, T); 49618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek } 49718f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek 49818f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal getBinding(RegionBindingsConstRef B, Loc L, QualType T = QualType()); 499490b0f0877b1a6d3caf18abb4ab62ed592e13c4aZhongxing Xu 50018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal getBindingForElement(RegionBindingsConstRef B, const ElementRegion *R); 501c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu 50218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal getBindingForField(RegionBindingsConstRef B, const FieldRegion *R); 5031eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 50418f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal getBindingForObjCIvar(RegionBindingsConstRef B, const ObjCIvarRegion *R); 5051eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 50618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal getBindingForVar(RegionBindingsConstRef B, const VarRegion *R); 5071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5081437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks SVal getBindingForLazySymbol(const TypedValueRegion *R); 5091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 51018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal getBindingForFieldOrElementCommon(RegionBindingsConstRef B, 51118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const TypedValueRegion *R, 512262e0d41e49c6b823d62743535e2accb117a6ea9Jordan Rose QualType Ty); 51387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 51411f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose SVal getLazyBinding(const SubRegion *LazyBindingRegion, 51518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef LazyBinding); 5161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5171437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks /// Get bindings for the values in a struct and return a CompoundVal, used 5181437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks /// when doing struct copy: 5191eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump /// struct s x, y; 5200b242ecdd5755e8662386b528aa0a5153ec0121bZhongxing Xu /// x = y; 5210b242ecdd5755e8662386b528aa0a5153ec0121bZhongxing Xu /// y's value is retrieved by this method. 522978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose SVal getBindingForStruct(RegionBindingsConstRef B, const TypedValueRegion *R); 523978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose SVal getBindingForArray(RegionBindingsConstRef B, const TypedValueRegion *R); 524978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose NonLoc createLazyBinding(RegionBindingsConstRef B, const TypedValueRegion *R); 5251eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 526dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek /// Used to lazily generate derived symbols for bindings that are defined 527deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose /// implicitly by default bindings in a super region. 528deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose /// 529deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose /// Note that callers may need to specially handle LazyCompoundVals, which 530deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose /// are returned as is in case the caller needs to treat them differently. 53118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek Optional<SVal> getBindingForDerivedDefaultValue(RegionBindingsConstRef B, 5321437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks const MemRegion *superR, 5331437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks const TypedValueRegion *R, 5341437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks QualType Ty); 535dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 53665f991ccbec43b4a860f70594c92528ee8fb7c6fJordan Rose /// Get the state and region whose binding this region \p R corresponds to. 53765f991ccbec43b4a860f70594c92528ee8fb7c6fJordan Rose /// 53865f991ccbec43b4a860f70594c92528ee8fb7c6fJordan Rose /// If there is no lazy binding for \p R, the returned value will have a null 53965f991ccbec43b4a860f70594c92528ee8fb7c6fJordan Rose /// \c second. Note that a null pointer can represents a valid Store. 54011f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose std::pair<Store, const SubRegion *> 54111f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose findLazyBinding(RegionBindingsConstRef B, const SubRegion *R, 54211f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose const SubRegion *originalRegion); 5431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 54428743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose /// Returns the cached set of interesting SVals contained within a lazy 54528743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose /// binding. 54628743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose /// 54728743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose /// The precise value of "interesting" is determined for the purposes of 54828743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose /// RegionStore's internal analysis. It must always contain all regions and 54928743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose /// symbols, but may omit constants and other kinds of SVal. 55028743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose const SValListTy &getInterestingValues(nonloc::LazyCompoundVal LCV); 55128743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose 55267f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek //===------------------------------------------------------------------===// 55367f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek // State pruning. 55467f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek //===------------------------------------------------------------------===// 5551eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 556db0594bfc013131f88429add4eb653c285fa94fbTed Kremenek /// removeDeadBindings - Scans the RegionStore of 'state' for dead values. 55767f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek /// It returns a new Store with these values removed. 55877a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek StoreRef removeDeadBindings(Store store, const StackFrameContext *LCtx, 559651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines SymbolReaper& SymReaper) override; 560651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines 56167f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek //===------------------------------------------------------------------===// 56267f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek // Region "extents". 56367f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek //===------------------------------------------------------------------===// 5641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 56532f2656b90900ac04c4b50e87c16749d0ceb9ef2Jordy Rose // FIXME: This method will soon be eliminated; see the note in Store.h. 5668bef8238181a30e52dea380789a7e2d760eac532Ted Kremenek DefinedOrUnknownSVal getSizeInElements(ProgramStateRef state, 567651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines const MemRegion* R, 568651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines QualType EleTy) override; 56963123d8e48d47920f20eb277550ff40a92493e21Zhongxing Xu 57067f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek //===------------------------------------------------------------------===// 5716e3f01cef27dd6cc7e36769618820c5b984f61daZhongxing Xu // Utility methods. 57267f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek //===------------------------------------------------------------------===// 5731eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 57429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef getRegionBindings(Store store) const { 57529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return RegionBindingsRef(CBFactory, 57629f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek static_cast<const RegionBindings::TreeTy*>(store), 57729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RBFactory.getTreeFactory()); 57867f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek } 57967f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek 5809c378f705405d37f49795d5e915989de774fe11fTed Kremenek void print(Store store, raw_ostream &Out, const char* nl, 581651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines const char *sep) override; 582a15f7ac7729b74d1d8bef0c009b803a4bbef20d3Zhongxing Xu 583651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines void iterBindings(Store store, BindingsHandler& f) override { 58429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef B = getRegionBindings(store); 58529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek for (RegionBindingsRef::iterator I = B.begin(), E = B.end(); I != E; ++I) { 5861e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const ClusterBindings &Cluster = I.getData(); 5871e934431adba0f459668a59c6059b9596fd627b4Jordan Rose for (ClusterBindings::iterator CI = Cluster.begin(), CE = Cluster.end(); 5881e934431adba0f459668a59c6059b9596fd627b4Jordan Rose CI != CE; ++CI) { 5891e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const BindingKey &K = CI.getKey(); 5901e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (!K.isDirect()) 5911e934431adba0f459668a59c6059b9596fd627b4Jordan Rose continue; 5921e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (const SubRegion *R = dyn_cast<SubRegion>(K.getRegion())) { 5931e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // FIXME: Possibly incorporate the offset? 5941e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (!f.HandleBinding(*this, store, R, CI.getData())) 5951e934431adba0f459668a59c6059b9596fd627b4Jordan Rose return; 5961e934431adba0f459668a59c6059b9596fd627b4Jordan Rose } 5970e9910f8fe2600187e876adfb5d4b434100850e3Ted Kremenek } 5980e9910f8fe2600187e876adfb5d4b434100850e3Ted Kremenek } 59967f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek } 600178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu}; 601178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu 602178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu} // end anonymous namespace 603178927517fa09ddbb04dc8ef725b5716c18aae21Zhongxing Xu 6049af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 6059af46f59242cfaec74fa491a66724970478263ebTed Kremenek// RegionStore creation. 6069af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 6079af46f59242cfaec74fa491a66724970478263ebTed Kremenek 608176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesstd::unique_ptr<StoreManager> 609176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesento::CreateRegionStoreManager(ProgramStateManager &StMgr) { 6109af46f59242cfaec74fa491a66724970478263ebTed Kremenek RegionStoreFeatures F = maximal_features_tag(); 611176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines return llvm::make_unique<RegionStoreManager>(StMgr, F); 6129af46f59242cfaec74fa491a66724970478263ebTed Kremenek} 6139af46f59242cfaec74fa491a66724970478263ebTed Kremenek 614176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesstd::unique_ptr<StoreManager> 6151437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaksento::CreateFieldsOnlyRegionStoreManager(ProgramStateManager &StMgr) { 6169af46f59242cfaec74fa491a66724970478263ebTed Kremenek RegionStoreFeatures F = minimal_features_tag(); 6179af46f59242cfaec74fa491a66724970478263ebTed Kremenek F.enableFields(true); 618176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines return llvm::make_unique<RegionStoreManager>(StMgr, F); 61995c7b00fe857a61a19185483aa0d85492ec9e258Ted Kremenek} 62095c7b00fe857a61a19185483aa0d85492ec9e258Ted Kremenek 621a5e81f1240bcc5b9b0721fc6275075ad7cadaf5eTed Kremenek 6229af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 623a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek// Region Cluster analysis. 624a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek//===----------------------------------------------------------------------===// 625a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 626a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremeneknamespace { 627e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose/// Used to determine which global regions are automatically included in the 628e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose/// initial worklist of a ClusterAnalysis. 629e0208ff84598f48e0aafecf5b543afeff8574045Jordan Roseenum GlobalsFilterKind { 630e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose /// Don't include any global regions. 631e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose GFK_None, 632e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose /// Only include system globals. 633e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose GFK_SystemOnly, 634e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose /// Include all global regions. 635e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose GFK_All 636e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose}; 637e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose 6385499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenektemplate <typename DERIVED> 639a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenekclass ClusterAnalysis { 640a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenekprotected: 6411e934431adba0f459668a59c6059b9596fd627b4Jordan Rose typedef llvm::DenseMap<const MemRegion *, const ClusterBindings *> ClusterMap; 642da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev typedef const MemRegion * WorkListElement; 643f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose typedef SmallVector<WorkListElement, 10> WorkList; 6441e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 6451e934431adba0f459668a59c6059b9596fd627b4Jordan Rose llvm::SmallPtrSet<const ClusterBindings *, 16> Visited; 6461e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 6475499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek WorkList WL; 648a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 649a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek RegionStoreManager &RM; 650a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek ASTContext &Ctx; 651c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek SValBuilder &svalBuilder; 652a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 65329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef B; 6545499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 655e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose 656e0208ff84598f48e0aafecf5b543afeff8574045Jordan Roseprotected: 6571e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const ClusterBindings *getCluster(const MemRegion *R) { 6581e934431adba0f459668a59c6059b9596fd627b4Jordan Rose return B.lookup(R); 6591e934431adba0f459668a59c6059b9596fd627b4Jordan Rose } 6601e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 66187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar /// Returns true if all clusters in the given memspace should be initially 66287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar /// included in the cluster analysis. Subclasses may provide their 66387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar /// own implementation. 66487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar bool includeEntireMemorySpace(const MemRegion *Base) { 66587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return false; 666e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose } 667e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose 668a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenekpublic: 66918c66fdc3c4008d335885695fe36fb5353c5f672Ted Kremenek ClusterAnalysis(RegionStoreManager &rm, ProgramStateManager &StateMgr, 6704967a710c84587c654b56c828382219c3937dacbPirama Arumuga Nainar RegionBindingsRef b) 6714967a710c84587c654b56c828382219c3937dacbPirama Arumuga Nainar : RM(rm), Ctx(StateMgr.getContext()), 6724967a710c84587c654b56c828382219c3937dacbPirama Arumuga Nainar svalBuilder(StateMgr.getSValBuilder()), B(std::move(b)) {} 6735499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 67429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef getRegionBindings() const { return B; } 6755499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 6765499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek bool isVisited(const MemRegion *R) { 6771e934431adba0f459668a59c6059b9596fd627b4Jordan Rose return Visited.count(getCluster(R)); 6785499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek } 679a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 680d45d59f4aebfe6399437074ed5391928c73993bbTed Kremenek void GenerateClusters() { 6811e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // Scan the entire set of bindings and record the region clusters. 68229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek for (RegionBindingsRef::iterator RI = B.begin(), RE = B.end(); 68329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RI != RE; ++RI){ 6841e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const MemRegion *Base = RI.getKey(); 6851e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 6861e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const ClusterBindings &Cluster = RI.getData(); 6871e934431adba0f459668a59c6059b9596fd627b4Jordan Rose assert(!Cluster.isEmpty() && "Empty clusters should be removed"); 6881e934431adba0f459668a59c6059b9596fd627b4Jordan Rose static_cast<DERIVED*>(this)->VisitAddedToCluster(Base, Cluster); 6891e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 69087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // If the base's memspace should be entirely invalidated, add the cluster 69187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // to the workspace up front. 69287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (static_cast<DERIVED*>(this)->includeEntireMemorySpace(Base)) 693e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose AddToWorkList(WorkListElement(Base), &Cluster); 6945499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek } 6955499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek } 6965499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 697f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose bool AddToWorkList(WorkListElement E, const ClusterBindings *C) { 698176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines if (C && !Visited.insert(C).second) 699ab9c04fda542d096c667d6a3746d94c884f80e7bTed Kremenek return false; 700f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose WL.push_back(E); 7015499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return true; 702a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek } 703a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 704da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev bool AddToWorkList(const MemRegion *R) { 70587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return static_cast<DERIVED*>(this)->AddToWorkList(R); 7065499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek } 7075499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 7085499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek void RunWorkList() { 7095499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek while (!WL.empty()) { 710f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose WorkListElement E = WL.pop_back_val(); 711da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev const MemRegion *BaseR = E; 7125499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 713da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev static_cast<DERIVED*>(this)->VisitCluster(BaseR, getCluster(BaseR)); 714a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek } 715a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek } 7165499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 7171e934431adba0f459668a59c6059b9596fd627b4Jordan Rose void VisitAddedToCluster(const MemRegion *baseR, const ClusterBindings &C) {} 718f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose void VisitCluster(const MemRegion *baseR, const ClusterBindings *C) {} 719f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose 720f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose void VisitCluster(const MemRegion *BaseR, const ClusterBindings *C, 721f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose bool Flag) { 722f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose static_cast<DERIVED*>(this)->VisitCluster(BaseR, C); 723f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose } 7245499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek}; 725a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek} 726a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 727a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek//===----------------------------------------------------------------------===// 7281004a9f2b9eaf885e55ad8656194ef2a341db0f5Ted Kremenek// Binding invalidation. 7291004a9f2b9eaf885e55ad8656194ef2a341db0f5Ted Kremenek//===----------------------------------------------------------------------===// 7301004a9f2b9eaf885e55ad8656194ef2a341db0f5Ted Kremenek 731e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rosebool RegionStoreManager::scanReachableSymbols(Store S, const MemRegion *R, 732e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose ScanReachableSymbols &Callbacks) { 7331e934431adba0f459668a59c6059b9596fd627b4Jordan Rose assert(R == R->getBaseRegion() && "Should only be called for base regions"); 73429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef B = getRegionBindings(S); 7351e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const ClusterBindings *Cluster = B.lookup(R); 7361e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 7371e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (!Cluster) 7381e934431adba0f459668a59c6059b9596fd627b4Jordan Rose return true; 7391e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 7401e934431adba0f459668a59c6059b9596fd627b4Jordan Rose for (ClusterBindings::iterator RI = Cluster->begin(), RE = Cluster->end(); 7411e934431adba0f459668a59c6059b9596fd627b4Jordan Rose RI != RE; ++RI) { 7421e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (!Callbacks.scan(RI.getData())) 7431e934431adba0f459668a59c6059b9596fd627b4Jordan Rose return false; 744e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose } 745a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 746e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose return true; 747e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose} 748e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose 7494e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rosestatic inline bool isUnionField(const FieldRegion *FR) { 7504e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose return FR->getDecl()->getParent()->isUnion(); 7514e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose} 7524e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 7534e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rosetypedef SmallVector<const FieldDecl *, 8> FieldVector; 7544e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 7553ea9e33ea25e0c2b12db56418ba3f994eb662c04Pirama Arumuga Nainarstatic void getSymbolicOffsetFields(BindingKey K, FieldVector &Fields) { 7564e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose assert(K.hasSymbolicOffset() && "Not implemented for concrete offset keys"); 7574e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 7584e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose const MemRegion *Base = K.getConcreteOffsetRegion(); 7594e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose const MemRegion *R = K.getRegion(); 7604e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 7614e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose while (R != Base) { 7624e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose if (const FieldRegion *FR = dyn_cast<FieldRegion>(R)) 7634e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose if (!isUnionField(FR)) 7644e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose Fields.push_back(FR->getDecl()); 7654e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 7664e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose R = cast<SubRegion>(R)->getSuperRegion(); 7674e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose } 7684e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose} 7694e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 7704e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rosestatic bool isCompatibleWithFields(BindingKey K, const FieldVector &Fields) { 7714e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose assert(K.hasSymbolicOffset() && "Not implemented for concrete offset keys"); 7724e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 7734e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose if (Fields.empty()) 7744e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose return true; 7754e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 7764e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose FieldVector FieldsInBindingKey; 7774e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose getSymbolicOffsetFields(K, FieldsInBindingKey); 7784e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 7794e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose ptrdiff_t Delta = FieldsInBindingKey.size() - Fields.size(); 7804e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose if (Delta >= 0) 7814e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose return std::equal(FieldsInBindingKey.begin() + Delta, 7824e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose FieldsInBindingKey.end(), 7834e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose Fields.begin()); 7844e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose else 7854e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose return std::equal(FieldsInBindingKey.begin(), FieldsInBindingKey.end(), 7864e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose Fields.begin() - Delta); 7874e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose} 7884e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 789e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose/// Collects all bindings in \p Cluster that may refer to bindings within 790e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose/// \p Top. 791e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose/// 792e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose/// Each binding is a pair whose \c first is the key (a BindingKey) and whose 793e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose/// \c second is the value (an SVal). 7940a0f1309d0fbeb0e77edbbc4e0b15cc330c3a28cJordan Rose/// 7950a0f1309d0fbeb0e77edbbc4e0b15cc330c3a28cJordan Rose/// The \p IncludeAllDefaultBindings parameter specifies whether to include 7960a0f1309d0fbeb0e77edbbc4e0b15cc330c3a28cJordan Rose/// default bindings that may extend beyond \p Top itself, e.g. if \p Top is 7970a0f1309d0fbeb0e77edbbc4e0b15cc330c3a28cJordan Rose/// an aggregate within a larger aggregate with a default binding. 798e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rosestatic void 799e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan RosecollectSubRegionBindings(SmallVectorImpl<BindingPair> &Bindings, 800e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose SValBuilder &SVB, const ClusterBindings &Cluster, 801e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose const SubRegion *Top, BindingKey TopKey, 802e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose bool IncludeAllDefaultBindings) { 8034e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose FieldVector FieldsInSymbolicSubregions; 8049d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose if (TopKey.hasSymbolicOffset()) { 8059d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose getSymbolicOffsetFields(TopKey, FieldsInSymbolicSubregions); 8069d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose Top = cast<SubRegion>(TopKey.getConcreteOffsetRegion()); 8079d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose TopKey = BindingKey::Make(Top, BindingKey::Default); 808e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose } 809e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose 810d764e20189dbb42b38ada383a0a159f6adc0d56cJordan Rose // Find the length (in bits) of the region being invalidated. 811e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose uint64_t Length = UINT64_MAX; 8129d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose SVal Extent = Top->getExtent(SVB); 813dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie if (Optional<nonloc::ConcreteInt> ExtentCI = 8145251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie Extent.getAs<nonloc::ConcreteInt>()) { 815e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose const llvm::APSInt &ExtentInt = ExtentCI->getValue(); 816e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose assert(ExtentInt.isNonNegative() || ExtentInt.isUnsigned()); 817e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose // Extents are in bytes but region offsets are in bits. Be careful! 8189d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose Length = ExtentInt.getLimitedValue() * SVB.getContext().getCharWidth(); 819d764e20189dbb42b38ada383a0a159f6adc0d56cJordan Rose } else if (const FieldRegion *FR = dyn_cast<FieldRegion>(Top)) { 820d764e20189dbb42b38ada383a0a159f6adc0d56cJordan Rose if (FR->getDecl()->isBitField()) 821d764e20189dbb42b38ada383a0a159f6adc0d56cJordan Rose Length = FR->getDecl()->getBitWidthValue(SVB.getContext()); 822e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose } 823e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose 8249d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose for (ClusterBindings::iterator I = Cluster.begin(), E = Cluster.end(); 8251e934431adba0f459668a59c6059b9596fd627b4Jordan Rose I != E; ++I) { 8261e934431adba0f459668a59c6059b9596fd627b4Jordan Rose BindingKey NextKey = I.getKey(); 8279d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose if (NextKey.getRegion() == TopKey.getRegion()) { 8284e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose // FIXME: This doesn't catch the case where we're really invalidating a 8294e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose // region with a symbolic offset. Example: 8304e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose // R: points[i].y 8314e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose // Next: points[0].x 8324e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 8339d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose if (NextKey.getOffset() > TopKey.getOffset() && 8349d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose NextKey.getOffset() - TopKey.getOffset() < Length) { 8351e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // Case 1: The next binding is inside the region we're invalidating. 836e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose // Include it. 837e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose Bindings.push_back(*I); 8384e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 8399d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose } else if (NextKey.getOffset() == TopKey.getOffset()) { 8401e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // Case 2: The next binding is at the same offset as the region we're 8411e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // invalidating. In this case, we need to leave default bindings alone, 8421e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // since they may be providing a default value for a regions beyond what 8431e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // we're invalidating. 8441e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // FIXME: This is probably incorrect; consider invalidating an outer 8451e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // struct whose first field is bound to a LazyCompoundVal. 8460a0f1309d0fbeb0e77edbbc4e0b15cc330c3a28cJordan Rose if (IncludeAllDefaultBindings || NextKey.isDirect()) 847e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose Bindings.push_back(*I); 8481e934431adba0f459668a59c6059b9596fd627b4Jordan Rose } 8499d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose 850e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose } else if (NextKey.hasSymbolicOffset()) { 851e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose const MemRegion *Base = NextKey.getConcreteOffsetRegion(); 8529d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose if (Top->isSubRegionOf(Base)) { 8531e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // Case 3: The next key is symbolic and we just changed something within 8541e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // its concrete region. We don't know if the binding is still valid, so 855e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose // we'll be conservative and include it. 8560a0f1309d0fbeb0e77edbbc4e0b15cc330c3a28cJordan Rose if (IncludeAllDefaultBindings || NextKey.isDirect()) 8574e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose if (isCompatibleWithFields(NextKey, FieldsInSymbolicSubregions)) 858e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose Bindings.push_back(*I); 8591e934431adba0f459668a59c6059b9596fd627b4Jordan Rose } else if (const SubRegion *BaseSR = dyn_cast<SubRegion>(Base)) { 8601e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // Case 4: The next key is symbolic, but we changed a known 861e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose // super-region. In this case the binding is certainly included. 8629d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose if (Top == Base || BaseSR->isSubRegionOf(Top)) 8634e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose if (isCompatibleWithFields(NextKey, FieldsInSymbolicSubregions)) 864e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose Bindings.push_back(*I); 8651e934431adba0f459668a59c6059b9596fd627b4Jordan Rose } 866e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose } 867e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose } 8689d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose} 8699d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose 870e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rosestatic void 871e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan RosecollectSubRegionBindings(SmallVectorImpl<BindingPair> &Bindings, 872e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose SValBuilder &SVB, const ClusterBindings &Cluster, 873e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose const SubRegion *Top, bool IncludeAllDefaultBindings) { 874e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose collectSubRegionBindings(Bindings, SVB, Cluster, Top, 875e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose BindingKey::Make(Top, BindingKey::Default), 876e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose IncludeAllDefaultBindings); 8770a0f1309d0fbeb0e77edbbc4e0b15cc330c3a28cJordan Rose} 8780a0f1309d0fbeb0e77edbbc4e0b15cc330c3a28cJordan Rose 8799d688e219caa37e60975ec8d5bebe74a176c9c2bJordan RoseRegionBindingsRef 8809d688e219caa37e60975ec8d5bebe74a176c9c2bJordan RoseRegionStoreManager::removeSubRegionBindings(RegionBindingsConstRef B, 8819d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose const SubRegion *Top) { 8829d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose BindingKey TopKey = BindingKey::Make(Top, BindingKey::Default); 8839d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose const MemRegion *ClusterHead = TopKey.getBaseRegion(); 8845db8fac5f304d9973f724d5aeb4108367d36f781Anna Zaks 8859d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose if (Top == ClusterHead) { 8869d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose // We can remove an entire cluster's bindings all in one go. 8879d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose return B.remove(Top); 8889d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose } 8899d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose 890df5f80f8a34e26a4fb77f48f858c7838426a0785Anna Zaks const ClusterBindings *Cluster = B.lookup(ClusterHead); 8915db8fac5f304d9973f724d5aeb4108367d36f781Anna Zaks if (!Cluster) { 8925db8fac5f304d9973f724d5aeb4108367d36f781Anna Zaks // If we're invalidating a region with a symbolic offset, we need to make 8935db8fac5f304d9973f724d5aeb4108367d36f781Anna Zaks // sure we don't treat the base region as uninitialized anymore. 8945db8fac5f304d9973f724d5aeb4108367d36f781Anna Zaks if (TopKey.hasSymbolicOffset()) { 8955db8fac5f304d9973f724d5aeb4108367d36f781Anna Zaks const SubRegion *Concrete = TopKey.getConcreteOffsetRegion(); 8965db8fac5f304d9973f724d5aeb4108367d36f781Anna Zaks return B.addBinding(Concrete, BindingKey::Default, UnknownVal()); 8975db8fac5f304d9973f724d5aeb4108367d36f781Anna Zaks } 8989d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose return B; 8995db8fac5f304d9973f724d5aeb4108367d36f781Anna Zaks } 9009d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose 901e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose SmallVector<BindingPair, 32> Bindings; 902e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose collectSubRegionBindings(Bindings, svalBuilder, *Cluster, Top, TopKey, 903e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose /*IncludeAllDefaultBindings=*/false); 9049d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose 9059d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose ClusterBindingsRef Result(*Cluster, CBFactory); 906e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose for (SmallVectorImpl<BindingPair>::const_iterator I = Bindings.begin(), 907e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose E = Bindings.end(); 9089d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose I != E; ++I) 909e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose Result = Result.remove(I->first); 910e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose 9114e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose // If we're invalidating a region with a symbolic offset, we need to make sure 9124e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose // we don't treat the base region as uninitialized anymore. 913683d25656f28937f78c815f70545139c432f1ff3Anna Zaks // FIXME: This isn't very precise; see the example in 914683d25656f28937f78c815f70545139c432f1ff3Anna Zaks // collectSubRegionBindings. 9159d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose if (TopKey.hasSymbolicOffset()) { 9169d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose const SubRegion *Concrete = TopKey.getConcreteOffsetRegion(); 9179d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose Result = Result.add(BindingKey::Make(Concrete, BindingKey::Default), 9189d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose UnknownVal()); 9199d688e219caa37e60975ec8d5bebe74a176c9c2bJordan Rose } 9204e674f77150b52d8e6ae82faf64fbdac79d675d3Jordan Rose 92114491490a5276ff4da9b28100fb8e7d442944288Ted Kremenek if (Result.isEmpty()) 92229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return B.remove(ClusterHead); 92323dca7d88f3e9a7925bfb2c5449499900c906633Ted Kremenek return B.add(ClusterHead, Result.asImmutableMap()); 92419e1f0ba5cec738ce6cebe3fe0e1edc782206494Ted Kremenek} 92519e1f0ba5cec738ce6cebe3fe0e1edc782206494Ted Kremenek 926e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremeneknamespace { 9272534528c22260211a073e192c38d0db84c70c327Ted Kremenekclass invalidateRegionsWorker : public ClusterAnalysis<invalidateRegionsWorker> 9285499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek{ 9295499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek const Expr *Ex; 9305499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek unsigned Count; 9313133f79cf451e6302dd05262b4bb53a3e4fd6300Ted Kremenek const LocationContext *LCtx; 932bf53dfac8195835028bd6347433f7dbebcc29fc1Anna Zaks InvalidatedSymbols &IS; 933da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev RegionAndSymbolInvalidationTraits &ITraits; 934c2b7dfaad674587cfd220ff447b3710d252130c3Jordy Rose StoreManager::InvalidatedRegions *Regions; 93587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar GlobalsFilterKind GlobalsFilter; 936e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenekpublic: 9372534528c22260211a073e192c38d0db84c70c327Ted Kremenek invalidateRegionsWorker(RegionStoreManager &rm, 93818c66fdc3c4008d335885695fe36fb5353c5f672Ted Kremenek ProgramStateManager &stateMgr, 93929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef b, 9405499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek const Expr *ex, unsigned count, 9413133f79cf451e6302dd05262b4bb53a3e4fd6300Ted Kremenek const LocationContext *lctx, 942bf53dfac8195835028bd6347433f7dbebcc29fc1Anna Zaks InvalidatedSymbols &is, 943da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev RegionAndSymbolInvalidationTraits &ITraitsIn, 944d45d59f4aebfe6399437074ed5391928c73993bbTed Kremenek StoreManager::InvalidatedRegions *r, 945e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose GlobalsFilterKind GFK) 94687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar : ClusterAnalysis<invalidateRegionsWorker>(rm, stateMgr, b), 94787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar Ex(ex), Count(count), LCtx(lctx), IS(is), ITraits(ITraitsIn), Regions(r), 94887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar GlobalsFilter(GFK) {} 949a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 950da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev void VisitCluster(const MemRegion *baseR, const ClusterBindings *C); 951c1ddcabef0b0e1185b6ea35d64a1ff41dabd7626Ted Kremenek void VisitBinding(SVal V); 95287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 95387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar using ClusterAnalysis::AddToWorkList; 95487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 95587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar bool AddToWorkList(const MemRegion *R); 95687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 95787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar /// Returns true if all clusters in the memory space for \p Base should be 95887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar /// be invalidated. 95987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar bool includeEntireMemorySpace(const MemRegion *Base); 96087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 96187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar /// Returns true if the memory space of the given region is one of the global 96287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar /// regions specially included at the start of invalidation. 96387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar bool isInitiallyIncludedGlobalRegion(const MemRegion *R); 964a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek}; 9655b290658c5af4cc186fe556311db2bfbb316c00aTed Kremenek} 9665b290658c5af4cc186fe556311db2bfbb316c00aTed Kremenek 96787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainarbool invalidateRegionsWorker::AddToWorkList(const MemRegion *R) { 96887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar bool doNotInvalidateSuperRegion = ITraits.hasTrait( 96987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar R, RegionAndSymbolInvalidationTraits::TK_DoNotInvalidateSuperRegion); 97087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar const MemRegion *BaseR = doNotInvalidateSuperRegion ? R : R->getBaseRegion(); 97187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return AddToWorkList(WorkListElement(BaseR), getCluster(BaseR)); 97287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar} 97387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 9742534528c22260211a073e192c38d0db84c70c327Ted Kremenekvoid invalidateRegionsWorker::VisitBinding(SVal V) { 975c1ddcabef0b0e1185b6ea35d64a1ff41dabd7626Ted Kremenek // A symbol? Mark it touched by the invalidation. 97635bdbf40624beba3fc00cb72ab444659939c1a6bTed Kremenek if (SymbolRef Sym = V.getAsSymbol()) 97735bdbf40624beba3fc00cb72ab444659939c1a6bTed Kremenek IS.insert(Sym); 978a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 97924c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek if (const MemRegion *R = V.getAsRegion()) { 98024c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek AddToWorkList(R); 98124c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek return; 98224c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek } 98324c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek 98424c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek // Is it a LazyCompoundVal? All references get invalidated as well. 985dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie if (Optional<nonloc::LazyCompoundVal> LCS = 9865251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie V.getAs<nonloc::LazyCompoundVal>()) { 98724c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek 98828743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose const RegionStoreManager::SValListTy &Vals = RM.getInterestingValues(*LCS); 98924c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek 99028743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose for (RegionStoreManager::SValListTy::const_iterator I = Vals.begin(), 99128743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose E = Vals.end(); 99228743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose I != E; ++I) 99328743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose VisitBinding(*I); 99424c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek 99524c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek return; 99624c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek } 99724c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek} 99824c37ad067320e9d40978d97a73e4bca0f0eae54Ted Kremenek 999f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rosevoid invalidateRegionsWorker::VisitCluster(const MemRegion *baseR, 1000da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev const ClusterBindings *C) { 1001da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev 100287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar bool PreserveRegionsContents = 100387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar ITraits.hasTrait(baseR, 1004da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev RegionAndSymbolInvalidationTraits::TK_PreserveContents); 1005da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev 1006f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose if (C) { 1007f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose for (ClusterBindings::iterator I = C->begin(), E = C->end(); I != E; ++I) 1008f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose VisitBinding(I.getData()); 10095b290658c5af4cc186fe556311db2bfbb316c00aTed Kremenek 1010da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev // Invalidate regions contents. 1011da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev if (!PreserveRegionsContents) 1012f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose B = B.remove(baseR); 1013f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose } 1014a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 10155499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // BlockDataRegion? If so, invalidate captured variables that are passed 10165499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // by reference. 10175499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek if (const BlockDataRegion *BR = dyn_cast<BlockDataRegion>(baseR)) { 10185499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek for (BlockDataRegion::referenced_vars_iterator 10195499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek BI = BR->referenced_vars_begin(), BE = BR->referenced_vars_end() ; 10205499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek BI != BE; ++BI) { 1021e3ce2c10c3f6ae7b26700d758de909deab190d42Ted Kremenek const VarRegion *VR = BI.getCapturedRegion(); 10225499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek const VarDecl *VD = VR->getDecl(); 1023651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines if (VD->hasAttr<BlocksAttr>() || !VD->hasLocalStorage()) { 10245499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek AddToWorkList(VR); 102585d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek } 102685d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek else if (Loc::isLocType(VR->getValueType())) { 102785d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek // Map the current bindings to a Store to retrieve the value 102885d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek // of the binding. If that binding itself is a region, we should 102985d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek // invalidate that region. This is because a block may capture 103085d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek // a pointer value, but the thing pointed by that pointer may 103185d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek // get invalidated. 103218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal V = RM.getBinding(B, loc::MemRegionVal(VR)); 1033dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie if (Optional<Loc> L = V.getAs<Loc>()) { 103485d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek if (const MemRegion *LR = L->getAsRegion()) 103585d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek AddToWorkList(LR); 103685d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek } 103785d87df66a50a15a1957f7213802000b451a8ec9Ted Kremenek } 10385b290658c5af4cc186fe556311db2bfbb316c00aTed Kremenek } 10395499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return; 10405499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek } 1041a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 104241988f331a74a72cf243a2a68ffb56418e9a174eAnna Zaks // Symbolic region? 1043da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev if (const SymbolicRegion *SR = dyn_cast<SymbolicRegion>(baseR)) 1044da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev IS.insert(SR->getSymbol()); 1045e0262e25206bef1d7efb0cb2f37abd1e42ada4cbAnton Yartsev 1046da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev // Nothing else should be done in the case when we preserve regions context. 1047da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev if (PreserveRegionsContents) 1048e0262e25206bef1d7efb0cb2f37abd1e42ada4cbAnton Yartsev return; 1049f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose 1050c2b7dfaad674587cfd220ff447b3710d252130c3Jordy Rose // Otherwise, we have a normal data region. Record that we touched the region. 1051c2b7dfaad674587cfd220ff447b3710d252130c3Jordy Rose if (Regions) 1052c2b7dfaad674587cfd220ff447b3710d252130c3Jordy Rose Regions->push_back(baseR); 1053c2b7dfaad674587cfd220ff447b3710d252130c3Jordy Rose 10545499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek if (isa<AllocaRegion>(baseR) || isa<SymbolicRegion>(baseR)) { 10555499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // Invalidate the region by setting its default value to 1056da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev // conjured symbol. The type of the symbol is irrelevant. 10573baf672378f105602d2b12f03f00277ae1936fe9Ted Kremenek DefinedOrUnknownSVal V = 10583b1df8bb941a18c4a7256d7cfcbccb9de7e39995Ted Kremenek svalBuilder.conjureSymbolVal(baseR, Ex, LCtx, Ctx.IntTy, Count); 105929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek B = B.addBinding(baseR, BindingKey::Default, V); 10605499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return; 10615499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek } 1062a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 10635499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek if (!baseR->isBoundable()) 10645499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return; 1065a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 10669697934650354bed2e509d8e7e44f21a1fb00f76Ted Kremenek const TypedValueRegion *TR = cast<TypedValueRegion>(baseR); 1067018220c343c103b7dfaa117a7a474c7a7fd6d068Zhongxing Xu QualType T = TR->getValueType(); 1068a4fab03fa3efd32f0c21d5dd721fe88b827c7716Ted Kremenek 1069b93fc8ebed158ed5516fd85d11e89fffaf80622bJordan Rose if (isInitiallyIncludedGlobalRegion(baseR)) { 1070b93fc8ebed158ed5516fd85d11e89fffaf80622bJordan Rose // If the region is a global and we are invalidating all globals, 1071b93fc8ebed158ed5516fd85d11e89fffaf80622bJordan Rose // erasing the entry is good enough. This causes all globals to be lazily 1072b93fc8ebed158ed5516fd85d11e89fffaf80622bJordan Rose // symbolicated from the same base symbol. 1073b93fc8ebed158ed5516fd85d11e89fffaf80622bJordan Rose return; 1074b93fc8ebed158ed5516fd85d11e89fffaf80622bJordan Rose } 1075b93fc8ebed158ed5516fd85d11e89fffaf80622bJordan Rose 1076bf1a66764a12f6cceb6ba8b349d4b74996e3786bTed Kremenek if (T->isStructureOrClassType()) { 10770b46b1bc647db68ed3511b53e96699cfe14658fdZhongxing Xu // Invalidate the region by setting its default value to 1078da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev // conjured symbol. The type of the symbol is irrelevant. 10793b1df8bb941a18c4a7256d7cfcbccb9de7e39995Ted Kremenek DefinedOrUnknownSVal V = svalBuilder.conjureSymbolVal(baseR, Ex, LCtx, 10803b1df8bb941a18c4a7256d7cfcbccb9de7e39995Ted Kremenek Ctx.IntTy, Count); 108129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek B = B.addBinding(baseR, BindingKey::Default, V); 10825499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return; 10835499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek } 10845b290658c5af4cc186fe556311db2bfbb316c00aTed Kremenek 10855499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek if (const ArrayType *AT = Ctx.getAsArrayType(T)) { 108687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar bool doNotInvalidateSuperRegion = ITraits.hasTrait( 108787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar baseR, 108887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar RegionAndSymbolInvalidationTraits::TK_DoNotInvalidateSuperRegion); 108987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 109087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (doNotInvalidateSuperRegion) { 109187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // We are not doing blank invalidation of the whole array region so we 109287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // have to manually invalidate each elements. 109387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar Optional<uint64_t> NumElements; 109487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 109587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // Compute lower and upper offsets for region within array. 109687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (const ConstantArrayType *CAT = dyn_cast<ConstantArrayType>(AT)) 109787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar NumElements = CAT->getSize().getZExtValue(); 109887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (!NumElements) // We are not dealing with a constant size array 109987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar goto conjure_default; 110087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar QualType ElementTy = AT->getElementType(); 110187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar uint64_t ElemSize = Ctx.getTypeSize(ElementTy); 110287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar const RegionOffset &RO = baseR->getAsOffset(); 110387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar const MemRegion *SuperR = baseR->getBaseRegion(); 110487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (RO.hasSymbolicOffset()) { 110587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // If base region has a symbolic offset, 110687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // we revert to invalidating the super region. 110787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (SuperR) 110887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar AddToWorkList(SuperR); 110987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar goto conjure_default; 111087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar } 111187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 111287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar uint64_t LowerOffset = RO.getOffset(); 111387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar uint64_t UpperOffset = LowerOffset + *NumElements * ElemSize; 111487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar bool UpperOverflow = UpperOffset < LowerOffset; 111587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 111687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // Invalidate regions which are within array boundaries, 111787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // or have a symbolic offset. 111887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (!SuperR) 111987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar goto conjure_default; 112087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 112187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar const ClusterBindings *C = B.lookup(SuperR); 112287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (!C) 112387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar goto conjure_default; 112487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 112587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar for (ClusterBindings::iterator I = C->begin(), E = C->end(); I != E; 112687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar ++I) { 112787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar const BindingKey &BK = I.getKey(); 112887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar Optional<uint64_t> ROffset = 112987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar BK.hasSymbolicOffset() ? Optional<uint64_t>() : BK.getOffset(); 113087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 113187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // Check offset is not symbolic and within array's boundaries. 113287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // Handles arrays of 0 elements and of 0-sized elements as well. 113387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (!ROffset || 11344967a710c84587c654b56c828382219c3937dacbPirama Arumuga Nainar ((*ROffset >= LowerOffset && *ROffset < UpperOffset) || 11354967a710c84587c654b56c828382219c3937dacbPirama Arumuga Nainar (UpperOverflow && 11364967a710c84587c654b56c828382219c3937dacbPirama Arumuga Nainar (*ROffset >= LowerOffset || *ROffset < UpperOffset)) || 11374967a710c84587c654b56c828382219c3937dacbPirama Arumuga Nainar (LowerOffset == UpperOffset && *ROffset == LowerOffset))) { 113887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar B = B.removeBinding(I.getKey()); 113987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // Bound symbolic regions need to be invalidated for dead symbol 114087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // detection. 114187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar SVal V = I.getData(); 114287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar const MemRegion *R = V.getAsRegion(); 114387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (R && isa<SymbolicRegion>(R)) 114487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar VisitBinding(V); 114587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar } 114687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar } 114787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar } 114887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar conjure_default: 11495b290658c5af4cc186fe556311db2bfbb316c00aTed Kremenek // Set the default value of the array to conjured symbol. 11505499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek DefinedOrUnknownSVal V = 11513b1df8bb941a18c4a7256d7cfcbccb9de7e39995Ted Kremenek svalBuilder.conjureSymbolVal(baseR, Ex, LCtx, 11523133f79cf451e6302dd05262b4bb53a3e4fd6300Ted Kremenek AT->getElementType(), Count); 115329f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek B = B.addBinding(baseR, BindingKey::Default, V); 11545499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return; 11551004a9f2b9eaf885e55ad8656194ef2a341db0f5Ted Kremenek } 11561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 11573b1df8bb941a18c4a7256d7cfcbccb9de7e39995Ted Kremenek DefinedOrUnknownSVal V = svalBuilder.conjureSymbolVal(baseR, Ex, LCtx, 11583b1df8bb941a18c4a7256d7cfcbccb9de7e39995Ted Kremenek T,Count); 11595499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek assert(SymbolManager::canSymbolicate(T) || V.isUnknown()); 116029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek B = B.addBinding(baseR, BindingKey::Direct, V); 11611004a9f2b9eaf885e55ad8656194ef2a341db0f5Ted Kremenek} 11621004a9f2b9eaf885e55ad8656194ef2a341db0f5Ted Kremenek 116387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainarbool invalidateRegionsWorker::isInitiallyIncludedGlobalRegion( 116487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar const MemRegion *R) { 116587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar switch (GlobalsFilter) { 116687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar case GFK_None: 116787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return false; 116887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar case GFK_SystemOnly: 116987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return isa<GlobalSystemSpaceRegion>(R->getMemorySpace()); 117087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar case GFK_All: 117187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return isa<NonStaticGlobalSpaceRegion>(R->getMemorySpace()); 117287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar } 117387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 117487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar llvm_unreachable("unknown globals filter"); 117587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar} 117687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 117787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainarbool invalidateRegionsWorker::includeEntireMemorySpace(const MemRegion *Base) { 117887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (isInitiallyIncludedGlobalRegion(Base)) 117987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return true; 118087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 118187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar const MemSpaceRegion *MemSpace = Base->getMemorySpace(); 118287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return ITraits.hasTrait(MemSpace, 118387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar RegionAndSymbolInvalidationTraits::TK_EntireMemSpace); 118487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar} 118587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 118629f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted KremenekRegionBindingsRef 118729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted KremenekRegionStoreManager::invalidateGlobalRegion(MemRegion::Kind K, 118829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const Expr *Ex, 118929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek unsigned Count, 119029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const LocationContext *LCtx, 119129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef B, 119229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek InvalidatedRegions *Invalidated) { 1193eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks // Bind the globals memory space to a new symbol that we will use to derive 1194eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks // the bindings for all globals. 1195eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks const GlobalsSpaceRegion *GS = MRMgr.getGlobalsRegion(K); 119631ba6135375433b617a8587ea6cc836a014ebd86Roman Divacky SVal V = svalBuilder.conjureSymbolVal(/* SymbolTag = */ (const void*) GS, Ex, LCtx, 11973b1df8bb941a18c4a7256d7cfcbccb9de7e39995Ted Kremenek /* type does not matter */ Ctx.IntTy, 11983b1df8bb941a18c4a7256d7cfcbccb9de7e39995Ted Kremenek Count); 1199eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks 120029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek B = B.removeBinding(GS) 120129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek .addBinding(BindingKey::Make(GS, BindingKey::Default), V); 1202eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks 1203eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks // Even if there are no bindings in the global scope, we still need to 1204eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks // record that we touched it. 1205eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks if (Invalidated) 1206eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks Invalidated->push_back(GS); 1207eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks 1208eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks return B; 1209eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks} 1210eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks 1211658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaksvoid RegionStoreManager::populateWorkList(invalidateRegionsWorker &W, 1212658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks ArrayRef<SVal> Values, 1213658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks InvalidatedRegions *TopLevelRegions) { 1214658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks for (ArrayRef<SVal>::iterator I = Values.begin(), 1215658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks E = Values.end(); I != E; ++I) { 1216658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks SVal V = *I; 1217658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks if (Optional<nonloc::LazyCompoundVal> LCS = 1218658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks V.getAs<nonloc::LazyCompoundVal>()) { 1219658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks 1220658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks const SValListTy &Vals = getInterestingValues(*LCS); 1221658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks 1222658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks for (SValListTy::const_iterator I = Vals.begin(), 1223658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks E = Vals.end(); I != E; ++I) { 12243d3fb9078f0112fa51d8d9862221f5544c5c80e7Anna Zaks // Note: the last argument is false here because these are 1225658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks // non-top-level regions. 1226658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks if (const MemRegion *R = (*I).getAsRegion()) 1227da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev W.AddToWorkList(R); 1228658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks } 1229658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks continue; 1230658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks } 1231658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks 1232658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks if (const MemRegion *R = V.getAsRegion()) { 1233658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks if (TopLevelRegions) 1234658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks TopLevelRegions->push_back(R); 1235da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev W.AddToWorkList(R); 1236658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks continue; 1237658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks } 1238658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks } 1239658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks} 1240658a28479dd775f6ff2c07fa5699a7ea01e04127Anna Zaks 124129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted KremenekStoreRef 124229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted KremenekRegionStoreManager::invalidateRegions(Store store, 1243da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev ArrayRef<SVal> Values, 1244da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev const Expr *Ex, unsigned Count, 1245da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev const LocationContext *LCtx, 1246da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev const CallEvent *Call, 1247da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev InvalidatedSymbols &IS, 1248da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev RegionAndSymbolInvalidationTraits &ITraits, 1249da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev InvalidatedRegions *TopLevelRegions, 1250da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev InvalidatedRegions *Invalidated) { 1251e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose GlobalsFilterKind GlobalsFilter; 1252e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose if (Call) { 1253e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose if (Call->isInSystemHeader()) 1254e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose GlobalsFilter = GFK_SystemOnly; 1255e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose else 1256e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose GlobalsFilter = GFK_All; 1257e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose } else { 1258e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose GlobalsFilter = GFK_None; 1259e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose } 1260e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose 1261e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose RegionBindingsRef B = getRegionBindings(store); 1262da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev invalidateRegionsWorker W(*this, StateMgr, B, Ex, Count, LCtx, IS, ITraits, 1263e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose Invalidated, GlobalsFilter); 12645499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 12655499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // Scan the bindings and generate the clusters. 1266d45d59f4aebfe6399437074ed5391928c73993bbTed Kremenek W.GenerateClusters(); 12675499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 1268537716ad8dd10f984b6cfe6985afade1185c5e3cJordy Rose // Add the regions to the worklist. 1269da8d37ce42d2db4e1e76ee6f7f38f10f6b0ef0f8Anton Yartsev populateWorkList(W, Values, TopLevelRegions); 12705499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 12715499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek W.RunWorkList(); 12725499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 12735499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // Return the new bindings. 1274f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose B = W.getRegionBindings(); 1275dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 1276f8e2c06cea1548c437761cb65cfbf97d50a057a7Jordan Rose // For calls, determine which global regions should be invalidated and 1277f8e2c06cea1548c437761cb65cfbf97d50a057a7Jordan Rose // invalidate them. (Note that function-static and immutable globals are never 1278f8e2c06cea1548c437761cb65cfbf97d50a057a7Jordan Rose // invalidated by this.) 1279eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks // TODO: This could possibly be more precise with modules. 1280e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose switch (GlobalsFilter) { 1281e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose case GFK_All: 1282e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose B = invalidateGlobalRegion(MemRegion::GlobalInternalSpaceRegionKind, 1283e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose Ex, Count, LCtx, B, Invalidated); 1284e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose // FALLTHROUGH 1285e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose case GFK_SystemOnly: 1286eb31a76d1cdaaf8874c549dc6bd964ff270d3822Anna Zaks B = invalidateGlobalRegion(MemRegion::GlobalSystemSpaceRegionKind, 12873133f79cf451e6302dd05262b4bb53a3e4fd6300Ted Kremenek Ex, Count, LCtx, B, Invalidated); 1288e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose // FALLTHROUGH 1289e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose case GFK_None: 1290e0208ff84598f48e0aafecf5b543afeff8574045Jordan Rose break; 1291dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek } 1292dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 12930c312a90c5b9d27e1425bf8d0448e133a97806ceTed Kremenek return StoreRef(B.asStore(), *this); 1294e393f4afcd1a5c3cd73697d838b064a9b5af832fTed Kremenek} 1295e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 12969af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 12979af46f59242cfaec74fa491a66724970478263ebTed Kremenek// Extents for regions. 12989af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 12999af46f59242cfaec74fa491a66724970478263ebTed Kremenek 13001437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna ZaksDefinedOrUnknownSVal 13018bef8238181a30e52dea380789a7e2d760eac532Ted KremenekRegionStoreManager::getSizeInElements(ProgramStateRef state, 13021437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks const MemRegion *R, 13031437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks QualType EleTy) { 1304c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek SVal Size = cast<SubRegion>(R)->getExtent(svalBuilder); 1305846eabd187be4bfe992e8bca131166b734d86e0dTed Kremenek const llvm::APSInt *SizeInt = svalBuilder.getKnownValue(state, Size); 130632f2656b90900ac04c4b50e87c16749d0ceb9ef2Jordy Rose if (!SizeInt) 130732f2656b90900ac04c4b50e87c16749d0ceb9ef2Jordy Rose return UnknownVal(); 13081eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 130932f2656b90900ac04c4b50e87c16749d0ceb9ef2Jordy Rose CharUnits RegionSize = CharUnits::fromQuantity(SizeInt->getSExtValue()); 1310555c77a27672186242019b38edac498ac9579b19Ted Kremenek 1311555c77a27672186242019b38edac498ac9579b19Ted Kremenek if (Ctx.getAsVariableArrayType(EleTy)) { 1312555c77a27672186242019b38edac498ac9579b19Ted Kremenek // FIXME: We need to track extra state to properly record the size 1313555c77a27672186242019b38edac498ac9579b19Ted Kremenek // of VLAs. Returning UnknownVal here, however, is a stop-gap so that 1314555c77a27672186242019b38edac498ac9579b19Ted Kremenek // we don't have a divide-by-zero below. 1315555c77a27672186242019b38edac498ac9579b19Ted Kremenek return UnknownVal(); 1316555c77a27672186242019b38edac498ac9579b19Ted Kremenek } 1317555c77a27672186242019b38edac498ac9579b19Ted Kremenek 131857663fe6c3c7a0fb792626537c4f3f7d3594aa66Zhongxing Xu CharUnits EleSize = Ctx.getTypeSizeInChars(EleTy); 13191eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 132032f2656b90900ac04c4b50e87c16749d0ceb9ef2Jordy Rose // If a variable is reinterpreted as a type that doesn't fit into a larger 132132f2656b90900ac04c4b50e87c16749d0ceb9ef2Jordy Rose // type evenly, round it down. 132232f2656b90900ac04c4b50e87c16749d0ceb9ef2Jordy Rose // This is a signed value, since it's used in arithmetic with signed indices. 1323c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.makeIntVal(RegionSize / EleSize, false); 1324e8a964bdb46349e4fa3433c8e5104d2a0f7f5c65Zhongxing Xu} 1325e8a964bdb46349e4fa3433c8e5104d2a0f7f5c65Zhongxing Xu 13269af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 13279af46f59242cfaec74fa491a66724970478263ebTed Kremenek// Location and region casting. 13289af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 13299af46f59242cfaec74fa491a66724970478263ebTed Kremenek 1330869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek/// ArrayToPointer - Emulates the "decay" of an array to a pointer 1331869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek/// type. 'Array' represents the lvalue of the array being decayed 1332869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek/// to a pointer, and the returned SVal represents the decayed 1333869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek/// version of that lvalue (i.e., a pointer to the first element of 1334d2592a34a059e7cbb2b11dc53649ac4912422909Argyrios Kyrtzidis/// the array). This is called by ExprEngine when evaluating casts 1335869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek/// from arrays to pointers. 13367f1fd2f182717d5ce6cde60398128910c90f98beAnna ZaksSVal RegionStoreManager::ArrayToPointer(Loc Array, QualType T) { 13375251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (!Array.getAs<loc::MemRegionVal>()) 1338abb042f33ea8e6107a7dc8efc51d2ace329f9f48Ted Kremenek return UnknownVal(); 13391eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 13405251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie const MemRegion* R = Array.castAs<loc::MemRegionVal>().getRegion(); 1341c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek NonLoc ZeroIdx = svalBuilder.makeZeroArrayIndex(); 13427f1fd2f182717d5ce6cde60398128910c90f98beAnna Zaks return loc::MemRegionVal(MRMgr.getElementRegion(T, ZeroIdx, R, Ctx)); 1343b1d542a46eb71f23dafb5ce60b68247f280beb41Zhongxing Xu} 1344b1d542a46eb71f23dafb5ce60b68247f280beb41Zhongxing Xu 13459af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 13469af46f59242cfaec74fa491a66724970478263ebTed Kremenek// Loading values from regions. 13479af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 13489af46f59242cfaec74fa491a66724970478263ebTed Kremenek 134918f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekSVal RegionStoreManager::getBinding(RegionBindingsConstRef B, Loc L, QualType T) { 13505251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie assert(!L.getAs<UnknownVal>() && "location unknown"); 13515251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie assert(!L.getAs<UndefinedVal>() && "location undefined"); 1352e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 135329836f9e4750f1ccb72c24f661c20686507f0063Ted Kremenek // For access to concrete addresses, return UnknownVal. Checks 135429836f9e4750f1ccb72c24f661c20686507f0063Ted Kremenek // for null dereferences (and similar errors) are done by checkers, not 135529836f9e4750f1ccb72c24f661c20686507f0063Ted Kremenek // the Store. 135629836f9e4750f1ccb72c24f661c20686507f0063Ted Kremenek // FIXME: We can consider lazily symbolicating such memory, but we really 135729836f9e4750f1ccb72c24f661c20686507f0063Ted Kremenek // should defer this when we can reason easily about symbolicating arrays 135829836f9e4750f1ccb72c24f661c20686507f0063Ted Kremenek // of bytes. 13595251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (L.getAs<loc::ConcreteInt>()) { 136029836f9e4750f1ccb72c24f661c20686507f0063Ted Kremenek return UnknownVal(); 136129836f9e4750f1ccb72c24f661c20686507f0063Ted Kremenek } 13625251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (!L.getAs<loc::MemRegionVal>()) { 136314429b918bd2f4cb52abc75546a7fe37142054caArgyrios Kyrtzidis return UnknownVal(); 136414429b918bd2f4cb52abc75546a7fe37142054caArgyrios Kyrtzidis } 1365e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 13665251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie const MemRegion *MR = L.castAs<loc::MemRegionVal>().getRegion(); 1367a1718c78770db93d1b762620f07728a56786f2aeZhongxing Xu 136887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (isa<BlockDataRegion>(MR)) { 136987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return UnknownVal(); 137087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar } 137187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 1372214323b78b01ef9c1ad226f0eb5bd1187f3efa70Ted Kremenek if (isa<AllocaRegion>(MR) || 1373214323b78b01ef9c1ad226f0eb5bd1187f3efa70Ted Kremenek isa<SymbolicRegion>(MR) || 1374214323b78b01ef9c1ad226f0eb5bd1187f3efa70Ted Kremenek isa<CodeTextRegion>(MR)) { 13757b050306b0ba3e7e564126fb12aca64b4c0b3f54Tom Care if (T.isNull()) { 1376ce8ef16b1c58a304b7b59fad9836ad32d6ed020cAnna Zaks if (const TypedRegion *TR = dyn_cast<TypedRegion>(MR)) 1377ce8ef16b1c58a304b7b59fad9836ad32d6ed020cAnna Zaks T = TR->getLocationType(); 1378ce8ef16b1c58a304b7b59fad9836ad32d6ed020cAnna Zaks else { 1379ce8ef16b1c58a304b7b59fad9836ad32d6ed020cAnna Zaks const SymbolicRegion *SR = cast<SymbolicRegion>(MR); 1380732cdf383f9030ff2b9fb28dfbdae2285ded80c6Ted Kremenek T = SR->getSymbol()->getType(); 1381ce8ef16b1c58a304b7b59fad9836ad32d6ed020cAnna Zaks } 13827b050306b0ba3e7e564126fb12aca64b4c0b3f54Tom Care } 138381491854222ad25953a643ce8efa0d6ea295ccfeZhongxing Xu MR = GetElementZeroRegion(MR, T); 13847b050306b0ba3e7e564126fb12aca64b4c0b3f54Tom Care } 13851eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1386869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // FIXME: Perhaps this method should just take a 'const MemRegion*' argument 1387869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // instead of 'Loc', and have the other Loc cases handled at a higher level. 13889697934650354bed2e509d8e7e44f21a1fb00f76Ted Kremenek const TypedValueRegion *R = cast<TypedValueRegion>(MR); 1389018220c343c103b7dfaa117a7a474c7a7fd6d068Zhongxing Xu QualType RTy = R->getValueType(); 139053bcdd4fadc022f4a37a929954a72af98f32e91aZhongxing Xu 1391beac9e3772e255f89dad0abe34811953121912b2Ted Kremenek // FIXME: we do not yet model the parts of a complex type, so treat the 1392beac9e3772e255f89dad0abe34811953121912b2Ted Kremenek // whole thing as "unknown". 1393beac9e3772e255f89dad0abe34811953121912b2Ted Kremenek if (RTy->isAnyComplexType()) 1394beac9e3772e255f89dad0abe34811953121912b2Ted Kremenek return UnknownVal(); 1395beac9e3772e255f89dad0abe34811953121912b2Ted Kremenek 1396869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // FIXME: We should eventually handle funny addressing. e.g.: 1397869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // 1398869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // int x = ...; 1399869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // int *p = &x; 1400869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // char *q = (char*) p; 1401869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // char c = *q; // returns the first byte of 'x'. 1402869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // 1403869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // Such funny addressing will occur due to layering of regions. 1404fb87b89fc9eb103e19fb8e4b925c23f0bd091b99Douglas Gregor if (RTy->isStructureOrClassType()) 140518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return getBindingForStruct(B, R); 14061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1407d4e5a606c9c64e24c05e5f4610796087e911fb9cTed Kremenek // FIXME: Handle unions. 1408d4e5a606c9c64e24c05e5f4610796087e911fb9cTed Kremenek if (RTy->isUnionType()) 14091dc31f5ead63d7197edf6f34a7821b93ea6698a1Jordan Rose return createLazyBinding(B, R); 14103e001f393d112a50e13c9a8f9a4c0d97f3f51cf4Zhongxing Xu 14119955e708ffadb479b82b26d93dfcf0f5a2a6e372Jordan Rose if (RTy->isArrayType()) { 14129955e708ffadb479b82b26d93dfcf0f5a2a6e372Jordan Rose if (RTy->isConstantArrayType()) 141318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return getBindingForArray(B, R); 14149955e708ffadb479b82b26d93dfcf0f5a2a6e372Jordan Rose else 14159955e708ffadb479b82b26d93dfcf0f5a2a6e372Jordan Rose return UnknownVal(); 14169955e708ffadb479b82b26d93dfcf0f5a2a6e372Jordan Rose } 14173e001f393d112a50e13c9a8f9a4c0d97f3f51cf4Zhongxing Xu 14181038f9f69978ea99efccdda01f66215a1c56dc55Zhongxing Xu // FIXME: handle Vector types. 14191038f9f69978ea99efccdda01f66215a1c56dc55Zhongxing Xu if (RTy->isVectorType()) 1420c999ed792900026c462027e546d63c3f39310755Zhongxing Xu return UnknownVal(); 142199c2030f917a76b792848e37d635067c902f96b2Zhongxing Xu 142299c2030f917a76b792848e37d635067c902f96b2Zhongxing Xu if (const FieldRegion* FR = dyn_cast<FieldRegion>(R)) 142318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return CastRetrievedVal(getBindingForField(B, FR), FR, T, false); 1424c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek 1425c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek if (const ElementRegion* ER = dyn_cast<ElementRegion>(R)) { 1426c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // FIXME: Here we actually perform an implicit conversion from the loaded 1427c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // value to the element type. Eventually we want to compose these values 1428c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // more intelligently. For example, an 'element' can encompass multiple 1429c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // bound regions (e.g., several bound bytes), or could be a subset of 1430c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // a larger value. 143118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return CastRetrievedVal(getBindingForElement(B, ER), ER, T, false); 1432e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek } 1433c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek 1434c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek if (const ObjCIvarRegion *IVR = dyn_cast<ObjCIvarRegion>(R)) { 1435c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // FIXME: Here we actually perform an implicit conversion from the loaded 1436c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // value to the ivar type. What we should model is stores to ivars 1437c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // that blow past the extent of the ivar. If the address of the ivar is 1438c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // reinterpretted, it is possible we stored a different value that could 1439c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // fit within the ivar. Either we need to cast these when storing them 1440c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // or reinterpret them lazily (as we do here). 144118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return CastRetrievedVal(getBindingForObjCIvar(B, IVR), IVR, T, false); 1442c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek } 14431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1444c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek if (const VarRegion *VR = dyn_cast<VarRegion>(R)) { 1445c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // FIXME: Here we actually perform an implicit conversion from the loaded 1446c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // value to the variable type. What we should model is stores to variables 1447c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // that blow past the extent of the variable. If the address of the 1448c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // variable is reinterpretted, it is possible we stored a different value 1449c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek // that could fit within the variable. Either we need to cast these when 1450e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek // storing them or reinterpret them lazily (as we do here). 145118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return CastRetrievedVal(getBindingForVar(B, VR), VR, T, false); 1452c50e6df965ff264952d8d5805d151f89c89af302Ted Kremenek } 145325c545788da6e3a725206cfa378b9b83a7da6024Ted Kremenek 145429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek const SVal *V = B.lookup(R, BindingKey::Direct); 145553bcdd4fadc022f4a37a929954a72af98f32e91aZhongxing Xu 14564193eca10ce0cc8b2dae887e935a43b26f492b5bZhongxing Xu // Check if the region has a binding. 14574193eca10ce0cc8b2dae887e935a43b26f492b5bZhongxing Xu if (V) 1458c999ed792900026c462027e546d63c3f39310755Zhongxing Xu return *V; 1459869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek 1460869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // The location does not have a bound value. This means that it has 1461869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // the value it had upon its creation and/or entry to the analyzed 1462869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // function/method. These are either symbolic values or 'undefined'. 1463de0d26310191215a6d1d189dc419f87af18ce6beTed Kremenek if (R->hasStackNonParametersStorage()) { 1464869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // All stack variables are considered to have undefined values 1465869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // upon creation. All heap allocated blocks are considered to 1466869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // have undefined values as well unless they are explicitly bound 1467869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek // to specific values. 1468c999ed792900026c462027e546d63c3f39310755Zhongxing Xu return UndefinedVal(); 1469869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek } 1470869fb4a8c5e53952fce508a690646ab9e3192f30Ted Kremenek 1471bb2b433ae14ca18e88a46032096ce5ec5c05c8e7Ted Kremenek // All other values are symbolic. 1472c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.getRegionValueSymbolVal(R); 147353bcdd4fadc022f4a37a929954a72af98f32e91aZhongxing Xu} 14741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 14759f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaksstatic QualType getUnderlyingType(const SubRegion *R) { 14769f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks QualType RegionTy; 14779f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks if (const TypedValueRegion *TVR = dyn_cast<TypedValueRegion>(R)) 14789f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks RegionTy = TVR->getValueType(); 14799f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks 14809f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks if (const SymbolicRegion *SR = dyn_cast<SymbolicRegion>(R)) 14819f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks RegionTy = SR->getSymbol()->getType(); 14829f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks 14839f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks return RegionTy; 14849f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks} 14859f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks 148611f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose/// Checks to see if store \p B has a lazy binding for region \p R. 148711f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose/// 148811f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose/// If \p AllowSubregionBindings is \c false, a lazy binding will be rejected 148911f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose/// if there are additional bindings within \p R. 149011f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose/// 149111f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose/// Note that unlike RegionStoreManager::findLazyBinding, this will not search 149211f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose/// for lazy bindings for super-regions of \p R. 149311f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rosestatic Optional<nonloc::LazyCompoundVal> 149411f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan RosegetExistingLazyBinding(SValBuilder &SVB, RegionBindingsConstRef B, 149511f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose const SubRegion *R, bool AllowSubregionBindings) { 149611f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose Optional<SVal> V = B.getDefaultBinding(R); 149711f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose if (!V) 1498472b0613ff67e8598ef6a69bb478c721b21a9294Jordan Rose return None; 149911f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose 150011f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose Optional<nonloc::LazyCompoundVal> LCV = V->getAs<nonloc::LazyCompoundVal>(); 150111f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose if (!LCV) 1502472b0613ff67e8598ef6a69bb478c721b21a9294Jordan Rose return None; 150311f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose 15049f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks // If the LCV is for a subregion, the types might not match, and we shouldn't 15059f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks // reuse the binding. 15069f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks QualType RegionTy = getUnderlyingType(R); 15079f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks if (!RegionTy.isNull() && 15089f3495aeaa24da4eacf8f6c274adcef65e2f3617Anna Zaks !RegionTy->isVoidPointerType()) { 150911f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose QualType SourceRegionTy = LCV->getRegion()->getValueType(); 151011f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose if (!SVB.getContext().hasSameUnqualifiedType(RegionTy, SourceRegionTy)) 1511472b0613ff67e8598ef6a69bb478c721b21a9294Jordan Rose return None; 151211f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose } 151311f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose 151411f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose if (!AllowSubregionBindings) { 151511f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose // If there are any other bindings within this region, we shouldn't reuse 151611f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose // the top-level binding. 1517e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose SmallVector<BindingPair, 16> Bindings; 1518e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose collectSubRegionBindings(Bindings, SVB, *B.lookup(R->getBaseRegion()), R, 1519e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose /*IncludeAllDefaultBindings=*/true); 1520e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose if (Bindings.size() > 1) 1521472b0613ff67e8598ef6a69bb478c721b21a9294Jordan Rose return None; 152211f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose } 152311f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose 152411f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose return *LCV; 152511f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose} 152665f991ccbec43b4a860f70594c92528ee8fb7c6fJordan Rose 152711f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose 152811f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rosestd::pair<Store, const SubRegion *> 152911f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan RoseRegionStoreManager::findLazyBinding(RegionBindingsConstRef B, 153011f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose const SubRegion *R, 153111f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose const SubRegion *originalRegion) { 153245fa623886dfb6a23b3cfd6d8764e05884382180Ted Kremenek if (originalRegion != R) { 153311f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose if (Optional<nonloc::LazyCompoundVal> V = 153411f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose getExistingLazyBinding(svalBuilder, B, R, true)) 153511f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose return std::make_pair(V->getStore(), V->getRegion()); 153645fa623886dfb6a23b3cfd6d8764e05884382180Ted Kremenek } 153711f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose 153811f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose typedef std::pair<Store, const SubRegion *> StoreRegionPair; 153911f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose StoreRegionPair Result = StoreRegionPair(); 154011f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose 1541a5e81f1240bcc5b9b0721fc6275075ad7cadaf5eTed Kremenek if (const ElementRegion *ER = dyn_cast<ElementRegion>(R)) { 154211f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose Result = findLazyBinding(B, cast<SubRegion>(ER->getSuperRegion()), 154311f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose originalRegion); 15441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 154511f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose if (Result.second) 154611f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose Result.second = MRMgr.getElementRegionWithSuper(ER, Result.second); 154711f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose 154811f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose } else if (const FieldRegion *FR = dyn_cast<FieldRegion>(R)) { 154911f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose Result = findLazyBinding(B, cast<SubRegion>(FR->getSuperRegion()), 155011f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose originalRegion); 155111f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose 155211f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose if (Result.second) 155311f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose Result.second = MRMgr.getFieldRegionWithSuper(FR, Result.second); 15541eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 155565f991ccbec43b4a860f70594c92528ee8fb7c6fJordan Rose } else if (const CXXBaseObjectRegion *BaseReg = 155665f991ccbec43b4a860f70594c92528ee8fb7c6fJordan Rose dyn_cast<CXXBaseObjectRegion>(R)) { 155765f991ccbec43b4a860f70594c92528ee8fb7c6fJordan Rose // C++ base object region is another kind of region that we should blast 155865f991ccbec43b4a860f70594c92528ee8fb7c6fJordan Rose // through to look for lazy compound value. It is like a field region. 155911f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose Result = findLazyBinding(B, cast<SubRegion>(BaseReg->getSuperRegion()), 156011f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose originalRegion); 156187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 156211f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose if (Result.second) 156311f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose Result.second = MRMgr.getCXXBaseObjectRegionWithSuper(BaseReg, 156411f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose Result.second); 1565d074441e027471a914cbb909a7aad1d43224950fZhongxing Xu } 1566613744181322b9680a4b3d59cce87d7e5e572c99Ted Kremenek 156711f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose return Result; 1568a5e81f1240bcc5b9b0721fc6275075ad7cadaf5eTed Kremenek} 156953bcdd4fadc022f4a37a929954a72af98f32e91aZhongxing Xu 157018f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekSVal RegionStoreManager::getBindingForElement(RegionBindingsConstRef B, 1571a8f2362307b436023095e66efd678ae591c02184Anna Zaks const ElementRegion* R) { 1572a8f2362307b436023095e66efd678ae591c02184Anna Zaks // We do not currently model bindings of the CompoundLiteralregion. 157350b5a5c32e07301e4edcc01aca1f8a49a128c66cAnna Zaks if (isa<CompoundLiteralRegion>(R->getBaseRegion())) 157450b5a5c32e07301e4edcc01aca1f8a49a128c66cAnna Zaks return UnknownVal(); 1575a8f2362307b436023095e66efd678ae591c02184Anna Zaks 1576c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu // Check if the region has a binding. 157729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (const Optional<SVal> &V = B.getDirectBinding(R)) 1578c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu return *V; 1579c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu 1580921109ab9c4a114da4588566bc56c09443ea2339Ted Kremenek const MemRegion* superR = R->getSuperRegion(); 1581921109ab9c4a114da4588566bc56c09443ea2339Ted Kremenek 1582c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu // Check if the region is an element region of a string literal. 1583921109ab9c4a114da4588566bc56c09443ea2339Ted Kremenek if (const StringRegion *StrR=dyn_cast<StringRegion>(superR)) { 1584e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek // FIXME: Handle loads from strings where the literal is treated as 158595efe0f7fb2ff2d83f9e6f97d707a79370034d73Ted Kremenek // an integer, e.g., *((unsigned int*)"hello") 1586018220c343c103b7dfaa117a7a474c7a7fd6d068Zhongxing Xu QualType T = Ctx.getAsArrayType(StrR->getValueType())->getElementType(); 1587df70700f5aa5744d7f70fb3e6610ff434f643a71Jordan Rose if (!Ctx.hasSameUnqualifiedType(T, R->getElementType())) 158895efe0f7fb2ff2d83f9e6f97d707a79370034d73Ted Kremenek return UnknownVal(); 1589e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 1590c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu const StringLiteral *Str = StrR->getStringLiteral(); 1591c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu SVal Idx = R->getIndex(); 1592dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie if (Optional<nonloc::ConcreteInt> CI = Idx.getAs<nonloc::ConcreteInt>()) { 1593c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu int64_t i = CI->getValue().getSExtValue(); 159431d922fdbf52ea14856f395cb1079173b33cefcdTed Kremenek // Abort on string underrun. This can be possible by arbitrary 15951437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks // clients of getBindingForElement(). 159631d922fdbf52ea14856f395cb1079173b33cefcdTed Kremenek if (i < 0) 159731d922fdbf52ea14856f395cb1079173b33cefcdTed Kremenek return UndefinedVal(); 1598729aa06b9d190ce01eccb7108415e698fc52f6f4Ted Kremenek int64_t length = Str->getLength(); 1599729aa06b9d190ce01eccb7108415e698fc52f6f4Ted Kremenek // Technically, only i == length is guaranteed to be null. 1600167cc379756e525bdf5b6b722fd78d415ed0eb2cJordy Rose // However, such overflows should be caught before reaching this point; 1601167cc379756e525bdf5b6b722fd78d415ed0eb2cJordy Rose // the only time such an access would be made is if a string literal was 1602167cc379756e525bdf5b6b722fd78d415ed0eb2cJordy Rose // used to initialize a larger array. 1603729aa06b9d190ce01eccb7108415e698fc52f6f4Ted Kremenek char c = (i >= length) ? '\0' : Str->getCodeUnit(i); 1604c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.makeIntVal(c, T); 1605c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu } 1606c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu } 160787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 16081e4a32acfad6a9f4cf555fdbc5c6c44c558b9fcbTed Kremenek // Check for loads from a code text region. For such loads, just give up. 160908140f99e507cfd593146bdf2efb01b24da822faTed Kremenek if (isa<CodeTextRegion>(superR)) 16101e4a32acfad6a9f4cf555fdbc5c6c44c558b9fcbTed Kremenek return UnknownVal(); 16111eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1612a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek // Handle the case where we are indexing into a larger scalar object. 1613a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek // For example, this handles: 1614a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek // int x = ... 1615a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek // char *y = &x; 1616a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek // return *y; 1617a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek // FIXME: This is a hack, and doesn't do anything really intelligent yet. 16187caf9b369cba6edaf6eac25121cbc65ee938f14dZhongxing Xu const RegionRawOffset &O = R->getAsArrayOffset(); 161987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 1620c46d6410947b18ac4c52cff4d0f8021b10a57c1eTed Kremenek // If we cannot reason about the offset, return an unknown value. 1621c46d6410947b18ac4c52cff4d0f8021b10a57c1eTed Kremenek if (!O.getRegion()) 1622c46d6410947b18ac4c52cff4d0f8021b10a57c1eTed Kremenek return UnknownVal(); 162387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 162487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (const TypedValueRegion *baseR = 16259697934650354bed2e509d8e7e44f21a1fb00f76Ted Kremenek dyn_cast_or_null<TypedValueRegion>(O.getRegion())) { 1626018220c343c103b7dfaa117a7a474c7a7fd6d068Zhongxing Xu QualType baseT = baseR->getValueType(); 1627a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek if (baseT->isScalarType()) { 1628a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek QualType elemT = R->getElementType(); 1629a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek if (elemT->isScalarType()) { 1630a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek if (Ctx.getTypeSizeInChars(baseT) >= Ctx.getTypeSizeInChars(elemT)) { 163129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (const Optional<SVal> &V = B.getDirectBinding(superR)) { 1632a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek if (SymbolRef parentSym = V->getAsSymbol()) 1633c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.getDerivedRegionValueSymbolVal(parentSym, R); 1634dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 1635a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek if (V->isUnknownOrUndef()) 1636a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek return *V; 1637a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek // Other cases: give up. We are indexing into a larger object 1638a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek // that has some value, but we don't know how to handle that yet. 1639a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek return UnknownVal(); 1640a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek } 1641a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek } 1642a709b87de4644c05d7787f9fb246d2b4dc38bf51Ted Kremenek } 1643566a6faa54235590ab8d7d177dfac08586f545b0Ted Kremenek } 16447abe019c2840e3890993c879c65acde9ea316166Zhongxing Xu } 1645262e0d41e49c6b823d62743535e2accb117a6ea9Jordan Rose return getBindingForFieldOrElementCommon(B, R, R->getElementType()); 1646c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu} 1647c00346fff95b961241abffdcc257a90e6cb1cb4bZhongxing Xu 164818f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekSVal RegionStoreManager::getBindingForField(RegionBindingsConstRef B, 164918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const FieldRegion* R) { 1650490b0f0877b1a6d3caf18abb4ab62ed592e13c4aZhongxing Xu 1651490b0f0877b1a6d3caf18abb4ab62ed592e13c4aZhongxing Xu // Check if the region has a binding. 165229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (const Optional<SVal> &V = B.getDirectBinding(R)) 1653490b0f0877b1a6d3caf18abb4ab62ed592e13c4aZhongxing Xu return *V; 1654490b0f0877b1a6d3caf18abb4ab62ed592e13c4aZhongxing Xu 1655018220c343c103b7dfaa117a7a474c7a7fd6d068Zhongxing Xu QualType Ty = R->getValueType(); 1656262e0d41e49c6b823d62743535e2accb117a6ea9Jordan Rose return getBindingForFieldOrElementCommon(B, R, Ty); 1657566a6faa54235590ab8d7d177dfac08586f545b0Ted Kremenek} 16581eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1659dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted KremenekOptional<SVal> 166018f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionStoreManager::getBindingForDerivedDefaultValue(RegionBindingsConstRef B, 16611437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks const MemRegion *superR, 16621437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks const TypedValueRegion *R, 16631437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks QualType Ty) { 1664dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 166529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (const Optional<SVal> &D = B.getDefaultBinding(superR)) { 1666613744181322b9680a4b3d59cce87d7e5e572c99Ted Kremenek const SVal &val = D.getValue(); 1667613744181322b9680a4b3d59cce87d7e5e572c99Ted Kremenek if (SymbolRef parentSym = val.getAsSymbol()) 1668c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.getDerivedRegionValueSymbolVal(parentSym, R); 1669dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 1670613744181322b9680a4b3d59cce87d7e5e572c99Ted Kremenek if (val.isZeroConstant()) 1671c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.makeZeroVal(Ty); 1672dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 1673613744181322b9680a4b3d59cce87d7e5e572c99Ted Kremenek if (val.isUnknownOrUndef()) 1674613744181322b9680a4b3d59cce87d7e5e572c99Ted Kremenek return val; 1675613744181322b9680a4b3d59cce87d7e5e572c99Ted Kremenek 1676deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // Lazy bindings are usually handled through getExistingLazyBinding(). 1677deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // We should unify these two code paths at some point. 16785251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (val.getAs<nonloc::LazyCompoundVal>()) 1679deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose return val; 1680dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 1681b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie llvm_unreachable("Unknown default value"); 1682dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek } 1683dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 168466874fb18afbffb8b2ca05576851a64534be3352David Blaikie return None; 1685dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek} 1686dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 168711f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan RoseSVal RegionStoreManager::getLazyBinding(const SubRegion *LazyBindingRegion, 168818f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef LazyBinding) { 16890e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose SVal Result; 169018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek if (const ElementRegion *ER = dyn_cast<ElementRegion>(LazyBindingRegion)) 16910e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose Result = getBindingForElement(LazyBinding, ER); 16920e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose else 16930e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose Result = getBindingForField(LazyBinding, 16940e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose cast<FieldRegion>(LazyBindingRegion)); 16950e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose 1696deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // FIXME: This is a hack to deal with RegionStore's inability to distinguish a 16970e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // default value for /part/ of an aggregate from a default value for the 16980e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // /entire/ aggregate. The most common case of this is when struct Outer 16990e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // has as its first member a struct Inner, which is copied in from a stack 17000e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // variable. In this case, even if the Outer's default value is symbolic, 0, 17010e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // or unknown, it gets overridden by the Inner's default value of undefined. 17020e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // 17030e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // This is a general problem -- if the Inner is zero-initialized, the Outer 17040e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // will now look zero-initialized. The proper way to solve this is with a 17050e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // new version of RegionStore that tracks the extent of a binding as well 17060e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // as the offset. 17070e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // 17080e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // This hack only takes care of the undefined case because that can very 17090e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose // quickly result in a warning. 17100e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose if (Result.isUndef()) 17110e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose Result = UnknownVal(); 17120e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose 17130e450cbd94e5936fdecf42b810069e7becd3938dJordan Rose return Result; 1714613744181322b9680a4b3d59cce87d7e5e572c99Ted Kremenek} 171587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 171618f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekSVal 171718f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionStoreManager::getBindingForFieldOrElementCommon(RegionBindingsConstRef B, 17189697934650354bed2e509d8e7e44f21a1fb00f76Ted Kremenek const TypedValueRegion *R, 1719262e0d41e49c6b823d62743535e2accb117a6ea9Jordan Rose QualType Ty) { 1720566a6faa54235590ab8d7d177dfac08586f545b0Ted Kremenek 17211437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks // At this point we have already checked in either getBindingForElement or 17221437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks // getBindingForField if 'R' has a direct binding. 17238f40afbf7740c39fccaa4b8cc5aa2814d5ed6fdcTed Kremenek 17248f40afbf7740c39fccaa4b8cc5aa2814d5ed6fdcTed Kremenek // Lazy binding? 17256bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines Store lazyBindingStore = nullptr; 17266bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines const SubRegion *lazyBindingRegion = nullptr; 1727651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines std::tie(lazyBindingStore, lazyBindingRegion) = findLazyBinding(B, R, R); 17288f40afbf7740c39fccaa4b8cc5aa2814d5ed6fdcTed Kremenek if (lazyBindingRegion) 172918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return getLazyBinding(lazyBindingRegion, 173018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek getRegionBindings(lazyBindingStore)); 17318f40afbf7740c39fccaa4b8cc5aa2814d5ed6fdcTed Kremenek 173231b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek // Record whether or not we see a symbolic index. That can completely 173331b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek // be out of scope of our lookup. 173431b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek bool hasSymbolicIndex = false; 17351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1736deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // FIXME: This is a hack to deal with RegionStore's inability to distinguish a 1737deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // default value for /part/ of an aggregate from a default value for the 1738deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // /entire/ aggregate. The most common case of this is when struct Outer 1739deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // has as its first member a struct Inner, which is copied in from a stack 1740deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // variable. In this case, even if the Outer's default value is symbolic, 0, 1741deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // or unknown, it gets overridden by the Inner's default value of undefined. 1742deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // 1743deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // This is a general problem -- if the Inner is zero-initialized, the Outer 1744deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // will now look zero-initialized. The proper way to solve this is with a 1745deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // new version of RegionStore that tracks the extent of a binding as well 1746deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // as the offset. 1747deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // 1748deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // This hack only takes care of the undefined case because that can very 1749deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose // quickly result in a warning. 1750deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose bool hasPartialLazyBinding = false; 1751deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose 1752262e0d41e49c6b823d62743535e2accb117a6ea9Jordan Rose const SubRegion *SR = dyn_cast<SubRegion>(R); 1753262e0d41e49c6b823d62743535e2accb117a6ea9Jordan Rose while (SR) { 1754262e0d41e49c6b823d62743535e2accb117a6ea9Jordan Rose const MemRegion *Base = SR->getSuperRegion(); 1755deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose if (Optional<SVal> D = getBindingForDerivedDefaultValue(B, Base, R, Ty)) { 1756deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose if (D->getAs<nonloc::LazyCompoundVal>()) { 1757deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose hasPartialLazyBinding = true; 1758deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose break; 1759deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose } 1760deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose 1761dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek return *D; 1762deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose } 17631eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1764deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose if (const ElementRegion *ER = dyn_cast<ElementRegion>(Base)) { 176531b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek NonLoc index = ER->getIndex(); 176631b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek if (!index.isConstant()) 176731b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek hasSymbolicIndex = true; 176831b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek } 176987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 177019e1f0ba5cec738ce6cebe3fe0e1edc782206494Ted Kremenek // If our super region is a field or element itself, walk up the region 177119e1f0ba5cec738ce6cebe3fe0e1edc782206494Ted Kremenek // hierarchy to see if there is a default value installed in an ancestor. 1772262e0d41e49c6b823d62743535e2accb117a6ea9Jordan Rose SR = dyn_cast<SubRegion>(Base); 1773a5e81f1240bcc5b9b0721fc6275075ad7cadaf5eTed Kremenek } 17741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1775de0d26310191215a6d1d189dc419f87af18ce6beTed Kremenek if (R->hasStackNonParametersStorage()) { 177631b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek if (isa<ElementRegion>(R)) { 1777566a6faa54235590ab8d7d177dfac08586f545b0Ted Kremenek // Currently we don't reason specially about Clang-style vectors. Check 1778566a6faa54235590ab8d7d177dfac08586f545b0Ted Kremenek // if superR is a vector and if so return Unknown. 177987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar if (const TypedValueRegion *typedSuperR = 1780262e0d41e49c6b823d62743535e2accb117a6ea9Jordan Rose dyn_cast<TypedValueRegion>(R->getSuperRegion())) { 1781018220c343c103b7dfaa117a7a474c7a7fd6d068Zhongxing Xu if (typedSuperR->getValueType()->isVectorType()) 1782566a6faa54235590ab8d7d177dfac08586f545b0Ted Kremenek return UnknownVal(); 17831eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump } 1784566a6faa54235590ab8d7d177dfac08586f545b0Ted Kremenek } 17851eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 178631b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek // FIXME: We also need to take ElementRegions with symbolic indexes into 178731b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek // account. This case handles both directly accessing an ElementRegion 178831b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek // with a symbolic offset, but also fields within an element with 178931b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek // a symbolic offset. 179031b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek if (hasSymbolicIndex) 179131b57628576a2355428fd4b57f828a3aa8423000Ted Kremenek return UnknownVal(); 1792deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose 1793deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose if (!hasPartialLazyBinding) 1794deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose return UndefinedVal(); 1795566a6faa54235590ab8d7d177dfac08586f545b0Ted Kremenek } 17961eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1797bb2b433ae14ca18e88a46032096ce5ec5c05c8e7Ted Kremenek // All other values are symbolic. 1798c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.getRegionValueSymbolVal(R); 1799490b0f0877b1a6d3caf18abb4ab62ed592e13c4aZhongxing Xu} 18001eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 180118f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekSVal RegionStoreManager::getBindingForObjCIvar(RegionBindingsConstRef B, 18021437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks const ObjCIvarRegion* R) { 180318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek // Check if the region has a binding. 180429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (const Optional<SVal> &V = B.getDirectBinding(R)) 18055bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek return *V; 18061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 18075bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek const MemRegion *superR = R->getSuperRegion(); 18085bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek 1809ab22ee9ede5532f35c64b8eaccb4210f3f16397dTed Kremenek // Check if the super region has a default binding. 181029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (const Optional<SVal> &V = B.getDefaultBinding(superR)) { 18115bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek if (SymbolRef parentSym = V->getAsSymbol()) 1812c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.getDerivedRegionValueSymbolVal(parentSym, R); 18131eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 18145bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek // Other cases: give up. 18155bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek return UnknownVal(); 18165bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek } 18171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 18181437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks return getBindingForLazySymbol(R); 181925c545788da6e3a725206cfa378b9b83a7da6024Ted Kremenek} 182025c545788da6e3a725206cfa378b9b83a7da6024Ted Kremenek 182118f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekSVal RegionStoreManager::getBindingForVar(RegionBindingsConstRef B, 182218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const VarRegion *R) { 18231eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 18249031dd7a989f893be0c3a9d8915b1218646be763Ted Kremenek // Check if the region has a binding. 182529f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek if (const Optional<SVal> &V = B.getDirectBinding(R)) 18269031dd7a989f893be0c3a9d8915b1218646be763Ted Kremenek return *V; 18271eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 18289031dd7a989f893be0c3a9d8915b1218646be763Ted Kremenek // Lazily derive a value for the VarRegion. 18299031dd7a989f893be0c3a9d8915b1218646be763Ted Kremenek const VarDecl *VD = R->getDecl(); 18304dc1566a80648a74a19409c425809fa6a1683befTed Kremenek const MemSpaceRegion *MS = R->getMemorySpace(); 1831e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 1832697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose // Arguments are always symbolic. 1833697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose if (isa<StackArgumentsSpaceRegion>(MS)) 1834697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose return svalBuilder.getRegionValueSymbolVal(R); 1835697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose 1836697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose // Is 'VD' declared constant? If so, retrieve the constant value. 1837e2b1246a24e8babf2f58c93713fba16b8edb8e2dJordan Rose if (VD->getType().isConstQualified()) 1838e2b1246a24e8babf2f58c93713fba16b8edb8e2dJordan Rose if (const Expr *Init = VD->getInit()) 1839e2b1246a24e8babf2f58c93713fba16b8edb8e2dJordan Rose if (Optional<SVal> V = svalBuilder.getConstantVal(Init)) 1840e2b1246a24e8babf2f58c93713fba16b8edb8e2dJordan Rose return *V; 1841697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose 1842697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose // This must come after the check for constants because closure-captured 1843697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose // constant variables may appear in UnknownSpaceRegion. 1844697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose if (isa<UnknownSpaceRegion>(MS)) 1845c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.getRegionValueSymbolVal(R); 18461eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 18474dc1566a80648a74a19409c425809fa6a1683befTed Kremenek if (isa<GlobalsSpaceRegion>(MS)) { 1848697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose QualType T = VD->getType(); 1849697a68590a75f5cd2326c8f686a6c666b51688b6Jordan Rose 185004870edbea6cf88412c8c9c1eba65f7fc1fa12d9Jordan Rose // Function-scoped static variables are default-initialized to 0; if they 185104870edbea6cf88412c8c9c1eba65f7fc1fa12d9Jordan Rose // have an initializer, it would have been processed by now. 185204870edbea6cf88412c8c9c1eba65f7fc1fa12d9Jordan Rose if (isa<StaticGlobalSpaceRegion>(MS)) 185304870edbea6cf88412c8c9c1eba65f7fc1fa12d9Jordan Rose return svalBuilder.makeZeroVal(T); 185404870edbea6cf88412c8c9c1eba65f7fc1fa12d9Jordan Rose 1855deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose if (Optional<SVal> V = getBindingForDerivedDefaultValue(B, MS, R, T)) { 1856deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose assert(!V->getAs<nonloc::LazyCompoundVal>()); 185704870edbea6cf88412c8c9c1eba65f7fc1fa12d9Jordan Rose return V.getValue(); 1858deb8f5d533b7bcd962976ecdbc1464fe754b6de0Jordan Rose } 185981861abe9cd1669ca46e13866f77f7ece8c4c85fTed Kremenek 186004870edbea6cf88412c8c9c1eba65f7fc1fa12d9Jordan Rose return svalBuilder.getRegionValueSymbolVal(R); 18614dc1566a80648a74a19409c425809fa6a1683befTed Kremenek } 1862e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 18639031dd7a989f893be0c3a9d8915b1218646be763Ted Kremenek return UndefinedVal(); 18649031dd7a989f893be0c3a9d8915b1218646be763Ted Kremenek} 18659031dd7a989f893be0c3a9d8915b1218646be763Ted Kremenek 18661437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna ZaksSVal RegionStoreManager::getBindingForLazySymbol(const TypedValueRegion *R) { 18675bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek // All other values are symbolic. 1868c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek return svalBuilder.getRegionValueSymbolVal(R); 18695bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek} 18705bd2fe365f29799a78a862df2d1cff365d792b63Ted Kremenek 187128743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Roseconst RegionStoreManager::SValListTy & 187228743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan RoseRegionStoreManager::getInterestingValues(nonloc::LazyCompoundVal LCV) { 187328743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose // First, check the cache. 187428743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose LazyBindingsMapTy::iterator I = LazyBindingsMap.find(LCV.getCVData()); 187528743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose if (I != LazyBindingsMap.end()) 187628743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose return I->second; 187728743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose 187828743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose // If we don't have a list of values cached, start constructing it. 1879206f49966f66ad7cbfe3d37c14fa7e6e7410f3beJordan Rose SValListTy List; 188028743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose 188128743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose const SubRegion *LazyR = LCV.getRegion(); 188228743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose RegionBindingsRef B = getRegionBindings(LCV.getStore()); 188328743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose 188428743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose // If this region had /no/ bindings at the time, there are no interesting 188528743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose // values to return. 188628743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose const ClusterBindings *Cluster = B.lookup(LazyR->getBaseRegion()); 188728743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose if (!Cluster) 1888651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines return (LazyBindingsMap[LCV.getCVData()] = std::move(List)); 188928743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose 1890e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose SmallVector<BindingPair, 32> Bindings; 1891e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose collectSubRegionBindings(Bindings, svalBuilder, *Cluster, LazyR, 1892e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose /*IncludeAllDefaultBindings=*/true); 1893e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose for (SmallVectorImpl<BindingPair>::const_iterator I = Bindings.begin(), 1894e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose E = Bindings.end(); 189528743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose I != E; ++I) { 1896e33d852452c7008ccd0677aae88f1055cf1a9af1Jordan Rose SVal V = I->second; 189728743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose if (V.isUnknownOrUndef() || V.isConstant()) 189828743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose continue; 189928743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose 1900dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie if (Optional<nonloc::LazyCompoundVal> InnerLCV = 19015251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie V.getAs<nonloc::LazyCompoundVal>()) { 190228743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose const SValListTy &InnerList = getInterestingValues(*InnerLCV); 190328743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose List.insert(List.end(), InnerList.begin(), InnerList.end()); 190428743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose continue; 190528743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose } 190687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 190728743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose List.push_back(V); 190828743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose } 190928743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose 1910651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines return (LazyBindingsMap[LCV.getCVData()] = std::move(List)); 191128743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose} 191228743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose 1913978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan RoseNonLoc RegionStoreManager::createLazyBinding(RegionBindingsConstRef B, 1914978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose const TypedValueRegion *R) { 191511f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose if (Optional<nonloc::LazyCompoundVal> V = 191611f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose getExistingLazyBinding(svalBuilder, B, R, false)) 191711f0cae4bf4f62dcc706d33c1f795d460cd64816Jordan Rose return *V; 1918978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose 1919978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose return svalBuilder.makeLazyCompoundVal(StoreRef(B.asStore(), *this), R); 1920752bee2493ec2931bd18899753552e3a47dc85feJordan Rose} 1921752bee2493ec2931bd18899753552e3a47dc85feJordan Rose 19223c114f704a882f6923d6107f22aab89ba3d0a6b5Pavel Labathstatic bool isRecordEmpty(const RecordDecl *RD) { 19233c114f704a882f6923d6107f22aab89ba3d0a6b5Pavel Labath if (!RD->field_empty()) 19243c114f704a882f6923d6107f22aab89ba3d0a6b5Pavel Labath return false; 19253c114f704a882f6923d6107f22aab89ba3d0a6b5Pavel Labath if (const CXXRecordDecl *CRD = dyn_cast<CXXRecordDecl>(RD)) 19263c114f704a882f6923d6107f22aab89ba3d0a6b5Pavel Labath return CRD->getNumBases() == 0; 19273c114f704a882f6923d6107f22aab89ba3d0a6b5Pavel Labath return true; 19283c114f704a882f6923d6107f22aab89ba3d0a6b5Pavel Labath} 19293c114f704a882f6923d6107f22aab89ba3d0a6b5Pavel Labath 193018f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekSVal RegionStoreManager::getBindingForStruct(RegionBindingsConstRef B, 1931978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose const TypedValueRegion *R) { 1932752bee2493ec2931bd18899753552e3a47dc85feJordan Rose const RecordDecl *RD = R->getValueType()->castAs<RecordType>()->getDecl(); 1933bf3d71e85f7449161a414c2ec3410e60394bf38aJordan Rose if (!RD->getDefinition() || isRecordEmpty(RD)) 1934752bee2493ec2931bd18899753552e3a47dc85feJordan Rose return UnknownVal(); 1935752bee2493ec2931bd18899753552e3a47dc85feJordan Rose 1936978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose return createLazyBinding(B, R); 19376e3f01cef27dd6cc7e36769618820c5b984f61daZhongxing Xu} 19386e3f01cef27dd6cc7e36769618820c5b984f61daZhongxing Xu 193918f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekSVal RegionStoreManager::getBindingForArray(RegionBindingsConstRef B, 1940978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose const TypedValueRegion *R) { 1941978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose assert(Ctx.getAsConstantArrayType(R->getValueType()) && 1942978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose "Only constant array types can have compound bindings."); 194387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 1944978aeac1a90020b2a0ae6c7eb7fe65aa8226f74aJordan Rose return createLazyBinding(B, R); 19453e001f393d112a50e13c9a8f9a4c0d97f3f51cf4Zhongxing Xu} 19463e001f393d112a50e13c9a8f9a4c0d97f3f51cf4Zhongxing Xu 1947fa7a95c62aa573a30d87c215b320b0086ed08bdcTed Kremenekbool RegionStoreManager::includedInBindings(Store store, 1948fa7a95c62aa573a30d87c215b320b0086ed08bdcTed Kremenek const MemRegion *region) const { 194929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef B = getRegionBindings(store); 1950fa7a95c62aa573a30d87c215b320b0086ed08bdcTed Kremenek region = region->getBaseRegion(); 19511e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 19521e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // Quick path: if the base is the head of a cluster, the region is live. 19531e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (B.lookup(region)) 19541e934431adba0f459668a59c6059b9596fd627b4Jordan Rose return true; 19551e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 19561e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // Slow path: if the region is the VALUE of any binding, it is live. 195729f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek for (RegionBindingsRef::iterator RI = B.begin(), RE = B.end(); RI != RE; ++RI) { 19581e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const ClusterBindings &Cluster = RI.getData(); 19591e934431adba0f459668a59c6059b9596fd627b4Jordan Rose for (ClusterBindings::iterator CI = Cluster.begin(), CE = Cluster.end(); 19601e934431adba0f459668a59c6059b9596fd627b4Jordan Rose CI != CE; ++CI) { 19611e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const SVal &D = CI.getData(); 19621e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (const MemRegion *R = D.getAsRegion()) 19631e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (R->getBaseRegion() == region) 19641e934431adba0f459668a59c6059b9596fd627b4Jordan Rose return true; 19651e934431adba0f459668a59c6059b9596fd627b4Jordan Rose } 1966fa7a95c62aa573a30d87c215b320b0086ed08bdcTed Kremenek } 19671e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 1968fa7a95c62aa573a30d87c215b320b0086ed08bdcTed Kremenek return false; 1969fa7a95c62aa573a30d87c215b320b0086ed08bdcTed Kremenek} 1970fa7a95c62aa573a30d87c215b320b0086ed08bdcTed Kremenek 19719af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 19729af46f59242cfaec74fa491a66724970478263ebTed Kremenek// Binding values to regions. 19739af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 19749af46f59242cfaec74fa491a66724970478263ebTed Kremenek 197556a46b51df691f857f7120aaf2d4deeff0b014deTed KremenekStoreRef RegionStoreManager::killBinding(Store ST, Loc L) { 1976dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie if (Optional<loc::MemRegionVal> LV = L.getAs<loc::MemRegionVal>()) 19775251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (const MemRegion* R = LV->getRegion()) 197829f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek return StoreRef(getRegionBindings(ST).removeBinding(R) 197929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek .asImmutableMap() 198029f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek .getRootWithoutRetain(), 198177a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek *this); 19821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 198356a46b51df691f857f7120aaf2d4deeff0b014deTed Kremenek return StoreRef(ST, *this); 19849af46f59242cfaec74fa491a66724970478263ebTed Kremenek} 19859af46f59242cfaec74fa491a66724970478263ebTed Kremenek 198618f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionBindingsRef 198718f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionStoreManager::bind(RegionBindingsConstRef B, Loc L, SVal V) { 19885251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (L.getAs<loc::ConcreteInt>()) 198918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return B; 199087453d1c39df791fb98618f6ba34b2edaae880e1Zhongxing Xu 19914193eca10ce0cc8b2dae887e935a43b26f492b5bZhongxing Xu // If we get here, the location should be a region. 19925251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie const MemRegion *R = L.castAs<loc::MemRegionVal>().getRegion(); 19931eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 19944193eca10ce0cc8b2dae887e935a43b26f492b5bZhongxing Xu // Check if the region is a struct region. 19958667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek if (const TypedValueRegion* TR = dyn_cast<TypedValueRegion>(R)) { 19968667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek QualType Ty = TR->getValueType(); 199732a549a64922af0903bdb777613ae7ae4490b70fTed Kremenek if (Ty->isArrayType()) 199818f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return bindArray(B, TR, V); 19998667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek if (Ty->isStructureOrClassType()) 200018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return bindStruct(B, TR, V); 20018667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek if (Ty->isVectorType()) 200218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return bindVector(B, TR, V); 20031dc31f5ead63d7197edf6f34a7821b93ea6698a1Jordan Rose if (Ty->isUnionType()) 20041dc31f5ead63d7197edf6f34a7821b93ea6698a1Jordan Rose return bindAggregate(B, TR, V); 20058667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek } 20061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2007e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose if (const SymbolicRegion *SR = dyn_cast<SymbolicRegion>(R)) { 20080954cdec4b13f1b3fd4c8711e02ded914968000bTed Kremenek // Binding directly to a symbolic region should be treated as binding 20090954cdec4b13f1b3fd4c8711e02ded914968000bTed Kremenek // to element 0. 2010732cdf383f9030ff2b9fb28dfbdae2285ded80c6Ted Kremenek QualType T = SR->getSymbol()->getType(); 20114e45dba1c0234eec7b7c348dbbf568c5ac9fc471Jordan Rose if (T->isAnyPointerType() || T->isReferenceType()) 20124e45dba1c0234eec7b7c348dbbf568c5ac9fc471Jordan Rose T = T->getPointeeType(); 2013852274d4257134906995cb252fb3dfd2d71deae8Ted Kremenek 20140954cdec4b13f1b3fd4c8711e02ded914968000bTed Kremenek R = GetElementZeroRegion(SR, T); 20150954cdec4b13f1b3fd4c8711e02ded914968000bTed Kremenek } 20161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2017e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose // Clear out bindings that may overlap with this binding. 201818f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef NewB = removeSubRegionBindings(B, cast<SubRegion>(R)); 201918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return NewB.addBinding(BindingKey::Make(R, BindingKey::Direct), V); 20209c9ca08fdd27fb0b025782aa41fae93612edf440Zhongxing Xu} 20219c9ca08fdd27fb0b025782aa41fae93612edf440Zhongxing Xu 202218f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionBindingsRef 202318f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionStoreManager::setImplicitDefaultValue(RegionBindingsConstRef B, 202418f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const MemRegion *R, 202518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek QualType T) { 2026027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek SVal V; 2027027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek 20287dfc9420babe83e236a47e752f8723bd06070d9dZhanyong Wan if (Loc::isLocType(T)) 2029c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek V = svalBuilder.makeNull(); 2030a5796f87229b4aeebca71fa6ee1790ae7a5a0382Jordan Rose else if (T->isIntegralOrEnumerationType()) 2031c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek V = svalBuilder.makeZeroVal(T); 2032fb87b89fc9eb103e19fb8e4b925c23f0bd091b99Douglas Gregor else if (T->isStructureOrClassType() || T->isArrayType()) { 2033027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek // Set the default value to a zero constant when it is a structure 2034027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek // or array. The type doesn't really matter. 2035c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek V = svalBuilder.makeZeroVal(Ctx.IntTy); 2036027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek } 2037027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek else { 2038eda368791b21aafaf87012c8552dc5181c0ff7a1Jordy Rose // We can't represent values of this type, but we still need to set a value 2039eda368791b21aafaf87012c8552dc5181c0ff7a1Jordy Rose // to record that the region has been initialized. 2040eda368791b21aafaf87012c8552dc5181c0ff7a1Jordy Rose // If this assertion ever fires, a new case should be added above -- we 2041eda368791b21aafaf87012c8552dc5181c0ff7a1Jordy Rose // should know how to default-initialize any value we can symbolicate. 2042eda368791b21aafaf87012c8552dc5181c0ff7a1Jordy Rose assert(!SymbolManager::canSymbolicate(T) && "This type is representable"); 2043eda368791b21aafaf87012c8552dc5181c0ff7a1Jordy Rose V = UnknownVal(); 2044027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek } 20451c1ae6bdaf89145648484db5dfebcd04a60595c9Ted Kremenek 204618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return B.addBinding(R, BindingKey::Default, V); 2047027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek} 2048e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 204918f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionBindingsRef 205018f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionStoreManager::bindArray(RegionBindingsConstRef B, 205118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const TypedValueRegion* R, 205218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal Init) { 2053e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 2054018220c343c103b7dfaa117a7a474c7a7fd6d068Zhongxing Xu const ArrayType *AT =cast<ArrayType>(Ctx.getCanonicalType(R->getValueType())); 2055e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek QualType ElementTy = AT->getElementType(); 2056fee90811c665893bc27a9bfa8b116548afe1b89bTed Kremenek Optional<uint64_t> Size; 2057e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 2058fee90811c665893bc27a9bfa8b116548afe1b89bTed Kremenek if (const ConstantArrayType* CAT = dyn_cast<ConstantArrayType>(AT)) 2059fee90811c665893bc27a9bfa8b116548afe1b89bTed Kremenek Size = CAT->getSize().getZExtValue(); 2060e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 2061167cc379756e525bdf5b6b722fd78d415ed0eb2cJordy Rose // Check if the init expr is a string literal. 2062dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie if (Optional<loc::MemRegionVal> MRV = Init.getAs<loc::MemRegionVal>()) { 20633881866dc782c5e13b21031bd363e93fbf367167Ted Kremenek const StringRegion *S = cast<StringRegion>(MRV->getRegion()); 20643881866dc782c5e13b21031bd363e93fbf367167Ted Kremenek 20653881866dc782c5e13b21031bd363e93fbf367167Ted Kremenek // Treat the string as a lazy compound value. 206618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek StoreRef store(B.asStore(), *this); 20675251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie nonloc::LazyCompoundVal LCV = svalBuilder.makeLazyCompoundVal(store, S) 20685251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie .castAs<nonloc::LazyCompoundVal>(); 206918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return bindAggregate(B, R, LCV); 20706987c7b74146b9658b1925c5981f8b0cd0672b55Zhongxing Xu } 20711a12a0ea00a62d785ce8c25e740a152015a3000aZhongxing Xu 2072a5e81f1240bcc5b9b0721fc6275075ad7cadaf5eTed Kremenek // Handle lazy compound values. 20735251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (Init.getAs<nonloc::LazyCompoundVal>()) 207418f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return bindAggregate(B, R, Init); 20751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 20761eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // Remaining case: explicit compound values. 2077e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 2078027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek if (Init.isUnknown()) 207918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return setImplicitDefaultValue(B, R, ElementTy); 2080e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 20815251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie const nonloc::CompoundVal& CV = Init.castAs<nonloc::CompoundVal>(); 20821a12a0ea00a62d785ce8c25e740a152015a3000aZhongxing Xu nonloc::CompoundVal::iterator VI = CV.begin(), VE = CV.end(); 2083465373946b5ae84f7c3d890cc25cb23fd88dd650Ted Kremenek uint64_t i = 0; 20841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 208518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef NewB(B); 208618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek 2087fee90811c665893bc27a9bfa8b116548afe1b89bTed Kremenek for (; Size.hasValue() ? i < Size.getValue() : true ; ++i, ++VI) { 2088087d6c20876ced37d544552b43cf33332687f074Zhongxing Xu // The init list might be shorter than the array length. 20894193eca10ce0cc8b2dae887e935a43b26f492b5bZhongxing Xu if (VI == VE) 20904193eca10ce0cc8b2dae887e935a43b26f492b5bZhongxing Xu break; 2091a82512a2735bed5a3498e7a5f24f4c365bbd5704Zhongxing Xu 2092c8413fd03f73084a5c93028f8b4db619fc388087Ted Kremenek const NonLoc &Idx = svalBuilder.makeArrayIndex(i); 209357663fe6c3c7a0fb792626537c4f3f7d3594aa66Zhongxing Xu const ElementRegion *ER = MRMgr.getElementRegion(ElementTy, Idx, R, Ctx); 2094c3a0599bac9dabbae9481674313aa6e1a26159b6Zhongxing Xu 2095fb87b89fc9eb103e19fb8e4b925c23f0bd091b99Douglas Gregor if (ElementTy->isStructureOrClassType()) 209618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek NewB = bindStruct(NewB, ER, *VI); 209759b6dca7e5160d6f2aff42b1cf077d1cbd64e330Jordy Rose else if (ElementTy->isArrayType()) 209818f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek NewB = bindArray(NewB, ER, *VI); 20994193eca10ce0cc8b2dae887e935a43b26f492b5bZhongxing Xu else 2100258277d5a922e06ef523f7805900689b680ddc7dJordan Rose NewB = bind(NewB, loc::MemRegionVal(ER), *VI); 2101c3a0599bac9dabbae9481674313aa6e1a26159b6Zhongxing Xu } 2102c3a0599bac9dabbae9481674313aa6e1a26159b6Zhongxing Xu 2103027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek // If the init list is shorter than the array length, set the 2104027e2667315f265a85c6241f26e8a514db219b3fTed Kremenek // array default value. 2105fee90811c665893bc27a9bfa8b116548afe1b89bTed Kremenek if (Size.hasValue() && i < Size.getValue()) 210618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek NewB = setImplicitDefaultValue(NewB, R, ElementTy); 2107087d6c20876ced37d544552b43cf33332687f074Zhongxing Xu 210818f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return NewB; 2109c3a0599bac9dabbae9481674313aa6e1a26159b6Zhongxing Xu} 2110c3a0599bac9dabbae9481674313aa6e1a26159b6Zhongxing Xu 211118f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionBindingsRef RegionStoreManager::bindVector(RegionBindingsConstRef B, 211218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const TypedValueRegion* R, 211318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal V) { 21148667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek QualType T = R->getValueType(); 21158667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek assert(T->isVectorType()); 21168667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek const VectorType *VT = T->getAs<VectorType>(); // Use getAs for typedefs. 211787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 21185ad76c073e1822d11901a8552c6aa9372038b5f0Jordan Rose // Handle lazy compound values and symbolic values. 21195251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (V.getAs<nonloc::LazyCompoundVal>() || V.getAs<nonloc::SymbolVal>()) 212018f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return bindAggregate(B, R, V); 212187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 21228667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek // We may get non-CompoundVal accidentally due to imprecise cast logic or 21238667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek // that we are binding symbolic struct value. Kill the field values, and if 21248667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek // the value is symbolic go and bind it as a "default" binding. 21255251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (!V.getAs<nonloc::CompoundVal>()) { 212618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return bindAggregate(B, R, UnknownVal()); 21278667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek } 21288667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek 21298667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek QualType ElemType = VT->getElementType(); 21305251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie nonloc::CompoundVal CV = V.castAs<nonloc::CompoundVal>(); 21318667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek nonloc::CompoundVal::iterator VI = CV.begin(), VE = CV.end(); 21328667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek unsigned index = 0, numElements = VT->getNumElements(); 213318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef NewB(B); 213418f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek 21358667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek for ( ; index != numElements ; ++index) { 21368667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek if (VI == VE) 21378667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek break; 213887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 21398667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek NonLoc Idx = svalBuilder.makeArrayIndex(index); 21408667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek const ElementRegion *ER = MRMgr.getElementRegion(ElemType, Idx, R, Ctx); 2141258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 21428667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek if (ElemType->isArrayType()) 214318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek NewB = bindArray(NewB, ER, *VI); 21448667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek else if (ElemType->isStructureOrClassType()) 214518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek NewB = bindStruct(NewB, ER, *VI); 21468667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek else 2147258277d5a922e06ef523f7805900689b680ddc7dJordan Rose NewB = bind(NewB, loc::MemRegionVal(ER), *VI); 2148258277d5a922e06ef523f7805900689b680ddc7dJordan Rose } 2149258277d5a922e06ef523f7805900689b680ddc7dJordan Rose return NewB; 2150258277d5a922e06ef523f7805900689b680ddc7dJordan Rose} 2151258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 2152258277d5a922e06ef523f7805900689b680ddc7dJordan RoseOptional<RegionBindingsRef> 2153258277d5a922e06ef523f7805900689b680ddc7dJordan RoseRegionStoreManager::tryBindSmallStruct(RegionBindingsConstRef B, 2154258277d5a922e06ef523f7805900689b680ddc7dJordan Rose const TypedValueRegion *R, 2155258277d5a922e06ef523f7805900689b680ddc7dJordan Rose const RecordDecl *RD, 2156258277d5a922e06ef523f7805900689b680ddc7dJordan Rose nonloc::LazyCompoundVal LCV) { 2157258277d5a922e06ef523f7805900689b680ddc7dJordan Rose FieldVector Fields; 2158258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 2159258277d5a922e06ef523f7805900689b680ddc7dJordan Rose if (const CXXRecordDecl *Class = dyn_cast<CXXRecordDecl>(RD)) 2160258277d5a922e06ef523f7805900689b680ddc7dJordan Rose if (Class->getNumBases() != 0 || Class->getNumVBases() != 0) 2161258277d5a922e06ef523f7805900689b680ddc7dJordan Rose return None; 2162258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 2163651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines for (const auto *FD : RD->fields()) { 2164258277d5a922e06ef523f7805900689b680ddc7dJordan Rose if (FD->isUnnamedBitfield()) 2165258277d5a922e06ef523f7805900689b680ddc7dJordan Rose continue; 2166258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 2167258277d5a922e06ef523f7805900689b680ddc7dJordan Rose // If there are too many fields, or if any of the fields are aggregates, 2168258277d5a922e06ef523f7805900689b680ddc7dJordan Rose // just use the LCV as a default binding. 2169258277d5a922e06ef523f7805900689b680ddc7dJordan Rose if (Fields.size() == SmallStructLimit) 2170258277d5a922e06ef523f7805900689b680ddc7dJordan Rose return None; 2171258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 2172258277d5a922e06ef523f7805900689b680ddc7dJordan Rose QualType Ty = FD->getType(); 2173258277d5a922e06ef523f7805900689b680ddc7dJordan Rose if (!(Ty->isScalarType() || Ty->isReferenceType())) 2174258277d5a922e06ef523f7805900689b680ddc7dJordan Rose return None; 2175258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 2176651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines Fields.push_back(FD); 21778667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek } 2178258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 2179258277d5a922e06ef523f7805900689b680ddc7dJordan Rose RegionBindingsRef NewB = B; 218087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 2181258277d5a922e06ef523f7805900689b680ddc7dJordan Rose for (FieldVector::iterator I = Fields.begin(), E = Fields.end(); I != E; ++I){ 2182258277d5a922e06ef523f7805900689b680ddc7dJordan Rose const FieldRegion *SourceFR = MRMgr.getFieldRegion(*I, LCV.getRegion()); 2183258277d5a922e06ef523f7805900689b680ddc7dJordan Rose SVal V = getBindingForField(getRegionBindings(LCV.getStore()), SourceFR); 2184258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 2185258277d5a922e06ef523f7805900689b680ddc7dJordan Rose const FieldRegion *DestFR = MRMgr.getFieldRegion(*I, R); 2186258277d5a922e06ef523f7805900689b680ddc7dJordan Rose NewB = bind(NewB, loc::MemRegionVal(DestFR), V); 2187258277d5a922e06ef523f7805900689b680ddc7dJordan Rose } 2188258277d5a922e06ef523f7805900689b680ddc7dJordan Rose 218918f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return NewB; 21908667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek} 21918667052a53a47a6290dc9ae98e5c3d9277df5f4aTed Kremenek 219218f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionBindingsRef RegionStoreManager::bindStruct(RegionBindingsConstRef B, 219318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const TypedValueRegion* R, 219418f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal V) { 219567f28534c090650ffa123afa84ff4a96f56de14eTed Kremenek if (!Features.supportsFields()) 219618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return B; 21971eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2198018220c343c103b7dfaa117a7a474c7a7fd6d068Zhongxing Xu QualType T = R->getValueType(); 2199fb87b89fc9eb103e19fb8e4b925c23f0bd091b99Douglas Gregor assert(T->isStructureOrClassType()); 2200af0a844542247d337947b4585e684b5eb72d4ffbZhongxing Xu 22016217b80b7a1379b74cced1c076338262c3c980b3Ted Kremenek const RecordType* RT = T->getAs<RecordType>(); 2202258277d5a922e06ef523f7805900689b680ddc7dJordan Rose const RecordDecl *RD = RT->getDecl(); 2203c45a8253cadb640dee1d8f23fba4a6c6f8da27f4Zhongxing Xu 22045e1cdac63c3d9c9b32fa41fa0b2d242a58a20d49John McCall if (!RD->isCompleteDefinition()) 220518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return B; 2206af0a844542247d337947b4585e684b5eb72d4ffbZhongxing Xu 22075ad76c073e1822d11901a8552c6aa9372038b5f0Jordan Rose // Handle lazy compound values and symbolic values. 2208258277d5a922e06ef523f7805900689b680ddc7dJordan Rose if (Optional<nonloc::LazyCompoundVal> LCV = 2209258277d5a922e06ef523f7805900689b680ddc7dJordan Rose V.getAs<nonloc::LazyCompoundVal>()) { 2210258277d5a922e06ef523f7805900689b680ddc7dJordan Rose if (Optional<RegionBindingsRef> NewB = tryBindSmallStruct(B, R, RD, *LCV)) 2211258277d5a922e06ef523f7805900689b680ddc7dJordan Rose return *NewB; 2212258277d5a922e06ef523f7805900689b680ddc7dJordan Rose return bindAggregate(B, R, V); 2213258277d5a922e06ef523f7805900689b680ddc7dJordan Rose } 2214258277d5a922e06ef523f7805900689b680ddc7dJordan Rose if (V.getAs<nonloc::SymbolVal>()) 221518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return bindAggregate(B, R, V); 22161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2217281e9dc6ba6ff10bf910b0fc8898dff2a429f156Ted Kremenek // We may get non-CompoundVal accidentally due to imprecise cast logic or 2218281e9dc6ba6ff10bf910b0fc8898dff2a429f156Ted Kremenek // that we are binding symbolic struct value. Kill the field values, and if 2219281e9dc6ba6ff10bf910b0fc8898dff2a429f156Ted Kremenek // the value is symbolic go and bind it as a "default" binding. 22205251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie if (V.isUnknown() || !V.getAs<nonloc::CompoundVal>()) 222118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return bindAggregate(B, R, UnknownVal()); 22223f6978a3fefc16f203afbc64697fe04af329cf2bZhongxing Xu 22235251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie const nonloc::CompoundVal& CV = V.castAs<nonloc::CompoundVal>(); 2224af0a844542247d337947b4585e684b5eb72d4ffbZhongxing Xu nonloc::CompoundVal::iterator VI = CV.begin(), VE = CV.end(); 2225dbdf2195803e8e723f25176627caef05740cfbb1Zhongxing Xu 2226dbdf2195803e8e723f25176627caef05740cfbb1Zhongxing Xu RecordDecl::field_iterator FI, FE; 222718f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek RegionBindingsRef NewB(B); 222818f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek 2229e42a0ab77ca4ad5201591aac5679ef47a08af4b6Jim Goodnow II for (FI = RD->field_begin(), FE = RD->field_end(); FI != FE; ++FI) { 2230af0a844542247d337947b4585e684b5eb72d4ffbZhongxing Xu 2231dbdf2195803e8e723f25176627caef05740cfbb1Zhongxing Xu if (VI == VE) 22324193eca10ce0cc8b2dae887e935a43b26f492b5bZhongxing Xu break; 2233ea8a1854137faca10ccb24acf4f1a74912fccfb2Zhongxing Xu 2234e42a0ab77ca4ad5201591aac5679ef47a08af4b6Jim Goodnow II // Skip any unnamed bitfields to stay in sync with the initializers. 2235262bc18e32500558af7cb0afa205b34bd37bafedDavid Blaikie if (FI->isUnnamedBitfield()) 2236e42a0ab77ca4ad5201591aac5679ef47a08af4b6Jim Goodnow II continue; 2237e42a0ab77ca4ad5201591aac5679ef47a08af4b6Jim Goodnow II 2238262bc18e32500558af7cb0afa205b34bd37bafedDavid Blaikie QualType FTy = FI->getType(); 2239581deb3da481053c4993c7600f97acf7768caac5David Blaikie const FieldRegion* FR = MRMgr.getFieldRegion(*FI, R); 2240ea8a1854137faca10ccb24acf4f1a74912fccfb2Zhongxing Xu 2241cf54959eae25fb3050f41833f0eab91042fb1269Ted Kremenek if (FTy->isArrayType()) 224218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek NewB = bindArray(NewB, FR, *VI); 2243fb87b89fc9eb103e19fb8e4b925c23f0bd091b99Douglas Gregor else if (FTy->isStructureOrClassType()) 224418f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek NewB = bindStruct(NewB, FR, *VI); 2245cf54959eae25fb3050f41833f0eab91042fb1269Ted Kremenek else 2246258277d5a922e06ef523f7805900689b680ddc7dJordan Rose NewB = bind(NewB, loc::MemRegionVal(FR), *VI); 2247e42a0ab77ca4ad5201591aac5679ef47a08af4b6Jim Goodnow II ++VI; 2248c3a0599bac9dabbae9481674313aa6e1a26159b6Zhongxing Xu } 2249c3a0599bac9dabbae9481674313aa6e1a26159b6Zhongxing Xu 2250dbdf2195803e8e723f25176627caef05740cfbb1Zhongxing Xu // There may be fewer values in the initialize list than the fields of struct. 225113d50177b13161b209579e1f30a5e3cc72f7e2bdZhongxing Xu if (FI != FE) { 225218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek NewB = NewB.addBinding(R, BindingKey::Default, 225318f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek svalBuilder.makeIntVal(0, false)); 225413d50177b13161b209579e1f30a5e3cc72f7e2bdZhongxing Xu } 2255dbdf2195803e8e723f25176627caef05740cfbb1Zhongxing Xu 225618f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return NewB; 2257c3a0599bac9dabbae9481674313aa6e1a26159b6Zhongxing Xu} 2258c3a0599bac9dabbae9481674313aa6e1a26159b6Zhongxing Xu 225918f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionBindingsRef 226018f860ee6cc43c8fc80834073b097eb5c02b22cfTed KremenekRegionStoreManager::bindAggregate(RegionBindingsConstRef B, 226118f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek const TypedRegion *R, 226218f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek SVal Val) { 2263e0d24eb1060a213ec9820dc02c45f26b2d5b348bJordan Rose // Remove the old bindings, using 'R' as the root of all regions 22645ad76c073e1822d11901a8552c6aa9372038b5f0Jordan Rose // we will invalidate. Then add the new binding. 226518f860ee6cc43c8fc80834073b097eb5c02b22cfTed Kremenek return removeSubRegionBindings(B, R).addBinding(R, BindingKey::Default, Val); 22661e934431adba0f459668a59c6059b9596fd627b4Jordan Rose} 22671e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 22689af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 22699af46f59242cfaec74fa491a66724970478263ebTed Kremenek// State pruning. 22709af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 2271e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 22725499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremeneknamespace { 2273db0594bfc013131f88429add4eb653c285fa94fbTed Kremenekclass removeDeadBindingsWorker : 2274db0594bfc013131f88429add4eb653c285fa94fbTed Kremenek public ClusterAnalysis<removeDeadBindingsWorker> { 22755f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner SmallVector<const SymbolicRegion*, 12> Postponed; 22765499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek SymbolReaper &SymReaper; 227717ddf1c108bb847fb05111fec09d664c9bb2e49bZhongxing Xu const StackFrameContext *CurrentLCtx; 2278dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 22795499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenekpublic: 22801437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks removeDeadBindingsWorker(RegionStoreManager &rm, 22811437425a62dbf7bdb0a855d3ed3b05ed2019ec1eAnna Zaks ProgramStateManager &stateMgr, 228229f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef b, SymbolReaper &symReaper, 22837dadf79bd809cc01fe275f9a7243593bc2af5c10Jordy Rose const StackFrameContext *LCtx) 228487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar : ClusterAnalysis<removeDeadBindingsWorker>(rm, stateMgr, b), 22857dadf79bd809cc01fe275f9a7243593bc2af5c10Jordy Rose SymReaper(symReaper), CurrentLCtx(LCtx) {} 22865499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 22875499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // Called by ClusterAnalysis. 22881e934431adba0f459668a59c6059b9596fd627b4Jordan Rose void VisitAddedToCluster(const MemRegion *baseR, const ClusterBindings &C); 2289f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose void VisitCluster(const MemRegion *baseR, const ClusterBindings *C); 2290aa5573364b79bf4d85380aaec59cae2eeefcb322Jordan Rose using ClusterAnalysis<removeDeadBindingsWorker>::VisitCluster; 22915499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 229287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar using ClusterAnalysis::AddToWorkList; 229387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 229487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar bool AddToWorkList(const MemRegion *R); 229587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 22965499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek bool UpdatePostponed(); 22975499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek void VisitBinding(SVal V); 22985499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek}; 22995499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek} 23001eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 230187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainarbool removeDeadBindingsWorker::AddToWorkList(const MemRegion *R) { 230287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar const MemRegion *BaseR = R->getBaseRegion(); 230387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar return AddToWorkList(WorkListElement(BaseR), getCluster(BaseR)); 230487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar} 230587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 2306db0594bfc013131f88429add4eb653c285fa94fbTed Kremenekvoid removeDeadBindingsWorker::VisitAddedToCluster(const MemRegion *baseR, 23071e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const ClusterBindings &C) { 2308e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 23095499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek if (const VarRegion *VR = dyn_cast<VarRegion>(baseR)) { 23107dadf79bd809cc01fe275f9a7243593bc2af5c10Jordy Rose if (SymReaper.isLive(VR)) 23111e934431adba0f459668a59c6059b9596fd627b4Jordan Rose AddToWorkList(baseR, &C); 2312e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 23135499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return; 23149af46f59242cfaec74fa491a66724970478263ebTed Kremenek } 2315e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 23165499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek if (const SymbolicRegion *SR = dyn_cast<SymbolicRegion>(baseR)) { 23175499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek if (SymReaper.isLive(SR->getSymbol())) 23181e934431adba0f459668a59c6059b9596fd627b4Jordan Rose AddToWorkList(SR, &C); 23195499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek else 23205499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek Postponed.push_back(SR); 2321e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 23225499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return; 23239af46f59242cfaec74fa491a66724970478263ebTed Kremenek } 232417ddf1c108bb847fb05111fec09d664c9bb2e49bZhongxing Xu 2325dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek if (isa<NonStaticGlobalSpaceRegion>(baseR)) { 23261e934431adba0f459668a59c6059b9596fd627b4Jordan Rose AddToWorkList(baseR, &C); 2327dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek return; 2328dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek } 2329dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek 233017ddf1c108bb847fb05111fec09d664c9bb2e49bZhongxing Xu // CXXThisRegion in the current or parent location context is live. 233117ddf1c108bb847fb05111fec09d664c9bb2e49bZhongxing Xu if (const CXXThisRegion *TR = dyn_cast<CXXThisRegion>(baseR)) { 2332dcee3ce97fc76f20ce8f5a7451071e3dec537073Ted Kremenek const StackArgumentsSpaceRegion *StackReg = 233317ddf1c108bb847fb05111fec09d664c9bb2e49bZhongxing Xu cast<StackArgumentsSpaceRegion>(TR->getSuperRegion()); 233417ddf1c108bb847fb05111fec09d664c9bb2e49bZhongxing Xu const StackFrameContext *RegCtx = StackReg->getStackFrame(); 23358501b7a1c4c4a9ba0ea6cb8e500e601ef3759debAnna Zaks if (CurrentLCtx && 23368501b7a1c4c4a9ba0ea6cb8e500e601ef3759debAnna Zaks (RegCtx == CurrentLCtx || RegCtx->isParentOf(CurrentLCtx))) 23371e934431adba0f459668a59c6059b9596fd627b4Jordan Rose AddToWorkList(TR, &C); 233817ddf1c108bb847fb05111fec09d664c9bb2e49bZhongxing Xu } 23395499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek} 23401eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2341db0594bfc013131f88429add4eb653c285fa94fbTed Kremenekvoid removeDeadBindingsWorker::VisitCluster(const MemRegion *baseR, 2342f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose const ClusterBindings *C) { 2343f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose if (!C) 2344f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose return; 2345f8ddc098981d4d85cad4e72fc6dfcfe83b842b66Jordan Rose 2346f6d05bbedd482e634507a099e3416fa05cbc0e78Jordan Rose // Mark the symbol for any SymbolicRegion with live bindings as live itself. 2347f6d05bbedd482e634507a099e3416fa05cbc0e78Jordan Rose // This means we should continue to track that symbol. 2348f6d05bbedd482e634507a099e3416fa05cbc0e78Jordan Rose if (const SymbolicRegion *SymR = dyn_cast<SymbolicRegion>(baseR)) 2349f6d05bbedd482e634507a099e3416fa05cbc0e78Jordan Rose SymReaper.markLive(SymR->getSymbol()); 2350f6d05bbedd482e634507a099e3416fa05cbc0e78Jordan Rose 235187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar for (ClusterBindings::iterator I = C->begin(), E = C->end(); I != E; ++I) { 235287d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar // Element index of a binding key is live. 235387d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar SymReaper.markElementIndicesLive(I.getKey().getRegion()); 235487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 23551e934431adba0f459668a59c6059b9596fd627b4Jordan Rose VisitBinding(I.getData()); 235687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar } 23575499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek} 2358df165014c2defd9120a8f105a855d6a8b35befbeTed Kremenek 2359db0594bfc013131f88429add4eb653c285fa94fbTed Kremenekvoid removeDeadBindingsWorker::VisitBinding(SVal V) { 23605499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // Is it a LazyCompoundVal? All referenced regions are live as well. 2361dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie if (Optional<nonloc::LazyCompoundVal> LCS = 23625251abea41b446c26e3239c8dd6c7edea6fc335dDavid Blaikie V.getAs<nonloc::LazyCompoundVal>()) { 23639e17cc6abb5d55bd776d379b20d5b476bcc46c71Ted Kremenek 236428743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose const RegionStoreManager::SValListTy &Vals = RM.getInterestingValues(*LCS); 23650a0f1309d0fbeb0e77edbbc4e0b15cc330c3a28cJordan Rose 236628743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose for (RegionStoreManager::SValListTy::const_iterator I = Vals.begin(), 236728743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose E = Vals.end(); 236828743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose I != E; ++I) 236928743b006bd88cd7d0ea97b4f17646f8fc429b89Jordan Rose VisitBinding(*I); 23701e934431adba0f459668a59c6059b9596fd627b4Jordan Rose 23715499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return; 23725499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek } 23739e17cc6abb5d55bd776d379b20d5b476bcc46c71Ted Kremenek 23745499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // If V is a region, then add it to the worklist. 23757fa9b4f258636d89342eda28f21a986c8ac353b1Ted Kremenek if (const MemRegion *R = V.getAsRegion()) { 23765499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek AddToWorkList(R); 237787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar SymReaper.markLive(R); 237887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 23797fa9b4f258636d89342eda28f21a986c8ac353b1Ted Kremenek // All regions captured by a block are also live. 23807fa9b4f258636d89342eda28f21a986c8ac353b1Ted Kremenek if (const BlockDataRegion *BR = dyn_cast<BlockDataRegion>(R)) { 23817fa9b4f258636d89342eda28f21a986c8ac353b1Ted Kremenek BlockDataRegion::referenced_vars_iterator I = BR->referenced_vars_begin(), 23827fa9b4f258636d89342eda28f21a986c8ac353b1Ted Kremenek E = BR->referenced_vars_end(); 2383f6d05bbedd482e634507a099e3416fa05cbc0e78Jordan Rose for ( ; I != E; ++I) 2384f6d05bbedd482e634507a099e3416fa05cbc0e78Jordan Rose AddToWorkList(I.getCapturedRegion()); 23857fa9b4f258636d89342eda28f21a986c8ac353b1Ted Kremenek } 23867fa9b4f258636d89342eda28f21a986c8ac353b1Ted Kremenek } 238787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar 23881eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2389aace9ef279be3dadd53b481aee568bd7701178b4Anna Zaks // Update the set of live symbols. 23901d1d515b2bafb59d624883d8fdda97d4b7dba0cbAnna Zaks for (SymExpr::symbol_iterator SI = V.symbol_begin(), SE = V.symbol_end(); 23911d1d515b2bafb59d624883d8fdda97d4b7dba0cbAnna Zaks SI!=SE; ++SI) 23925499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek SymReaper.markLive(*SI); 23935499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek} 2394e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 2395db0594bfc013131f88429add4eb653c285fa94fbTed Kremenekbool removeDeadBindingsWorker::UpdatePostponed() { 239601756192fe41f07b36498ab5ead5653d6dae16feTed Kremenek // See if any postponed SymbolicRegions are actually live now, after 239701756192fe41f07b36498ab5ead5653d6dae16feTed Kremenek // having done a scan. 23985499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek bool changed = false; 23995499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 24005f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner for (SmallVectorImpl<const SymbolicRegion*>::iterator 24015499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek I = Postponed.begin(), E = Postponed.end() ; I != E ; ++I) { 2402f6d05bbedd482e634507a099e3416fa05cbc0e78Jordan Rose if (const SymbolicRegion *SR = *I) { 240301756192fe41f07b36498ab5ead5653d6dae16feTed Kremenek if (SymReaper.isLive(SR->getSymbol())) { 24045499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek changed |= AddToWorkList(SR); 24056bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines *I = nullptr; 240601756192fe41f07b36498ab5ead5653d6dae16feTed Kremenek } 240701756192fe41f07b36498ab5ead5653d6dae16feTed Kremenek } 240801756192fe41f07b36498ab5ead5653d6dae16feTed Kremenek } 2409e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 24105499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek return changed; 24115499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek} 24125499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 241377a4d5687c2cb3199c689892c9d040a94ff270afTed KremenekStoreRef RegionStoreManager::removeDeadBindings(Store store, 241477a4d5687c2cb3199c689892c9d040a94ff270afTed Kremenek const StackFrameContext *LCtx, 2415bea2753da897ede723e70bcd17023d050b0603d0Ted Kremenek SymbolReaper& SymReaper) { 241629f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef B = getRegionBindings(store); 2417db0594bfc013131f88429add4eb653c285fa94fbTed Kremenek removeDeadBindingsWorker W(*this, StateMgr, B, SymReaper, LCtx); 24185499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek W.GenerateClusters(); 24195499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 24205499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // Enqueue the region roots onto the worklist. 2421bea2753da897ede723e70bcd17023d050b0603d0Ted Kremenek for (SymbolReaper::region_iterator I = SymReaper.region_begin(), 2422bea2753da897ede723e70bcd17023d050b0603d0Ted Kremenek E = SymReaper.region_end(); I != E; ++I) { 24235499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek W.AddToWorkList(*I); 2424bea2753da897ede723e70bcd17023d050b0603d0Ted Kremenek } 24255499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 24265499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek do W.RunWorkList(); while (W.UpdatePostponed()); 2427e5ea0cae7769866b5a5f9fa979e7c9d1d23a6bccTed Kremenek 24289af46f59242cfaec74fa491a66724970478263ebTed Kremenek // We have now scanned the store, marking reachable regions and symbols 24299af46f59242cfaec74fa491a66724970478263ebTed Kremenek // as live. We now remove all the regions that are dead from the store 24301eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // as well as update DSymbols with the set symbols that are now dead. 243129f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek for (RegionBindingsRef::iterator I = B.begin(), E = B.end(); I != E; ++I) { 24321e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const MemRegion *Base = I.getKey(); 24335499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek 2434b7118f7c379a652a910f92c4566cffceb2a8b5feTed Kremenek // If the cluster has been visited, we know the region has been marked. 24351e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (W.isVisited(Base)) 24369af46f59242cfaec74fa491a66724970478263ebTed Kremenek continue; 24371eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24385499b8487c56917e17ed5a03d95898e8b7e41e45Ted Kremenek // Remove the dead entry. 243929f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek B = B.remove(Base); 24401eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24411e934431adba0f459668a59c6059b9596fd627b4Jordan Rose if (const SymbolicRegion *SymR = dyn_cast<SymbolicRegion>(Base)) 24429af46f59242cfaec74fa491a66724970478263ebTed Kremenek SymReaper.maybeDead(SymR->getSymbol()); 24431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24441e934431adba0f459668a59c6059b9596fd627b4Jordan Rose // Mark all non-live symbols that this binding references as dead. 24451e934431adba0f459668a59c6059b9596fd627b4Jordan Rose const ClusterBindings &Cluster = I.getData(); 24461e934431adba0f459668a59c6059b9596fd627b4Jordan Rose for (ClusterBindings::iterator CI = Cluster.begin(), CE = Cluster.end(); 24471e934431adba0f459668a59c6059b9596fd627b4Jordan Rose CI != CE; ++CI) { 24481e934431adba0f459668a59c6059b9596fd627b4Jordan Rose SVal X = CI.getData(); 24491e934431adba0f459668a59c6059b9596fd627b4Jordan Rose SymExpr::symbol_iterator SI = X.symbol_begin(), SE = X.symbol_end(); 24501e934431adba0f459668a59c6059b9596fd627b4Jordan Rose for (; SI != SE; ++SI) 24511e934431adba0f459668a59c6059b9596fd627b4Jordan Rose SymReaper.maybeDead(*SI); 24521e934431adba0f459668a59c6059b9596fd627b4Jordan Rose } 2453093569cfab473e7b461523136a4df30a0473324dTed Kremenek } 24545e4cb347cbf12c292b80386c872e5eaef21b5c23Zhongxing Xu 24550c312a90c5b9d27e1425bf8d0448e133a97806ceTed Kremenek return StoreRef(B.asStore(), *this); 24569af46f59242cfaec74fa491a66724970478263ebTed Kremenek} 24579af46f59242cfaec74fa491a66724970478263ebTed Kremenek 24589af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 24599af46f59242cfaec74fa491a66724970478263ebTed Kremenek// Utility methods. 24609af46f59242cfaec74fa491a66724970478263ebTed Kremenek//===----------------------------------------------------------------------===// 24619af46f59242cfaec74fa491a66724970478263ebTed Kremenek 24629c378f705405d37f49795d5e915989de774fe11fTed Kremenekvoid RegionStoreManager::print(Store store, raw_ostream &OS, 24639af46f59242cfaec74fa491a66724970478263ebTed Kremenek const char* nl, const char *sep) { 246429f5ccd7ef9bc066cb5894834945eaad2c4c7e53Ted Kremenek RegionBindingsRef B = getRegionBindings(store); 24656341931b144cbf369ab816e871322c99ee62bea7Ted Kremenek OS << "Store (direct and default bindings), " 24660c312a90c5b9d27e1425bf8d0448e133a97806ceTed Kremenek << B.asStore() 24676341931b144cbf369ab816e871322c99ee62bea7Ted Kremenek << " :" << nl; 2468b0abacf2f1f77214e4c77d6ec8a02b097bb98f7aTed Kremenek B.dump(OS, nl); 24699af46f59242cfaec74fa491a66724970478263ebTed Kremenek} 2470