//== SymbolManager.h - Management of Symbolic Values ------------*- C++ -*--==// // // The LLVM Compiler Infrastructure // // This file is distributed under the University of Illinois Open Source // License. See LICENSE.TXT for details. // //===----------------------------------------------------------------------===// // // This file defines SymbolManager, a class that manages symbolic values // created for use by GRExprEngine and related classes. // //===----------------------------------------------------------------------===// #include "clang/Analysis/PathSensitive/SymbolManager.h" #include "clang/Analysis/PathSensitive/MemRegion.h" #include "llvm/Support/raw_ostream.h" using namespace clang; void SymbolRef::print(llvm::raw_ostream& os) const { os << getNumber(); } SymbolRef SymbolManager::getRegionRValueSymbol(const MemRegion* R) { llvm::FoldingSetNodeID profile; SymbolRegionRValue::Profile(profile, R); void* InsertPos; SymbolData* SD = DataSet.FindNodeOrInsertPos(profile, InsertPos); if (SD) return SD->getSymbol(); SD = (SymbolData*) BPAlloc.Allocate(); new (SD) SymbolRegionRValue(SymbolCounter, R); DataSet.InsertNode(SD, InsertPos); DataMap[SymbolCounter] = SD; return SymbolCounter++; } SymbolRef SymbolManager::getConjuredSymbol(Stmt* E, QualType T, unsigned Count){ llvm::FoldingSetNodeID profile; SymbolConjured::Profile(profile, E, T, Count); void* InsertPos; SymbolData* SD = DataSet.FindNodeOrInsertPos(profile, InsertPos); if (SD) return SD->getSymbol(); SD = (SymbolData*) BPAlloc.Allocate(); new (SD) SymbolConjured(SymbolCounter, E, T, Count); DataSet.InsertNode(SD, InsertPos); DataMap[SymbolCounter] = SD; return SymbolCounter++; } const SymbolData& SymbolManager::getSymbolData(SymbolRef Sym) const { DataMapTy::const_iterator I = DataMap.find(Sym); assert (I != DataMap.end()); return *I->second; } QualType SymbolConjured::getType(ASTContext&) const { return T; } QualType SymbolRegionRValue::getType(ASTContext& C) const { if (const TypedRegion* TR = dyn_cast(R)) return TR->getRValueType(C); return QualType(); } SymbolManager::~SymbolManager() {} void SymbolReaper::markLive(SymbolRef sym) { TheLiving = F.Add(TheLiving, sym); TheDead = F.Remove(TheDead, sym); } bool SymbolReaper::maybeDead(SymbolRef sym) { if (isLive(sym)) return false; TheDead = F.Add(TheDead, sym); return true; } bool SymbolReaper::isLive(SymbolRef sym) { if (TheLiving.contains(sym)) return true; // Interogate the symbol. It may derive from an input value to // the analyzed function/method. return isa(SymMgr.getSymbolData(sym)); }