diff options
Diffstat (limited to 'lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.cpp')
-rw-r--r-- | lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.cpp | 142 |
1 files changed, 120 insertions, 22 deletions
diff --git a/lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.cpp b/lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.cpp index f52aa982308..228de6f118c 100644 --- a/lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.cpp +++ b/lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.cpp @@ -551,8 +551,7 @@ lldb_private::Type *SymbolFilePDB::ResolveTypeUID(lldb::user_id_t type_uid) { llvm::dyn_cast_or_null<ClangASTContext>(type_system); if (!clang_type_system) return nullptr; - PDBASTParser *pdb = - llvm::dyn_cast<PDBASTParser>(clang_type_system->GetPDBParser()); + PDBASTParser *pdb = clang_type_system->GetPDBParser(); if (!pdb) return nullptr; @@ -579,8 +578,7 @@ bool SymbolFilePDB::CompleteType(lldb_private::CompilerType &compiler_type) { if (!clang_ast_ctx) return false; - PDBASTParser *pdb = - llvm::dyn_cast<PDBASTParser>(clang_ast_ctx->GetPDBParser()); + PDBASTParser *pdb = clang_ast_ctx->GetPDBParser(); if (!pdb) return false; @@ -588,24 +586,83 @@ bool SymbolFilePDB::CompleteType(lldb_private::CompilerType &compiler_type) { } lldb_private::CompilerDecl SymbolFilePDB::GetDeclForUID(lldb::user_id_t uid) { - return lldb_private::CompilerDecl(); + ClangASTContext *clang_ast_ctx = llvm::dyn_cast_or_null<ClangASTContext>( + GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus)); + if (!clang_ast_ctx) + return CompilerDecl(); + + PDBASTParser *pdb = clang_ast_ctx->GetPDBParser(); + if (!pdb) + return CompilerDecl(); + + auto symbol = m_session_up->getSymbolById(uid); + if (!symbol) + return CompilerDecl(); + + auto decl = pdb->GetDeclForSymbol(*symbol); + if (!decl) + return CompilerDecl(); + + return CompilerDecl(clang_ast_ctx, decl); } lldb_private::CompilerDeclContext SymbolFilePDB::GetDeclContextForUID(lldb::user_id_t uid) { - // PDB always uses the translation unit decl context for everything. We can - // improve this later but it's not easy because PDB doesn't provide a high - // enough level of type fidelity in this area. - return *m_tu_decl_ctx_up; + ClangASTContext *clang_ast_ctx = llvm::dyn_cast_or_null<ClangASTContext>( + GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus)); + if (!clang_ast_ctx) + return CompilerDeclContext(); + + PDBASTParser *pdb = clang_ast_ctx->GetPDBParser(); + if (!pdb) + return CompilerDeclContext(); + + auto symbol = m_session_up->getSymbolById(uid); + if (!symbol) + return CompilerDeclContext(); + + auto decl_context = pdb->GetDeclContextForSymbol(*symbol); + if (!decl_context) + return GetDeclContextContainingUID(uid); + + return CompilerDeclContext(clang_ast_ctx, decl_context); } lldb_private::CompilerDeclContext SymbolFilePDB::GetDeclContextContainingUID(lldb::user_id_t uid) { - return *m_tu_decl_ctx_up; + ClangASTContext *clang_ast_ctx = llvm::dyn_cast_or_null<ClangASTContext>( + GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus)); + if (!clang_ast_ctx) + return CompilerDeclContext(); + + PDBASTParser *pdb = clang_ast_ctx->GetPDBParser(); + if (!pdb) + return CompilerDeclContext(); + + auto symbol = m_session_up->getSymbolById(uid); + if (!symbol) + return CompilerDeclContext(); + + auto decl_context = pdb->GetDeclContextContainingSymbol(*symbol); + assert(decl_context); + + return CompilerDeclContext(clang_ast_ctx, decl_context); } void SymbolFilePDB::ParseDeclsForContext( - lldb_private::CompilerDeclContext decl_ctx) {} + lldb_private::CompilerDeclContext decl_ctx) { + ClangASTContext *clang_ast_ctx = llvm::dyn_cast_or_null<ClangASTContext>( + GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus)); + if (!clang_ast_ctx) + return; + + PDBASTParser *pdb = clang_ast_ctx->GetPDBParser(); + if (!pdb) + return; + + pdb->ParseDeclsForDeclContext( + static_cast<clang::DeclContext *>(decl_ctx.GetOpaqueDeclContext())); +} uint32_t SymbolFilePDB::ResolveSymbolContext(const lldb_private::Address &so_addr, @@ -876,7 +933,7 @@ VariableSP SymbolFilePDB::ParseVariableForPDBData( if (scope == eValueTypeVariableLocal) { if (sc.function) { context_scope = sc.function->GetBlock(true).FindBlockByID( - pdb_data.getClassParentId()); + pdb_data.getLexicalParentId()); if (context_scope == nullptr) context_scope = sc.function; } @@ -973,14 +1030,14 @@ uint32_t SymbolFilePDB::FindGlobalVariables( const lldb_private::ConstString &name, const lldb_private::CompilerDeclContext *parent_decl_ctx, uint32_t max_matches, lldb_private::VariableList &variables) { + if (!parent_decl_ctx) + parent_decl_ctx = m_tu_decl_ctx_up.get(); if (!DeclContextMatchesThisSymbolFile(parent_decl_ctx)) return 0; if (name.IsEmpty()) return 0; - auto results = - m_global_scope_up->findChildren(PDB_SymType::Data, name.GetStringRef(), - PDB_NameSearchFlags::NS_CaseSensitive); + auto results = m_global_scope_up->findAllChildren<PDBSymbolData>(); if (!results) return 0; @@ -1000,6 +1057,15 @@ uint32_t SymbolFilePDB::FindGlobalVariables( if (sc.comp_unit == nullptr) continue; + if (!name.GetStringRef().equals( + PDBASTParser::PDBNameDropScope(pdb_data->getName()))) + continue; + + auto actual_parent_decl_ctx = + GetDeclContextContainingUID(result->getSymIndexId()); + if (actual_parent_decl_ctx != *parent_decl_ctx) + continue; + ParseVariables(sc, *pdb_data, &variables); matches = variables.GetSize() - old_size; } @@ -1275,7 +1341,7 @@ uint32_t SymbolFilePDB::FindTypes( std::string name_str = name.AsCString(); // There is an assumption 'name' is not a regex - FindTypesByName(name_str, max_matches, types); + FindTypesByName(name_str, parent_decl_ctx, max_matches, types); return types.GetSize(); } @@ -1335,14 +1401,16 @@ void SymbolFilePDB::FindTypesByRegex( } } -void SymbolFilePDB::FindTypesByName(const std::string &name, - uint32_t max_matches, - lldb_private::TypeMap &types) { +void SymbolFilePDB::FindTypesByName( + const std::string &name, + const lldb_private::CompilerDeclContext *parent_decl_ctx, + uint32_t max_matches, lldb_private::TypeMap &types) { + if (!parent_decl_ctx) + parent_decl_ctx = m_tu_decl_ctx_up.get(); std::unique_ptr<IPDBEnumSymbols> results; if (name.empty()) return; - results = m_global_scope_up->findChildren(PDB_SymType::None, name, - PDB_NameSearchFlags::NS_Default); + results = m_global_scope_up->findAllChildren(PDB_SymType::None); if (!results) return; @@ -1351,6 +1419,11 @@ void SymbolFilePDB::FindTypesByName(const std::string &name, while (auto result = results->getNext()) { if (max_matches > 0 && matches >= max_matches) break; + + if (PDBASTParser::PDBNameDropScope(result->getRawSymbol().getName()) != + name) + continue; + switch (result->getSymTag()) { case PDB_SymType::Enum: case PDB_SymType::UDT: @@ -1367,6 +1440,11 @@ void SymbolFilePDB::FindTypesByName(const std::string &name, if (!ResolveTypeUID(result->getSymIndexId())) continue; + auto actual_parent_decl_ctx = + GetDeclContextContainingUID(result->getSymIndexId()); + if (actual_parent_decl_ctx != *parent_decl_ctx) + continue; + auto iter = m_types.find(result->getSymIndexId()); if (iter == m_types.end()) continue; @@ -1477,7 +1555,27 @@ lldb_private::CompilerDeclContext SymbolFilePDB::FindNamespace( const lldb_private::SymbolContext &sc, const lldb_private::ConstString &name, const lldb_private::CompilerDeclContext *parent_decl_ctx) { - return lldb_private::CompilerDeclContext(); + auto type_system = GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus); + auto clang_type_system = llvm::dyn_cast_or_null<ClangASTContext>(type_system); + if (!clang_type_system) + return CompilerDeclContext(); + + PDBASTParser *pdb = clang_type_system->GetPDBParser(); + if (!pdb) + return CompilerDeclContext(); + + clang::DeclContext *decl_context = nullptr; + if (parent_decl_ctx) + decl_context = static_cast<clang::DeclContext *>( + parent_decl_ctx->GetOpaqueDeclContext()); + + auto namespace_decl = + pdb->FindNamespaceDecl(decl_context, name.GetStringRef()); + if (!namespace_decl) + return CompilerDeclContext(); + + return CompilerDeclContext(type_system, + static_cast<clang::DeclContext *>(namespace_decl)); } lldb_private::ConstString SymbolFilePDB::GetPluginName() { |