enum CXChildVisitResult foundChild(CXCursor cursor, CXCursor parent, CXClientData client_data) { if(clang_getCursorKind(cursor) == CXCursor_CallExpr) { printf("-%s\n", clang_getCString(clang_getCursorSpelling(cursor))); } if(clang_isDeclaration(clang_getCursorKind(cursor)) && (clang_getCursorLinkage(cursor) == CXLinkage_External || clang_getCursorLinkage(cursor) == CXLinkage_Internal)) { CXFile file; const char * filename, * wantFilename; CXSourceLocation cloc; cloc = clang_getCursorLocation(cursor); clang_getInstantiationLocation(cloc, &file, NULL, NULL, NULL); filename = clang_getCString(clang_getFileName(file)); wantFilename = (const char *)client_data; if(!filename || strcmp(wantFilename, filename)) return CXChildVisit_Recurse; if(clang_getCursorLinkage(cursor) == CXLinkage_External) printf("+%s\n", clang_getCString(clang_getCursorSpelling(cursor))); else printf("?%s\n", clang_getCString(clang_getCursorSpelling(cursor))); } return CXChildVisit_Recurse; }
CXChildVisitResult visitor( CXCursor cursor, CXCursor parent, CXClientData client_data) { ClangTools::TranslationUnit::AstWalker * astWalker = reinterpret_cast<ClangTools::TranslationUnit::AstWalker *>(client_data); std::vector<std::string> & funcNames = *(reinterpret_cast<std::vector<std::string> *>(astWalker->getClientData())); auto sourceLocation = clang_getCursorLocation(cursor); CXFile file; clang_getFileLocation(sourceLocation, &file, 0, 0, 0); auto fileName = clang_getFileName(file); auto fileNameStr = ClangTools::String(fileName); if (fileNameStr != astWalker->getFileName()) { return CXChildVisit_Recurse; } auto func = std::string{}; auto def = bool{false}; if (clang_isCursorDefinition(cursor)) { def = true; } switch (clang_getCursorKind(cursor)) { case CXCursor_FunctionDecl: func = "Function "; break; case CXCursor_FunctionTemplate: func = "FunctionTemplate "; break; case CXCursor_CXXMethod: func = "CXXMethod "; break; default: return CXChildVisit_Recurse; break; } func += clang_isCursorDefinition(cursor) ? "definition: " : "declaration: "; auto semanticParent = clang_getCursorSemanticParent(cursor); auto semanticParentSpelling = clang_getCursorSpelling(semanticParent); func += ClangTools::String(semanticParentSpelling) + "::"; auto cursorSpelling = clang_getCursorSpelling(cursor); func += ClangTools::String(cursorSpelling); auto lexicalParent = clang_getCursorLexicalParent(cursor); auto lexicalParentSpelling = clang_getCursorSpelling(lexicalParent); func += " found in: " + ClangTools::String(lexicalParentSpelling); funcNames.push_back(func); return CXChildVisit_Recurse; }
std::string libclang_vim::stringize_parent(CXCursor const& cursor, CXCursor const& parent) { auto const semantic_parent = clang_getCursorSemanticParent(cursor); auto const lexical_parent = clang_getCursorLexicalParent(cursor); cxstring_ptr parent_name = clang_getCursorSpelling(parent); cxstring_ptr semantic_parent_name = clang_getCursorSpelling(semantic_parent); cxstring_ptr lexical_parent_name = clang_getCursorSpelling(lexical_parent); return stringize_key_value("parent", parent_name) + stringize_key_value("semantic_parent", semantic_parent_name) + stringize_key_value("lexical_parent", lexical_parent_name); }
static void PrintCursor(CXCursor Cursor) { if (clang_isInvalid(Cursor.kind)) { CXString ks = clang_getCursorKindSpelling(Cursor.kind); printf("Invalid Cursor => %s", clang_getCString(ks)); clang_disposeString(ks); } else { CXString string, ks; CXCursor Referenced; unsigned line, column; ks = clang_getCursorKindSpelling(Cursor.kind); string = clang_getCursorSpelling(Cursor); printf("%s=%s", clang_getCString(ks), clang_getCString(string)); clang_disposeString(ks); clang_disposeString(string); Referenced = clang_getCursorReferenced(Cursor); if (!clang_equalCursors(Referenced, clang_getNullCursor())) { CXSourceLocation Loc = clang_getCursorLocation(Referenced); clang_getInstantiationLocation(Loc, 0, &line, &column, 0); printf(":%d:%d", line, column); } if (clang_isCursorDefinition(Cursor)) printf(" (Definition)"); } }
static enum CXChildVisitResult visitor_enum_cb(CXCursor cursor, CXCursor parent, CXClientData client_data) { EnumData* data = (EnumData*)client_data; ErlNifEnv *env = data->env; ERL_NIF_TERM name; ERL_NIF_TERM value; long long cvalue; CXString tmp; char* cstr; switch (clang_getCursorKind(cursor)) { case CXCursor_EnumConstantDecl: { tmp = clang_getCursorSpelling(cursor); cstr = (char*)clang_getCString(tmp); cvalue = clang_getEnumConstantDeclValue(cursor); name = enif_make_string(env, cstr, ERL_NIF_LATIN1); value = enif_make_int64(env, cvalue); data->enum_values = enif_make_list_cell(env, enif_make_tuple2(env, name, value), data->enum_values); } default: { return CXChildVisit_Continue; } } }
void IndexerJob::nestedClassConstructorCallUgleHack(const CXCursor &parent, CursorInfo &info, CXCursorKind refKind, const Location &refLoc) { if (refKind == CXCursor_Constructor && clang_getCursorKind(mLastCursor) == CXCursor_TypeRef && clang_getCursorKind(parent) == CXCursor_CXXFunctionalCastExpr) { const CXStringScope str = clang_getCursorSpelling(mLastCursor); int start = -1; const char *cstr = str.data(); int idx = 0; while (cstr[idx]) { if (start == -1 && cstr[idx] == ' ') { start = idx; } ++idx; } if (start != -1) { // error() << "Changed symbolLength from" << info.symbolLength << "to" << (idx - start - 1) << "for dude reffing" << refLoc; info.symbolLength = idx - start - 1; } RTags::Filter in; in.kinds.insert(CXCursor_TypeRef); const List<CXCursor> typeRefs = RTags::children(parent, in); for (int i=0; i<typeRefs.size(); ++i) { const Location loc = createLocation(typeRefs.at(i)); // error() << "Added" << refLoc << "to targets for" << typeRefs.at(i); mData->symbols[loc].targets.insert(refLoc); } } }
enum CXChildVisitResult property_list_builder(CXCursor cursor, CXCursor cursor_parent, CXClientData client_data) { ScintillaObject *current_doc_sci = (ScintillaObject *)client_data; enum CXCursorKind code_cursor_kind; CXSourceLocation code_source_location; code_source_location = clang_getCursorLocation(cursor); code_cursor_kind = clang_getCursorKind(cursor); if (code_cursor_kind == 1) { property_kind = property_helper_get_kind(current_doc_sci,code_source_location); } else if (code_cursor_kind == 6) { gchar *type = NULL; gchar *name = NULL; type = property_helper_get_type(current_doc_sci,code_source_location); name = (gchar *)clang_getCString(clang_getCursorSpelling(cursor)); chunked_property_add(&property_list, type, name, sg_do_getters, sg_do_setters, sg_placement_inner, property_kind); free(type); free(name); } return CXChildVisit_Continue; }
String IndexerJob::typeName(const CXCursor &cursor) { String ret; switch (clang_getCursorKind(cursor)) { case CXCursor_FunctionTemplate: // ### If the return value is a template type we get an empty string here case CXCursor_FunctionDecl: case CXCursor_CXXMethod: ret = typeString(clang_getResultType(clang_getCursorType(cursor))); break; case CXCursor_ClassTemplate: case CXCursor_ClassDecl: case CXCursor_StructDecl: case CXCursor_UnionDecl: ret = RTags::eatString(clang_getCursorSpelling(cursor)); break; case CXCursor_FieldDecl: // ### If the return value is a template type we get an empty string here case CXCursor_VarDecl: case CXCursor_ParmDecl: ret = typeString(clang_getCursorType(cursor)); break; default: return String(); } if (!ret.isEmpty() && !ret.endsWith('*') && !ret.endsWith('&')) ret.append(' '); return ret; }
static CXChildVisitResult visitClass(CXCursor cursor, CXCursor /*parent*/, CXClientData client_data) { visitClassData *data = static_cast<visitClassData*>(client_data); DUMP_PARSE("visitClass", cursor); switch(cursor.kind) { case CXCursor_ClassDecl: clang_visitChildren(cursor, ::visitClass, &data); break; /* Prevent infinite recursion case CXCursor_CXXBaseSpecifier: { CXType classCursorType = clang_getCursorType(cursor); CXCursor classCursor = clang_getTypeDeclaration(classCursorType); clang_visitChildren(classCursor, ::visitClass, &data); } break; */ case CXCursor_CXXMethod: case CXCursor_FieldDecl: { std::string name(getDisposedString(clang_getCursorSpelling(cursor))); data->mMembers.push_back(name); } break; default: break; } return CXChildVisit_Continue; // return CXChildVisit_Recurse; }
static enum CXChildVisitResult ide_clang_service_build_index_visitor (CXCursor cursor, CXCursor parent, CXClientData user_data) { IndexRequest *request = user_data; enum CXCursorKind kind; const gchar *style_name = NULL; g_assert (request != NULL); kind = clang_getCursorKind (cursor); switch ((int)kind) { case CXCursor_TypedefDecl: case CXCursor_TypeAliasDecl: style_name = IDE_CLANG_HIGHLIGHTER_TYPE; break; case CXCursor_FunctionDecl: style_name = IDE_CLANG_HIGHLIGHTER_FUNCTION_NAME; break; case CXCursor_EnumDecl: style_name = IDE_CLANG_HIGHLIGHTER_ENUM_NAME; clang_visitChildren (cursor, ide_clang_service_build_index_visitor, user_data); break; case CXCursor_EnumConstantDecl: style_name = IDE_CLANG_HIGHLIGHTER_ENUM_NAME; break; case CXCursor_MacroDefinition: style_name = IDE_CLANG_HIGHLIGHTER_MACRO_NAME; break; default: break; } if (style_name != NULL) { CXString cxstr; const gchar *word; cxstr = clang_getCursorSpelling (cursor); word = clang_getCString (cxstr); ide_highlight_index_insert (request->index, word, (gpointer)style_name); clang_disposeString (cxstr); } return CXChildVisit_Continue; }
QASTField::QASTField( QAnnotatedTokenSet *tokenSet, QSourceLocation* cursorLocation, QSourceLocation* rangeStartLocation, QSourceLocation* rangeEndLocation, QASTNode* parent) : QASTNode("field", tokenSet, cursorLocation, rangeStartLocation, rangeEndLocation, parent){ // Get Identifier // -------------- CXString id = clang_getCursorSpelling(tokenSet->cursor()); setIdentifier(clang_getCString(id)); // Get Field Type // --------------- CXType type = clang_getCursorType(tokenSet->cursor()); CXString typeSpelling = clang_getTypeSpelling(type); m_fieldType = clang_getCString(typeSpelling); clang_disposeString(typeSpelling); // Determine field type // -------------------- if ( type.kind == CXType_Unexposed || type.kind == CXType_Invalid || m_fieldType.contains("int") ){ m_fieldType = ""; bool doubleColonFlag = false; for ( QAnnotatedTokenSet::Iterator it = tokenSet->begin(); it != tokenSet->end(); ++it ){ CXToken t = (*it)->token().token; CXString tSpelling = clang_getTokenSpelling(tokenSet->translationUnit(), t); const char* tCSpelling = clang_getCString(tSpelling); CXTokenKind tKind = clang_getTokenKind(t); if ( tKind == CXToken_Identifier && std::string(clang_getCString(id)) == tCSpelling ){ break; } else if ( tKind == CXToken_Punctuation && std::string("::") == tCSpelling ){ doubleColonFlag = true; m_fieldType += tCSpelling; } else if ( ( tKind == CXToken_Identifier || tKind == CXToken_Keyword ) && !m_fieldType.isEmpty() && !doubleColonFlag ){ m_fieldType += QString(" ") + tCSpelling; } else { doubleColonFlag = false; m_fieldType += tCSpelling; } } } clang_disposeString(id); }
std::string Cursor::spelling() const { if ( m_spelling.empty() ) { UniqueCXString cx_string(clang_getCursorSpelling(m_cx_cursor)); if ( !cx_string ) { CLANGXX_THROW_LogicError("Error retrieving a name for the entity referenced by this cursor."); } m_spelling = clang_getCString(cx_string.get()); } return m_spelling; }
int main(int argc, char *argv[]) { CXIndex index = clang_createIndex(0, 1); CXTranslationUnit tu = clang_parseTranslationUnit(index, "ast_clang.m", NULL, 0, NULL, 0, CXTranslationUnit_None); clang_visitChildrenWithBlock(clang_getTranslationUnitCursor(tu), ^enum CXChildVisitResult (CXCursor cursor, CXCursor parent) { enum CXCursorKind cursor_kind = clang_getCursorKind(cursor); switch(cursor_kind) { case CXCursor_ObjCInterfaceDecl:{ CXString cxname = clang_getCursorSpelling(cursor); printf("class: %s\n", clang_getCString(cxname)); clang_disposeString(cxname); } break; case CXCursor_ObjCPropertyDecl:{ CXString cxname = clang_getCursorSpelling(cursor); printf(" -> %s\n", clang_getCString(cxname)); clang_disposeString(cxname); } break; default:{}break; } return CXChildVisit_Recurse; });
void ast_json::record_spelling(json_t& obj, CXCursor cursor) { // Get cursor spelling CXString cursorspelling = clang_getCursorSpelling(cursor); // Record spelling std::string result = clang_getCString(cursorspelling); obj[node::DATA] = result; // Release memory clang_disposeString(cursorspelling); }
enum CXChildVisitResult filterer(CXCursor cursor, CXCursor cursor_parent, CXClientData client_data) { struct GcharTuple *tuple = (struct GcharTuple *)client_data; gchar *gettername = tuple->first; gchar *settername = tuple->second; gchar *classname = tuple->class_name; size_t number = tuple->number; enum CXCursorKind code_cursor_kind; enum CXCursorKind parent_cursor_kind; gchar *source_name = NULL; code_cursor_kind = clang_getCursorKind(cursor); parent_cursor_kind = clang_getCursorKind(cursor_parent); if (code_cursor_kind == 4) { source_name = (gchar *)clang_getCString(clang_getCursorSpelling(cursor)); if (strncmp(source_name,classname,strlen(classname)) == 0) { free(source_name); source_name = NULL; return CXChildVisit_Recurse; } free(source_name); source_name = NULL; } if (code_cursor_kind == 21) { source_name = (gchar *)clang_getCString(clang_getCursorSpelling(cursor)); if (strncmp(source_name,settername,strlen(settername)) == 0) { property_list.data[number].do_setter = FALSE; property_list.data[number].is_inner = FALSE; } if (strncmp(source_name,gettername,strlen(gettername)) == 0) { property_list.data[number].do_getter = FALSE; property_list.data[number].is_inner = FALSE; } free(source_name); source_name = NULL; } return CXChildVisit_Continue; }
DocumentationData::DocumentationData( const CXCursor& cursor ) : raw_comment( CXStringToString( clang_Cursor_getRawCommentText( cursor ) ) ) , brief_comment( CXStringToString( clang_Cursor_getBriefCommentText( cursor ) ) ) , canonical_type( CXStringToString( clang_getTypeSpelling( clang_getCursorType( cursor ) ) ) ) , display_name( CXStringToString( clang_getCursorSpelling( cursor ) ) ) { CXComment parsed_comment = clang_Cursor_getParsedComment( cursor ); if ( CXCommentValid( parsed_comment ) ) { comment_xml = CXStringToString( clang_FullComment_getAsXML( parsed_comment ) ); } }
static void dumpCursor(char const * const str, CXCursor cursor) { CXStringDisposer name(clang_getCursorSpelling(cursor)); CXStringDisposer spstr = clang_getCursorKindSpelling(clang_getCursorKind(cursor)); std::string tokenStr; appendCursorTokenString(cursor, tokenStr); if(tokenStr.length() > 100) { tokenStr.resize(100); tokenStr += "..."; } fprintf(sLog.mFp, "%s: %s %s %s\n", str, spstr.c_str(), name.c_str(), tokenStr.c_str()); fflush(sLog.mFp); }
enum CXChildVisitResult visit_enum(CXCursor cursor, CXCursor parent, CXClientData data) { json_t* structure = (json_t*)data; json_t* js = NULL; switch (clang_getCursorKind(cursor)) { case CXCursor_EnumConstantDecl: js = json_object(); json_object_set_new(js, "name", render_string(clang_getCursorSpelling(cursor))); json_object_set_new(js, "value", json_integer(clang_getEnumConstantDeclValue(cursor))); json_object_set_new(js, "type", render_type(clang_getCursorType(cursor))); json_array_append_new(json_object_get(structure, "values"), js); break; default: break; } return CXChildVisit_Continue; }
static CXChildVisitResult findChildVisitor(CXCursor cursor, CXCursor, CXClientData data) { FindChildVisitor *u = reinterpret_cast<FindChildVisitor*>(data); if (u->name.isEmpty()) { if (clang_getCursorKind(cursor) == u->kind) { u->cursor = cursor; return CXChildVisit_Break; } } else { CXStringScope str = clang_getCursorSpelling(cursor); if (str.data() && u->name == str.data()) { u->cursor = cursor; return CXChildVisit_Break; } } return CXChildVisit_Continue; }
std::ostream& operator<<( std::ostream &os, CXCursor cursor ) { auto spelling = clang_getCursorKindSpelling( cursor.kind ); auto morespell = clang_getCursorSpelling( cursor ); os << clang_getCString( spelling ) << ":" << clang_getCString( morespell ) << " "; clang_disposeString( spelling ); clang_disposeString( morespell ); auto refcursor = clang_getCursorReferenced( cursor ); if ( clang_equalCursors( refcursor, clang_getNullCursor() )|| clang_equalCursors( refcursor, cursor ) ) return os; return os << " [ " << refcursor << " ] "; }
static CXChildVisitResult visitTranslationUnit(CXCursor cursor, CXCursor parent, CXClientData client_data) { visitTranslationUnitData *data = static_cast<visitTranslationUnitData*>(client_data); CXSourceRange range = clang_getCursorExtent(cursor); CXSourceLocation startLoc = clang_getRangeStart(range); CXSourceLocation endLoc = clang_getRangeEnd(range); CXFile file; unsigned startOffset; unsigned endOffset; clang_getSpellingLocation(startLoc, &file, nullptr, nullptr, &startOffset); clang_getSpellingLocation(endLoc, &file, nullptr, nullptr, &endOffset); // Use the smallest cursor that surrounds the desired location. unsigned size = endOffset - startOffset; if(clangFilesEqual(file, data->mFile) && startOffset < data->mDesiredOffset && endOffset > data->mDesiredOffset) { if(size < data->mSize) { data->mCursor = cursor; data->mSize = size; fprintf(sLog.mFp, "GOOD:\n "); } } CXStringDisposer sp = clang_getCursorSpelling(cursor); CXStringDisposer kind = clang_getCursorKindSpelling(cursor.kind); std::string fn; if(file) { CXStringDisposer s = clang_getFileName(file); fn = s; } fprintf(sLog.mFp, "%s %s off %d size %d des offset %d file %s\n", kind.c_str(), sp.c_str(), startOffset, size, data->mDesiredOffset, fn.c_str()); DUMP_PARSE("visitTU", cursor); // clang_visitChildren(cursor, ::visitTranslationUnit, client_data); // return CXChildVisit_Continue; return CXChildVisit_Recurse; }
enum CXChildVisitResult visit_object(CXCursor cursor, CXCursor parent, CXClientData data) { json_t* object = (json_t*)data; json_t* arguments = json_object_get(object, "argument_names"); switch (clang_getCursorKind(cursor)) { case CXCursor_ParmDecl: if (arguments) { json_array_append_new(arguments, render_string_or_null(clang_getCursorSpelling(cursor))); } break; case CXCursor_IntegerLiteral: case CXCursor_FloatingLiteral: case CXCursor_StringLiteral: //putstring(clang_getCursorSpelling(cursor)); //putstring(clang_getCursorDisplayName(cursor)); //printf("%d\n", clang_getEnumConstantDeclValue(cursor)); break; default: break; } return CXChildVisit_Continue; }
/** * @brief globalsFinder * @param cursor - исследуемый курсор * @param parent - неиспользуемая, курсор всегда показывает на весь unit * @param client_data - неиспользуемая * @return Всегда CXChildVisit_Continue, потому что нам не нужны вложенные объекты */ CXChildVisitResult globalsFinder(CXCursor cursor, CXCursor parent, CXClientData client_data) { (void)client_data; (void)parent; CXCursorKind kind = clang_getCursorKind(cursor); if (kind == CXCursor_VarDecl) { GlobalVariable var; CXString spelling = clang_getCursorSpelling(cursor); var.identifier = clang_getCString(spelling); clang_disposeString(spelling); CXSourceRange range = clang_getCursorExtent(cursor); decodeLocation(clang_getRangeStart(range), var.file, var.line, var.column); g_globals.insert(var); } return CXChildVisit_Continue; }
void Clang_AST_CXTreeNode::calculateFullName() { if(m_parentNode) { m_fullName = m_parentNode->m_fullName; switch(m_canonicalCursor.kind) { // C case CXCursor_VarDecl: case CXCursor_UnionDecl: case CXCursor_TypedefDecl: case CXCursor_StructDecl: case CXCursor_FunctionDecl: case CXCursor_FieldDecl: // C++ case CXCursor_Namespace: case CXCursor_ClassDecl: case CXCursor_Constructor: case CXCursor_Destructor: case CXCursor_CXXMethod: case CXCursor_EnumDecl: case CXCursor_EnumConstantDecl: // C++: Templates case CXCursor_ClassTemplate: case CXCursor_ClassTemplatePartialSpecialization: case CXCursor_FunctionTemplate: { SelfDisposingCXString name(clang_getCursorSpelling(m_canonicalCursor)); m_fullName += "::"; m_fullName += name.c_str(); break; } default: break; } } }
void CppInstr::insertNonCompoundInstr(CXCursor cursor) { if(!clang_Cursor_isNull(cursor)) { CXCursorKind cursKind = clang_getCursorKind(cursor); // return statements that are children of if statements must be instrumented // if not in a compound statement. // if(cursKind != CXCursor_CompoundStmt /*&& clang_isStatement(cursKind)*/) // If this is a compound statement, then it will be instrumented anyway. if(cursKind != CXCursor_CompoundStmt) { bool doInstr = true; // There is sometimes a parsing error where a null statement is returned. // This occurs when all headers are not included or defines are not proper? if(cursKind == CXCursor_NullStmt) { CXStringDisposer name(clang_getCursorSpelling(cursor)); if(name[0] != ';') { SourceLocation loc(cursor); fprintf(stderr, "Unable to instrument line %d\n", loc.getLine()); doInstr = false; } } if(doInstr) { #if(DEBUG_PARSE) debugInstr(cursor, "insertNCI", mInstrCount); #endif SourceRange range(cursor); OovString covStr; makeCovInstr(covStr); covStr.insert(0, "{"); insertOutputText(covStr, range.getStartLocation().getOffset()); insertOutputText("\n}\n", range.getEndLocation().getOffset()+1); } } } }
static enum CXChildVisitResult visitor_struct_cb(CXCursor cursor, CXCursor parent, CXClientData client_data) { ERL_NIF_TERM name; ERL_NIF_TERM typename; CXString tmp; CXType type; ERL_NIF_TERM etmp; unsigned len; SubData *data = (SubData*)client_data; ErlNifEnv *env = data->env; switch (clang_getCursorKind(cursor)) { case CXCursor_FieldDecl: { enif_get_list_length(env, data->data, &len); tmp = clang_getCursorSpelling(cursor); name = enif_make_string(env, clang_getCString(tmp), ERL_NIF_LATIN1); clang_disposeString(tmp); type = clang_getCursorType(cursor); tmp = clang_getTypeSpelling(type); typename = enif_make_string(env, clang_getCString(tmp), ERL_NIF_LATIN1); data->types = enif_make_list_cell(env, typename, data->types); clang_disposeString(tmp); etmp = enif_make_tuple4(env, enif_make_atom(env, "field"), name, typename, enif_make_uint(env, len)); data->data = enif_make_list_cell(env, etmp, data->data); return CXChildVisit_Continue; } default: { return CXChildVisit_Continue; } } }
std::string cursor::spelling() { return string(clang_getCursorSpelling(cur)).str(); }
std::string libclang_vim::stringize_spell(CXCursor const& cursor) { cxstring_ptr spell = clang_getCursorSpelling(cursor); return stringize_key_value("spell", spell); }
bool IndexerJob::handleCursor(const CXCursor &cursor, CXCursorKind kind, const Location &location) { CursorInfo &info = mData->symbols[location]; if (!info.symbolLength || !RTags::isCursor(info.kind)) { CXStringScope name = clang_getCursorSpelling(cursor); const char *cstr = name.data(); info.symbolLength = cstr ? strlen(cstr) : 0; info.type = clang_getCursorType(cursor).kind; if (!info.symbolLength) { // this is for these constructs: // typedef struct { // int a; // } foobar; // // We end up not getting a spelling for the cursor switch (kind) { case CXCursor_ClassDecl: info.symbolLength = 5; info.symbolName = "class"; break; case CXCursor_UnionDecl: info.symbolLength = 5; info.symbolName = "union"; break; case CXCursor_StructDecl: info.symbolLength = 6; info.symbolName = "struct"; break; default: mData->symbols.remove(location); return false; } } else { info.symbolName = addNamePermutations(cursor, location); } CXSourceRange range = clang_getCursorExtent(cursor); unsigned start, end; clang_getSpellingLocation(clang_getRangeStart(range), 0, 0, 0, &start); clang_getSpellingLocation(clang_getRangeEnd(range), 0, 0, 0, &end); info.start = start; info.end = end; if (kind == CXCursor_EnumConstantDecl) { #if CLANG_VERSION_MINOR > 1 info.enumValue = clang_getEnumConstantDeclValue(cursor); #else info.definition = clang_isCursorDefinition(cursor); #endif } else{ info.definition = clang_isCursorDefinition(cursor); } info.kind = kind; const String usr = RTags::eatString(clang_getCursorUSR(cursor)); if (!usr.isEmpty()) mData->usrMap[usr].insert(location); switch (info.kind) { case CXCursor_Constructor: case CXCursor_Destructor: { Location parentLocation = createLocation(clang_getCursorSemanticParent(cursor)); // consider doing this for only declaration/inline definition since // declaration and definition should know of one another if (parentLocation.isValid()) { CursorInfo &parent = mData->symbols[parentLocation]; parent.references.insert(location); info.references.insert(parentLocation); } break; } case CXCursor_CXXMethod: { List<CursorInfo*> infos; infos.append(&info); addOverriddenCursors(cursor, location, infos); break; } default: break; } } return true; }
String Cursor::GetSpelling() const { return clang_getCursorSpelling(cursor_); }