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 "CXString.h" 17 #include "clang/Index/USRGeneration.h" 18 #include "clang/Lex/PreprocessingRecord.h" 19 #include "llvm/ADT/SmallString.h" 20 #include "llvm/Support/raw_ostream.h" 21 22 using namespace clang; 23 24 //===----------------------------------------------------------------------===// 25 // API hooks. 26 //===----------------------------------------------------------------------===// 27 28 static inline StringRef extractUSRSuffix(StringRef s) { 29 return s.startswith("c:") ? s.substr(2) : ""; 30 } 31 32 bool cxcursor::getDeclCursorUSR(const Decl *D, SmallVectorImpl<char> &Buf) { 33 return index::generateUSRForDecl(D, Buf); 34 } 35 36 extern "C" { 37 38 CXString clang_getCursorUSR(CXCursor C) { 39 const CXCursorKind &K = clang_getCursorKind(C); 40 41 if (clang_isDeclaration(K)) { 42 const Decl *D = cxcursor::getCursorDecl(C); 43 if (!D) 44 return cxstring::createEmpty(); 45 46 CXTranslationUnit TU = cxcursor::getCursorTU(C); 47 if (!TU) 48 return cxstring::createEmpty(); 49 50 cxstring::CXStringBuf *buf = cxstring::getCXStringBuf(TU); 51 if (!buf) 52 return cxstring::createEmpty(); 53 54 bool Ignore = cxcursor::getDeclCursorUSR(D, buf->Data); 55 if (Ignore) { 56 buf->dispose(); 57 return cxstring::createEmpty(); 58 } 59 60 // Return the C-string, but don't make a copy since it is already in 61 // the string buffer. 62 buf->Data.push_back('\0'); 63 return createCXString(buf); 64 } 65 66 if (K == CXCursor_MacroDefinition) { 67 CXTranslationUnit TU = cxcursor::getCursorTU(C); 68 if (!TU) 69 return cxstring::createEmpty(); 70 71 cxstring::CXStringBuf *buf = cxstring::getCXStringBuf(TU); 72 if (!buf) 73 return cxstring::createEmpty(); 74 75 buf->Data += index::getUSRSpacePrefix(); 76 buf->Data += "macro@"; 77 buf->Data += 78 cxcursor::getCursorMacroDefinition(C)->getName()->getNameStart(); 79 buf->Data.push_back('\0'); 80 return createCXString(buf); 81 } 82 83 return cxstring::createEmpty(); 84 } 85 86 CXString clang_constructUSR_ObjCIvar(const char *name, CXString classUSR) { 87 SmallString<128> Buf(index::getUSRSpacePrefix()); 88 llvm::raw_svector_ostream OS(Buf); 89 OS << extractUSRSuffix(clang_getCString(classUSR)); 90 index::generateUSRForObjCIvar(name, OS); 91 return cxstring::createDup(OS.str()); 92 } 93 94 CXString clang_constructUSR_ObjCMethod(const char *name, 95 unsigned isInstanceMethod, 96 CXString classUSR) { 97 SmallString<128> Buf(index::getUSRSpacePrefix()); 98 llvm::raw_svector_ostream OS(Buf); 99 OS << extractUSRSuffix(clang_getCString(classUSR)); 100 index::generateUSRForObjCMethod(name, isInstanceMethod, OS); 101 return cxstring::createDup(OS.str()); 102 } 103 104 CXString clang_constructUSR_ObjCClass(const char *name) { 105 SmallString<128> Buf(index::getUSRSpacePrefix()); 106 llvm::raw_svector_ostream OS(Buf); 107 index::generateUSRForObjCClass(name, OS); 108 return cxstring::createDup(OS.str()); 109 } 110 111 CXString clang_constructUSR_ObjCProtocol(const char *name) { 112 SmallString<128> Buf(index::getUSRSpacePrefix()); 113 llvm::raw_svector_ostream OS(Buf); 114 index::generateUSRForObjCProtocol(name, OS); 115 return cxstring::createDup(OS.str()); 116 } 117 118 CXString clang_constructUSR_ObjCCategory(const char *class_name, 119 const char *category_name) { 120 SmallString<128> Buf(index::getUSRSpacePrefix()); 121 llvm::raw_svector_ostream OS(Buf); 122 index::generateUSRForObjCCategory(class_name, category_name, OS); 123 return cxstring::createDup(OS.str()); 124 } 125 126 CXString clang_constructUSR_ObjCProperty(const char *property, 127 CXString classUSR) { 128 SmallString<128> Buf(index::getUSRSpacePrefix()); 129 llvm::raw_svector_ostream OS(Buf); 130 OS << extractUSRSuffix(clang_getCString(classUSR)); 131 index::generateUSRForObjCProperty(property, OS); 132 return cxstring::createDup(OS.str()); 133 } 134 135 } // end extern "C" 136