1 //===-- SymbolFileDWARFDwo.cpp --------------------------------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #include "SymbolFileDWARFDwo.h" 10 11 #include "lldb/Core/Section.h" 12 #include "lldb/Expression/DWARFExpression.h" 13 #include "lldb/Symbol/ObjectFile.h" 14 #include "lldb/Utility/LLDBAssert.h" 15 #include "llvm/Support/Casting.h" 16 17 #include "DWARFCompileUnit.h" 18 #include "DWARFDebugInfo.h" 19 #include "DWARFUnit.h" 20 21 using namespace lldb; 22 using namespace lldb_private; 23 24 char SymbolFileDWARFDwo::ID; 25 26 SymbolFileDWARFDwo::SymbolFileDWARFDwo(SymbolFileDWARF &base_symbol_file, 27 ObjectFileSP objfile, uint32_t id) 28 : SymbolFileDWARF(objfile, objfile->GetSectionList( 29 /*update_module_section_list*/ false)), 30 m_base_symbol_file(base_symbol_file) { 31 SetID(user_id_t(id) << 32); 32 } 33 34 void SymbolFileDWARFDwo::LoadSectionData(lldb::SectionType sect_type, 35 DWARFDataExtractor &data) { 36 const SectionList *section_list = 37 m_objfile_sp->GetSectionList(false /* update_module_section_list */); 38 if (section_list) { 39 SectionSP section_sp(section_list->FindSectionByType(sect_type, true)); 40 if (section_sp) { 41 42 if (m_objfile_sp->ReadSectionData(section_sp.get(), data) != 0) 43 return; 44 45 data.Clear(); 46 } 47 } 48 49 SymbolFileDWARF::LoadSectionData(sect_type, data); 50 } 51 52 DWARFCompileUnit *SymbolFileDWARFDwo::GetDWOCompileUnitForHash(uint64_t hash) { 53 DWARFCompileUnit *cu = FindSingleCompileUnit(); 54 if (!cu) 55 return nullptr; 56 if (hash != 57 cu->GetUnitDIEOnly().GetAttributeValueAsUnsigned(DW_AT_GNU_dwo_id, 0)) 58 return nullptr; 59 return cu; 60 } 61 62 DWARFCompileUnit *SymbolFileDWARFDwo::FindSingleCompileUnit() { 63 DWARFDebugInfo *debug_info = DebugInfo(); 64 if (!debug_info) 65 return nullptr; 66 67 // Right now we only support dwo files with one compile unit. If we don't have 68 // type units, we can just check for the unit count. 69 if (!debug_info->ContainsTypeUnits() && debug_info->GetNumUnits() == 1) 70 return llvm::cast<DWARFCompileUnit>(debug_info->GetUnitAtIndex(0)); 71 72 // Otherwise, we have to run through all units, and find the compile unit that 73 // way. 74 DWARFCompileUnit *cu = nullptr; 75 for (size_t i = 0; i < debug_info->GetNumUnits(); ++i) { 76 if (auto *candidate = 77 llvm::dyn_cast<DWARFCompileUnit>(debug_info->GetUnitAtIndex(i))) { 78 if (cu) 79 return nullptr; // More that one CU found. 80 cu = candidate; 81 } 82 } 83 return cu; 84 } 85 86 SymbolFileDWARF::DIEToTypePtr &SymbolFileDWARFDwo::GetDIEToType() { 87 return GetBaseSymbolFile().GetDIEToType(); 88 } 89 90 SymbolFileDWARF::DIEToVariableSP &SymbolFileDWARFDwo::GetDIEToVariable() { 91 return GetBaseSymbolFile().GetDIEToVariable(); 92 } 93 94 SymbolFileDWARF::DIEToClangType & 95 SymbolFileDWARFDwo::GetForwardDeclDieToClangType() { 96 return GetBaseSymbolFile().GetForwardDeclDieToClangType(); 97 } 98 99 SymbolFileDWARF::ClangTypeToDIE & 100 SymbolFileDWARFDwo::GetForwardDeclClangTypeToDie() { 101 return GetBaseSymbolFile().GetForwardDeclClangTypeToDie(); 102 } 103 104 size_t SymbolFileDWARFDwo::GetObjCMethodDIEOffsets( 105 lldb_private::ConstString class_name, DIEArray &method_die_offsets) { 106 return GetBaseSymbolFile().GetObjCMethodDIEOffsets(class_name, 107 method_die_offsets); 108 } 109 110 UniqueDWARFASTTypeMap &SymbolFileDWARFDwo::GetUniqueDWARFASTTypeMap() { 111 return GetBaseSymbolFile().GetUniqueDWARFASTTypeMap(); 112 } 113 114 lldb::TypeSP SymbolFileDWARFDwo::FindDefinitionTypeForDWARFDeclContext( 115 const DWARFDeclContext &die_decl_ctx) { 116 return GetBaseSymbolFile().FindDefinitionTypeForDWARFDeclContext( 117 die_decl_ctx); 118 } 119 120 lldb::TypeSP SymbolFileDWARFDwo::FindCompleteObjCDefinitionTypeForDIE( 121 const DWARFDIE &die, lldb_private::ConstString type_name, 122 bool must_be_implementation) { 123 return GetBaseSymbolFile().FindCompleteObjCDefinitionTypeForDIE( 124 die, type_name, must_be_implementation); 125 } 126 127 llvm::Expected<TypeSystem &> 128 SymbolFileDWARFDwo::GetTypeSystemForLanguage(LanguageType language) { 129 return GetBaseSymbolFile().GetTypeSystemForLanguage(language); 130 } 131 132 DWARFDIE 133 SymbolFileDWARFDwo::GetDIE(const DIERef &die_ref) { 134 if (*die_ref.dwo_num() == GetDwoNum()) 135 return DebugInfo()->GetDIE(die_ref); 136 return GetBaseSymbolFile().GetDIE(die_ref); 137 } 138