blob: 013202990a6bc8920ebf5c6b6053a3712b4e9497 [file] [log] [blame]
Ted Kremenekd70d0b02008-02-16 01:12:31 +00001//== SymbolManager.h - Management of Symbolic Values ------------*- C++ -*--==//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
Gabor Greif843e9342008-03-06 10:40:09 +000010// This file defines SymbolManager, a class that manages symbolic values
Ted Kremenekd70d0b02008-02-16 01:12:31 +000011// created for use by GRExprEngine and related classes.
12//
13//===----------------------------------------------------------------------===//
14
15#include "clang/Analysis/PathSensitive/SymbolManager.h"
16
17using namespace clang;
18
Ted Kremenek2dabd432008-12-05 02:27:51 +000019SymbolRef SymbolManager::getSymbol(VarDecl* D) {
Ted Kremenekd763eb92008-02-26 02:15:56 +000020
Ted Kremenek72c59d02008-08-13 03:28:04 +000021 assert (isa<ParmVarDecl>(D) || isa<ImplicitParamDecl>(D) ||
22 D->hasGlobalStorage());
Ted Kremenekd763eb92008-02-26 02:15:56 +000023
Ted Kremenek00a3a5f2008-03-12 01:21:45 +000024 llvm::FoldingSetNodeID profile;
Ted Kremenekd70d0b02008-02-16 01:12:31 +000025
Ted Kremenek00a3a5f2008-03-12 01:21:45 +000026 ParmVarDecl* PD = dyn_cast<ParmVarDecl>(D);
27
28 if (PD)
29 SymbolDataParmVar::Profile(profile, PD);
30 else
31 SymbolDataGlobalVar::Profile(profile, D);
32
33 void* InsertPos;
34
35 SymbolData* SD = DataSet.FindNodeOrInsertPos(profile, InsertPos);
36
37 if (SD)
38 return SD->getSymbol();
39
40 if (PD) {
41 SD = (SymbolData*) BPAlloc.Allocate<SymbolDataParmVar>();
42 new (SD) SymbolDataParmVar(SymbolCounter, PD);
43 }
44 else {
45 SD = (SymbolData*) BPAlloc.Allocate<SymbolDataGlobalVar>();
46 new (SD) SymbolDataGlobalVar(SymbolCounter, D);
Ted Kremenekd70d0b02008-02-16 01:12:31 +000047 }
48
Ted Kremenek00a3a5f2008-03-12 01:21:45 +000049 DataSet.InsertNode(SD, InsertPos);
50
51 DataMap[SymbolCounter] = SD;
52 return SymbolCounter++;
Ted Kremenekd763eb92008-02-26 02:15:56 +000053}
Zhongxing Xueabf7762008-11-19 11:03:17 +000054
Ted Kremenek2dabd432008-12-05 02:27:51 +000055SymbolRef SymbolManager::getElementSymbol(const MemRegion* R,
Zhongxing Xueabf7762008-11-19 11:03:17 +000056 const llvm::APSInt* Idx){
57 llvm::FoldingSetNodeID ID;
58 SymbolDataElement::Profile(ID, R, Idx);
59 void* InsertPos;
60 SymbolData* SD = DataSet.FindNodeOrInsertPos(ID, InsertPos);
61
62 if (SD)
63 return SD->getSymbol();
64
65 SD = (SymbolData*) BPAlloc.Allocate<SymbolDataElement>();
66 new (SD) SymbolDataElement(SymbolCounter, R, Idx);
67
68 DataSet.InsertNode(SD, InsertPos);
69 DataMap[SymbolCounter] = SD;
70 return SymbolCounter++;
71}
72
Ted Kremenek2dabd432008-12-05 02:27:51 +000073SymbolRef SymbolManager::getFieldSymbol(const MemRegion* R, const FieldDecl* D) {
Zhongxing Xueabf7762008-11-19 11:03:17 +000074 llvm::FoldingSetNodeID ID;
75 SymbolDataField::Profile(ID, R, D);
76 void* InsertPos;
77 SymbolData* SD = DataSet.FindNodeOrInsertPos(ID, InsertPos);
78
79 if (SD)
80 return SD->getSymbol();
81
82 SD = (SymbolData*) BPAlloc.Allocate<SymbolDataField>();
83 new (SD) SymbolDataField(SymbolCounter, R, D);
84
85 DataSet.InsertNode(SD, InsertPos);
86 DataMap[SymbolCounter] = SD;
87 return SymbolCounter++;
88}
Ted Kremenek00a3a5f2008-03-12 01:21:45 +000089
Ted Kremenek2dabd432008-12-05 02:27:51 +000090SymbolRef SymbolManager::getConjuredSymbol(Stmt* E, QualType T, unsigned Count) {
Ted Kremenek00a3a5f2008-03-12 01:21:45 +000091
92 llvm::FoldingSetNodeID profile;
Ted Kremenek60a6e0c2008-10-01 00:21:14 +000093 SymbolConjured::Profile(profile, E, T, Count);
Ted Kremenek00a3a5f2008-03-12 01:21:45 +000094 void* InsertPos;
95
96 SymbolData* SD = DataSet.FindNodeOrInsertPos(profile, InsertPos);
97
98 if (SD)
99 return SD->getSymbol();
100
Ted Kremenek361fa8e2008-03-12 21:45:47 +0000101 SD = (SymbolData*) BPAlloc.Allocate<SymbolConjured>();
Ted Kremenek60a6e0c2008-10-01 00:21:14 +0000102 new (SD) SymbolConjured(SymbolCounter, E, T, Count);
Ted Kremenek00a3a5f2008-03-12 01:21:45 +0000103
104 DataSet.InsertNode(SD, InsertPos);
105 DataMap[SymbolCounter] = SD;
106
107 return SymbolCounter++;
108}
109
Ted Kremenek2dabd432008-12-05 02:27:51 +0000110const SymbolData& SymbolManager::getSymbolData(SymbolRef Sym) const {
Ted Kremenek00a3a5f2008-03-12 01:21:45 +0000111 DataMapTy::const_iterator I = DataMap.find(Sym);
112 assert (I != DataMap.end());
113 return *I->second;
114}
115
Ted Kremenekd70d0b02008-02-16 01:12:31 +0000116
Ted Kremeneka888c982008-02-19 20:51:40 +0000117QualType SymbolData::getType(const SymbolManager& SymMgr) const {
Ted Kremenekd70d0b02008-02-16 01:12:31 +0000118 switch (getKind()) {
119 default:
120 assert (false && "getType() not implemented for this symbol.");
121
122 case ParmKind:
123 return cast<SymbolDataParmVar>(this)->getDecl()->getType();
Ted Kremenekd763eb92008-02-26 02:15:56 +0000124
125 case GlobalKind:
126 return cast<SymbolDataGlobalVar>(this)->getDecl()->getType();
Ted Kremenekf3d41622008-12-05 01:31:31 +0000127
Ted Kremenek361fa8e2008-03-12 21:45:47 +0000128 case ConjuredKind:
Ted Kremenek60a6e0c2008-10-01 00:21:14 +0000129 return cast<SymbolConjured>(this)->getType();
Ted Kremenekd70d0b02008-02-16 01:12:31 +0000130 }
131}
132
Ted Kremenekd70d0b02008-02-16 01:12:31 +0000133SymbolManager::~SymbolManager() {}