197e8b6f3c5c578f35c3f392cc7cfdec88cef74f2Chris Lattner//===--- ASTConsumers.cpp - ASTConsumer implementations -------------------===//
25f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//
35f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//                     The LLVM Compiler Infrastructure
45f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//
50bc735ffcfb223c0186419547abaa5c84482663eChris Lattner// This file is distributed under the University of Illinois Open Source
60bc735ffcfb223c0186419547abaa5c84482663eChris Lattner// License. See LICENSE.TXT for details.
75f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//
85f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//===----------------------------------------------------------------------===//
95f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//
1097e8b6f3c5c578f35c3f392cc7cfdec88cef74f2Chris Lattner// AST Consumer Implementations.
115f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//
125f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//===----------------------------------------------------------------------===//
135f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer
1439d7c4d2d980651c4263b67cf0ab61dec34cd76bEli Friedman#include "clang/Frontend/ASTConsumers.h"
15e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko#include "clang/Basic/FileManager.h"
16dae86966bbfcf7a6e9fbc7c7ac9dfaa983308d51Nico Weber#include "clang/Basic/Diagnostic.h"
175411772b87c41ab91856bebca752b551d41be421Ted Kremenek#include "clang/Basic/SourceManager.h"
185f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer#include "clang/AST/AST.h"
193d4997da95b169f0ac32cf83af3368778c429898Chris Lattner#include "clang/AST/ASTConsumer.h"
20557c5b1717bc8919b1b40cf2064b51491ec53a44Chris Lattner#include "clang/AST/ASTContext.h"
21d249e1d1f1498b81314459ceda19d6ff25c278adDouglas Gregor#include "clang/AST/PrettyPrinter.h"
22e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko#include "clang/AST/RecordLayout.h"
23e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko#include "clang/AST/RecursiveASTVisitor.h"
24815c78fd9ab8bd5dfe8e8a91b8c6a413e2b8c889Ted Kremenek#include "llvm/Module.h"
2503013fa9a0bf1ef4b907f5fec006c8f4000fdd21Michael J. Spencer#include "llvm/Support/Path.h"
26e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko#include "llvm/Support/raw_ostream.h"
27e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko#include "llvm/Support/Timer.h"
286000dace22f110d8768476989313e9d981d690d0Chris Lattnerusing namespace clang;
295f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer
301b5a4bdc852cc3d808746bd344a65397067ab1c0Ted Kremenek//===----------------------------------------------------------------------===//
314fe0c8e9c76b96e7aff21696a40dacc09d0237bcDouglas Gregor/// ASTPrinter - Pretty-printer and dumper of ASTs
321b5a4bdc852cc3d808746bd344a65397067ab1c0Ted Kremenek
331b5a4bdc852cc3d808746bd344a65397067ab1c0Ted Kremeneknamespace {
34e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko  class ASTPrinter : public ASTConsumer,
35e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko                     public RecursiveASTVisitor<ASTPrinter> {
36e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    typedef RecursiveASTVisitor<ASTPrinter> base;
371eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
381b5a4bdc852cc3d808746bd344a65397067ab1c0Ted Kremenek  public:
39e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    ASTPrinter(raw_ostream *Out = NULL, bool Dump = false,
40e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko               StringRef FilterString = "")
41e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        : Out(Out ? *Out : llvm::outs()), Dump(Dump),
42e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko          FilterString(FilterString) {}
431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
444fe0c8e9c76b96e7aff21696a40dacc09d0237bcDouglas Gregor    virtual void HandleTranslationUnit(ASTContext &Context) {
45e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      TranslationUnitDecl *D = Context.getTranslationUnitDecl();
46e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko
47e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      if (FilterString.empty()) {
48e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        if (Dump)
49e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko          D->dump(Out);
50e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        else
51e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko          D->print(Out, /*Indentation=*/0, /*PrintInstantiation=*/true);
52e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        return;
53e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      }
54e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko
55e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      TraverseDecl(D);
56e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    }
57e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko
58e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    bool shouldWalkTypesOfTypeLocs() const { return false; }
59e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko
60e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    bool TraverseDecl(Decl *D) {
61a7612aec79bf7f7c7791941aa0a5c59b1dc82463Alexander Kornienko      if (D == NULL)
62a7612aec79bf7f7c7791941aa0a5c59b1dc82463Alexander Kornienko        return false;
63e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      if (filterMatches(D)) {
64e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        Out.changeColor(llvm::raw_ostream::BLUE) <<
65e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko            (Dump ? "Dumping " : "Printing ") << getName(D) << ":\n";
66e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        Out.resetColor();
67e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        if (Dump)
68e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko          D->dump(Out);
69e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        else
70e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko          D->print(Out, /*Indentation=*/0, /*PrintInstantiation=*/true);
71a7612aec79bf7f7c7791941aa0a5c59b1dc82463Alexander Kornienko        Out << "\n";
72e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        // Don't traverse child nodes to avoid output duplication.
73e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        return true;
74e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      }
75e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      return base::TraverseDecl(D);
76e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    }
77e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko
78e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko  private:
79e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    std::string getName(Decl *D) {
80e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      if (isa<NamedDecl>(D))
81e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko        return cast<NamedDecl>(D)->getQualifiedNameAsString();
82e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      return "";
83e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    }
84e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    bool filterMatches(Decl *D) {
85e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko      return getName(D).find(FilterString) != std::string::npos;
865f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer    }
87e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko
88e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    raw_ostream &Out;
89e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    bool Dump;
90e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko    std::string FilterString;
913d4997da95b169f0ac32cf83af3368778c429898Chris Lattner  };
92171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko
93171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko  class ASTDeclNodeLister : public ASTConsumer,
94171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko                     public RecursiveASTVisitor<ASTDeclNodeLister> {
95171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko  public:
96171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko    ASTDeclNodeLister(raw_ostream *Out = NULL)
97171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko        : Out(Out ? *Out : llvm::outs()) {}
98171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko
99171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko    virtual void HandleTranslationUnit(ASTContext &Context) {
100171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko      TraverseDecl(Context.getTranslationUnitDecl());
101171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko    }
102171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko
103171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko    bool shouldWalkTypesOfTypeLocs() const { return false; }
104171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko
105171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko    virtual bool VisitNamedDecl(NamedDecl *D) {
106171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko      Out << D->getQualifiedNameAsString() << "\n";
107171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko      return true;
108171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko    }
109171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko
110171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko  private:
111171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko    raw_ostream &Out;
112171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko  };
113b23ff6b4ebefe9c0fd531d2247171500e5d0a5b7Chris Lattner} // end anonymous namespace
1146000dace22f110d8768476989313e9d981d690d0Chris Lattner
115e34a052d642ba7830174b1a51787251d7f704f80Alexander KornienkoASTConsumer *clang::CreateASTPrinter(raw_ostream *Out,
116e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko                                     StringRef FilterString) {
117e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko  return new ASTPrinter(Out, /*Dump=*/ false, FilterString);
118ea75c5599072bda2dc9fc1dec2e680936c84f6f1Ted Kremenek}
1191b5a4bdc852cc3d808746bd344a65397067ab1c0Ted Kremenek
120e34a052d642ba7830174b1a51787251d7f704f80Alexander KornienkoASTConsumer *clang::CreateASTDumper(StringRef FilterString) {
121e34a052d642ba7830174b1a51787251d7f704f80Alexander Kornienko  return new ASTPrinter(0, /*Dump=*/ true, FilterString);
122609e72f55a04cbef59a7d493d5121c066ca3dff5Douglas Gregor}
1233d4997da95b169f0ac32cf83af3368778c429898Chris Lattner
124171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander KornienkoASTConsumer *clang::CreateASTDeclNodeLister() {
125171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko  return new ASTDeclNodeLister(0);
126171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko}
127171af64ef10ae816ed2a4f15f5d17aca1d71769fAlexander Kornienko
1281b5a4bdc852cc3d808746bd344a65397067ab1c0Ted Kremenek//===----------------------------------------------------------------------===//
1291b5a4bdc852cc3d808746bd344a65397067ab1c0Ted Kremenek/// ASTViewer - AST Visualization
1301b5a4bdc852cc3d808746bd344a65397067ab1c0Ted Kremenek
13180de08fc6f7ebfee07b1b2c520c99e31c3243365Ted Kremeneknamespace {
13280de08fc6f7ebfee07b1b2c520c99e31c3243365Ted Kremenek  class ASTViewer : public ASTConsumer {
1334fe0c8e9c76b96e7aff21696a40dacc09d0237bcDouglas Gregor    ASTContext *Context;
13480de08fc6f7ebfee07b1b2c520c99e31c3243365Ted Kremenek  public:
13595041a2029a069386ee67439f6d0fb524a9d184fTed Kremenek    void Initialize(ASTContext &Context) {
1364fe0c8e9c76b96e7aff21696a40dacc09d0237bcDouglas Gregor      this->Context = &Context;
13780de08fc6f7ebfee07b1b2c520c99e31c3243365Ted Kremenek    }
138682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner
13988c2596edc8eb475e20f6033de1ea01669695a0cArgyrios Kyrtzidis    virtual bool HandleTopLevelDecl(DeclGroupRef D) {
140682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner      for (DeclGroupRef::iterator I = D.begin(), E = D.end(); I != E; ++I)
141682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner        HandleTopLevelSingleDecl(*I);
14288c2596edc8eb475e20f6033de1ea01669695a0cArgyrios Kyrtzidis      return true;
143682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner    }
1441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
145682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattner    void HandleTopLevelSingleDecl(Decl *D);
14680de08fc6f7ebfee07b1b2c520c99e31c3243365Ted Kremenek  };
14780de08fc6f7ebfee07b1b2c520c99e31c3243365Ted Kremenek}
14880de08fc6f7ebfee07b1b2c520c99e31c3243365Ted Kremenek
149682bf92db408a6cbc3d37b5496a99b6ef85041ecChris Lattnervoid ASTViewer::HandleTopLevelSingleDecl(Decl *D) {
1509d96f9239e9250864435b25ed93bf6d08c4e5febArgyrios Kyrtzidis  if (isa<FunctionDecl>(D) || isa<ObjCMethodDecl>(D)) {
1519d96f9239e9250864435b25ed93bf6d08c4e5febArgyrios Kyrtzidis    D->print(llvm::errs());
1529d96f9239e9250864435b25ed93bf6d08c4e5febArgyrios Kyrtzidis
1539d96f9239e9250864435b25ed93bf6d08c4e5febArgyrios Kyrtzidis    if (Stmt *Body = D->getBody()) {
1546cb7c1a43b0c8f739d1f54b7fdae5ede86033496Benjamin Kramer      llvm::errs() << '\n';
155af3280fadbdab6305581955c973e1229970958ebDouglas Gregor      Body->viewAST();
1566cb7c1a43b0c8f739d1f54b7fdae5ede86033496Benjamin Kramer      llvm::errs() << '\n';
157b23ff6b4ebefe9c0fd531d2247171500e5d0a5b7Chris Lattner    }
158b23ff6b4ebefe9c0fd531d2247171500e5d0a5b7Chris Lattner  }
159b23ff6b4ebefe9c0fd531d2247171500e5d0a5b7Chris Lattner}
160b23ff6b4ebefe9c0fd531d2247171500e5d0a5b7Chris Lattner
161b23ff6b4ebefe9c0fd531d2247171500e5d0a5b7Chris Lattner
16280de08fc6f7ebfee07b1b2c520c99e31c3243365Ted KremenekASTConsumer *clang::CreateASTViewer() { return new ASTViewer(); }
16380de08fc6f7ebfee07b1b2c520c99e31c3243365Ted Kremenek
16474bf2c9a4c749e9facba90b3a3ab3f369efa7682Ted Kremenek//===----------------------------------------------------------------------===//
1652d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu/// DeclContextPrinter - Decl and DeclContext Visualization
1662d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
1672d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xunamespace {
1682d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
1692d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xuclass DeclContextPrinter : public ASTConsumer {
1705f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner  raw_ostream& Out;
1712d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xupublic:
1722d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  DeclContextPrinter() : Out(llvm::errs()) {}
1732d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
174dacbc5d46aaeea817742b8c76c987b87d2490c85Chris Lattner  void HandleTranslationUnit(ASTContext &C) {
175dacbc5d46aaeea817742b8c76c987b87d2490c85Chris Lattner    PrintDeclContext(C.getTranslationUnitDecl(), 4);
1762d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
1772d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
1782d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  void PrintDeclContext(const DeclContext* DC, unsigned Indentation);
1792d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu};
180b23ff6b4ebefe9c0fd531d2247171500e5d0a5b7Chris Lattner}  // end anonymous namespace
1812d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
1821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpvoid DeclContextPrinter::PrintDeclContext(const DeclContext* DC,
1832d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu                                          unsigned Indentation) {
1842d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  // Print DeclContext name.
1859b9ca01ff3136a7539dc08a4c4e1a3dd8c8d3a7dArgyrios Kyrtzidis  switch (DC->getDeclKind()) {
1862d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::TranslationUnit:
1872d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[translation unit] " << DC;
1882d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
1892d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::Namespace: {
1902d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[namespace] ";
1917ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const NamespaceDecl* ND = cast<NamespaceDecl>(DC);
192b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer    Out << *ND;
1932d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
1942d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
195867c39e8c4a2ccdbc1edae45966dc5f3e910954bZhongxing Xu  case Decl::Enum: {
1967ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const EnumDecl* ED = cast<EnumDecl>(DC);
1975e1cdac63c3d9c9b32fa41fa0b2d242a58a20d49John McCall    if (ED->isCompleteDefinition())
198867c39e8c4a2ccdbc1edae45966dc5f3e910954bZhongxing Xu      Out << "[enum] ";
199867c39e8c4a2ccdbc1edae45966dc5f3e910954bZhongxing Xu    else
200867c39e8c4a2ccdbc1edae45966dc5f3e910954bZhongxing Xu      Out << "<enum> ";
201b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer    Out << *ED;
2022d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
203867c39e8c4a2ccdbc1edae45966dc5f3e910954bZhongxing Xu  }
2042d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::Record: {
2057ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const RecordDecl* RD = cast<RecordDecl>(DC);
2065e1cdac63c3d9c9b32fa41fa0b2d242a58a20d49John McCall    if (RD->isCompleteDefinition())
2072d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "[struct] ";
2082d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    else
2092d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "<struct> ";
210b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer    Out << *RD;
2112d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2122d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
2132d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::CXXRecord: {
2147ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const CXXRecordDecl* RD = cast<CXXRecordDecl>(DC);
2155e1cdac63c3d9c9b32fa41fa0b2d242a58a20d49John McCall    if (RD->isCompleteDefinition())
2162d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "[class] ";
2172d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    else
2182d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "<class> ";
219b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer    Out << *RD << ' ' << DC;
2202d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2212d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
2222d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::ObjCMethod:
2232d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[objc method]";
2242d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2252d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::ObjCInterface:
2262d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[objc interface]";
2272d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2282d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::ObjCCategory:
2292d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[objc category]";
2302d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2312d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::ObjCProtocol:
2322d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[objc protocol]";
2332d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2342d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::ObjCImplementation:
2352d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[objc implementation]";
2362d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2372d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::ObjCCategoryImpl:
2382d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[objc categoryimpl]";
2392d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2402d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::LinkageSpec:
2412d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[linkage spec]";
2422d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2432d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::Block:
2442d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Out << "[block]";
2452d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2462d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::Function: {
2477ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const FunctionDecl* FD = cast<FunctionDecl>(DC);
24810620eb5164e31208fcbf0437cd79ae535ed0559Sean Hunt    if (FD->doesThisDeclarationHaveABody())
2492d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "[function] ";
2502d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    else
2512d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "<function> ";
252b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer    Out << *FD;
253ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    // Print the parameters.
254ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    Out << "(";
255ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    bool PrintComma = false;
2561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    for (FunctionDecl::param_const_iterator I = FD->param_begin(),
257ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu           E = FD->param_end(); I != E; ++I) {
258ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu      if (PrintComma)
259ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu        Out << ", ";
260ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu      else
261ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu        PrintComma = true;
262b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << **I;
263ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    }
264ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    Out << ")";
2652d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2662d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
2672d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::CXXMethod: {
2687ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const CXXMethodDecl* D = cast<CXXMethodDecl>(DC);
269f5cecfbdcd20be224861f9e67c5973a9a2b61512Argyrios Kyrtzidis    if (D->isOutOfLine())
2702d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "[c++ method] ";
2712a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    else if (D->isImplicit())
2722a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu      Out << "(c++ method) ";
2732d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    else
2742d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "<c++ method> ";
275b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer    Out << *D;
276ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    // Print the parameters.
277ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    Out << "(";
278ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    bool PrintComma = false;
2791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    for (FunctionDecl::param_const_iterator I = D->param_begin(),
280ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu           E = D->param_end(); I != E; ++I) {
281ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu      if (PrintComma)
282ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu        Out << ", ";
283ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu      else
284ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu        PrintComma = true;
285b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << **I;
286ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    }
287ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    Out << ")";
2882d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
2892d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    // Check the semantic DeclContext.
2907ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const DeclContext* SemaDC = D->getDeclContext();
2917ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const DeclContext* LexicalDC = D->getLexicalDeclContext();
2922a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    if (SemaDC != LexicalDC)
2932d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << " [[" << SemaDC << "]]";
2942a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu
2952d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
2962d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
2972d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::CXXConstructor: {
2987ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const CXXConstructorDecl* D = cast<CXXConstructorDecl>(DC);
299f5cecfbdcd20be224861f9e67c5973a9a2b61512Argyrios Kyrtzidis    if (D->isOutOfLine())
3002d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "[c++ ctor] ";
3012a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    else if (D->isImplicit())
3022a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu      Out << "(c++ ctor) ";
3032d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    else
3042d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "<c++ ctor> ";
305b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer    Out << *D;
306ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    // Print the parameters.
307ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    Out << "(";
308ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    bool PrintComma = false;
3091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    for (FunctionDecl::param_const_iterator I = D->param_begin(),
310ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu           E = D->param_end(); I != E; ++I) {
311ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu      if (PrintComma)
312ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu        Out << ", ";
313ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu      else
314ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu        PrintComma = true;
315b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << **I;
316ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    }
317ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu    Out << ")";
318ca04ce46e1458089a1dec90d19d7d676a8229bd1Zhongxing Xu
3192a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    // Check the semantic DC.
3207ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const DeclContext* SemaDC = D->getDeclContext();
3217ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const DeclContext* LexicalDC = D->getLexicalDeclContext();
3222a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    if (SemaDC != LexicalDC)
3232a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu      Out << " [[" << SemaDC << "]]";
3242d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
3252d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
3262d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::CXXDestructor: {
3277ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const CXXDestructorDecl* D = cast<CXXDestructorDecl>(DC);
328f5cecfbdcd20be224861f9e67c5973a9a2b61512Argyrios Kyrtzidis    if (D->isOutOfLine())
3292d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "[c++ dtor] ";
3302a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    else if (D->isImplicit())
3312a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu      Out << "(c++ dtor) ";
3322d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    else
3332d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "<c++ dtor> ";
334b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer    Out << *D;
3352a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    // Check the semantic DC.
3367ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const DeclContext* SemaDC = D->getDeclContext();
3377ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const DeclContext* LexicalDC = D->getLexicalDeclContext();
3382a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    if (SemaDC != LexicalDC)
3392a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu      Out << " [[" << SemaDC << "]]";
3402d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
3412d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
3422d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  case Decl::CXXConversion: {
3437ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const CXXConversionDecl* D = cast<CXXConversionDecl>(DC);
344f5cecfbdcd20be224861f9e67c5973a9a2b61512Argyrios Kyrtzidis    if (D->isOutOfLine())
3452d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "[c++ conversion] ";
3462a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    else if (D->isImplicit())
3472a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu      Out << "(c++ conversion) ";
3482d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    else
3492d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      Out << "<c++ conversion> ";
350b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer    Out << *D;
3512a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    // Check the semantic DC.
3527ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const DeclContext* SemaDC = D->getDeclContext();
3537ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis    const DeclContext* LexicalDC = D->getLexicalDeclContext();
3542a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu    if (SemaDC != LexicalDC)
3552a3eb0e22e671112ab19b62e9a40615d195a7f17Zhongxing Xu      Out << " [[" << SemaDC << "]]";
3562d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    break;
3572d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
3582d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
3592d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  default:
360b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie    llvm_unreachable("a decl that inherits DeclContext isn't handled");
3612d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
3622d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
3632d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  Out << "\n";
3642d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
3652d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  // Print decls in the DeclContext.
36617945a0f64fe03ff6ec0c2146005a87636e3ac12Argyrios Kyrtzidis  for (DeclContext::decl_iterator I = DC->decls_begin(), E = DC->decls_end();
3672d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu       I != E; ++I) {
3682d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    for (unsigned i = 0; i < Indentation; ++i)
369071e4da10b07ca5278a7ce9dcabd853e0d57e5a4Mike Stump      Out << "  ";
3702d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
3712d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    Decl::Kind DK = I->getKind();
3722d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    switch (DK) {
3732d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::Namespace:
3742d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::Enum:
3752d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::Record:
3762d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::CXXRecord:
3772d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::ObjCMethod:
3782d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::ObjCInterface:
3791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    case Decl::ObjCCategory:
3802d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::ObjCProtocol:
3812d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::ObjCImplementation:
3822d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::ObjCCategoryImpl:
3832d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::LinkageSpec:
3842d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::Block:
3852d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::Function:
3862d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::CXXMethod:
3872d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::CXXConstructor:
3882d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::CXXDestructor:
3892d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::CXXConversion:
3902d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    {
3917ad5bf3152d4fe8f0de4611347fc6e24c45fba60Argyrios Kyrtzidis      DeclContext* DC = cast<DeclContext>(*I);
392071e4da10b07ca5278a7ce9dcabd853e0d57e5a4Mike Stump      PrintDeclContext(DC, Indentation+2);
3932d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      break;
3942d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    }
395a3d39c066521a76fb30c83c560ece9a18d296b20Francois Pichet    case Decl::IndirectField: {
396a3d39c066521a76fb30c83c560ece9a18d296b20Francois Pichet      IndirectFieldDecl* IFD = cast<IndirectFieldDecl>(*I);
397b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<IndirectField> " << *IFD << '\n';
398a3d39c066521a76fb30c83c560ece9a18d296b20Francois Pichet      break;
399a3d39c066521a76fb30c83c560ece9a18d296b20Francois Pichet    }
40021ac10d5e6f8781b498ed0338af435c117bd27d8Chris Lattner    case Decl::Label: {
40121ac10d5e6f8781b498ed0338af435c117bd27d8Chris Lattner      LabelDecl *LD = cast<LabelDecl>(*I);
402b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<Label> " << *LD << '\n';
40321ac10d5e6f8781b498ed0338af435c117bd27d8Chris Lattner      break;
40421ac10d5e6f8781b498ed0338af435c117bd27d8Chris Lattner    }
4052d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::Field: {
40621ac10d5e6f8781b498ed0338af435c117bd27d8Chris Lattner      FieldDecl *FD = cast<FieldDecl>(*I);
407b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<field> " << *FD << '\n';
4082d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      break;
4092d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    }
410162e1c1b487352434552147967c3dd296ebee2f7Richard Smith    case Decl::Typedef:
411162e1c1b487352434552147967c3dd296ebee2f7Richard Smith    case Decl::TypeAlias: {
412162e1c1b487352434552147967c3dd296ebee2f7Richard Smith      TypedefNameDecl* TD = cast<TypedefNameDecl>(*I);
413b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<typedef> " << *TD << '\n';
4142d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      break;
4152d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    }
4162d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::EnumConstant: {
4172d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      EnumConstantDecl* ECD = cast<EnumConstantDecl>(*I);
418b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<enum constant> " << *ECD << '\n';
4192d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      break;
4202d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    }
4212d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::Var: {
4222d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      VarDecl* VD = cast<VarDecl>(*I);
423b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<var> " << *VD << '\n';
4242d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      break;
4252d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    }
4262d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::ImplicitParam: {
4272d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      ImplicitParamDecl* IPD = cast<ImplicitParamDecl>(*I);
428b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<implicit parameter> " << *IPD << '\n';
4292d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      break;
4302d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    }
4312d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::ParmVar: {
4322d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      ParmVarDecl* PVD = cast<ParmVarDecl>(*I);
433b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<parameter> " << *PVD << '\n';
4342d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      break;
4352d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    }
4362d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    case Decl::ObjCProperty: {
4372d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      ObjCPropertyDecl* OPD = cast<ObjCPropertyDecl>(*I);
438b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<objc property> " << *OPD << '\n';
4392d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu      break;
4402d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    }
4417ac1c9ef0bd250da82ddf3f5213182278e351753Eli Friedman    case Decl::FunctionTemplate: {
4427ac1c9ef0bd250da82ddf3f5213182278e351753Eli Friedman      FunctionTemplateDecl* FTD = cast<FunctionTemplateDecl>(*I);
443b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<function template> " << *FTD << '\n';
4447ac1c9ef0bd250da82ddf3f5213182278e351753Eli Friedman      break;
4457ac1c9ef0bd250da82ddf3f5213182278e351753Eli Friedman    }
446368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman    case Decl::FileScopeAsm: {
447368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman      Out << "<file-scope asm>\n";
448368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman      break;
449368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman    }
450368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman    case Decl::UsingDirective: {
451368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman      Out << "<using directive>\n";
452368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman      break;
453368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman    }
454368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman    case Decl::NamespaceAlias: {
455368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman      NamespaceAliasDecl* NAD = cast<NamespaceAliasDecl>(*I);
456b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<namespace alias> " << *NAD << '\n';
457368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman      break;
458368a55d3ce5d66c6d0502c6f8bf061c06961042cEli Friedman    }
4592f3cd9cb830aba522ad5d6884c0dab23770609a2Zhongxing Xu    case Decl::ClassTemplate: {
4602f3cd9cb830aba522ad5d6884c0dab23770609a2Zhongxing Xu      ClassTemplateDecl *CTD = cast<ClassTemplateDecl>(*I);
461b8989f27f116ff2400e92a52c067a69846119eb5Benjamin Kramer      Out << "<class template> " << *CTD << '\n';
4622f3cd9cb830aba522ad5d6884c0dab23770609a2Zhongxing Xu      break;
4632f3cd9cb830aba522ad5d6884c0dab23770609a2Zhongxing Xu    }
4642d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    default:
465900fc6388e803868a34b9483510c345e9b49d7ebBenjamin Kramer      Out << "DeclKind: " << DK << '"' << *I << "\"\n";
466b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie      llvm_unreachable("decl unhandled");
4672d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu    }
4682d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu  }
4692d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu}
4701eb4433ac451dc16f4133a88af2d002ac26c58efMike StumpASTConsumer *clang::CreateDeclContextPrinter() {
4711eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  return new DeclContextPrinter();
4722d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu}
4732d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu
4742d75d6f56c2937d67aecb6008793694f9eb51349Zhongxing Xu//===----------------------------------------------------------------------===//
475f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall/// ASTDumperXML - In-depth XML dumping.
476f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall
477f35142413974e9dfe2c5f202084db4bd1c2073e9John McCallnamespace {
478f35142413974e9dfe2c5f202084db4bd1c2073e9John McCallclass ASTDumpXML : public ASTConsumer {
4795f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner  raw_ostream &OS;
480f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall
481f35142413974e9dfe2c5f202084db4bd1c2073e9John McCallpublic:
4825f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner  ASTDumpXML(raw_ostream &OS) : OS(OS) {}
483f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall
484f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall  void HandleTranslationUnit(ASTContext &C) {
485f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall    C.getTranslationUnitDecl()->dumpXML(OS);
486f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall  }
487f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall};
488f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall}
489f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall
4905f9e272e632e951b1efe824cd16acb4d96077930Chris LattnerASTConsumer *clang::CreateASTDumperXML(raw_ostream &OS) {
491f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall  return new ASTDumpXML(OS);
492f35142413974e9dfe2c5f202084db4bd1c2073e9John McCall}
493