diff options
Diffstat (limited to 'contrib/llvm/tools/clang/lib/StaticAnalyzer/Checkers/DebugCheckers.cpp')
| -rw-r--r-- | contrib/llvm/tools/clang/lib/StaticAnalyzer/Checkers/DebugCheckers.cpp | 214 | 
1 files changed, 214 insertions, 0 deletions
diff --git a/contrib/llvm/tools/clang/lib/StaticAnalyzer/Checkers/DebugCheckers.cpp b/contrib/llvm/tools/clang/lib/StaticAnalyzer/Checkers/DebugCheckers.cpp new file mode 100644 index 000000000000..810a33ed404d --- /dev/null +++ b/contrib/llvm/tools/clang/lib/StaticAnalyzer/Checkers/DebugCheckers.cpp @@ -0,0 +1,214 @@ +//==- DebugCheckers.cpp - Debugging Checkers ---------------------*- 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 checkers that display debugging information. +// +//===----------------------------------------------------------------------===// + +#include "ClangSACheckers.h" +#include "clang/Analysis/Analyses/Dominators.h" +#include "clang/Analysis/Analyses/LiveVariables.h" +#include "clang/Analysis/CallGraph.h" +#include "clang/StaticAnalyzer/Core/Checker.h" +#include "clang/StaticAnalyzer/Core/BugReporter/BugType.h" +#include "clang/StaticAnalyzer/Core/PathSensitive/AnalysisManager.h" +#include "clang/StaticAnalyzer/Core/PathSensitive/CheckerContext.h" +#include "clang/StaticAnalyzer/Core/PathSensitive/ExplodedGraph.h" +#include "clang/StaticAnalyzer/Core/PathSensitive/ExprEngine.h" +#include "llvm/Support/Process.h" + +using namespace clang; +using namespace ento; + +//===----------------------------------------------------------------------===// +// DominatorsTreeDumper +//===----------------------------------------------------------------------===// + +namespace { +class DominatorsTreeDumper : public Checker<check::ASTCodeBody> { +public: +  void checkASTCodeBody(const Decl *D, AnalysisManager& mgr, +                        BugReporter &BR) const { +    if (AnalysisDeclContext *AC = mgr.getAnalysisDeclContext(D)) { +      DominatorTree dom; +      dom.buildDominatorTree(*AC); +      dom.dump(); +    } +  } +}; +} + +void ento::registerDominatorsTreeDumper(CheckerManager &mgr) { +  mgr.registerChecker<DominatorsTreeDumper>(); +} + +//===----------------------------------------------------------------------===// +// LiveVariablesDumper +//===----------------------------------------------------------------------===// + +namespace { +class LiveVariablesDumper : public Checker<check::ASTCodeBody> { +public: +  void checkASTCodeBody(const Decl *D, AnalysisManager& mgr, +                        BugReporter &BR) const { +    if (LiveVariables* L = mgr.getAnalysis<LiveVariables>(D)) { +      L->dumpBlockLiveness(mgr.getSourceManager()); +    } +  } +}; +} + +void ento::registerLiveVariablesDumper(CheckerManager &mgr) { +  mgr.registerChecker<LiveVariablesDumper>(); +} + +//===----------------------------------------------------------------------===// +// CFGViewer +//===----------------------------------------------------------------------===// + +namespace { +class CFGViewer : public Checker<check::ASTCodeBody> { +public: +  void checkASTCodeBody(const Decl *D, AnalysisManager& mgr, +                        BugReporter &BR) const { +    if (CFG *cfg = mgr.getCFG(D)) { +      cfg->viewCFG(mgr.getLangOpts()); +    } +  } +}; +} + +void ento::registerCFGViewer(CheckerManager &mgr) { +  mgr.registerChecker<CFGViewer>(); +} + +//===----------------------------------------------------------------------===// +// CFGDumper +//===----------------------------------------------------------------------===// + +namespace { +class CFGDumper : public Checker<check::ASTCodeBody> { +public: +  void checkASTCodeBody(const Decl *D, AnalysisManager& mgr, +                        BugReporter &BR) const { +    PrintingPolicy Policy(mgr.getLangOpts()); +    Policy.TerseOutput = true; +    Policy.PolishForDeclaration = true; +    D->print(llvm::errs(), Policy); + +    if (CFG *cfg = mgr.getCFG(D)) { +      cfg->dump(mgr.getLangOpts(), +                llvm::sys::Process::StandardErrHasColors()); +    } +  } +}; +} + +void ento::registerCFGDumper(CheckerManager &mgr) { +  mgr.registerChecker<CFGDumper>(); +} + +//===----------------------------------------------------------------------===// +// CallGraphViewer +//===----------------------------------------------------------------------===// + +namespace { +class CallGraphViewer : public Checker< check::ASTDecl<TranslationUnitDecl> > { +public: +  void checkASTDecl(const TranslationUnitDecl *TU, AnalysisManager& mgr, +                    BugReporter &BR) const { +    CallGraph CG; +    CG.addToCallGraph(const_cast<TranslationUnitDecl*>(TU)); +    CG.viewGraph(); +  } +}; +} + +void ento::registerCallGraphViewer(CheckerManager &mgr) { +  mgr.registerChecker<CallGraphViewer>(); +} + +//===----------------------------------------------------------------------===// +// CallGraphDumper +//===----------------------------------------------------------------------===// + +namespace { +class CallGraphDumper : public Checker< check::ASTDecl<TranslationUnitDecl> > { +public: +  void checkASTDecl(const TranslationUnitDecl *TU, AnalysisManager& mgr, +                    BugReporter &BR) const { +    CallGraph CG; +    CG.addToCallGraph(const_cast<TranslationUnitDecl*>(TU)); +    CG.dump(); +  } +}; +} + +void ento::registerCallGraphDumper(CheckerManager &mgr) { +  mgr.registerChecker<CallGraphDumper>(); +} + + +//===----------------------------------------------------------------------===// +// ConfigDumper +//===----------------------------------------------------------------------===// + +namespace { +class ConfigDumper : public Checker< check::EndOfTranslationUnit > { +  typedef AnalyzerOptions::ConfigTable Table; + +  static int compareEntry(const Table::MapEntryTy *const *LHS, +                          const Table::MapEntryTy *const *RHS) { +    return (*LHS)->getKey().compare((*RHS)->getKey()); +  } + +public: +  void checkEndOfTranslationUnit(const TranslationUnitDecl *TU, +                                 AnalysisManager& mgr, +                                 BugReporter &BR) const { +    const Table &Config = mgr.options.Config; + +    SmallVector<const Table::MapEntryTy *, 32> Keys; +    for (Table::const_iterator I = Config.begin(), E = Config.end(); I != E; +         ++I) +      Keys.push_back(&*I); +    llvm::array_pod_sort(Keys.begin(), Keys.end(), compareEntry); + +    llvm::errs() << "[config]\n"; +    for (unsigned I = 0, E = Keys.size(); I != E; ++I) +      llvm::errs() << Keys[I]->getKey() << " = " << Keys[I]->second << '\n'; + +    llvm::errs() << "[stats]\n" << "num-entries = " << Keys.size() << '\n'; +  } +}; +} + +void ento::registerConfigDumper(CheckerManager &mgr) { +  mgr.registerChecker<ConfigDumper>(); +} + +//===----------------------------------------------------------------------===// +// ExplodedGraph Viewer +//===----------------------------------------------------------------------===// + +namespace { +class ExplodedGraphViewer : public Checker< check::EndAnalysis > { +public: +  ExplodedGraphViewer() {} +  void checkEndAnalysis(ExplodedGraph &G, BugReporter &B,ExprEngine &Eng) const { +    Eng.ViewGraph(0); +  } +}; + +} + +void ento::registerExplodedGraphViewer(CheckerManager &mgr) { +  mgr.registerChecker<ExplodedGraphViewer>(); +} +  | 
