mirror of
				https://github.com/MaskRay/ccls.git
				synced 2025-11-03 22:04:24 +00:00 
			
		
		
		
	Small code cleanups/renames
This commit is contained in:
		
							parent
							
								
									ce4c2232d7
								
							
						
					
					
						commit
						d867d962d8
					
				@ -13,7 +13,6 @@ std::vector<CompilationEntry> LoadCompilationEntriesFromDirectory(const std::str
 | 
				
			|||||||
    exit(1);
 | 
					    exit(1);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					 | 
				
			||||||
  CXCompileCommands cx_commands = clang_CompilationDatabase_getAllCompileCommands(cx_db);
 | 
					  CXCompileCommands cx_commands = clang_CompilationDatabase_getAllCompileCommands(cx_db);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  unsigned int num_commands = clang_CompileCommands_getSize(cx_commands);
 | 
					  unsigned int num_commands = clang_CompileCommands_getSize(cx_commands);
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										92
									
								
								indexer.cpp
									
									
									
									
									
								
							
							
						
						
									
										92
									
								
								indexer.cpp
									
									
									
									
									
								
							@ -1,59 +1,59 @@
 | 
				
			|||||||
#include "indexer.h"
 | 
					#include "indexer.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
ParsingDatabase::ParsingDatabase() {}
 | 
					IndexedFile::IndexedFile() {}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// TODO: Optimize for const char*?
 | 
					// TODO: Optimize for const char*?
 | 
				
			||||||
TypeId ParsingDatabase::ToTypeId(const std::string& usr) {
 | 
					TypeId IndexedFile::ToTypeId(const std::string& usr) {
 | 
				
			||||||
  auto it = usr_to_type_id.find(usr);
 | 
					  auto it = usr_to_type_id.find(usr);
 | 
				
			||||||
  if (it != usr_to_type_id.end())
 | 
					  if (it != usr_to_type_id.end())
 | 
				
			||||||
    return it->second;
 | 
					    return it->second;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  TypeId id(types.size());
 | 
					  TypeId id(types.size());
 | 
				
			||||||
  types.push_back(TypeDef(id, usr));
 | 
					  types.push_back(IndexedTypeDef(id, usr));
 | 
				
			||||||
  usr_to_type_id[usr] = id;
 | 
					  usr_to_type_id[usr] = id;
 | 
				
			||||||
  return id;
 | 
					  return id;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
FuncId ParsingDatabase::ToFuncId(const std::string& usr) {
 | 
					FuncId IndexedFile::ToFuncId(const std::string& usr) {
 | 
				
			||||||
  auto it = usr_to_func_id.find(usr);
 | 
					  auto it = usr_to_func_id.find(usr);
 | 
				
			||||||
  if (it != usr_to_func_id.end())
 | 
					  if (it != usr_to_func_id.end())
 | 
				
			||||||
    return it->second;
 | 
					    return it->second;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  FuncId id(funcs.size());
 | 
					  FuncId id(funcs.size());
 | 
				
			||||||
  funcs.push_back(FuncDef(id, usr));
 | 
					  funcs.push_back(IndexedFuncDef(id, usr));
 | 
				
			||||||
  usr_to_func_id[usr] = id;
 | 
					  usr_to_func_id[usr] = id;
 | 
				
			||||||
  return id;
 | 
					  return id;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
VarId ParsingDatabase::ToVarId(const std::string& usr) {
 | 
					VarId IndexedFile::ToVarId(const std::string& usr) {
 | 
				
			||||||
  auto it = usr_to_var_id.find(usr);
 | 
					  auto it = usr_to_var_id.find(usr);
 | 
				
			||||||
  if (it != usr_to_var_id.end())
 | 
					  if (it != usr_to_var_id.end())
 | 
				
			||||||
    return it->second;
 | 
					    return it->second;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  VarId id(vars.size());
 | 
					  VarId id(vars.size());
 | 
				
			||||||
  vars.push_back(VarDef(id, usr));
 | 
					  vars.push_back(IndexedVarDef(id, usr));
 | 
				
			||||||
  usr_to_var_id[usr] = id;
 | 
					  usr_to_var_id[usr] = id;
 | 
				
			||||||
  return id;
 | 
					  return id;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
TypeId ParsingDatabase::ToTypeId(const CXCursor& cursor) {
 | 
					TypeId IndexedFile::ToTypeId(const CXCursor& cursor) {
 | 
				
			||||||
  return ToTypeId(clang::Cursor(cursor).get_usr());
 | 
					  return ToTypeId(clang::Cursor(cursor).get_usr());
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
FuncId ParsingDatabase::ToFuncId(const CXCursor& cursor) {
 | 
					FuncId IndexedFile::ToFuncId(const CXCursor& cursor) {
 | 
				
			||||||
  return ToFuncId(clang::Cursor(cursor).get_usr());
 | 
					  return ToFuncId(clang::Cursor(cursor).get_usr());
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
VarId ParsingDatabase::ToVarId(const CXCursor& cursor) {
 | 
					VarId IndexedFile::ToVarId(const CXCursor& cursor) {
 | 
				
			||||||
  return ToVarId(clang::Cursor(cursor).get_usr());
 | 
					  return ToVarId(clang::Cursor(cursor).get_usr());
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
TypeDef* ParsingDatabase::Resolve(TypeId id) {
 | 
					IndexedTypeDef* IndexedFile::Resolve(TypeId id) {
 | 
				
			||||||
  return &types[id.local_id];
 | 
					  return &types[id.local_id];
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
FuncDef* ParsingDatabase::Resolve(FuncId id) {
 | 
					IndexedFuncDef* IndexedFile::Resolve(FuncId id) {
 | 
				
			||||||
  return &funcs[id.local_id];
 | 
					  return &funcs[id.local_id];
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
VarDef* ParsingDatabase::Resolve(VarId id) {
 | 
					IndexedVarDef* IndexedFile::Resolve(VarId id) {
 | 
				
			||||||
  return &vars[id.local_id];
 | 
					  return &vars[id.local_id];
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -148,7 +148,7 @@ void Write(Writer& writer, const char* key, uint64_t value) {
 | 
				
			|||||||
  writer.Uint64(value);
 | 
					  writer.Uint64(value);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
std::string ParsingDatabase::ToString() {
 | 
					std::string IndexedFile::ToString() {
 | 
				
			||||||
  auto it = usr_to_type_id.find("");
 | 
					  auto it = usr_to_type_id.find("");
 | 
				
			||||||
  if (it != usr_to_type_id.end()) {
 | 
					  if (it != usr_to_type_id.end()) {
 | 
				
			||||||
    Resolve(it->second)->short_name = "<fundamental>";
 | 
					    Resolve(it->second)->short_name = "<fundamental>";
 | 
				
			||||||
@ -168,7 +168,7 @@ std::string ParsingDatabase::ToString() {
 | 
				
			|||||||
  // Types
 | 
					  // Types
 | 
				
			||||||
  writer.Key("types");
 | 
					  writer.Key("types");
 | 
				
			||||||
  writer.StartArray();
 | 
					  writer.StartArray();
 | 
				
			||||||
  for (TypeDef& def : types) {
 | 
					  for (IndexedTypeDef& def : types) {
 | 
				
			||||||
    if (def.is_system_def) continue;
 | 
					    if (def.is_system_def) continue;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    writer.StartObject();
 | 
					    writer.StartObject();
 | 
				
			||||||
@ -191,7 +191,7 @@ std::string ParsingDatabase::ToString() {
 | 
				
			|||||||
  // Functions
 | 
					  // Functions
 | 
				
			||||||
  writer.Key("functions");
 | 
					  writer.Key("functions");
 | 
				
			||||||
  writer.StartArray();
 | 
					  writer.StartArray();
 | 
				
			||||||
  for (FuncDef& def : funcs) {
 | 
					  for (IndexedFuncDef& def : funcs) {
 | 
				
			||||||
    if (def.is_system_def) continue;
 | 
					    if (def.is_system_def) continue;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    writer.StartObject();
 | 
					    writer.StartObject();
 | 
				
			||||||
@ -215,7 +215,7 @@ std::string ParsingDatabase::ToString() {
 | 
				
			|||||||
  // Variables
 | 
					  // Variables
 | 
				
			||||||
  writer.Key("variables");
 | 
					  writer.Key("variables");
 | 
				
			||||||
  writer.StartArray();
 | 
					  writer.StartArray();
 | 
				
			||||||
  for (VarDef& def : vars) {
 | 
					  for (IndexedVarDef& def : vars) {
 | 
				
			||||||
    if (def.is_system_def) continue;
 | 
					    if (def.is_system_def) continue;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    writer.StartObject();
 | 
					    writer.StartObject();
 | 
				
			||||||
@ -404,7 +404,7 @@ struct NamespaceHelper {
 | 
				
			|||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct IndexParam {
 | 
					struct IndexParam {
 | 
				
			||||||
  ParsingDatabase* db;
 | 
					  IndexedFile* db;
 | 
				
			||||||
  NamespaceHelper* ns;
 | 
					  NamespaceHelper* ns;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // Record the last type usage location we recorded. Clang will sometimes
 | 
					  // Record the last type usage location we recorded. Clang will sometimes
 | 
				
			||||||
@ -413,7 +413,7 @@ struct IndexParam {
 | 
				
			|||||||
  Location last_type_usage_location;
 | 
					  Location last_type_usage_location;
 | 
				
			||||||
  Location last_func_usage_location;
 | 
					  Location last_func_usage_location;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  IndexParam(ParsingDatabase* db, NamespaceHelper* ns) : db(db), ns(ns) {}
 | 
					  IndexParam(IndexedFile* db, NamespaceHelper* ns) : db(db), ns(ns) {}
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/*
 | 
					/*
 | 
				
			||||||
@ -443,19 +443,19 @@ bool IsTypeDefinition(const CXIdxContainerInfo* container) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct VisitDeclForTypeUsageParam {
 | 
					struct VisitDeclForTypeUsageParam {
 | 
				
			||||||
  ParsingDatabase* db;
 | 
					  IndexedFile* db;
 | 
				
			||||||
  bool is_interesting;
 | 
					  bool is_interesting;
 | 
				
			||||||
  int has_processed_any = false;
 | 
					  int has_processed_any = false;
 | 
				
			||||||
  optional<clang::Cursor> previous_cursor;
 | 
					  optional<clang::Cursor> previous_cursor;
 | 
				
			||||||
  optional<TypeId> initial_type;
 | 
					  optional<TypeId> initial_type;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  VisitDeclForTypeUsageParam(ParsingDatabase* db, bool is_interesting)
 | 
					  VisitDeclForTypeUsageParam(IndexedFile* db, bool is_interesting)
 | 
				
			||||||
    : db(db), is_interesting(is_interesting) {}
 | 
					    : db(db), is_interesting(is_interesting) {}
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void VisitDeclForTypeUsageVisitorHandler(clang::Cursor cursor, VisitDeclForTypeUsageParam* param) {
 | 
					void VisitDeclForTypeUsageVisitorHandler(clang::Cursor cursor, VisitDeclForTypeUsageParam* param) {
 | 
				
			||||||
  param->has_processed_any = true;
 | 
					  param->has_processed_any = true;
 | 
				
			||||||
  ParsingDatabase* db = param->db;
 | 
					  IndexedFile* db = param->db;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // TODO: Something in STL (type_traits)? reports an empty USR.
 | 
					  // TODO: Something in STL (type_traits)? reports an empty USR.
 | 
				
			||||||
  std::string referenced_usr = cursor.get_referenced().get_usr();
 | 
					  std::string referenced_usr = cursor.get_referenced().get_usr();
 | 
				
			||||||
@ -467,7 +467,7 @@ void VisitDeclForTypeUsageVisitorHandler(clang::Cursor cursor, VisitDeclForTypeU
 | 
				
			|||||||
    param->initial_type = ref_type_id;
 | 
					    param->initial_type = ref_type_id;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if (param->is_interesting) {
 | 
					  if (param->is_interesting) {
 | 
				
			||||||
    TypeDef* ref_type_def = db->Resolve(ref_type_id);
 | 
					    IndexedTypeDef* ref_type_def = db->Resolve(ref_type_id);
 | 
				
			||||||
    Location loc = db->file_db.Resolve(cursor, true /*interesting*/);
 | 
					    Location loc = db->file_db.Resolve(cursor, true /*interesting*/);
 | 
				
			||||||
    ref_type_def->AddUsage(loc);
 | 
					    ref_type_def->AddUsage(loc);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
@ -496,7 +496,7 @@ clang::VisiterResult VisitDeclForTypeUsageVisitor(clang::Cursor cursor, clang::C
 | 
				
			|||||||
  return clang::VisiterResult::Continue;
 | 
					  return clang::VisiterResult::Continue;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
optional<TypeId> ResolveDeclToType(ParsingDatabase* db, clang::Cursor decl_cursor,
 | 
					optional<TypeId> ResolveDeclToType(IndexedFile* db, clang::Cursor decl_cursor,
 | 
				
			||||||
  bool is_interesting, const CXIdxContainerInfo* semantic_container,
 | 
					  bool is_interesting, const CXIdxContainerInfo* semantic_container,
 | 
				
			||||||
  const CXIdxContainerInfo* lexical_container) {
 | 
					  const CXIdxContainerInfo* lexical_container) {
 | 
				
			||||||
  //
 | 
					  //
 | 
				
			||||||
@ -563,7 +563,7 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
 | 
				
			|||||||
  bool is_system_def = clang_Location_isInSystemHeader(clang_getCursorLocation(decl->cursor));
 | 
					  bool is_system_def = clang_Location_isInSystemHeader(clang_getCursorLocation(decl->cursor));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  IndexParam* param = static_cast<IndexParam*>(client_data);
 | 
					  IndexParam* param = static_cast<IndexParam*>(client_data);
 | 
				
			||||||
  ParsingDatabase* db = param->db;
 | 
					  IndexedFile* db = param->db;
 | 
				
			||||||
  NamespaceHelper* ns = param->ns;
 | 
					  NamespaceHelper* ns = param->ns;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  switch (decl->entityInfo->kind) {
 | 
					  switch (decl->entityInfo->kind) {
 | 
				
			||||||
@ -580,7 +580,7 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
 | 
				
			|||||||
  {
 | 
					  {
 | 
				
			||||||
    clang::Cursor decl_cursor = decl->cursor;
 | 
					    clang::Cursor decl_cursor = decl->cursor;
 | 
				
			||||||
    VarId var_id = db->ToVarId(decl->entityInfo->USR);
 | 
					    VarId var_id = db->ToVarId(decl->entityInfo->USR);
 | 
				
			||||||
    VarDef* var_def = db->Resolve(var_id);
 | 
					    IndexedVarDef* var_def = db->Resolve(var_id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    var_def->is_system_def = is_system_def;
 | 
					    var_def->is_system_def = is_system_def;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -610,7 +610,7 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
    if (decl->isDefinition && IsTypeDefinition(decl->semanticContainer)) {
 | 
					    if (decl->isDefinition && IsTypeDefinition(decl->semanticContainer)) {
 | 
				
			||||||
      TypeId declaring_type_id = db->ToTypeId(decl->semanticContainer->cursor);
 | 
					      TypeId declaring_type_id = db->ToTypeId(decl->semanticContainer->cursor);
 | 
				
			||||||
      TypeDef* declaring_type_def = db->Resolve(declaring_type_id);
 | 
					      IndexedTypeDef* declaring_type_def = db->Resolve(declaring_type_id);
 | 
				
			||||||
      var_def->declaring_type = declaring_type_id;
 | 
					      var_def->declaring_type = declaring_type_id;
 | 
				
			||||||
      declaring_type_def->vars.push_back(var_id);
 | 
					      declaring_type_def->vars.push_back(var_id);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
@ -627,7 +627,7 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
 | 
				
			|||||||
  {
 | 
					  {
 | 
				
			||||||
    clang::Cursor decl_cursor = decl->cursor;
 | 
					    clang::Cursor decl_cursor = decl->cursor;
 | 
				
			||||||
    FuncId func_id = db->ToFuncId(decl->entityInfo->USR);
 | 
					    FuncId func_id = db->ToFuncId(decl->entityInfo->USR);
 | 
				
			||||||
    FuncDef* func_def = db->Resolve(func_id);
 | 
					    IndexedFuncDef* func_def = db->Resolve(func_id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    func_def->is_system_def = is_system_def;
 | 
					    func_def->is_system_def = is_system_def;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -653,7 +653,7 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
 | 
				
			|||||||
    // be one of those in the entire program.
 | 
					    // be one of those in the entire program.
 | 
				
			||||||
    if (IsTypeDefinition(decl->semanticContainer)) {
 | 
					    if (IsTypeDefinition(decl->semanticContainer)) {
 | 
				
			||||||
      TypeId declaring_type_id = db->ToTypeId(decl->semanticContainer->cursor);
 | 
					      TypeId declaring_type_id = db->ToTypeId(decl->semanticContainer->cursor);
 | 
				
			||||||
      TypeDef* declaring_type_def = db->Resolve(declaring_type_id);
 | 
					      IndexedTypeDef* declaring_type_def = db->Resolve(declaring_type_id);
 | 
				
			||||||
      func_def->declaring_type = declaring_type_id;
 | 
					      func_def->declaring_type = declaring_type_id;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
      // Mark a type reference at the ctor/dtor location.
 | 
					      // Mark a type reference at the ctor/dtor location.
 | 
				
			||||||
@ -716,7 +716,7 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
 | 
				
			|||||||
        for (unsigned int i = 0; i < num_overridden; ++i) {
 | 
					        for (unsigned int i = 0; i < num_overridden; ++i) {
 | 
				
			||||||
          clang::Cursor parent = overridden[i];
 | 
					          clang::Cursor parent = overridden[i];
 | 
				
			||||||
          FuncId parent_id = db->ToFuncId(parent.get_usr());
 | 
					          FuncId parent_id = db->ToFuncId(parent.get_usr());
 | 
				
			||||||
          FuncDef* parent_def = db->Resolve(parent_id);
 | 
					          IndexedFuncDef* parent_def = db->Resolve(parent_id);
 | 
				
			||||||
          func_def = db->Resolve(func_id); // ToFuncId invalidated func_def
 | 
					          func_def = db->Resolve(func_id); // ToFuncId invalidated func_def
 | 
				
			||||||
 | 
					
 | 
				
			||||||
          func_def->base = parent_id;
 | 
					          func_def->base = parent_id;
 | 
				
			||||||
@ -744,7 +744,7 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
 | 
				
			|||||||
    optional<TypeId> alias_of = ResolveDeclToType(db, decl->cursor, true /*is_interesting*/, decl->semanticContainer, decl->lexicalContainer);
 | 
					    optional<TypeId> alias_of = ResolveDeclToType(db, decl->cursor, true /*is_interesting*/, decl->semanticContainer, decl->lexicalContainer);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    TypeId type_id = db->ToTypeId(decl->entityInfo->USR);
 | 
					    TypeId type_id = db->ToTypeId(decl->entityInfo->USR);
 | 
				
			||||||
    TypeDef* type_def = db->Resolve(type_id);
 | 
					    IndexedTypeDef* type_def = db->Resolve(type_id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    type_def->is_system_def = is_system_def;
 | 
					    type_def->is_system_def = is_system_def;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -766,7 +766,7 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
 | 
				
			|||||||
  case CXIdxEntity_CXXClass:
 | 
					  case CXIdxEntity_CXXClass:
 | 
				
			||||||
  {
 | 
					  {
 | 
				
			||||||
    TypeId type_id = db->ToTypeId(decl->entityInfo->USR);
 | 
					    TypeId type_id = db->ToTypeId(decl->entityInfo->USR);
 | 
				
			||||||
    TypeDef* type_def = db->Resolve(type_id);
 | 
					    IndexedTypeDef* type_def = db->Resolve(type_id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    type_def->is_system_def = is_system_def;
 | 
					    type_def->is_system_def = is_system_def;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -805,9 +805,9 @@ void indexDeclaration(CXClientData client_data, const CXIdxDeclInfo* decl) {
 | 
				
			|||||||
        const CXIdxBaseClassInfo* base_class = class_info->bases[i];
 | 
					        const CXIdxBaseClassInfo* base_class = class_info->bases[i];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        optional<TypeId> parent_type_id = ResolveDeclToType(db, base_class->cursor, true /*is_interesting*/, decl->semanticContainer, decl->lexicalContainer);
 | 
					        optional<TypeId> parent_type_id = ResolveDeclToType(db, base_class->cursor, true /*is_interesting*/, decl->semanticContainer, decl->lexicalContainer);
 | 
				
			||||||
        TypeDef* type_def = db->Resolve(type_id); // type_def ptr could be invalidated by ResolveDeclToType.
 | 
					        IndexedTypeDef* type_def = db->Resolve(type_id); // type_def ptr could be invalidated by ResolveDeclToType.
 | 
				
			||||||
        if (parent_type_id) {
 | 
					        if (parent_type_id) {
 | 
				
			||||||
          TypeDef* parent_type_def = db->Resolve(parent_type_id.value());
 | 
					          IndexedTypeDef* parent_type_def = db->Resolve(parent_type_id.value());
 | 
				
			||||||
          parent_type_def->derived.push_back(type_id);
 | 
					          parent_type_def->derived.push_back(type_id);
 | 
				
			||||||
          type_def->parents.push_back(parent_type_id.value());
 | 
					          type_def->parents.push_back(parent_type_id.value());
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
@ -842,7 +842,7 @@ bool IsFunction(CXCursorKind kind) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
void indexEntityReference(CXClientData client_data, const CXIdxEntityRefInfo* ref) {
 | 
					void indexEntityReference(CXClientData client_data, const CXIdxEntityRefInfo* ref) {
 | 
				
			||||||
  IndexParam* param = static_cast<IndexParam*>(client_data);
 | 
					  IndexParam* param = static_cast<IndexParam*>(client_data);
 | 
				
			||||||
  ParsingDatabase* db = param->db;
 | 
					  IndexedFile* db = param->db;
 | 
				
			||||||
  clang::Cursor cursor(ref->cursor);
 | 
					  clang::Cursor cursor(ref->cursor);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  switch (ref->referencedEntity->kind) {
 | 
					  switch (ref->referencedEntity->kind) {
 | 
				
			||||||
@ -852,7 +852,7 @@ void indexEntityReference(CXClientData client_data, const CXIdxEntityRefInfo* re
 | 
				
			|||||||
  case CXIdxEntity_Field:
 | 
					  case CXIdxEntity_Field:
 | 
				
			||||||
  {
 | 
					  {
 | 
				
			||||||
    VarId var_id = db->ToVarId(ref->referencedEntity->cursor);
 | 
					    VarId var_id = db->ToVarId(ref->referencedEntity->cursor);
 | 
				
			||||||
    VarDef* var_def = db->Resolve(var_id);
 | 
					    IndexedVarDef* var_def = db->Resolve(var_id);
 | 
				
			||||||
    var_def->uses.push_back(db->file_db.Resolve(ref->loc, false /*interesting*/));
 | 
					    var_def->uses.push_back(db->file_db.Resolve(ref->loc, false /*interesting*/));
 | 
				
			||||||
    break;
 | 
					    break;
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
@ -883,15 +883,15 @@ void indexEntityReference(CXClientData client_data, const CXIdxEntityRefInfo* re
 | 
				
			|||||||
    FuncId called_id = db->ToFuncId(ref->referencedEntity->USR);
 | 
					    FuncId called_id = db->ToFuncId(ref->referencedEntity->USR);
 | 
				
			||||||
    if (IsFunction(ref->container->cursor.kind)) {
 | 
					    if (IsFunction(ref->container->cursor.kind)) {
 | 
				
			||||||
      FuncId caller_id = db->ToFuncId(ref->container->cursor);
 | 
					      FuncId caller_id = db->ToFuncId(ref->container->cursor);
 | 
				
			||||||
      FuncDef* caller_def = db->Resolve(caller_id);
 | 
					      IndexedFuncDef* caller_def = db->Resolve(caller_id);
 | 
				
			||||||
      FuncDef* called_def = db->Resolve(called_id);
 | 
					      IndexedFuncDef* called_def = db->Resolve(called_id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
      caller_def->callees.push_back(FuncRef(called_id, loc));
 | 
					      caller_def->callees.push_back(FuncRef(called_id, loc));
 | 
				
			||||||
      called_def->callers.push_back(FuncRef(caller_id, loc));
 | 
					      called_def->callers.push_back(FuncRef(caller_id, loc));
 | 
				
			||||||
      called_def->uses.push_back(loc);
 | 
					      called_def->uses.push_back(loc);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
    else {
 | 
					    else {
 | 
				
			||||||
      FuncDef* called_def = db->Resolve(called_id);
 | 
					      IndexedFuncDef* called_def = db->Resolve(called_id);
 | 
				
			||||||
      called_def->uses.push_back(loc);
 | 
					      called_def->uses.push_back(loc);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -906,9 +906,9 @@ void indexEntityReference(CXClientData client_data, const CXIdxEntityRefInfo* re
 | 
				
			|||||||
      Location parent_loc = db->file_db.Resolve(ref->parentEntity->cursor, true /*interesting*/);
 | 
					      Location parent_loc = db->file_db.Resolve(ref->parentEntity->cursor, true /*interesting*/);
 | 
				
			||||||
      Location our_loc = db->file_db.Resolve(ref->loc, true /*is_interesting*/);
 | 
					      Location our_loc = db->file_db.Resolve(ref->loc, true /*is_interesting*/);
 | 
				
			||||||
      if (!parent_loc.IsEqualTo(our_loc)) {
 | 
					      if (!parent_loc.IsEqualTo(our_loc)) {
 | 
				
			||||||
        FuncDef* called_def = db->Resolve(called_id);
 | 
					        IndexedFuncDef* called_def = db->Resolve(called_id);
 | 
				
			||||||
        assert(called_def->declaring_type.has_value());
 | 
					        assert(called_def->declaring_type.has_value());
 | 
				
			||||||
        TypeDef* type_def = db->Resolve(called_def->declaring_type.value());
 | 
					        IndexedTypeDef* type_def = db->Resolve(called_def->declaring_type.value());
 | 
				
			||||||
        type_def->AddUsage(our_loc);
 | 
					        type_def->AddUsage(our_loc);
 | 
				
			||||||
      }
 | 
					      }
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
@ -923,7 +923,7 @@ void indexEntityReference(CXClientData client_data, const CXIdxEntityRefInfo* re
 | 
				
			|||||||
  case CXIdxEntity_CXXClass:
 | 
					  case CXIdxEntity_CXXClass:
 | 
				
			||||||
  {
 | 
					  {
 | 
				
			||||||
    TypeId referenced_id = db->ToTypeId(ref->referencedEntity->USR);
 | 
					    TypeId referenced_id = db->ToTypeId(ref->referencedEntity->USR);
 | 
				
			||||||
    TypeDef* referenced_def = db->Resolve(referenced_id);
 | 
					    IndexedTypeDef* referenced_def = db->Resolve(referenced_id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    //
 | 
					    //
 | 
				
			||||||
    // The following will generate two TypeRefs to Foo, both located at the
 | 
					    // The following will generate two TypeRefs to Foo, both located at the
 | 
				
			||||||
@ -964,7 +964,7 @@ void indexEntityReference(CXClientData client_data, const CXIdxEntityRefInfo* re
 | 
				
			|||||||
static bool DUMP_AST = true;
 | 
					static bool DUMP_AST = true;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
ParsingDatabase Parse(std::string filename, std::vector<std::string> args) {
 | 
					IndexedFile Parse(std::string filename, std::vector<std::string> args) {
 | 
				
			||||||
  clang::Index index(0 /*excludeDeclarationsFromPCH*/, 0 /*displayDiagnostics*/);
 | 
					  clang::Index index(0 /*excludeDeclarationsFromPCH*/, 0 /*displayDiagnostics*/);
 | 
				
			||||||
  clang::TranslationUnit tu(index, filename, args);
 | 
					  clang::TranslationUnit tu(index, filename, args);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -987,7 +987,7 @@ ParsingDatabase Parse(std::string filename, std::vector<std::string> args) {
 | 
				
			|||||||
    */
 | 
					    */
 | 
				
			||||||
  };
 | 
					  };
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  ParsingDatabase db;
 | 
					  IndexedFile db;
 | 
				
			||||||
  NamespaceHelper ns;
 | 
					  NamespaceHelper ns;
 | 
				
			||||||
  IndexParam param(&db, &ns);
 | 
					  IndexParam param(&db, &ns);
 | 
				
			||||||
  clang_indexTranslationUnit(index_action, ¶m, callbacks, sizeof(callbacks),
 | 
					  clang_indexTranslationUnit(index_action, ¶m, callbacks, sizeof(callbacks),
 | 
				
			||||||
@ -1089,7 +1089,7 @@ void WriteToFile(const std::string& filename, const std::string& content) {
 | 
				
			|||||||
  file << content;
 | 
					  file << content;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
int mai2n(int argc, char** argv) {
 | 
					int main(int argc, char** argv) {
 | 
				
			||||||
  // TODO: Assert that we need to be on clang >= 3.9.1
 | 
					  // TODO: Assert that we need to be on clang >= 3.9.1
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  /*
 | 
					  /*
 | 
				
			||||||
@ -1128,7 +1128,7 @@ int mai2n(int argc, char** argv) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
    // Run test.
 | 
					    // Run test.
 | 
				
			||||||
    std::cout << "[START] " << path << std::endl;
 | 
					    std::cout << "[START] " << path << std::endl;
 | 
				
			||||||
    ParsingDatabase db = Parse(path, {});
 | 
					    IndexedFile db = Parse(path, {});
 | 
				
			||||||
    std::string actual_output = db.ToString();
 | 
					    std::string actual_output = db.ToString();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    //WriteToFile("output.json", actual_output);
 | 
					    //WriteToFile("output.json", actual_output);
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										36
									
								
								indexer.h
									
									
									
									
									
								
							
							
						
						
									
										36
									
								
								indexer.h
									
									
									
									
									
								
							@ -80,11 +80,11 @@ Location WithInteresting(bool interesting) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
END_BITFIELD_TYPE()
 | 
					END_BITFIELD_TYPE()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct FileDb {
 | 
					struct IndexedFileDb {
 | 
				
			||||||
  std::unordered_map<std::string, FileId> file_path_to_file_id;
 | 
					  std::unordered_map<std::string, FileId> file_path_to_file_id;
 | 
				
			||||||
  std::unordered_map<FileId, std::string> file_id_to_file_path;
 | 
					  std::unordered_map<FileId, std::string> file_id_to_file_path;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  FileDb() {
 | 
					  IndexedFileDb() {
 | 
				
			||||||
    // Reserve id 0 for unfound.
 | 
					    // Reserve id 0 for unfound.
 | 
				
			||||||
    file_path_to_file_id[""] = 0;
 | 
					    file_path_to_file_id[""] = 0;
 | 
				
			||||||
    file_id_to_file_path[0] = "";
 | 
					    file_id_to_file_path[0] = "";
 | 
				
			||||||
@ -167,7 +167,7 @@ using VarRef = Ref<VarDef>;
 | 
				
			|||||||
// TODO: Either eliminate the defs created as a by-product of cross-referencing,
 | 
					// TODO: Either eliminate the defs created as a by-product of cross-referencing,
 | 
				
			||||||
//       or do not emit things we don't have definitions for.
 | 
					//       or do not emit things we don't have definitions for.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct TypeDef {
 | 
					struct IndexedTypeDef {
 | 
				
			||||||
  bool is_system_def = false;
 | 
					  bool is_system_def = false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // General metadata.
 | 
					  // General metadata.
 | 
				
			||||||
@ -204,7 +204,7 @@ struct TypeDef {
 | 
				
			|||||||
  // NOTE: Do not insert directly! Use AddUsage instead.
 | 
					  // NOTE: Do not insert directly! Use AddUsage instead.
 | 
				
			||||||
  std::vector<Location> uses;
 | 
					  std::vector<Location> uses;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  TypeDef(TypeId id, const std::string& usr) : id(id), usr(usr) {
 | 
					  IndexedTypeDef(TypeId id, const std::string& usr) : id(id), usr(usr) {
 | 
				
			||||||
    assert(usr.size() > 0);
 | 
					    assert(usr.size() > 0);
 | 
				
			||||||
    //std::cout << "Creating type with usr " << usr << std::endl;
 | 
					    //std::cout << "Creating type with usr " << usr << std::endl;
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
@ -226,7 +226,7 @@ struct TypeDef {
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct FuncDef {
 | 
					struct IndexedFuncDef {
 | 
				
			||||||
  bool is_system_def = false;
 | 
					  bool is_system_def = false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // General metadata.
 | 
					  // General metadata.
 | 
				
			||||||
@ -260,12 +260,12 @@ struct FuncDef {
 | 
				
			|||||||
  // All usages. For interesting usages, see callees.
 | 
					  // All usages. For interesting usages, see callees.
 | 
				
			||||||
  std::vector<Location> uses;
 | 
					  std::vector<Location> uses;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  FuncDef(FuncId id, const std::string& usr) : id(id), usr(usr) {
 | 
					  IndexedFuncDef(FuncId id, const std::string& usr) : id(id), usr(usr) {
 | 
				
			||||||
    assert(usr.size() > 0);
 | 
					    assert(usr.size() > 0);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct VarDef {
 | 
					struct IndexedVarDef {
 | 
				
			||||||
  bool is_system_def = false;
 | 
					  bool is_system_def = false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // General metadata.
 | 
					  // General metadata.
 | 
				
			||||||
@ -287,26 +287,26 @@ struct VarDef {
 | 
				
			|||||||
  // Usages.
 | 
					  // Usages.
 | 
				
			||||||
  std::vector<Location> uses;
 | 
					  std::vector<Location> uses;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  VarDef(VarId id, const std::string& usr) : id(id), usr(usr) {
 | 
					  IndexedVarDef(VarId id, const std::string& usr) : id(id), usr(usr) {
 | 
				
			||||||
    assert(usr.size() > 0);
 | 
					    assert(usr.size() > 0);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct ParsingDatabase {
 | 
					struct IndexedFile {
 | 
				
			||||||
  // NOTE: Every Id is resolved to a file_id of 0. The correct file_id needs
 | 
					  // NOTE: Every Id is resolved to a file_id of 0. The correct file_id needs
 | 
				
			||||||
  //       to get fixed up when inserting into the real db.
 | 
					  //       to get fixed up when inserting into the real db.
 | 
				
			||||||
  std::unordered_map<std::string, TypeId> usr_to_type_id;
 | 
					  std::unordered_map<std::string, TypeId> usr_to_type_id;
 | 
				
			||||||
  std::unordered_map<std::string, FuncId> usr_to_func_id;
 | 
					  std::unordered_map<std::string, FuncId> usr_to_func_id;
 | 
				
			||||||
  std::unordered_map<std::string, VarId> usr_to_var_id;
 | 
					  std::unordered_map<std::string, VarId> usr_to_var_id;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  std::vector<TypeDef> types;
 | 
					  std::vector<IndexedTypeDef> types;
 | 
				
			||||||
  std::vector<FuncDef> funcs;
 | 
					  std::vector<IndexedFuncDef> funcs;
 | 
				
			||||||
  std::vector<VarDef> vars;
 | 
					  std::vector<IndexedVarDef> vars;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  FileDb file_db;
 | 
					  IndexedFileDb file_db;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  ParsingDatabase();
 | 
					  IndexedFile();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  TypeId ToTypeId(const std::string& usr);
 | 
					  TypeId ToTypeId(const std::string& usr);
 | 
				
			||||||
  FuncId ToFuncId(const std::string& usr);
 | 
					  FuncId ToFuncId(const std::string& usr);
 | 
				
			||||||
@ -315,11 +315,11 @@ struct ParsingDatabase {
 | 
				
			|||||||
  FuncId ToFuncId(const CXCursor& usr);
 | 
					  FuncId ToFuncId(const CXCursor& usr);
 | 
				
			||||||
  VarId ToVarId(const CXCursor& usr);
 | 
					  VarId ToVarId(const CXCursor& usr);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  TypeDef* Resolve(TypeId id);
 | 
					  IndexedTypeDef* Resolve(TypeId id);
 | 
				
			||||||
  FuncDef* Resolve(FuncId id);
 | 
					  IndexedFuncDef* Resolve(FuncId id);
 | 
				
			||||||
  VarDef* Resolve(VarId id);
 | 
					  IndexedVarDef* Resolve(VarId id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  std::string ToString();
 | 
					  std::string ToString();
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
ParsingDatabase Parse(std::string filename, std::vector<std::string> args);
 | 
					IndexedFile Parse(std::string filename, std::vector<std::string> args);
 | 
				
			||||||
							
								
								
									
										107
									
								
								query_db.cc
									
									
									
									
									
								
							
							
						
						
									
										107
									
								
								query_db.cc
									
									
									
									
									
								
							@ -24,7 +24,7 @@ struct SymbolIdx {
 | 
				
			|||||||
  };
 | 
					  };
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct File {
 | 
					struct QueryableFile {
 | 
				
			||||||
  // Symbols declared in the file.
 | 
					  // Symbols declared in the file.
 | 
				
			||||||
  std::vector<SymbolIdx> declared_symbols;
 | 
					  std::vector<SymbolIdx> declared_symbols;
 | 
				
			||||||
  // Symbols which have definitions in the file.
 | 
					  // Symbols which have definitions in the file.
 | 
				
			||||||
@ -37,7 +37,7 @@ struct QueryableEntry {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
// The query database is heavily optimized for fast queries. It is stored
 | 
					// The query database is heavily optimized for fast queries. It is stored
 | 
				
			||||||
// in-memory.
 | 
					// in-memory.
 | 
				
			||||||
struct QueryDatabase {
 | 
					struct QueryableDatabase {
 | 
				
			||||||
  // Indicies between lookup vectors are related to symbols, ie, index 5 in
 | 
					  // Indicies between lookup vectors are related to symbols, ie, index 5 in
 | 
				
			||||||
  // |qualified_names| matches index 5 in |symbols|.
 | 
					  // |qualified_names| matches index 5 in |symbols|.
 | 
				
			||||||
  std::vector<QueryableEntry> qualified_names;
 | 
					  std::vector<QueryableEntry> qualified_names;
 | 
				
			||||||
@ -51,7 +51,7 @@ struct QueryDatabase {
 | 
				
			|||||||
  // |files| is indexed by FileId. Retrieve a FileId from a path using
 | 
					  // |files| is indexed by FileId. Retrieve a FileId from a path using
 | 
				
			||||||
  // |file_locator|.
 | 
					  // |file_locator|.
 | 
				
			||||||
  FileDatabase file_locator;
 | 
					  FileDatabase file_locator;
 | 
				
			||||||
  std::vector<File> files;
 | 
					  std::vector<QueryableFile> files;
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -91,27 +91,45 @@ struct Query {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void fail(const std::string& message) {
 | 
					 | 
				
			||||||
  std::cerr << "Fatal error: " << message << std::endl;
 | 
					 | 
				
			||||||
  std::exit(1);
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					struct CachedIndexedFile {
 | 
				
			||||||
 | 
					  // Path to the file indexed.
 | 
				
			||||||
 | 
					  std::string path;
 | 
				
			||||||
 | 
					  
 | 
				
			||||||
 | 
					  // Full in-memory storage for the index. Empty if not loaded into memory.
 | 
				
			||||||
 | 
					  // |path| can be used to fetch the index from disk.
 | 
				
			||||||
 | 
					  optional<rapidjson::Document> index;
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					struct DocumentDiff {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					// Compute a diff between |original| and |updated|.
 | 
				
			||||||
 | 
					//rapidjson::Document DiffIndex(rapidjson::Document original, rapidjson::Document updated) {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					//}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// NOTE: If updating this enum, make sure to also update the parser and the
 | 
				
			||||||
 | 
					//       help text.
 | 
				
			||||||
enum class PreferredSymbolLocation {
 | 
					enum class PreferredSymbolLocation {
 | 
				
			||||||
  Declaration,
 | 
					  Declaration,
 | 
				
			||||||
  Definition
 | 
					  Definition
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
std::istream& operator >> (std::istream& is, PreferredSymbolLocation& obj) {
 | 
					 | 
				
			||||||
  std::string content;
 | 
					 | 
				
			||||||
  is >> content;
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if (content == "declaration")
 | 
					bool ParsePreferredSymbolLocation(const std::string& content, PreferredSymbolLocation* obj) {
 | 
				
			||||||
    obj = PreferredSymbolLocation::Declaration;
 | 
					#define PARSE_AS(name, string)      \
 | 
				
			||||||
  else if (content == "definition")
 | 
					  if (content == #string) {         \
 | 
				
			||||||
    obj = PreferredSymbolLocation::Definition;
 | 
					    *obj = name;                    \
 | 
				
			||||||
  else
 | 
					    return true;                    \
 | 
				
			||||||
    is.setstate(std::ios::failbit);
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return is;
 | 
					  PARSE_AS(PreferredSymbolLocation::Declaration, "declaration");
 | 
				
			||||||
 | 
					  PARSE_AS(PreferredSymbolLocation::Definition, "definition");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  return false;
 | 
				
			||||||
 | 
					#undef PARSE_AS
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// NOTE: If updating this enum, make sure to also update the parser and the
 | 
					// NOTE: If updating this enum, make sure to also update the parser and the
 | 
				
			||||||
@ -127,34 +145,24 @@ enum class Command {
 | 
				
			|||||||
  Search
 | 
					  Search
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
//std::ostream& operator<<(std::ostream& os, const Command& obj) {
 | 
					bool ParseCommand(const std::string& content, Command* obj) {
 | 
				
			||||||
  // write obj to stream
 | 
					#define PARSE_AS(name, string)      \
 | 
				
			||||||
//  return os;
 | 
					  if (content == #string) {         \
 | 
				
			||||||
//}
 | 
					    *obj = name;                    \
 | 
				
			||||||
std::istream& operator >> (std::istream& is, Command& obj) {
 | 
					    return true;                    \
 | 
				
			||||||
  std::string content;
 | 
					  }
 | 
				
			||||||
  is >> content;
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if (content == "callees")
 | 
					  PARSE_AS(Command::Callees, "callees");
 | 
				
			||||||
    obj = Command::Callees;
 | 
					  PARSE_AS(Command::Callers, "callers");
 | 
				
			||||||
  else if (content == "callers")
 | 
					  PARSE_AS(Command::FindAllUsages, "find-all-usages");
 | 
				
			||||||
    obj = Command::Callers;
 | 
					  PARSE_AS(Command::FindInterestingUsages, "find-interesting-usages");
 | 
				
			||||||
  else if (content == "find-all-usages")
 | 
					  PARSE_AS(Command::GotoReferenced, "goto-referenced");
 | 
				
			||||||
    obj = Command::FindAllUsages;
 | 
					  PARSE_AS(Command::Hierarchy, "hierarchy");
 | 
				
			||||||
  else if (content == "find-interesting-usages")
 | 
					  PARSE_AS(Command::Outline, "outline");
 | 
				
			||||||
    obj = Command::FindInterestingUsages;
 | 
					  PARSE_AS(Command::Search, "search");
 | 
				
			||||||
  else if (content == "goto-referenced")
 | 
					 | 
				
			||||||
    obj = Command::GotoReferenced;
 | 
					 | 
				
			||||||
  else if (content == "hierarchy")
 | 
					 | 
				
			||||||
    obj = Command::Hierarchy;
 | 
					 | 
				
			||||||
  else if (content == "outline")
 | 
					 | 
				
			||||||
    obj = Command::Outline;
 | 
					 | 
				
			||||||
  else if (content == "search")
 | 
					 | 
				
			||||||
    obj = Command::Search;
 | 
					 | 
				
			||||||
  else
 | 
					 | 
				
			||||||
    is.setstate(std::ios::failbit);
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return is;
 | 
					  return false;
 | 
				
			||||||
 | 
					#undef PARSE_AS
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// TODO: I think we can run libclang multiple times in one process. So we might
 | 
					// TODO: I think we can run libclang multiple times in one process. So we might
 | 
				
			||||||
@ -196,7 +204,7 @@ bool HasOption(const std::unordered_map<std::string, std::string>& options, cons
 | 
				
			|||||||
  return options.find(option) != options.end();
 | 
					  return options.find(option) != options.end();
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
int main(int argc, char** argv) {
 | 
					int main2(int argc, char** argv) {
 | 
				
			||||||
  std::unordered_map<std::string, std::string> options = ParseOptions(argc, argv);
 | 
					  std::unordered_map<std::string, std::string> options = ParseOptions(argc, argv);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if (argc == 1 || options.find("--help") != options.end()) {
 | 
					  if (argc == 1 || options.find("--help") != options.end()) {
 | 
				
			||||||
@ -283,10 +291,10 @@ int main(int argc, char** argv) {
 | 
				
			|||||||
    std::vector<CompilationEntry> entries = LoadCompilationEntriesFromDirectory(options["--project"]);
 | 
					    std::vector<CompilationEntry> entries = LoadCompilationEntriesFromDirectory(options["--project"]);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    std::vector<ParsingDatabase> dbs;
 | 
					    std::vector<IndexedFile> dbs;
 | 
				
			||||||
    for (const CompilationEntry& entry : entries) {
 | 
					    for (const CompilationEntry& entry : entries) {
 | 
				
			||||||
      std::cout << "Parsing " << entry.filename << std::endl;
 | 
					      std::cout << "Parsing " << entry.filename << std::endl;
 | 
				
			||||||
      ParsingDatabase db = Parse(entry.filename, entry.args);
 | 
					      IndexedFile db = Parse(entry.filename, entry.args);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
      dbs.emplace_back(db);
 | 
					      dbs.emplace_back(db);
 | 
				
			||||||
      std::cout << db.ToString() << std::endl << std::endl;
 | 
					      std::cout << db.ToString() << std::endl << std::endl;
 | 
				
			||||||
@ -296,6 +304,13 @@ int main(int argc, char** argv) {
 | 
				
			|||||||
    exit(0);
 | 
					    exit(0);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  if (HasOption(options, "--command")) {
 | 
				
			||||||
 | 
					    Command command;
 | 
				
			||||||
 | 
					    if (!ParseCommand(options["--command"], &command))
 | 
				
			||||||
 | 
					      Fail("Unknown command \"" + options["--command"] + "\"; see --help-commands");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  std::cout << "Invalid arguments. Try --help.";
 | 
					  std::cout << "Invalid arguments. Try --help.";
 | 
				
			||||||
  exit(1);
 | 
					  exit(1);
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										7
									
								
								utils.cc
									
									
									
									
									
								
							
							
						
						
									
										7
									
								
								utils.cc
									
									
									
									
									
								
							@ -1,5 +1,6 @@
 | 
				
			|||||||
#include "utils.h"
 | 
					#include "utils.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <iostream>
 | 
				
			||||||
#include <fstream>
 | 
					#include <fstream>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#include "tinydir.h"
 | 
					#include "tinydir.h"
 | 
				
			||||||
@ -66,3 +67,9 @@ void ParseTestExpectation(std::string filename, std::string* expected_output) {
 | 
				
			|||||||
      in_output = true;
 | 
					      in_output = true;
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void Fail(const std::string& message) {
 | 
				
			||||||
 | 
					  std::cerr << "Fatal error: " << message << std::endl;
 | 
				
			||||||
 | 
					  std::exit(1);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
							
								
								
									
										2
									
								
								utils.h
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								utils.h
									
									
									
									
									
								
							@ -6,3 +6,5 @@
 | 
				
			|||||||
std::vector<std::string> GetFilesInFolder(std::string folder);
 | 
					std::vector<std::string> GetFilesInFolder(std::string folder);
 | 
				
			||||||
std::vector<std::string> ReadLines(std::string filename);
 | 
					std::vector<std::string> ReadLines(std::string filename);
 | 
				
			||||||
void ParseTestExpectation(std::string filename, std::string* expected_output);
 | 
					void ParseTestExpectation(std::string filename, std::string* expected_output);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void Fail(const std::string& message);
 | 
				
			||||||
		Loading…
	
		Reference in New Issue
	
	Block a user