• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //== AnalysisManager.h - Path sensitive analysis data manager ------*- 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 //
10 // This file defines the AnalysisManager class that manages the data and policy
11 // for path sensitive analysis.
12 //
13 //===----------------------------------------------------------------------===//
14 
15 #ifndef LLVM_CLANG_GR_ANALYSISMANAGER_H
16 #define LLVM_CLANG_GR_ANALYSISMANAGER_H
17 
18 #include "clang/Analysis/AnalysisContext.h"
19 #include "clang/StaticAnalyzer/Core/BugReporter/BugReporter.h"
20 #include "clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h"
21 
22 namespace clang {
23 
24 namespace idx {
25   class Indexer;
26   class TranslationUnit;
27 }
28 
29 namespace ento {
30   class CheckerManager;
31 
32 class AnalysisManager : public BugReporterData {
33   AnalysisContextManager AnaCtxMgr;
34   LocationContextManager LocCtxMgr;
35 
36   ASTContext &Ctx;
37   Diagnostic &Diags;
38   const LangOptions &LangInfo;
39 
40   llvm::OwningPtr<PathDiagnosticClient> PD;
41 
42   // Configurable components creators.
43   StoreManagerCreator CreateStoreMgr;
44   ConstraintManagerCreator CreateConstraintMgr;
45 
46   CheckerManager *CheckerMgr;
47 
48   /// \brief Provide function definitions in other translation units. This is
49   /// NULL if we don't have multiple translation units. AnalysisManager does
50   /// not own the Indexer.
51   idx::Indexer *Idxer;
52 
53   enum AnalysisScope { ScopeTU, ScopeDecl } AScope;
54 
55   // The maximum number of exploded nodes the analyzer will generate.
56   unsigned MaxNodes;
57 
58   // The maximum number of times the analyzer visit a block.
59   unsigned MaxVisit;
60 
61   bool VisualizeEGDot;
62   bool VisualizeEGUbi;
63   bool PurgeDead;
64 
65   /// EargerlyAssume - A flag indicating how the engine should handle
66   //   expressions such as: 'x = (y != 0)'.  When this flag is true then
67   //   the subexpression 'y != 0' will be eagerly assumed to be true or false,
68   //   thus evaluating it to the integers 0 or 1 respectively.  The upside
69   //   is that this can increase analysis precision until we have a better way
70   //   to lazily evaluate such logic.  The downside is that it eagerly
71   //   bifurcates paths.
72   bool EagerlyAssume;
73   bool TrimGraph;
74   bool InlineCall;
75   bool EagerlyTrimEGraph;
76 
77 public:
AnalysisManager(ASTContext & ctx,Diagnostic & diags,const LangOptions & lang,PathDiagnosticClient * pd,StoreManagerCreator storemgr,ConstraintManagerCreator constraintmgr,CheckerManager * checkerMgr,idx::Indexer * idxer,unsigned maxnodes,unsigned maxvisit,bool vizdot,bool vizubi,bool purge,bool eager,bool trim,bool inlinecall,bool useUnoptimizedCFG,bool addImplicitDtors,bool addInitializers,bool eagerlyTrimEGraph)78   AnalysisManager(ASTContext &ctx, Diagnostic &diags,
79                   const LangOptions &lang, PathDiagnosticClient *pd,
80                   StoreManagerCreator storemgr,
81                   ConstraintManagerCreator constraintmgr,
82                   CheckerManager *checkerMgr,
83                   idx::Indexer *idxer,
84                   unsigned maxnodes, unsigned maxvisit,
85                   bool vizdot, bool vizubi, bool purge, bool eager, bool trim,
86                   bool inlinecall, bool useUnoptimizedCFG,
87                   bool addImplicitDtors, bool addInitializers,
88                   bool eagerlyTrimEGraph)
89 
90     : AnaCtxMgr(useUnoptimizedCFG, addImplicitDtors, addInitializers),
91       Ctx(ctx), Diags(diags), LangInfo(lang), PD(pd),
92       CreateStoreMgr(storemgr), CreateConstraintMgr(constraintmgr),
93       CheckerMgr(checkerMgr), Idxer(idxer),
94       AScope(ScopeDecl), MaxNodes(maxnodes), MaxVisit(maxvisit),
95       VisualizeEGDot(vizdot), VisualizeEGUbi(vizubi), PurgeDead(purge),
96       EagerlyAssume(eager), TrimGraph(trim), InlineCall(inlinecall),
97       EagerlyTrimEGraph(eagerlyTrimEGraph) {}
98 
~AnalysisManager()99   ~AnalysisManager() { FlushDiagnostics(); }
100 
ClearContexts()101   void ClearContexts() {
102     LocCtxMgr.clear();
103     AnaCtxMgr.clear();
104   }
105 
getAnalysisContextManager()106   AnalysisContextManager& getAnalysisContextManager() {
107     return AnaCtxMgr;
108   }
109 
getStoreManagerCreator()110   StoreManagerCreator getStoreManagerCreator() {
111     return CreateStoreMgr;
112   }
113 
getConstraintManagerCreator()114   ConstraintManagerCreator getConstraintManagerCreator() {
115     return CreateConstraintMgr;
116   }
117 
getCheckerManager()118   CheckerManager *getCheckerManager() const { return CheckerMgr; }
119 
getIndexer()120   idx::Indexer *getIndexer() const { return Idxer; }
121 
getASTContext()122   virtual ASTContext &getASTContext() {
123     return Ctx;
124   }
125 
getSourceManager()126   virtual SourceManager &getSourceManager() {
127     return getASTContext().getSourceManager();
128   }
129 
getDiagnostic()130   virtual Diagnostic &getDiagnostic() {
131     return Diags;
132   }
133 
getLangOptions()134   const LangOptions &getLangOptions() const {
135     return LangInfo;
136   }
137 
getPathDiagnosticClient()138   virtual PathDiagnosticClient *getPathDiagnosticClient() {
139     return PD.get();
140   }
141 
FlushDiagnostics()142   void FlushDiagnostics() {
143     if (PD.get())
144       PD->FlushDiagnostics();
145   }
146 
getMaxNodes()147   unsigned getMaxNodes() const { return MaxNodes; }
148 
getMaxVisit()149   unsigned getMaxVisit() const { return MaxVisit; }
150 
shouldVisualizeGraphviz()151   bool shouldVisualizeGraphviz() const { return VisualizeEGDot; }
152 
shouldVisualizeUbigraph()153   bool shouldVisualizeUbigraph() const { return VisualizeEGUbi; }
154 
shouldVisualize()155   bool shouldVisualize() const {
156     return VisualizeEGDot || VisualizeEGUbi;
157   }
158 
shouldEagerlyTrimExplodedGraph()159   bool shouldEagerlyTrimExplodedGraph() const { return EagerlyTrimEGraph; }
160 
shouldTrimGraph()161   bool shouldTrimGraph() const { return TrimGraph; }
162 
shouldPurgeDead()163   bool shouldPurgeDead() const { return PurgeDead; }
164 
shouldEagerlyAssume()165   bool shouldEagerlyAssume() const { return EagerlyAssume; }
166 
shouldInlineCall()167   bool shouldInlineCall() const { return InlineCall; }
168 
hasIndexer()169   bool hasIndexer() const { return Idxer != 0; }
170 
171   AnalysisContext *getAnalysisContextInAnotherTU(const Decl *D);
172 
getCFG(Decl const * D)173   CFG *getCFG(Decl const *D) {
174     return AnaCtxMgr.getContext(D)->getCFG();
175   }
176 
getLiveVariables(Decl const * D)177   LiveVariables *getLiveVariables(Decl const *D) {
178     return AnaCtxMgr.getContext(D)->getLiveVariables();
179   }
180 
getParentMap(Decl const * D)181   ParentMap &getParentMap(Decl const *D) {
182     return AnaCtxMgr.getContext(D)->getParentMap();
183   }
184 
getAnalysisContext(const Decl * D)185   AnalysisContext *getAnalysisContext(const Decl *D) {
186     return AnaCtxMgr.getContext(D);
187   }
188 
getAnalysisContext(const Decl * D,idx::TranslationUnit * TU)189   AnalysisContext *getAnalysisContext(const Decl *D, idx::TranslationUnit *TU) {
190     return AnaCtxMgr.getContext(D, TU);
191   }
192 
getStackFrame(AnalysisContext * Ctx,LocationContext const * Parent,const Stmt * S,const CFGBlock * Blk,unsigned Idx)193   const StackFrameContext *getStackFrame(AnalysisContext *Ctx,
194                                          LocationContext const *Parent,
195                                          const Stmt *S,
196                                          const CFGBlock *Blk, unsigned Idx) {
197     return LocCtxMgr.getStackFrame(Ctx, Parent, S, Blk, Idx);
198   }
199 
200   // Get the top level stack frame.
getStackFrame(Decl const * D,idx::TranslationUnit * TU)201   const StackFrameContext *getStackFrame(Decl const *D,
202                                          idx::TranslationUnit *TU) {
203     return LocCtxMgr.getStackFrame(AnaCtxMgr.getContext(D, TU), 0, 0, 0, 0);
204   }
205 
206   // Get a stack frame with parent.
getStackFrame(const Decl * D,LocationContext const * Parent,const Stmt * S,const CFGBlock * Blk,unsigned Idx)207   StackFrameContext const *getStackFrame(const Decl *D,
208                                          LocationContext const *Parent,
209                                          const Stmt *S,
210                                          const CFGBlock *Blk, unsigned Idx) {
211     return LocCtxMgr.getStackFrame(AnaCtxMgr.getContext(D), Parent, S,
212                                    Blk,Idx);
213   }
214 };
215 
216 } // end GR namespace
217 
218 } // end clang namespace
219 
220 #endif
221