SVals.h revision a90ccfe03ce62f4c33cbb96982947cf474b4fae4
1a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//== RValues.h - Abstract RValues for Path-Sens. Value Tracking -*- C++ -*--==// 2a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// 3a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// The LLVM Compiler Infrastructure 4a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// 5a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// This file is distributed under the University of Illinois Open Source 6a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// License. See LICENSE.TXT for details. 7a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// 8a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//===----------------------------------------------------------------------===// 9a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// 10a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// This files defines RValue, LValue, and NonLValue, classes that represent 11a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// abstract r-values for use with path-sensitive value tracking. 12a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// 13a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//===----------------------------------------------------------------------===// 14a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 15a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#ifndef LLVM_CLANG_ANALYSIS_RVALUE_H 16a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#define LLVM_CLANG_ANALYSIS_RVALUE_H 17a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 18a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// FIXME: reduce the number of includes. 19a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 20a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "clang/Analysis/PathSensitive/GREngine.h" 21a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "clang/AST/Expr.h" 22a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "clang/AST/Decl.h" 23a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "clang/AST/ASTContext.h" 24a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "clang/Analysis/Analyses/LiveVariables.h" 25a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 26a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/Support/Casting.h" 27a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/Support/DataTypes.h" 28a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/ADT/APSInt.h" 29a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/ADT/FoldingSet.h" 30a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/ADT/ImmutableMap.h" 31a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/ADT/SmallVector.h" 32a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/ADT/SmallPtrSet.h" 33a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/Support/Allocator.h" 34a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/Support/Compiler.h" 35a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include "llvm/Support/Streams.h" 36a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 37a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#include <functional> 38a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 39a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 40a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// RValue "management" data structures. 41a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 42a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 43a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremeneknamespace clang { 44a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 45a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass SymbolID { 46a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek unsigned Data; 47a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 48a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolID() : Data(~0) {} 49a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolID(unsigned x) : Data(x) {} 50a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 51a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek bool isInitialized() const { return Data != (unsigned) ~0; } 52a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek operator unsigned() const { assert (isInitialized()); return Data; } 53a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 54a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 55a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass SymbolData { 56a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek uintptr_t Data; 57a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 58a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek enum Kind { ParmKind = 0x0, Mask = 0x3 }; 59a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 60a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolData(ParmVarDecl* D) 61a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek : Data(reinterpret_cast<uintptr_t>(D) | ParmKind) {} 62a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 63a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek inline Kind getKind() const { return (Kind) (Data & Mask); } 64a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek inline void* getPtr() const { return reinterpret_cast<void*>(Data & ~Mask); } 65a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek inline bool operator==(const SymbolData& R) const { return Data == R.Data; } 66a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 67a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 68a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass SymbolManager { 69a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek std::vector<SymbolData> SymbolToData; 70a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 71a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek typedef llvm::DenseMap<void*,SymbolID> MapTy; 72a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek MapTy DataToSymbol; 73a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 74a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 75a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolManager(); 76a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ~SymbolManager(); 77a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 78a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolData getSymbolData(SymbolID id) const { 79a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek assert (id < SymbolToData.size()); 80a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return SymbolToData[id]; 81a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 82a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 83a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolID getSymbol(ParmVarDecl* D); 84a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 85a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 86a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass ValueManager { 87a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek typedef llvm::FoldingSet<llvm::FoldingSetNodeWrapper<llvm::APSInt> > 88a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek APSIntSetTy; 89a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 90a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ASTContext& Ctx; 91a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek APSIntSetTy APSIntSet; 92a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek llvm::BumpPtrAllocator BPAlloc; 93a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 94a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 95a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ValueManager(ASTContext& ctx) : Ctx(ctx) {} 96a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ~ValueManager(); 97a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 98a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ASTContext& getContext() const { return Ctx; } 99a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek llvm::APSInt& getValue(const llvm::APSInt& X); 100a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek llvm::APSInt& getValue(uint64_t X, unsigned BitWidth, bool isUnsigned); 101a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek llvm::APSInt& getValue(uint64_t X, QualType T, 102a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SourceLocation Loc = SourceLocation()); 103a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 104a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 105a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 106a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// Base RValue types. 107a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 108a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 109a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass RValue { 110a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 111a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek enum BaseKind { LValueKind=0x0, 112a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValueKind=0x1, 113a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek UninitializedKind=0x2, 114a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek InvalidKind=0x3 }; 115a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 116a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek enum { BaseBits = 2, 117a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek BaseMask = 0x3 }; 118a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 119a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekprivate: 120a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek void* Data; 121a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek unsigned Kind; 122a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 123a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekprotected: 124a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek RValue(const void* d, bool isLValue, unsigned ValKind) 125a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek : Data(const_cast<void*>(d)), 126a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek Kind((isLValue ? LValueKind : NonLValueKind) | (ValKind << BaseBits)) {} 127a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 128a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek explicit RValue(BaseKind k) 129a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek : Data(0), Kind(k) {} 130a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 131a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek void* getRawPtr() const { 132a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return reinterpret_cast<void*>(Data); 133a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 134a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 135a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 136a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ~RValue() {}; 137a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 138a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek RValue Cast(ValueManager& ValMgr, Expr* CastExpr) const; 139a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 140a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek unsigned getRawKind() const { return Kind; } 141a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek BaseKind getBaseKind() const { return (BaseKind) (Kind & BaseMask); } 142a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek unsigned getSubKind() const { return (Kind & ~BaseMask) >> BaseBits; } 143a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 144a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek void Profile(llvm::FoldingSetNodeID& ID) const { 145a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ID.AddInteger((unsigned) getRawKind()); 146a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ID.AddPointer(reinterpret_cast<void*>(Data)); 147a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 148a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 149a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek bool operator==(const RValue& RHS) const { 150a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return getRawKind() == RHS.getRawKind() && Data == RHS.Data; 151a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 152a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 153a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static RValue GetSymbolValue(SymbolManager& SymMgr, ParmVarDecl *D); 154a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 155a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek inline bool isValid() const { return getRawKind() != InvalidKind; } 156a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek inline bool isInvalid() const { return getRawKind() == InvalidKind; } 157a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 158a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek void print(std::ostream& OS) const; 159a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek void print() const { print(*llvm::cerr.stream()); } 160a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 161a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Implement isa<T> support. 162a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline bool classof(const RValue*) { return true; } 163a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 164a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 165a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass InvalidValue : public RValue { 166a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 167a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek InvalidValue() : RValue(InvalidKind) {} 168a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 169a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline bool classof(const RValue* V) { 170a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V->getBaseKind() == InvalidKind; 171a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 172a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 173a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 174a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass UninitializedValue : public RValue { 175a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 176a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek UninitializedValue() : RValue(UninitializedKind) {} 177a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 178a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline bool classof(const RValue* V) { 179a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V->getBaseKind() == UninitializedKind; 180a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 181a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 182a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 183a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass NonLValue : public RValue { 184a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekprotected: 185a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue(unsigned SubKind, const void* d) : RValue(d, false, SubKind) {} 186a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 187a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 188a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek void print(std::ostream& Out) const; 189a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 190a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Arithmetic operators. 191a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue Add(ValueManager& ValMgr, const NonLValue& RHS) const; 192a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue Sub(ValueManager& ValMgr, const NonLValue& RHS) const; 193a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue Mul(ValueManager& ValMgr, const NonLValue& RHS) const; 194a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue Div(ValueManager& ValMgr, const NonLValue& RHS) const; 195a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue Rem(ValueManager& ValMgr, const NonLValue& RHS) const; 196a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue UnaryMinus(ValueManager& ValMgr, UnaryOperator* U) const; 197a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 198a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Equality operators. 199a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue EQ(ValueManager& ValMgr, const NonLValue& RHS) const; 200a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue NE(ValueManager& ValMgr, const NonLValue& RHS) const; 201a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 202a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Utility methods to create NonLValues. 203a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static NonLValue GetValue(ValueManager& ValMgr, uint64_t X, QualType T, 204a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SourceLocation Loc = SourceLocation()); 205a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 206a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static NonLValue GetValue(ValueManager& ValMgr, IntegerLiteral* I); 207a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 208a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline NonLValue GetIntTruthValue(ValueManager& ValMgr, bool X) { 209a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return GetValue(ValMgr, X ? 1U : 0U, ValMgr.getContext().IntTy); 210a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 211a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 212a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Implement isa<T> support. 213a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline bool classof(const RValue* V) { 214a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V->getBaseKind() >= NonLValueKind; 215a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 216a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 217a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 218a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass LValue : public RValue { 219a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekprotected: 220a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek LValue(unsigned SubKind, void* D) : RValue(D, true, SubKind) {} 221a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 222a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 223a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek void print(std::ostream& Out) const; 224a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 225a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Equality operators. 226a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue EQ(ValueManager& ValMgr, const LValue& RHS) const; 227a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek NonLValue NE(ValueManager& ValMgr, const LValue& RHS) const; 228a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 229a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Implement isa<T> support. 230a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline bool classof(const RValue* V) { 231a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V->getBaseKind() == LValueKind; 232a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 233a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 234a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 235a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 236a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// Subclasses of LValue. 237a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 238a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 239a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekenum LValueKind { SymbolicLValueKind, LValueDeclKind, NumLValueKind }; 240a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 241a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass SymbolicLValue : public LValue { 242a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 243a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolicLValue(unsigned SymID) 244a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek : LValue(SymbolicLValueKind, reinterpret_cast<void*>((uintptr_t) SymID)) {} 245a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 246a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolID getSymbolID() const { 247a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return (SymbolID) reinterpret_cast<uintptr_t>(getRawPtr()); 248a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 249a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 250a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline bool classof(const RValue* V) { 251a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V->getSubKind() == SymbolicLValueKind; 252a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 253a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 254a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 255a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass LValueDecl : public LValue { 256a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 257a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek LValueDecl(const ValueDecl* vd) 258a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek : LValue(LValueDeclKind,const_cast<ValueDecl*>(vd)) {} 259a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 260a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ValueDecl* getDecl() const { 261a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return static_cast<ValueDecl*>(getRawPtr()); 262a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 263a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 264a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek inline bool operator==(const LValueDecl& R) const { 265a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return getDecl() == R.getDecl(); 266a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 267a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 268a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek inline bool operator!=(const LValueDecl& R) const { 269a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return getDecl() != R.getDecl(); 270a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 271a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 272a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Implement isa<T> support. 273a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline bool classof(const RValue* V) { 274a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V->getSubKind() == LValueDeclKind; 275a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 276a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 277a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 278a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 279a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// Subclasses of NonLValue. 280a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 281a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 282a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekenum NonLValueKind { SymbolicNonLValueKind, ConcreteIntKind, 283a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted KremenekNumNonLValueKind }; 284a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 285a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass SymbolicNonLValue : public NonLValue { 286a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 287a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolicNonLValue(unsigned SymID) 288a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek : NonLValue(SymbolicNonLValueKind, 289a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek reinterpret_cast<void*>((uintptr_t) SymID)) {} 290a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 291a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek SymbolID getSymbolID() const { 292a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return (SymbolID) reinterpret_cast<uintptr_t>(getRawPtr()); 293a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 294a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 295a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline bool classof(const RValue* V) { 296a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V->getSubKind() == SymbolicNonLValueKind; 297a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 298a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 299a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 300a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekclass ConcreteInt : public NonLValue { 301a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekpublic: 302a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt(const llvm::APSInt& V) : NonLValue(ConcreteIntKind, &V) {} 303a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 304a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek const llvm::APSInt& getValue() const { 305a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return *static_cast<llvm::APSInt*>(getRawPtr()); 306a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 307a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 308a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Arithmetic operators. 309a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 310a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt Add(ValueManager& ValMgr, const ConcreteInt& V) const { 311a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return ValMgr.getValue(getValue() + V.getValue()); 312a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 313a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 314a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt Sub(ValueManager& ValMgr, const ConcreteInt& V) const { 315a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return ValMgr.getValue(getValue() - V.getValue()); 316a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 317a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 318a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt Mul(ValueManager& ValMgr, const ConcreteInt& V) const { 319a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return ValMgr.getValue(getValue() * V.getValue()); 320a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 321a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 322a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt Div(ValueManager& ValMgr, const ConcreteInt& V) const { 323a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return ValMgr.getValue(getValue() / V.getValue()); 324a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 325a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 326a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt Rem(ValueManager& ValMgr, const ConcreteInt& V) const { 327a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return ValMgr.getValue(getValue() % V.getValue()); 328a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 329a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 330a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt UnaryMinus(ValueManager& ValMgr, UnaryOperator* U) const { 331a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek assert (U->getType() == U->getSubExpr()->getType()); 332a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek assert (U->getType()->isIntegerType()); 333a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return ValMgr.getValue(-getValue()); 334a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 335a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 336a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Casting. 337a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 338a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt Cast(ValueManager& ValMgr, Expr* CastExpr) const { 339a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek assert (CastExpr->getType()->isIntegerType()); 340a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 341a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek llvm::APSInt X(getValue()); 342a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek X.extOrTrunc(ValMgr.getContext().getTypeSize(CastExpr->getType(), 343a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek CastExpr->getLocStart())); 344a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return ValMgr.getValue(X); 345a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 346a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 347a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Equality operators. 348a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 349a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt EQ(ValueManager& ValMgr, const ConcreteInt& V) const { 350a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek const llvm::APSInt& Val = getValue(); 351a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return ValMgr.getValue(Val == V.getValue() ? 1U : 0U, 352a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek Val.getBitWidth(), Val.isUnsigned()); 353a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 354a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 355a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek ConcreteInt NE(ValueManager& ValMgr, const ConcreteInt& V) const { 356a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek const llvm::APSInt& Val = getValue(); 357a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return ValMgr.getValue(Val != V.getValue() ? 1U : 0U, 358a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek Val.getBitWidth(), Val.isUnsigned()); 359a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 360a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 361a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek // Implement isa<T> support. 362a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline bool classof(const RValue* V) { 363a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V->getSubKind() == ConcreteIntKind; 364a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 365a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 366a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 367a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek} // end clang namespace 368a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 369a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 370a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek// Casting machinery to get cast<> and dyn_cast<> working with SymbolData. 371a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek//==------------------------------------------------------------------------==// 372a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 373a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremeneknamespace llvm { 374a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 375a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenektemplate<> inline bool 376a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenekisa<clang::ParmVarDecl,clang::SymbolData>(const clang::SymbolData& V) { 377a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V.getKind() == clang::SymbolData::ParmKind; 378a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek} 379a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 380a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenektemplate<> struct cast_retty_impl<clang::ParmVarDecl,clang::SymbolData> { 381a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek typedef const clang::ParmVarDecl* ret_type; 382a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 383a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 384a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenektemplate<> struct simplify_type<clang::SymbolData> { 385a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek typedef void* SimpleType; 386a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek static inline SimpleType getSimplifiedValue(const clang::SymbolData &V) { 387a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek return V.getPtr(); 388a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek } 389a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek}; 390a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 391a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek} // end llvm namespace 392a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek 393a90ccfe03ce62f4c33cbb96982947cf474b4fae4Ted Kremenek#endif 394