zcov: / tools/CIndex/CIndexUSRs.cpp


Files: 1 Branches Taken: 0.0% 0 / 32
Generated: 2010-02-10 01:31 Branches Executed: 0.0% 0 / 32
Line Coverage: 0.0% 0 / 86


Programs: 1 Runs 121


       1                 : //===- CIndexUSR.cpp - Clang-C Source Indexing Library --------------------===//
       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 implements the generation and use of USRs from CXEntities.
      11                 : //
      12                 : //===----------------------------------------------------------------------===//
      13                 : 
      14                 : #include "CIndexer.h"
      15                 : #include "CXCursor.h"
      16                 : #include "clang/AST/DeclVisitor.h"
      17                 : #include "llvm/ADT/SmallString.h"
      18                 : #include "llvm/Support/raw_ostream.h"
      19                 : 
      20                 : //===----------------------------------------------------------------------===//
      21                 : // USR generation.
      22                 : //===----------------------------------------------------------------------===//
      23                 : 
      24                 : namespace {
      25                 : class USRGenerator : public DeclVisitor<USRGenerator> {
      26                 :   llvm::raw_ostream &Out;
      27                 :   bool IgnoreResults;
      28                 : public:
      29                0:   USRGenerator(llvm::raw_ostream &out) : Out(out), IgnoreResults(false) {}
      30                 :   
      31                0:   bool ignoreResults() const { return IgnoreResults; }
      32                 :   
      33                 :   void VisitBlockDecl(BlockDecl *D);
      34                 :   void VisitDeclContext(DeclContext *D);
      35                 :   void VisitFieldDecl(FieldDecl *D);
      36                 :   void VisitFunctionDecl(FunctionDecl *D);
      37                 :   void VisitNamedDecl(NamedDecl *D);
      38                 :   void VisitNamespaceDecl(NamespaceDecl *D);
      39                 :   void VisitObjCContainerDecl(ObjCContainerDecl *CD);  
      40                 :   void VisitObjCMethodDecl(ObjCMethodDecl *MD);
      41                 :   void VisitObjCPropertyDecl(ObjCPropertyDecl *D);
      42                 :   void VisitTagDecl(TagDecl *D);
      43                 :   void VisitTypedefDecl(TypedefDecl *D);
      44                 : };
      45                 : } // end anonymous namespace
      46                 : 
      47                0: void USRGenerator::VisitBlockDecl(BlockDecl *D) {
      48                0:   VisitDeclContext(D->getDeclContext());
      49                 :   // FIXME: Better support for anonymous blocks.
      50                0:   Out << "@B^anon";
      51                0: }
      52                 : 
      53                0: void USRGenerator::VisitDeclContext(DeclContext *DC) {
                        0: branch 1 not taken
                        0: branch 2 not taken
      54                0:   if (NamedDecl *D = dyn_cast<NamedDecl>(DC))
      55                0:     Visit(D);
      56                0: }
      57                 : 
      58                0: void USRGenerator::VisitFieldDecl(FieldDecl *D) {
      59                0:   const std::string &s = D->getNameAsString();
                        0: branch 1 not taken
                        0: branch 2 not taken
      60                0:   if (s.empty()) {
      61                 :     // Bit fields can be anonymous.
      62                0:     IgnoreResults = true;
      63                0:     return;
      64                 :   }
      65                0:   VisitDeclContext(D->getDeclContext());
                        0: branch 3 not taken
                        0: branch 4 not taken
      66                0:   Out << "@^FI^" << s;
      67                 : }
      68                 : 
      69                0: void USRGenerator::VisitFunctionDecl(FunctionDecl *D) {
      70                0:   VisitDeclContext(D->getDeclContext());
      71                0:   Out << "@F^" << D->getNameAsString();
      72                0: }
      73                 : 
      74                0: void USRGenerator::VisitNamedDecl(NamedDecl *D) {
      75                0:   VisitDeclContext(D->getDeclContext());
      76                0:   const std::string &s = D->getNameAsString();
      77                 : //  assert(!s.empty());
      78                0:   Out << "@^" << s;
      79                0: }
      80                 : 
      81                0: void USRGenerator::VisitNamespaceDecl(NamespaceDecl *D) {
      82                0:   VisitDeclContext(D->getDeclContext());
      83                0:   Out << "@N^" << D->getNameAsString();
      84                0: }
      85                 : 
      86                0: void USRGenerator::VisitObjCMethodDecl(ObjCMethodDecl *D) {
      87                0:   Visit(cast<Decl>(D->getDeclContext()));
                        0: branch 1 not taken
                        0: branch 2 not taken
      88                0:   Out << (D->isInstanceMethod() ? "(im)" : "(cm)");
      89                0:   Out << DeclarationName(D->getSelector()).getAsString();
      90                0: }
      91                 : 
      92                0: void USRGenerator::VisitObjCContainerDecl(ObjCContainerDecl *D) {
                        0: branch 1 not taken
                        0: branch 2 not taken
                        0: branch 3 not taken
                        0: branch 4 not taken
                        0: branch 5 not taken
      93                0:   switch (D->getKind()) {
      94                 :     default:
      95                0:       assert(false && "Invalid ObjC container.");
      96                 :     case Decl::ObjCInterface:
      97                 :     case Decl::ObjCImplementation:
      98                0:       Out << "objc(cs)" << D->getName();
      99                0:       break;
     100                 :     case Decl::ObjCCategory: {
     101                0:       ObjCCategoryDecl *CD = cast<ObjCCategoryDecl>(D);
     102                 :       Out << "objc(cy)" << CD->getClassInterface()->getName()
     103                0:       << '^' << CD->getName();
     104                0:       break;
     105                 :     }
     106                 :     case Decl::ObjCCategoryImpl: {
     107                0:       ObjCCategoryImplDecl *CD = cast<ObjCCategoryImplDecl>(D);
     108                 :       Out << "objc(cy)" << CD->getClassInterface()->getName()
     109                0:       << '^' << CD->getName();
     110                0:       break;
     111                 :     }
     112                 :     case Decl::ObjCProtocol:
     113                0:       Out << "objc(pl)" << cast<ObjCProtocolDecl>(D)->getName();
     114                 :       break;
     115                 :   }
     116                0: }
     117                 : 
     118                0: void USRGenerator::VisitObjCPropertyDecl(ObjCPropertyDecl *D) {
     119                0:   Visit(cast<Decl>(D->getDeclContext()));
     120                0:   Out << "(py)" << D->getName();
     121                0: }
     122                 : 
     123                0: void USRGenerator::VisitTagDecl(TagDecl *D) {
     124                0:   VisitDeclContext(D->getDeclContext());
                        0: branch 1 not taken
                        0: branch 2 not taken
                        0: branch 3 not taken
                        0: branch 4 not taken
                        0: branch 5 not taken
     125                0:   switch (D->getTagKind()) {
     126                0:     case TagDecl::TK_struct: Out << "@S^"; break;
     127                0:     case TagDecl::TK_class:  Out << "@C^"; break;
     128                0:     case TagDecl::TK_union:  Out << "@U^"; break;
     129                0:     case TagDecl::TK_enum:   Out << "@E^"; break;
     130                 :   }
     131                 :   
     132                 :   // FIXME: Better support for anonymous structures and enums.
     133                0:   const std::string &s = D->getNameAsString();
                        0: branch 1 not taken
                        0: branch 2 not taken
     134                0:   if (s.empty()) {
                        0: branch 1 not taken
                        0: branch 2 not taken
     135                0:     if (TypedefDecl *TD = D->getTypedefForAnonDecl())
     136                0:       Out << "^anontd^" << TD->getNameAsString();    
     137                 :     else
     138                0:       Out << "^anon";
     139                 :   }
     140                 :   else
     141                0:     Out << s;
     142                0: }
     143                 : 
     144                0: void USRGenerator::VisitTypedefDecl(TypedefDecl *D) {
     145                0:   DeclContext *DC = D->getDeclContext();
                        0: branch 1 not taken
                        0: branch 2 not taken
     146                0:   if (NamedDecl *DCN = dyn_cast<NamedDecl>(DC))
     147                0:     Visit(DCN);  
     148                0:   Out << "typedef@" << D->getName();
     149                0: }
     150                 : 
     151                 : // FIXME: This is a skeleton implementation.  It will be overhauled.
     152                0: static CXString ConstructUSR(Decl *D) {
     153                0:   llvm::SmallString<1024> StrBuf;
     154                 :   {
     155                0:     llvm::raw_svector_ostream Out(StrBuf);
     156                0:     USRGenerator UG(Out);
     157                0:     UG.Visit(static_cast<Decl*>(D));
                        0: branch 1 not taken
                        0: branch 2 not taken
     158                0:     if (UG.ignoreResults())
                        0: branch 2 not taken
                        0: branch 3 not taken
     159                0:       return CIndexer::createCXString(NULL);
     160                 :   }
     161                 :   
                        0: branch 1 not taken
                        0: branch 2 not taken
     162                0:   if (StrBuf.empty())
     163                0:     return CIndexer::createCXString(NULL);
     164                 :   
     165                 :   // Return a copy of the string that must be disposed by the caller.
     166                0:   return CIndexer::createCXString(StrBuf.c_str(), true);
     167                 : }  
     168                 : 
     169                 : 
     170                 : extern "C" {
     171                 : 
     172                0: CXString clang_getCursorUSR(CXCursor C) {
                        0: branch 1 not taken
                        0: branch 2 not taken
     173                0:   if (Decl *D = cxcursor::getCursorDecl(C))
     174                0:     return ConstructUSR(D);  
     175                 :   
     176                0:   return CIndexer::createCXString(NULL);
     177                 : }
     178                 : 
     179                 : } // end extern "C"

Generated: 2010-02-10 01:31 by zcov