1 //===-- SymbolFileDWARF.cpp ------------------------------------*- C++ -*-===// 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 #include "SymbolFileDWARF.h" 11 12 // Other libraries and framework includes 13 #include "clang/AST/ASTConsumer.h" 14 #include "clang/AST/ASTContext.h" 15 #include "clang/AST/Decl.h" 16 #include "clang/AST/DeclGroup.h" 17 #include "clang/AST/DeclObjC.h" 18 #include "clang/AST/DeclTemplate.h" 19 #include "clang/Basic/Builtins.h" 20 #include "clang/Basic/IdentifierTable.h" 21 #include "clang/Basic/LangOptions.h" 22 #include "clang/Basic/SourceManager.h" 23 #include "clang/Basic/TargetInfo.h" 24 #include "clang/Basic/Specifiers.h" 25 #include "clang/Sema/DeclSpec.h" 26 27 #include "llvm/Support/Casting.h" 28 29 #include "lldb/Core/ArchSpec.h" 30 #include "lldb/Core/Module.h" 31 #include "lldb/Core/ModuleList.h" 32 #include "lldb/Core/ModuleSpec.h" 33 #include "lldb/Core/PluginManager.h" 34 #include "lldb/Core/RegularExpression.h" 35 #include "lldb/Core/Scalar.h" 36 #include "lldb/Core/Section.h" 37 #include "lldb/Core/StreamFile.h" 38 #include "lldb/Core/StreamString.h" 39 #include "lldb/Core/Timer.h" 40 #include "lldb/Core/Value.h" 41 42 #include "lldb/Expression/ClangModulesDeclVendor.h" 43 44 #include "lldb/Host/FileSystem.h" 45 #include "lldb/Host/Host.h" 46 47 #include "lldb/Interpreter/OptionValueFileSpecList.h" 48 #include "lldb/Interpreter/OptionValueProperties.h" 49 50 #include "lldb/Symbol/Block.h" 51 #include "lldb/Symbol/CompileUnit.h" 52 #include "lldb/Symbol/LineTable.h" 53 #include "lldb/Symbol/ObjectFile.h" 54 #include "lldb/Symbol/SymbolVendor.h" 55 #include "lldb/Symbol/VariableList.h" 56 57 #include "lldb/Target/ObjCLanguageRuntime.h" 58 #include "lldb/Target/CPPLanguageRuntime.h" 59 60 #include "DWARFCompileUnit.h" 61 #include "DWARFDebugAbbrev.h" 62 #include "DWARFDebugAranges.h" 63 #include "DWARFDebugInfo.h" 64 #include "DWARFDebugInfoEntry.h" 65 #include "DWARFDebugLine.h" 66 #include "DWARFDebugPubnames.h" 67 #include "DWARFDebugRanges.h" 68 #include "DWARFDeclContext.h" 69 #include "DWARFDIECollection.h" 70 #include "DWARFFormValue.h" 71 #include "DWARFLocationList.h" 72 #include "LogChannelDWARF.h" 73 #include "SymbolFileDWARFDebugMap.h" 74 75 #include <map> 76 77 #include <ctype.h> 78 #include <string.h> 79 80 //#define ENABLE_DEBUG_PRINTF // COMMENT OUT THIS LINE PRIOR TO CHECKIN 81 82 #ifdef ENABLE_DEBUG_PRINTF 83 #include <stdio.h> 84 #define DEBUG_PRINTF(fmt, ...) printf(fmt, __VA_ARGS__) 85 #else 86 #define DEBUG_PRINTF(fmt, ...) 87 #endif 88 89 using namespace lldb; 90 using namespace lldb_private; 91 92 //static inline bool 93 //child_requires_parent_class_union_or_struct_to_be_completed (dw_tag_t tag) 94 //{ 95 // switch (tag) 96 // { 97 // default: 98 // break; 99 // case DW_TAG_subprogram: 100 // case DW_TAG_inlined_subroutine: 101 // case DW_TAG_class_type: 102 // case DW_TAG_structure_type: 103 // case DW_TAG_union_type: 104 // return true; 105 // } 106 // return false; 107 //} 108 // 109 110 namespace { 111 112 PropertyDefinition 113 g_properties[] = 114 { 115 { "comp-dir-symlink-paths" , OptionValue::eTypeFileSpecList, true, 0 , nullptr, nullptr, "If the DW_AT_comp_dir matches any of these paths the symbolic links will be resolved at DWARF parse time." }, 116 { nullptr , OptionValue::eTypeInvalid , false, 0, nullptr, nullptr, nullptr } 117 }; 118 119 enum 120 { 121 ePropertySymLinkPaths 122 }; 123 124 125 class PluginProperties : public Properties 126 { 127 public: 128 static ConstString 129 GetSettingName() 130 { 131 return SymbolFileDWARF::GetPluginNameStatic(); 132 } 133 134 PluginProperties() 135 { 136 m_collection_sp.reset (new OptionValueProperties(GetSettingName())); 137 m_collection_sp->Initialize(g_properties); 138 } 139 140 FileSpecList& 141 GetSymLinkPaths() 142 { 143 OptionValueFileSpecList *option_value = m_collection_sp->GetPropertyAtIndexAsOptionValueFileSpecList(nullptr, true, ePropertySymLinkPaths); 144 assert(option_value); 145 return option_value->GetCurrentValue(); 146 } 147 148 }; 149 150 typedef std::shared_ptr<PluginProperties> SymbolFileDWARFPropertiesSP; 151 152 static const SymbolFileDWARFPropertiesSP& 153 GetGlobalPluginProperties() 154 { 155 static const auto g_settings_sp(std::make_shared<PluginProperties>()); 156 return g_settings_sp; 157 } 158 159 } // anonymous namespace end 160 161 162 static const char* 163 removeHostnameFromPathname(const char* path_from_dwarf) 164 { 165 if (!path_from_dwarf || !path_from_dwarf[0]) 166 { 167 return path_from_dwarf; 168 } 169 170 const char *colon_pos = strchr(path_from_dwarf, ':'); 171 if (nullptr == colon_pos) 172 { 173 return path_from_dwarf; 174 } 175 176 const char *slash_pos = strchr(path_from_dwarf, '/'); 177 if (slash_pos && (slash_pos < colon_pos)) 178 { 179 return path_from_dwarf; 180 } 181 182 // check whether we have a windows path, and so the first character 183 // is a drive-letter not a hostname. 184 if ( 185 colon_pos == path_from_dwarf + 1 && 186 isalpha(*path_from_dwarf) && 187 strlen(path_from_dwarf) > 2 && 188 '\\' == path_from_dwarf[2]) 189 { 190 return path_from_dwarf; 191 } 192 193 return colon_pos + 1; 194 } 195 196 static const char* 197 resolveCompDir(const char* path_from_dwarf) 198 { 199 if (!path_from_dwarf) 200 return nullptr; 201 202 // DWARF2/3 suggests the form hostname:pathname for compilation directory. 203 // Remove the host part if present. 204 const char* local_path = removeHostnameFromPathname(path_from_dwarf); 205 if (!local_path) 206 return nullptr; 207 208 bool is_symlink = false; 209 FileSpec local_path_spec(local_path, false); 210 const auto& file_specs = GetGlobalPluginProperties()->GetSymLinkPaths(); 211 for (size_t i = 0; i < file_specs.GetSize() && !is_symlink; ++i) 212 is_symlink = FileSpec::Equal(file_specs.GetFileSpecAtIndex(i), local_path_spec, true); 213 214 if (!is_symlink) 215 return local_path; 216 217 if (!local_path_spec.IsSymbolicLink()) 218 return local_path; 219 220 FileSpec resolved_local_path_spec; 221 const auto error = FileSystem::Readlink(local_path_spec, resolved_local_path_spec); 222 if (error.Success()) 223 return resolved_local_path_spec.GetCString(); 224 225 return nullptr; 226 } 227 228 229 void 230 SymbolFileDWARF::Initialize() 231 { 232 LogChannelDWARF::Initialize(); 233 PluginManager::RegisterPlugin (GetPluginNameStatic(), 234 GetPluginDescriptionStatic(), 235 CreateInstance, 236 DebuggerInitialize); 237 } 238 239 void 240 SymbolFileDWARF::DebuggerInitialize(Debugger &debugger) 241 { 242 if (!PluginManager::GetSettingForSymbolFilePlugin(debugger, PluginProperties::GetSettingName())) 243 { 244 const bool is_global_setting = true; 245 PluginManager::CreateSettingForSymbolFilePlugin(debugger, 246 GetGlobalPluginProperties()->GetValueProperties(), 247 ConstString ("Properties for the dwarf symbol-file plug-in."), 248 is_global_setting); 249 } 250 } 251 252 void 253 SymbolFileDWARF::Terminate() 254 { 255 PluginManager::UnregisterPlugin (CreateInstance); 256 LogChannelDWARF::Initialize(); 257 } 258 259 260 lldb_private::ConstString 261 SymbolFileDWARF::GetPluginNameStatic() 262 { 263 static ConstString g_name("dwarf"); 264 return g_name; 265 } 266 267 const char * 268 SymbolFileDWARF::GetPluginDescriptionStatic() 269 { 270 return "DWARF and DWARF3 debug symbol file reader."; 271 } 272 273 274 SymbolFile* 275 SymbolFileDWARF::CreateInstance (ObjectFile* obj_file) 276 { 277 return new SymbolFileDWARF(obj_file); 278 } 279 280 TypeList * 281 SymbolFileDWARF::GetTypeList () 282 { 283 if (GetDebugMapSymfile ()) 284 return m_debug_map_symfile->GetTypeList(); 285 return m_obj_file->GetModule()->GetTypeList(); 286 287 } 288 void 289 SymbolFileDWARF::GetTypes (DWARFCompileUnit* cu, 290 const DWARFDebugInfoEntry *die, 291 dw_offset_t min_die_offset, 292 dw_offset_t max_die_offset, 293 uint32_t type_mask, 294 TypeSet &type_set) 295 { 296 if (cu) 297 { 298 if (die) 299 { 300 const dw_offset_t die_offset = die->GetOffset(); 301 302 if (die_offset >= max_die_offset) 303 return; 304 305 if (die_offset >= min_die_offset) 306 { 307 const dw_tag_t tag = die->Tag(); 308 309 bool add_type = false; 310 311 switch (tag) 312 { 313 case DW_TAG_array_type: add_type = (type_mask & eTypeClassArray ) != 0; break; 314 case DW_TAG_unspecified_type: 315 case DW_TAG_base_type: add_type = (type_mask & eTypeClassBuiltin ) != 0; break; 316 case DW_TAG_class_type: add_type = (type_mask & eTypeClassClass ) != 0; break; 317 case DW_TAG_structure_type: add_type = (type_mask & eTypeClassStruct ) != 0; break; 318 case DW_TAG_union_type: add_type = (type_mask & eTypeClassUnion ) != 0; break; 319 case DW_TAG_enumeration_type: add_type = (type_mask & eTypeClassEnumeration ) != 0; break; 320 case DW_TAG_subroutine_type: 321 case DW_TAG_subprogram: 322 case DW_TAG_inlined_subroutine: add_type = (type_mask & eTypeClassFunction ) != 0; break; 323 case DW_TAG_pointer_type: add_type = (type_mask & eTypeClassPointer ) != 0; break; 324 case DW_TAG_rvalue_reference_type: 325 case DW_TAG_reference_type: add_type = (type_mask & eTypeClassReference ) != 0; break; 326 case DW_TAG_typedef: add_type = (type_mask & eTypeClassTypedef ) != 0; break; 327 case DW_TAG_ptr_to_member_type: add_type = (type_mask & eTypeClassMemberPointer ) != 0; break; 328 } 329 330 if (add_type) 331 { 332 const bool assert_not_being_parsed = true; 333 Type *type = ResolveTypeUID (cu, die, assert_not_being_parsed); 334 if (type) 335 { 336 if (type_set.find(type) == type_set.end()) 337 type_set.insert(type); 338 } 339 } 340 } 341 342 for (const DWARFDebugInfoEntry *child_die = die->GetFirstChild(); 343 child_die != NULL; 344 child_die = child_die->GetSibling()) 345 { 346 GetTypes (cu, child_die, min_die_offset, max_die_offset, type_mask, type_set); 347 } 348 } 349 } 350 } 351 352 size_t 353 SymbolFileDWARF::GetTypes (SymbolContextScope *sc_scope, 354 uint32_t type_mask, 355 TypeList &type_list) 356 357 { 358 TypeSet type_set; 359 360 CompileUnit *comp_unit = NULL; 361 DWARFCompileUnit* dwarf_cu = NULL; 362 if (sc_scope) 363 comp_unit = sc_scope->CalculateSymbolContextCompileUnit(); 364 365 if (comp_unit) 366 { 367 dwarf_cu = GetDWARFCompileUnit(comp_unit); 368 if (dwarf_cu == 0) 369 return 0; 370 GetTypes (dwarf_cu, 371 dwarf_cu->DIE(), 372 dwarf_cu->GetOffset(), 373 dwarf_cu->GetNextCompileUnitOffset(), 374 type_mask, 375 type_set); 376 } 377 else 378 { 379 DWARFDebugInfo* info = DebugInfo(); 380 if (info) 381 { 382 const size_t num_cus = info->GetNumCompileUnits(); 383 for (size_t cu_idx=0; cu_idx<num_cus; ++cu_idx) 384 { 385 dwarf_cu = info->GetCompileUnitAtIndex(cu_idx); 386 if (dwarf_cu) 387 { 388 GetTypes (dwarf_cu, 389 dwarf_cu->DIE(), 390 0, 391 UINT32_MAX, 392 type_mask, 393 type_set); 394 } 395 } 396 } 397 } 398 // if (m_using_apple_tables) 399 // { 400 // DWARFMappedHash::MemoryTable *apple_types = m_apple_types_ap.get(); 401 // if (apple_types) 402 // { 403 // apple_types->ForEach([this, &type_set, apple_types, type_mask](const DWARFMappedHash::DIEInfoArray &die_info_array) -> bool { 404 // 405 // for (auto die_info: die_info_array) 406 // { 407 // bool add_type = TagMatchesTypeMask (type_mask, 0); 408 // if (!add_type) 409 // { 410 // dw_tag_t tag = die_info.tag; 411 // if (tag == 0) 412 // { 413 // const DWARFDebugInfoEntry *die = DebugInfo()->GetDIEPtr(die_info.offset, NULL); 414 // tag = die->Tag(); 415 // } 416 // add_type = TagMatchesTypeMask (type_mask, tag); 417 // } 418 // if (add_type) 419 // { 420 // Type *type = ResolveTypeUID(die_info.offset); 421 // 422 // if (type_set.find(type) == type_set.end()) 423 // type_set.insert(type); 424 // } 425 // } 426 // return true; // Keep iterating 427 // }); 428 // } 429 // } 430 // else 431 // { 432 // if (!m_indexed) 433 // Index (); 434 // 435 // m_type_index.ForEach([this, &type_set, type_mask](const char *name, uint32_t die_offset) -> bool { 436 // 437 // bool add_type = TagMatchesTypeMask (type_mask, 0); 438 // 439 // if (!add_type) 440 // { 441 // const DWARFDebugInfoEntry *die = DebugInfo()->GetDIEPtr(die_offset, NULL); 442 // if (die) 443 // { 444 // const dw_tag_t tag = die->Tag(); 445 // add_type = TagMatchesTypeMask (type_mask, tag); 446 // } 447 // } 448 // 449 // if (add_type) 450 // { 451 // Type *type = ResolveTypeUID(die_offset); 452 // 453 // if (type_set.find(type) == type_set.end()) 454 // type_set.insert(type); 455 // } 456 // return true; // Keep iterating 457 // }); 458 // } 459 460 std::set<CompilerType> clang_type_set; 461 size_t num_types_added = 0; 462 for (Type *type : type_set) 463 { 464 CompilerType clang_type = type->GetForwardCompilerType (); 465 if (clang_type_set.find(clang_type) == clang_type_set.end()) 466 { 467 clang_type_set.insert(clang_type); 468 type_list.Insert (type->shared_from_this()); 469 ++num_types_added; 470 } 471 } 472 return num_types_added; 473 } 474 475 476 //---------------------------------------------------------------------- 477 // Gets the first parent that is a lexical block, function or inlined 478 // subroutine, or compile unit. 479 //---------------------------------------------------------------------- 480 const DWARFDebugInfoEntry * 481 SymbolFileDWARF::GetParentSymbolContextDIE(const DWARFDebugInfoEntry *child_die) 482 { 483 const DWARFDebugInfoEntry *die; 484 for (die = child_die->GetParent(); die != NULL; die = die->GetParent()) 485 { 486 dw_tag_t tag = die->Tag(); 487 488 switch (tag) 489 { 490 case DW_TAG_compile_unit: 491 case DW_TAG_subprogram: 492 case DW_TAG_inlined_subroutine: 493 case DW_TAG_lexical_block: 494 return die; 495 } 496 } 497 return NULL; 498 } 499 500 501 SymbolFileDWARF::SymbolFileDWARF(ObjectFile* objfile) : 502 SymbolFile (objfile), 503 UserID (0), // Used by SymbolFileDWARFDebugMap to when this class parses .o files to contain the .o file index/ID 504 m_debug_map_module_wp (), 505 m_debug_map_symfile (NULL), 506 m_flags(), 507 m_data_debug_abbrev (), 508 m_data_debug_aranges (), 509 m_data_debug_frame (), 510 m_data_debug_info (), 511 m_data_debug_line (), 512 m_data_debug_loc (), 513 m_data_debug_ranges (), 514 m_data_debug_str (), 515 m_data_apple_names (), 516 m_data_apple_types (), 517 m_data_apple_namespaces (), 518 m_abbr(), 519 m_info(), 520 m_line(), 521 m_apple_names_ap (), 522 m_apple_types_ap (), 523 m_apple_namespaces_ap (), 524 m_apple_objc_ap (), 525 m_function_basename_index(), 526 m_function_fullname_index(), 527 m_function_method_index(), 528 m_function_selector_index(), 529 m_objc_class_selectors_index(), 530 m_global_index(), 531 m_type_index(), 532 m_namespace_index(), 533 m_indexed (false), 534 m_using_apple_tables (false), 535 m_fetched_external_modules (false), 536 m_supports_DW_AT_APPLE_objc_complete_type (eLazyBoolCalculate), 537 m_ranges(), 538 m_unique_ast_type_map () 539 { 540 } 541 542 SymbolFileDWARF::~SymbolFileDWARF() 543 { 544 } 545 546 static const ConstString & 547 GetDWARFMachOSegmentName () 548 { 549 static ConstString g_dwarf_section_name ("__DWARF"); 550 return g_dwarf_section_name; 551 } 552 553 UniqueDWARFASTTypeMap & 554 SymbolFileDWARF::GetUniqueDWARFASTTypeMap () 555 { 556 if (GetDebugMapSymfile ()) 557 return m_debug_map_symfile->GetUniqueDWARFASTTypeMap (); 558 return m_unique_ast_type_map; 559 } 560 561 ClangASTContext & 562 SymbolFileDWARF::GetClangASTContext () 563 { 564 if (GetDebugMapSymfile ()) 565 return m_debug_map_symfile->GetClangASTContext (); 566 else 567 return m_obj_file->GetModule()->GetClangASTContext(); 568 } 569 570 TypeSystem * 571 SymbolFileDWARF::GetTypeSystemForLanguage (LanguageType language) 572 { 573 SymbolFileDWARFDebugMap * debug_map_symfile = GetDebugMapSymfile (); 574 if (debug_map_symfile) 575 return debug_map_symfile->GetTypeSystemForLanguage (language); 576 else 577 return m_obj_file->GetModule()->GetTypeSystemForLanguage (language); 578 } 579 580 void 581 SymbolFileDWARF::InitializeObject() 582 { 583 ModuleSP module_sp (m_obj_file->GetModule()); 584 if (module_sp) 585 { 586 const SectionList *section_list = module_sp->GetSectionList(); 587 588 const Section* section = section_list->FindSectionByName(GetDWARFMachOSegmentName ()).get(); 589 590 // Memory map the DWARF mach-o segment so we have everything mmap'ed 591 // to keep our heap memory usage down. 592 if (section) 593 m_obj_file->MemoryMapSectionData(section, m_dwarf_data); 594 } 595 get_apple_names_data(); 596 if (m_data_apple_names.GetByteSize() > 0) 597 { 598 m_apple_names_ap.reset (new DWARFMappedHash::MemoryTable (m_data_apple_names, get_debug_str_data(), ".apple_names")); 599 if (m_apple_names_ap->IsValid()) 600 m_using_apple_tables = true; 601 else 602 m_apple_names_ap.reset(); 603 } 604 get_apple_types_data(); 605 if (m_data_apple_types.GetByteSize() > 0) 606 { 607 m_apple_types_ap.reset (new DWARFMappedHash::MemoryTable (m_data_apple_types, get_debug_str_data(), ".apple_types")); 608 if (m_apple_types_ap->IsValid()) 609 m_using_apple_tables = true; 610 else 611 m_apple_types_ap.reset(); 612 } 613 614 get_apple_namespaces_data(); 615 if (m_data_apple_namespaces.GetByteSize() > 0) 616 { 617 m_apple_namespaces_ap.reset (new DWARFMappedHash::MemoryTable (m_data_apple_namespaces, get_debug_str_data(), ".apple_namespaces")); 618 if (m_apple_namespaces_ap->IsValid()) 619 m_using_apple_tables = true; 620 else 621 m_apple_namespaces_ap.reset(); 622 } 623 624 get_apple_objc_data(); 625 if (m_data_apple_objc.GetByteSize() > 0) 626 { 627 m_apple_objc_ap.reset (new DWARFMappedHash::MemoryTable (m_data_apple_objc, get_debug_str_data(), ".apple_objc")); 628 if (m_apple_objc_ap->IsValid()) 629 m_using_apple_tables = true; 630 else 631 m_apple_objc_ap.reset(); 632 } 633 634 // Set the symbol file to this file if we don't have a debug map symbol 635 // file as our main symbol file. This allows the clang ASTContext to complete 636 // types using this symbol file when it needs to complete classes and structures. 637 if (GetDebugMapSymfile () == nullptr) 638 GetClangASTContext().SetSymbolFile(this); 639 } 640 641 bool 642 SymbolFileDWARF::SupportedVersion(uint16_t version) 643 { 644 return version == 2 || version == 3 || version == 4; 645 } 646 647 uint32_t 648 SymbolFileDWARF::CalculateAbilities () 649 { 650 uint32_t abilities = 0; 651 if (m_obj_file != NULL) 652 { 653 const Section* section = NULL; 654 const SectionList *section_list = m_obj_file->GetSectionList(); 655 if (section_list == NULL) 656 return 0; 657 658 uint64_t debug_abbrev_file_size = 0; 659 uint64_t debug_info_file_size = 0; 660 uint64_t debug_line_file_size = 0; 661 662 section = section_list->FindSectionByName(GetDWARFMachOSegmentName ()).get(); 663 664 if (section) 665 section_list = §ion->GetChildren (); 666 667 section = section_list->FindSectionByType (eSectionTypeDWARFDebugInfo, true).get(); 668 if (section != NULL) 669 { 670 debug_info_file_size = section->GetFileSize(); 671 672 section = section_list->FindSectionByType (eSectionTypeDWARFDebugAbbrev, true).get(); 673 if (section) 674 debug_abbrev_file_size = section->GetFileSize(); 675 else 676 m_flags.Set (flagsGotDebugAbbrevData); 677 678 section = section_list->FindSectionByType (eSectionTypeDWARFDebugAranges, true).get(); 679 if (!section) 680 m_flags.Set (flagsGotDebugArangesData); 681 682 section = section_list->FindSectionByType (eSectionTypeDWARFDebugFrame, true).get(); 683 if (!section) 684 m_flags.Set (flagsGotDebugFrameData); 685 686 section = section_list->FindSectionByType (eSectionTypeDWARFDebugLine, true).get(); 687 if (section) 688 debug_line_file_size = section->GetFileSize(); 689 else 690 m_flags.Set (flagsGotDebugLineData); 691 692 section = section_list->FindSectionByType (eSectionTypeDWARFDebugLoc, true).get(); 693 if (!section) 694 m_flags.Set (flagsGotDebugLocData); 695 696 section = section_list->FindSectionByType (eSectionTypeDWARFDebugMacInfo, true).get(); 697 if (!section) 698 m_flags.Set (flagsGotDebugMacInfoData); 699 700 section = section_list->FindSectionByType (eSectionTypeDWARFDebugPubNames, true).get(); 701 if (!section) 702 m_flags.Set (flagsGotDebugPubNamesData); 703 704 section = section_list->FindSectionByType (eSectionTypeDWARFDebugPubTypes, true).get(); 705 if (!section) 706 m_flags.Set (flagsGotDebugPubTypesData); 707 708 section = section_list->FindSectionByType (eSectionTypeDWARFDebugRanges, true).get(); 709 if (!section) 710 m_flags.Set (flagsGotDebugRangesData); 711 712 section = section_list->FindSectionByType (eSectionTypeDWARFDebugStr, true).get(); 713 if (!section) 714 m_flags.Set (flagsGotDebugStrData); 715 } 716 else 717 { 718 const char *symfile_dir_cstr = m_obj_file->GetFileSpec().GetDirectory().GetCString(); 719 if (symfile_dir_cstr) 720 { 721 if (strcasestr(symfile_dir_cstr, ".dsym")) 722 { 723 if (m_obj_file->GetType() == ObjectFile::eTypeDebugInfo) 724 { 725 // We have a dSYM file that didn't have a any debug info. 726 // If the string table has a size of 1, then it was made from 727 // an executable with no debug info, or from an executable that 728 // was stripped. 729 section = section_list->FindSectionByType (eSectionTypeDWARFDebugStr, true).get(); 730 if (section && section->GetFileSize() == 1) 731 { 732 m_obj_file->GetModule()->ReportWarning ("empty dSYM file detected, dSYM was created with an executable with no debug info."); 733 } 734 } 735 } 736 } 737 } 738 739 if (debug_abbrev_file_size > 0 && debug_info_file_size > 0) 740 abilities |= CompileUnits | Functions | Blocks | GlobalVariables | LocalVariables | VariableTypes; 741 742 if (debug_line_file_size > 0) 743 abilities |= LineTables; 744 } 745 return abilities; 746 } 747 748 const DWARFDataExtractor& 749 SymbolFileDWARF::GetCachedSectionData (uint32_t got_flag, SectionType sect_type, DWARFDataExtractor &data) 750 { 751 if (m_flags.IsClear (got_flag)) 752 { 753 ModuleSP module_sp (m_obj_file->GetModule()); 754 m_flags.Set (got_flag); 755 const SectionList *section_list = module_sp->GetSectionList(); 756 if (section_list) 757 { 758 SectionSP section_sp (section_list->FindSectionByType(sect_type, true)); 759 if (section_sp) 760 { 761 // See if we memory mapped the DWARF segment? 762 if (m_dwarf_data.GetByteSize()) 763 { 764 data.SetData(m_dwarf_data, section_sp->GetOffset (), section_sp->GetFileSize()); 765 } 766 else 767 { 768 if (m_obj_file->ReadSectionData (section_sp.get(), data) == 0) 769 data.Clear(); 770 } 771 } 772 } 773 } 774 return data; 775 } 776 777 const DWARFDataExtractor& 778 SymbolFileDWARF::get_debug_abbrev_data() 779 { 780 return GetCachedSectionData (flagsGotDebugAbbrevData, eSectionTypeDWARFDebugAbbrev, m_data_debug_abbrev); 781 } 782 783 const DWARFDataExtractor& 784 SymbolFileDWARF::get_debug_addr_data() 785 { 786 return GetCachedSectionData (flagsGotDebugAddrData, eSectionTypeDWARFDebugAddr, m_data_debug_addr); 787 } 788 789 const DWARFDataExtractor& 790 SymbolFileDWARF::get_debug_aranges_data() 791 { 792 return GetCachedSectionData (flagsGotDebugArangesData, eSectionTypeDWARFDebugAranges, m_data_debug_aranges); 793 } 794 795 const DWARFDataExtractor& 796 SymbolFileDWARF::get_debug_frame_data() 797 { 798 return GetCachedSectionData (flagsGotDebugFrameData, eSectionTypeDWARFDebugFrame, m_data_debug_frame); 799 } 800 801 const DWARFDataExtractor& 802 SymbolFileDWARF::get_debug_info_data() 803 { 804 return GetCachedSectionData (flagsGotDebugInfoData, eSectionTypeDWARFDebugInfo, m_data_debug_info); 805 } 806 807 const DWARFDataExtractor& 808 SymbolFileDWARF::get_debug_line_data() 809 { 810 return GetCachedSectionData (flagsGotDebugLineData, eSectionTypeDWARFDebugLine, m_data_debug_line); 811 } 812 813 const DWARFDataExtractor& 814 SymbolFileDWARF::get_debug_loc_data() 815 { 816 return GetCachedSectionData (flagsGotDebugLocData, eSectionTypeDWARFDebugLoc, m_data_debug_loc); 817 } 818 819 const DWARFDataExtractor& 820 SymbolFileDWARF::get_debug_ranges_data() 821 { 822 return GetCachedSectionData (flagsGotDebugRangesData, eSectionTypeDWARFDebugRanges, m_data_debug_ranges); 823 } 824 825 const DWARFDataExtractor& 826 SymbolFileDWARF::get_debug_str_data() 827 { 828 return GetCachedSectionData (flagsGotDebugStrData, eSectionTypeDWARFDebugStr, m_data_debug_str); 829 } 830 831 const DWARFDataExtractor& 832 SymbolFileDWARF::get_debug_str_offsets_data() 833 { 834 return GetCachedSectionData (flagsGotDebugStrOffsetsData, eSectionTypeDWARFDebugStrOffsets, m_data_debug_str_offsets); 835 } 836 837 const DWARFDataExtractor& 838 SymbolFileDWARF::get_apple_names_data() 839 { 840 return GetCachedSectionData (flagsGotAppleNamesData, eSectionTypeDWARFAppleNames, m_data_apple_names); 841 } 842 843 const DWARFDataExtractor& 844 SymbolFileDWARF::get_apple_types_data() 845 { 846 return GetCachedSectionData (flagsGotAppleTypesData, eSectionTypeDWARFAppleTypes, m_data_apple_types); 847 } 848 849 const DWARFDataExtractor& 850 SymbolFileDWARF::get_apple_namespaces_data() 851 { 852 return GetCachedSectionData (flagsGotAppleNamespacesData, eSectionTypeDWARFAppleNamespaces, m_data_apple_namespaces); 853 } 854 855 const DWARFDataExtractor& 856 SymbolFileDWARF::get_apple_objc_data() 857 { 858 return GetCachedSectionData (flagsGotAppleObjCData, eSectionTypeDWARFAppleObjC, m_data_apple_objc); 859 } 860 861 862 DWARFDebugAbbrev* 863 SymbolFileDWARF::DebugAbbrev() 864 { 865 if (m_abbr.get() == NULL) 866 { 867 const DWARFDataExtractor &debug_abbrev_data = get_debug_abbrev_data(); 868 if (debug_abbrev_data.GetByteSize() > 0) 869 { 870 m_abbr.reset(new DWARFDebugAbbrev()); 871 if (m_abbr.get()) 872 m_abbr->Parse(debug_abbrev_data); 873 } 874 } 875 return m_abbr.get(); 876 } 877 878 const DWARFDebugAbbrev* 879 SymbolFileDWARF::DebugAbbrev() const 880 { 881 return m_abbr.get(); 882 } 883 884 885 DWARFDebugInfo* 886 SymbolFileDWARF::DebugInfo() 887 { 888 if (m_info.get() == NULL) 889 { 890 Timer scoped_timer(__PRETTY_FUNCTION__, "%s this = %p", 891 __PRETTY_FUNCTION__, static_cast<void*>(this)); 892 if (get_debug_info_data().GetByteSize() > 0) 893 { 894 m_info.reset(new DWARFDebugInfo()); 895 if (m_info.get()) 896 { 897 m_info->SetDwarfData(this); 898 } 899 } 900 } 901 return m_info.get(); 902 } 903 904 const DWARFDebugInfo* 905 SymbolFileDWARF::DebugInfo() const 906 { 907 return m_info.get(); 908 } 909 910 DWARFCompileUnit* 911 SymbolFileDWARF::GetDWARFCompileUnit(lldb_private::CompileUnit *comp_unit) 912 { 913 DWARFDebugInfo* info = DebugInfo(); 914 if (info) 915 { 916 if (GetDebugMapSymfile ()) 917 { 918 // The debug map symbol file made the compile units for this DWARF 919 // file which is .o file with DWARF in it, and we should have 920 // only 1 compile unit which is at offset zero in the DWARF. 921 // TODO: modify to support LTO .o files where each .o file might 922 // have multiple DW_TAG_compile_unit tags. 923 924 DWARFCompileUnit *dwarf_cu = info->GetCompileUnit(0).get(); 925 if (dwarf_cu && dwarf_cu->GetUserData() == NULL) 926 dwarf_cu->SetUserData(comp_unit); 927 return dwarf_cu; 928 } 929 else 930 { 931 // Just a normal DWARF file whose user ID for the compile unit is 932 // the DWARF offset itself 933 934 DWARFCompileUnit *dwarf_cu = info->GetCompileUnit((dw_offset_t)comp_unit->GetID()).get(); 935 if (dwarf_cu && dwarf_cu->GetUserData() == NULL) 936 dwarf_cu->SetUserData(comp_unit); 937 return dwarf_cu; 938 939 } 940 } 941 return NULL; 942 } 943 944 945 DWARFDebugRanges* 946 SymbolFileDWARF::DebugRanges() 947 { 948 if (m_ranges.get() == NULL) 949 { 950 Timer scoped_timer(__PRETTY_FUNCTION__, "%s this = %p", 951 __PRETTY_FUNCTION__, static_cast<void*>(this)); 952 if (get_debug_ranges_data().GetByteSize() > 0) 953 { 954 m_ranges.reset(new DWARFDebugRanges()); 955 if (m_ranges.get()) 956 m_ranges->Extract(this); 957 } 958 } 959 return m_ranges.get(); 960 } 961 962 const DWARFDebugRanges* 963 SymbolFileDWARF::DebugRanges() const 964 { 965 return m_ranges.get(); 966 } 967 968 lldb::CompUnitSP 969 SymbolFileDWARF::ParseCompileUnit (DWARFCompileUnit* dwarf_cu, uint32_t cu_idx) 970 { 971 CompUnitSP cu_sp; 972 if (dwarf_cu) 973 { 974 CompileUnit *comp_unit = (CompileUnit*)dwarf_cu->GetUserData(); 975 if (comp_unit) 976 { 977 // We already parsed this compile unit, had out a shared pointer to it 978 cu_sp = comp_unit->shared_from_this(); 979 } 980 else 981 { 982 if (GetDebugMapSymfile ()) 983 { 984 // Let the debug map create the compile unit 985 cu_sp = m_debug_map_symfile->GetCompileUnit(this); 986 dwarf_cu->SetUserData(cu_sp.get()); 987 } 988 else 989 { 990 ModuleSP module_sp (m_obj_file->GetModule()); 991 if (module_sp) 992 { 993 const DWARFDebugInfoEntry * cu_die = dwarf_cu->GetCompileUnitDIEOnly (); 994 if (cu_die) 995 { 996 FileSpec cu_file_spec{cu_die->GetName(this, dwarf_cu), false}; 997 if (cu_file_spec) 998 { 999 // If we have a full path to the compile unit, we don't need to resolve 1000 // the file. This can be expensive e.g. when the source files are NFS mounted. 1001 if (cu_file_spec.IsRelative()) 1002 { 1003 const char *cu_comp_dir{cu_die->GetAttributeValueAsString(this, dwarf_cu, DW_AT_comp_dir, nullptr)}; 1004 cu_file_spec.PrependPathComponent(resolveCompDir(cu_comp_dir)); 1005 } 1006 1007 std::string remapped_file; 1008 if (module_sp->RemapSourceFile(cu_file_spec.GetCString(), remapped_file)) 1009 cu_file_spec.SetFile(remapped_file, false); 1010 } 1011 1012 LanguageType cu_language = DWARFCompileUnit::LanguageTypeFromDWARF(cu_die->GetAttributeValueAsUnsigned(this, dwarf_cu, DW_AT_language, 0)); 1013 1014 bool is_optimized = dwarf_cu->GetIsOptimized (); 1015 cu_sp.reset(new CompileUnit (module_sp, 1016 dwarf_cu, 1017 cu_file_spec, 1018 MakeUserID(dwarf_cu->GetOffset()), 1019 cu_language, 1020 is_optimized)); 1021 if (cu_sp) 1022 { 1023 // If we just created a compile unit with an invalid file spec, try and get the 1024 // first entry in the supports files from the line table as that should be the 1025 // compile unit. 1026 if (!cu_file_spec) 1027 { 1028 cu_file_spec = cu_sp->GetSupportFiles().GetFileSpecAtIndex(1); 1029 if (cu_file_spec) 1030 { 1031 (FileSpec &)(*cu_sp) = cu_file_spec; 1032 // Also fix the invalid file spec which was copied from the compile unit. 1033 cu_sp->GetSupportFiles().Replace(0, cu_file_spec); 1034 } 1035 } 1036 1037 dwarf_cu->SetUserData(cu_sp.get()); 1038 1039 // Figure out the compile unit index if we weren't given one 1040 if (cu_idx == UINT32_MAX) 1041 DebugInfo()->GetCompileUnit(dwarf_cu->GetOffset(), &cu_idx); 1042 1043 m_obj_file->GetModule()->GetSymbolVendor()->SetCompileUnitAtIndex(cu_idx, cu_sp); 1044 } 1045 } 1046 } 1047 } 1048 } 1049 } 1050 return cu_sp; 1051 } 1052 1053 uint32_t 1054 SymbolFileDWARF::GetNumCompileUnits() 1055 { 1056 DWARFDebugInfo* info = DebugInfo(); 1057 if (info) 1058 return info->GetNumCompileUnits(); 1059 return 0; 1060 } 1061 1062 CompUnitSP 1063 SymbolFileDWARF::ParseCompileUnitAtIndex(uint32_t cu_idx) 1064 { 1065 CompUnitSP cu_sp; 1066 DWARFDebugInfo* info = DebugInfo(); 1067 if (info) 1068 { 1069 DWARFCompileUnit* dwarf_cu = info->GetCompileUnitAtIndex(cu_idx); 1070 if (dwarf_cu) 1071 cu_sp = ParseCompileUnit(dwarf_cu, cu_idx); 1072 } 1073 return cu_sp; 1074 } 1075 1076 Function * 1077 SymbolFileDWARF::ParseCompileUnitFunction (const SymbolContext& sc, DWARFCompileUnit* dwarf_cu, const DWARFDebugInfoEntry *die) 1078 { 1079 TypeSystem *type_system = GetTypeSystemForLanguage(dwarf_cu->GetLanguageType()); 1080 1081 if (type_system) 1082 return type_system->ParseFunctionFromDWARF(sc, this, dwarf_cu, die); 1083 else 1084 return nullptr; 1085 } 1086 1087 bool 1088 SymbolFileDWARF::FixupAddress (Address &addr) 1089 { 1090 SymbolFileDWARFDebugMap * debug_map_symfile = GetDebugMapSymfile (); 1091 if (debug_map_symfile) 1092 { 1093 return debug_map_symfile->LinkOSOAddress(addr); 1094 } 1095 // This is a normal DWARF file, no address fixups need to happen 1096 return true; 1097 } 1098 lldb::LanguageType 1099 SymbolFileDWARF::ParseCompileUnitLanguage (const SymbolContext& sc) 1100 { 1101 assert (sc.comp_unit); 1102 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnit(sc.comp_unit); 1103 if (dwarf_cu) 1104 { 1105 const DWARFDebugInfoEntry *die = dwarf_cu->GetCompileUnitDIEOnly(); 1106 if (die) 1107 return DWARFCompileUnit::LanguageTypeFromDWARF(die->GetAttributeValueAsUnsigned(this, dwarf_cu, DW_AT_language, 0)); 1108 } 1109 return eLanguageTypeUnknown; 1110 } 1111 1112 size_t 1113 SymbolFileDWARF::ParseCompileUnitFunctions(const SymbolContext &sc) 1114 { 1115 assert (sc.comp_unit); 1116 size_t functions_added = 0; 1117 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnit(sc.comp_unit); 1118 if (dwarf_cu) 1119 { 1120 DWARFDIECollection function_dies; 1121 const size_t num_functions = dwarf_cu->AppendDIEsWithTag (DW_TAG_subprogram, function_dies); 1122 size_t func_idx; 1123 for (func_idx = 0; func_idx < num_functions; ++func_idx) 1124 { 1125 const DWARFDebugInfoEntry *die = function_dies.GetDIEPtrAtIndex(func_idx); 1126 if (sc.comp_unit->FindFunctionByUID (MakeUserID(die->GetOffset())).get() == NULL) 1127 { 1128 if (ParseCompileUnitFunction(sc, dwarf_cu, die)) 1129 ++functions_added; 1130 } 1131 } 1132 //FixupTypes(); 1133 } 1134 return functions_added; 1135 } 1136 1137 bool 1138 SymbolFileDWARF::ParseCompileUnitSupportFiles (const SymbolContext& sc, FileSpecList& support_files) 1139 { 1140 assert (sc.comp_unit); 1141 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnit(sc.comp_unit); 1142 if (dwarf_cu) 1143 { 1144 const DWARFDebugInfoEntry * cu_die = dwarf_cu->GetCompileUnitDIEOnly(); 1145 1146 if (cu_die) 1147 { 1148 const char * cu_comp_dir = resolveCompDir(cu_die->GetAttributeValueAsString(this, dwarf_cu, DW_AT_comp_dir, nullptr)); 1149 1150 dw_offset_t stmt_list = cu_die->GetAttributeValueAsUnsigned(this, dwarf_cu, DW_AT_stmt_list, DW_INVALID_OFFSET); 1151 1152 // All file indexes in DWARF are one based and a file of index zero is 1153 // supposed to be the compile unit itself. 1154 support_files.Append (*sc.comp_unit); 1155 1156 return DWARFDebugLine::ParseSupportFiles(sc.comp_unit->GetModule(), get_debug_line_data(), cu_comp_dir, stmt_list, support_files); 1157 } 1158 } 1159 return false; 1160 } 1161 1162 bool 1163 SymbolFileDWARF::ParseImportedModules (const lldb_private::SymbolContext &sc, std::vector<lldb_private::ConstString> &imported_modules) 1164 { 1165 assert (sc.comp_unit); 1166 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnit(sc.comp_unit); 1167 if (dwarf_cu) 1168 { 1169 if (ClangModulesDeclVendor::LanguageSupportsClangModules(sc.comp_unit->GetLanguage())) 1170 { 1171 UpdateExternalModuleListIfNeeded(); 1172 for (const std::pair<uint64_t, const ClangModuleInfo> &external_type_module : m_external_type_modules) 1173 { 1174 imported_modules.push_back(external_type_module.second.m_name); 1175 } 1176 } 1177 } 1178 return false; 1179 } 1180 1181 struct ParseDWARFLineTableCallbackInfo 1182 { 1183 LineTable* line_table; 1184 std::unique_ptr<LineSequence> sequence_ap; 1185 }; 1186 1187 //---------------------------------------------------------------------- 1188 // ParseStatementTableCallback 1189 //---------------------------------------------------------------------- 1190 static void 1191 ParseDWARFLineTableCallback(dw_offset_t offset, const DWARFDebugLine::State& state, void* userData) 1192 { 1193 if (state.row == DWARFDebugLine::State::StartParsingLineTable) 1194 { 1195 // Just started parsing the line table 1196 } 1197 else if (state.row == DWARFDebugLine::State::DoneParsingLineTable) 1198 { 1199 // Done parsing line table, nothing to do for the cleanup 1200 } 1201 else 1202 { 1203 ParseDWARFLineTableCallbackInfo* info = (ParseDWARFLineTableCallbackInfo*)userData; 1204 LineTable* line_table = info->line_table; 1205 1206 // If this is our first time here, we need to create a 1207 // sequence container. 1208 if (!info->sequence_ap.get()) 1209 { 1210 info->sequence_ap.reset(line_table->CreateLineSequenceContainer()); 1211 assert(info->sequence_ap.get()); 1212 } 1213 line_table->AppendLineEntryToSequence (info->sequence_ap.get(), 1214 state.address, 1215 state.line, 1216 state.column, 1217 state.file, 1218 state.is_stmt, 1219 state.basic_block, 1220 state.prologue_end, 1221 state.epilogue_begin, 1222 state.end_sequence); 1223 if (state.end_sequence) 1224 { 1225 // First, put the current sequence into the line table. 1226 line_table->InsertSequence(info->sequence_ap.get()); 1227 // Then, empty it to prepare for the next sequence. 1228 info->sequence_ap->Clear(); 1229 } 1230 } 1231 } 1232 1233 bool 1234 SymbolFileDWARF::ParseCompileUnitLineTable (const SymbolContext &sc) 1235 { 1236 assert (sc.comp_unit); 1237 if (sc.comp_unit->GetLineTable() != NULL) 1238 return true; 1239 1240 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnit(sc.comp_unit); 1241 if (dwarf_cu) 1242 { 1243 const DWARFDebugInfoEntry *dwarf_cu_die = dwarf_cu->GetCompileUnitDIEOnly(); 1244 if (dwarf_cu_die) 1245 { 1246 const dw_offset_t cu_line_offset = dwarf_cu_die->GetAttributeValueAsUnsigned(this, dwarf_cu, DW_AT_stmt_list, DW_INVALID_OFFSET); 1247 if (cu_line_offset != DW_INVALID_OFFSET) 1248 { 1249 std::unique_ptr<LineTable> line_table_ap(new LineTable(sc.comp_unit)); 1250 if (line_table_ap.get()) 1251 { 1252 ParseDWARFLineTableCallbackInfo info; 1253 info.line_table = line_table_ap.get(); 1254 lldb::offset_t offset = cu_line_offset; 1255 DWARFDebugLine::ParseStatementTable(get_debug_line_data(), &offset, ParseDWARFLineTableCallback, &info); 1256 if (m_debug_map_symfile) 1257 { 1258 // We have an object file that has a line table with addresses 1259 // that are not linked. We need to link the line table and convert 1260 // the addresses that are relative to the .o file into addresses 1261 // for the main executable. 1262 sc.comp_unit->SetLineTable (m_debug_map_symfile->LinkOSOLineTable (this, line_table_ap.get())); 1263 } 1264 else 1265 { 1266 sc.comp_unit->SetLineTable(line_table_ap.release()); 1267 return true; 1268 } 1269 } 1270 } 1271 } 1272 } 1273 return false; 1274 } 1275 1276 size_t 1277 SymbolFileDWARF::ParseFunctionBlocks 1278 ( 1279 const SymbolContext& sc, 1280 Block *parent_block, 1281 DWARFCompileUnit* dwarf_cu, 1282 const DWARFDebugInfoEntry *die, 1283 addr_t subprogram_low_pc, 1284 uint32_t depth 1285 ) 1286 { 1287 size_t blocks_added = 0; 1288 while (die != NULL) 1289 { 1290 dw_tag_t tag = die->Tag(); 1291 1292 switch (tag) 1293 { 1294 case DW_TAG_inlined_subroutine: 1295 case DW_TAG_subprogram: 1296 case DW_TAG_lexical_block: 1297 { 1298 Block *block = NULL; 1299 if (tag == DW_TAG_subprogram) 1300 { 1301 // Skip any DW_TAG_subprogram DIEs that are inside 1302 // of a normal or inlined functions. These will be 1303 // parsed on their own as separate entities. 1304 1305 if (depth > 0) 1306 break; 1307 1308 block = parent_block; 1309 } 1310 else 1311 { 1312 BlockSP block_sp(new Block (MakeUserID(die->GetOffset()))); 1313 parent_block->AddChild(block_sp); 1314 block = block_sp.get(); 1315 } 1316 DWARFDebugRanges::RangeList ranges; 1317 const char *name = NULL; 1318 const char *mangled_name = NULL; 1319 1320 int decl_file = 0; 1321 int decl_line = 0; 1322 int decl_column = 0; 1323 int call_file = 0; 1324 int call_line = 0; 1325 int call_column = 0; 1326 if (die->GetDIENamesAndRanges (this, 1327 dwarf_cu, 1328 name, 1329 mangled_name, 1330 ranges, 1331 decl_file, decl_line, decl_column, 1332 call_file, call_line, call_column)) 1333 { 1334 if (tag == DW_TAG_subprogram) 1335 { 1336 assert (subprogram_low_pc == LLDB_INVALID_ADDRESS); 1337 subprogram_low_pc = ranges.GetMinRangeBase(0); 1338 } 1339 else if (tag == DW_TAG_inlined_subroutine) 1340 { 1341 // We get called here for inlined subroutines in two ways. 1342 // The first time is when we are making the Function object 1343 // for this inlined concrete instance. Since we're creating a top level block at 1344 // here, the subprogram_low_pc will be LLDB_INVALID_ADDRESS. So we need to 1345 // adjust the containing address. 1346 // The second time is when we are parsing the blocks inside the function that contains 1347 // the inlined concrete instance. Since these will be blocks inside the containing "real" 1348 // function the offset will be for that function. 1349 if (subprogram_low_pc == LLDB_INVALID_ADDRESS) 1350 { 1351 subprogram_low_pc = ranges.GetMinRangeBase(0); 1352 } 1353 } 1354 1355 const size_t num_ranges = ranges.GetSize(); 1356 for (size_t i = 0; i<num_ranges; ++i) 1357 { 1358 const DWARFDebugRanges::Range &range = ranges.GetEntryRef (i); 1359 const addr_t range_base = range.GetRangeBase(); 1360 if (range_base >= subprogram_low_pc) 1361 block->AddRange(Block::Range (range_base - subprogram_low_pc, range.GetByteSize())); 1362 else 1363 { 1364 GetObjectFile()->GetModule()->ReportError ("0x%8.8" PRIx64 ": adding range [0x%" PRIx64 "-0x%" PRIx64 ") which has a base that is less than the function's low PC 0x%" PRIx64 ". Please file a bug and attach the file at the start of this error message", 1365 block->GetID(), 1366 range_base, 1367 range.GetRangeEnd(), 1368 subprogram_low_pc); 1369 } 1370 } 1371 block->FinalizeRanges (); 1372 1373 if (tag != DW_TAG_subprogram && (name != NULL || mangled_name != NULL)) 1374 { 1375 std::unique_ptr<Declaration> decl_ap; 1376 if (decl_file != 0 || decl_line != 0 || decl_column != 0) 1377 decl_ap.reset(new Declaration(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(decl_file), 1378 decl_line, decl_column)); 1379 1380 std::unique_ptr<Declaration> call_ap; 1381 if (call_file != 0 || call_line != 0 || call_column != 0) 1382 call_ap.reset(new Declaration(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(call_file), 1383 call_line, call_column)); 1384 1385 block->SetInlinedFunctionInfo (name, mangled_name, decl_ap.get(), call_ap.get()); 1386 } 1387 1388 ++blocks_added; 1389 1390 if (die->HasChildren()) 1391 { 1392 blocks_added += ParseFunctionBlocks (sc, 1393 block, 1394 dwarf_cu, 1395 die->GetFirstChild(), 1396 subprogram_low_pc, 1397 depth + 1); 1398 } 1399 } 1400 } 1401 break; 1402 default: 1403 break; 1404 } 1405 1406 // Only parse siblings of the block if we are not at depth zero. A depth 1407 // of zero indicates we are currently parsing the top level 1408 // DW_TAG_subprogram DIE 1409 1410 if (depth == 0) 1411 die = NULL; 1412 else 1413 die = die->GetSibling(); 1414 } 1415 return blocks_added; 1416 } 1417 1418 bool 1419 SymbolFileDWARF::ClassOrStructIsVirtual (DWARFCompileUnit* dwarf_cu, 1420 const DWARFDebugInfoEntry *parent_die) 1421 { 1422 if (parent_die) 1423 { 1424 for (const DWARFDebugInfoEntry *die = parent_die->GetFirstChild(); die != NULL; die = die->GetSibling()) 1425 { 1426 dw_tag_t tag = die->Tag(); 1427 bool check_virtuality = false; 1428 switch (tag) 1429 { 1430 case DW_TAG_inheritance: 1431 case DW_TAG_subprogram: 1432 check_virtuality = true; 1433 break; 1434 default: 1435 break; 1436 } 1437 if (check_virtuality) 1438 { 1439 if (die->GetAttributeValueAsUnsigned(this, dwarf_cu, DW_AT_virtuality, 0) != 0) 1440 return true; 1441 } 1442 } 1443 } 1444 return false; 1445 } 1446 1447 CompilerDeclContext 1448 SymbolFileDWARF::GetDeclContextForUID (lldb::user_id_t type_uid) 1449 { 1450 if (UserIDMatches(type_uid)) 1451 { 1452 DWARFDebugInfo* debug_info = DebugInfo(); 1453 if (debug_info) 1454 { 1455 DWARFCompileUnitSP cu_sp; 1456 const DWARFDebugInfoEntry* die = debug_info->GetDIEPtr(type_uid, &cu_sp); 1457 if (die) 1458 { 1459 TypeSystem *type_system = GetTypeSystemForLanguage(cu_sp->GetLanguageType()); 1460 if (type_system) 1461 return type_system->GetDeclContextForUIDFromDWARF(this, cu_sp.get(), die); 1462 } 1463 } 1464 } 1465 return CompilerDeclContext(); 1466 } 1467 1468 CompilerDeclContext 1469 SymbolFileDWARF::GetDeclContextContainingUID (lldb::user_id_t type_uid) 1470 { 1471 if (UserIDMatches(type_uid)) 1472 { 1473 DWARFDebugInfo* debug_info = DebugInfo(); 1474 if (debug_info) 1475 { 1476 DWARFCompileUnitSP cu_sp; 1477 const DWARFDebugInfoEntry* die = debug_info->GetDIEPtr(type_uid, &cu_sp); 1478 if (die) 1479 { 1480 TypeSystem *type_system = GetTypeSystemForLanguage(cu_sp->GetLanguageType()); 1481 if (type_system) 1482 return type_system->GetDeclContextContainingUIDFromDWARF(this, cu_sp.get(), die); 1483 } 1484 } 1485 } 1486 return CompilerDeclContext(); 1487 } 1488 1489 1490 Type* 1491 SymbolFileDWARF::ResolveTypeUID (lldb::user_id_t type_uid) 1492 { 1493 if (UserIDMatches(type_uid)) 1494 { 1495 DWARFDebugInfo* debug_info = DebugInfo(); 1496 if (debug_info) 1497 { 1498 DWARFCompileUnitSP cu_sp; 1499 const DWARFDebugInfoEntry* type_die = debug_info->GetDIEPtr(type_uid, &cu_sp); 1500 const bool assert_not_being_parsed = true; 1501 return ResolveTypeUID (cu_sp.get(), type_die, assert_not_being_parsed); 1502 } 1503 } 1504 return NULL; 1505 } 1506 1507 Type* 1508 SymbolFileDWARF::ResolveTypeUID (DWARFCompileUnit* cu, const DWARFDebugInfoEntry* die, bool assert_not_being_parsed) 1509 { 1510 if (die != NULL) 1511 { 1512 Log *log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_DEBUG_INFO)); 1513 if (log) 1514 GetObjectFile()->GetModule()->LogMessage (log, 1515 "SymbolFileDWARF::ResolveTypeUID (die = 0x%8.8x) %s '%s'", 1516 die->GetOffset(), 1517 DW_TAG_value_to_name(die->Tag()), 1518 die->GetName(this, cu)); 1519 1520 // We might be coming in in the middle of a type tree (a class 1521 // withing a class, an enum within a class), so parse any needed 1522 // parent DIEs before we get to this one... 1523 const DWARFDebugInfoEntry *decl_ctx_die = GetDeclContextDIEContainingDIE (cu, die); 1524 switch (decl_ctx_die->Tag()) 1525 { 1526 case DW_TAG_structure_type: 1527 case DW_TAG_union_type: 1528 case DW_TAG_class_type: 1529 { 1530 // Get the type, which could be a forward declaration 1531 if (log) 1532 GetObjectFile()->GetModule()->LogMessage (log, 1533 "SymbolFileDWARF::ResolveTypeUID (die = 0x%8.8x) %s '%s' resolve parent forward type for 0x%8.8x", 1534 die->GetOffset(), 1535 DW_TAG_value_to_name(die->Tag()), 1536 die->GetName(this, cu), 1537 decl_ctx_die->GetOffset()); 1538 // 1539 // Type *parent_type = ResolveTypeUID (cu, decl_ctx_die, assert_not_being_parsed); 1540 // if (child_requires_parent_class_union_or_struct_to_be_completed(die->Tag())) 1541 // { 1542 // if (log) 1543 // GetObjectFile()->GetModule()->LogMessage (log, 1544 // "SymbolFileDWARF::ResolveTypeUID (die = 0x%8.8x) %s '%s' resolve parent full type for 0x%8.8x since die is a function", 1545 // die->GetOffset(), 1546 // DW_TAG_value_to_name(die->Tag()), 1547 // die->GetName(this, cu), 1548 // decl_ctx_die->GetOffset()); 1549 // // Ask the type to complete itself if it already hasn't since if we 1550 // // want a function (method or static) from a class, the class must 1551 // // create itself and add it's own methods and class functions. 1552 // if (parent_type) 1553 // parent_type->GetFullCompilerType (); 1554 // } 1555 } 1556 break; 1557 1558 default: 1559 break; 1560 } 1561 return ResolveType (cu, die); 1562 } 1563 return NULL; 1564 } 1565 1566 // This function is used when SymbolFileDWARFDebugMap owns a bunch of 1567 // SymbolFileDWARF objects to detect if this DWARF file is the one that 1568 // can resolve a clang_type. 1569 bool 1570 SymbolFileDWARF::HasForwardDeclForClangType (const CompilerType &clang_type) 1571 { 1572 CompilerType clang_type_no_qualifiers = ClangASTContext::RemoveFastQualifiers(clang_type); 1573 const DWARFDebugInfoEntry* die = m_forward_decl_clang_type_to_die.lookup (clang_type_no_qualifiers.GetOpaqueQualType()); 1574 return die != NULL; 1575 } 1576 1577 1578 bool 1579 SymbolFileDWARF::CompleteType (CompilerType &clang_type) 1580 { 1581 // We have a struct/union/class/enum that needs to be fully resolved. 1582 CompilerType clang_type_no_qualifiers = ClangASTContext::RemoveFastQualifiers(clang_type); 1583 const DWARFDebugInfoEntry* die = m_forward_decl_clang_type_to_die.lookup (clang_type_no_qualifiers.GetOpaqueQualType()); 1584 if (die == NULL) 1585 { 1586 // We have already resolved this type... 1587 return true; 1588 } 1589 // Once we start resolving this type, remove it from the forward declaration 1590 // map in case anyone child members or other types require this type to get resolved. 1591 // The type will get resolved when all of the calls to SymbolFileDWARF::ResolveClangOpaqueTypeDefinition 1592 // are done. 1593 m_forward_decl_clang_type_to_die.erase (clang_type_no_qualifiers.GetOpaqueQualType()); 1594 1595 DWARFDebugInfo* debug_info = DebugInfo(); 1596 DWARFCompileUnit *dwarf_cu = debug_info->GetCompileUnitContainingDIE (die->GetOffset()).get(); 1597 Type *type = m_die_to_type.lookup (die); 1598 1599 Log *log (LogChannelDWARF::GetLogIfAny(DWARF_LOG_DEBUG_INFO|DWARF_LOG_TYPE_COMPLETION)); 1600 if (log) 1601 GetObjectFile()->GetModule()->LogMessageVerboseBacktrace (log, 1602 "0x%8.8" PRIx64 ": %s '%s' resolving forward declaration...", 1603 MakeUserID(die->GetOffset()), 1604 DW_TAG_value_to_name(die->Tag()), 1605 type->GetName().AsCString()); 1606 assert (clang_type); 1607 DWARFDebugInfoEntry::Attributes attributes; 1608 1609 1610 TypeSystem *type_system = GetTypeSystemForLanguage(dwarf_cu->GetLanguageType()); 1611 1612 if (type_system) 1613 return type_system->CompleteTypeFromDWARF (this, dwarf_cu, die, type, clang_type); 1614 1615 return false; 1616 } 1617 1618 void 1619 SymbolFileDWARF::ClearDIEBeingParsed (const DWARFDebugInfoEntry* type_die) 1620 { 1621 if (type_die) 1622 { 1623 if (m_die_to_type.lookup (type_die) == DIE_IS_BEING_PARSED) 1624 m_die_to_type[type_die] = nullptr; 1625 } 1626 } 1627 Type* 1628 SymbolFileDWARF::GetCachedTypeForDIE (const DWARFDebugInfoEntry* type_die) const 1629 { 1630 if (type_die) 1631 { 1632 Type *type = m_die_to_type.lookup (type_die); 1633 if (type != DIE_IS_BEING_PARSED) 1634 return type; 1635 } 1636 return nullptr; 1637 } 1638 1639 Type* 1640 SymbolFileDWARF::ResolveType (DWARFCompileUnit* dwarf_cu, const DWARFDebugInfoEntry* type_die, bool assert_not_being_parsed) 1641 { 1642 if (type_die != NULL) 1643 { 1644 Type *type = m_die_to_type.lookup (type_die); 1645 1646 if (type == NULL) 1647 type = GetTypeForDIE (dwarf_cu, type_die).get(); 1648 1649 if (assert_not_being_parsed) 1650 { 1651 if (type != DIE_IS_BEING_PARSED) 1652 return type; 1653 1654 GetObjectFile()->GetModule()->ReportError ("Parsing a die that is being parsed die: 0x%8.8x: %s %s", 1655 type_die->GetOffset(), 1656 DW_TAG_value_to_name(type_die->Tag()), 1657 type_die->GetName(this, dwarf_cu)); 1658 1659 } 1660 else 1661 return type; 1662 } 1663 return NULL; 1664 } 1665 1666 CompileUnit* 1667 SymbolFileDWARF::GetCompUnitForDWARFCompUnit (DWARFCompileUnit* dwarf_cu, uint32_t cu_idx) 1668 { 1669 // Check if the symbol vendor already knows about this compile unit? 1670 if (dwarf_cu->GetUserData() == NULL) 1671 { 1672 // The symbol vendor doesn't know about this compile unit, we 1673 // need to parse and add it to the symbol vendor object. 1674 return ParseCompileUnit(dwarf_cu, cu_idx).get(); 1675 } 1676 return (CompileUnit*)dwarf_cu->GetUserData(); 1677 } 1678 1679 size_t 1680 SymbolFileDWARF::GetObjCMethodDIEOffsets (ConstString class_name, DIEArray &method_die_offsets) 1681 { 1682 method_die_offsets.clear(); 1683 if (m_using_apple_tables) 1684 { 1685 if (m_apple_objc_ap.get()) 1686 m_apple_objc_ap->FindByName(class_name.GetCString(), method_die_offsets); 1687 } 1688 else 1689 { 1690 if (!m_indexed) 1691 Index (); 1692 1693 m_objc_class_selectors_index.Find (class_name, method_die_offsets); 1694 } 1695 return method_die_offsets.size(); 1696 } 1697 1698 bool 1699 SymbolFileDWARF::GetFunction (DWARFCompileUnit* dwarf_cu, const DWARFDebugInfoEntry* func_die, SymbolContext& sc) 1700 { 1701 sc.Clear(false); 1702 // Check if the symbol vendor already knows about this compile unit? 1703 sc.comp_unit = GetCompUnitForDWARFCompUnit(dwarf_cu, UINT32_MAX); 1704 1705 sc.function = sc.comp_unit->FindFunctionByUID (MakeUserID(func_die->GetOffset())).get(); 1706 if (sc.function == NULL) 1707 sc.function = ParseCompileUnitFunction(sc, dwarf_cu, func_die); 1708 1709 if (sc.function) 1710 { 1711 sc.module_sp = sc.function->CalculateSymbolContextModule(); 1712 return true; 1713 } 1714 1715 return false; 1716 } 1717 1718 void 1719 SymbolFileDWARF::UpdateExternalModuleListIfNeeded() 1720 { 1721 if (m_fetched_external_modules) 1722 return; 1723 m_fetched_external_modules = true; 1724 1725 DWARFDebugInfo * debug_info = DebugInfo(); 1726 debug_info->GetNumCompileUnits(); 1727 1728 const uint32_t num_compile_units = GetNumCompileUnits(); 1729 for (uint32_t cu_idx = 0; cu_idx < num_compile_units; ++cu_idx) 1730 { 1731 DWARFCompileUnit* dwarf_cu = debug_info->GetCompileUnitAtIndex(cu_idx); 1732 1733 const DWARFDebugInfoEntry *die = dwarf_cu->GetCompileUnitDIEOnly(); 1734 if (die && die->HasChildren() == false) 1735 { 1736 const uint64_t name_strp = die->GetAttributeValueAsUnsigned(this, dwarf_cu, DW_AT_name, UINT64_MAX); 1737 const uint64_t dwo_path_strp = die->GetAttributeValueAsUnsigned(this, dwarf_cu, DW_AT_GNU_dwo_name, UINT64_MAX); 1738 1739 if (name_strp != UINT64_MAX) 1740 { 1741 if (m_external_type_modules.find(dwo_path_strp) == m_external_type_modules.end()) 1742 { 1743 const char *name = get_debug_str_data().PeekCStr(name_strp); 1744 const char *dwo_path = get_debug_str_data().PeekCStr(dwo_path_strp); 1745 if (name || dwo_path) 1746 { 1747 ModuleSP module_sp; 1748 if (dwo_path) 1749 { 1750 ModuleSpec dwo_module_spec; 1751 dwo_module_spec.GetFileSpec().SetFile(dwo_path, false); 1752 dwo_module_spec.GetArchitecture() = m_obj_file->GetModule()->GetArchitecture(); 1753 //printf ("Loading dwo = '%s'\n", dwo_path); 1754 Error error = ModuleList::GetSharedModule (dwo_module_spec, module_sp, NULL, NULL, NULL); 1755 } 1756 1757 if (dwo_path_strp != LLDB_INVALID_UID) 1758 { 1759 m_external_type_modules[dwo_path_strp] = ClangModuleInfo { ConstString(name), module_sp }; 1760 } 1761 else 1762 { 1763 // This hack should be removed promptly once clang emits both. 1764 m_external_type_modules[name_strp] = ClangModuleInfo { ConstString(name), module_sp }; 1765 } 1766 } 1767 } 1768 } 1769 } 1770 } 1771 } 1772 1773 SymbolFileDWARF::GlobalVariableMap & 1774 SymbolFileDWARF::GetGlobalAranges() 1775 { 1776 if (!m_global_aranges_ap) 1777 { 1778 m_global_aranges_ap.reset (new GlobalVariableMap()); 1779 1780 ModuleSP module_sp = GetObjectFile()->GetModule(); 1781 if (module_sp) 1782 { 1783 const size_t num_cus = module_sp->GetNumCompileUnits(); 1784 for (size_t i = 0; i < num_cus; ++i) 1785 { 1786 CompUnitSP cu_sp = module_sp->GetCompileUnitAtIndex(i); 1787 if (cu_sp) 1788 { 1789 VariableListSP globals_sp = cu_sp->GetVariableList(true); 1790 if (globals_sp) 1791 { 1792 const size_t num_globals = globals_sp->GetSize(); 1793 for (size_t g = 0; g < num_globals; ++g) 1794 { 1795 VariableSP var_sp = globals_sp->GetVariableAtIndex(g); 1796 if (var_sp && !var_sp->GetLocationIsConstantValueData()) 1797 { 1798 const DWARFExpression &location = var_sp->LocationExpression(); 1799 Value location_result; 1800 Error error; 1801 if (location.Evaluate(NULL, NULL, NULL, LLDB_INVALID_ADDRESS, NULL, location_result, &error)) 1802 { 1803 if (location_result.GetValueType() == Value::eValueTypeFileAddress) 1804 { 1805 lldb::addr_t file_addr = location_result.GetScalar().ULongLong(); 1806 lldb::addr_t byte_size = 1; 1807 if (var_sp->GetType()) 1808 byte_size = var_sp->GetType()->GetByteSize(); 1809 m_global_aranges_ap->Append(GlobalVariableMap::Entry(file_addr, byte_size, var_sp.get())); 1810 } 1811 } 1812 } 1813 } 1814 } 1815 } 1816 } 1817 } 1818 m_global_aranges_ap->Sort(); 1819 } 1820 return *m_global_aranges_ap; 1821 } 1822 1823 1824 uint32_t 1825 SymbolFileDWARF::ResolveSymbolContext (const Address& so_addr, uint32_t resolve_scope, SymbolContext& sc) 1826 { 1827 Timer scoped_timer(__PRETTY_FUNCTION__, 1828 "SymbolFileDWARF::ResolveSymbolContext (so_addr = { section = %p, offset = 0x%" PRIx64 " }, resolve_scope = 0x%8.8x)", 1829 static_cast<void*>(so_addr.GetSection().get()), 1830 so_addr.GetOffset(), resolve_scope); 1831 uint32_t resolved = 0; 1832 if (resolve_scope & ( eSymbolContextCompUnit | 1833 eSymbolContextFunction | 1834 eSymbolContextBlock | 1835 eSymbolContextLineEntry | 1836 eSymbolContextVariable )) 1837 { 1838 lldb::addr_t file_vm_addr = so_addr.GetFileAddress(); 1839 1840 DWARFDebugInfo* debug_info = DebugInfo(); 1841 if (debug_info) 1842 { 1843 const dw_offset_t cu_offset = debug_info->GetCompileUnitAranges().FindAddress(file_vm_addr); 1844 if (cu_offset == DW_INVALID_OFFSET) 1845 { 1846 // Global variables are not in the compile unit address ranges. The only way to 1847 // currently find global variables is to iterate over the .debug_pubnames or the 1848 // __apple_names table and find all items in there that point to DW_TAG_variable 1849 // DIEs and then find the address that matches. 1850 if (resolve_scope & eSymbolContextVariable) 1851 { 1852 GlobalVariableMap &map = GetGlobalAranges(); 1853 const GlobalVariableMap::Entry *entry = map.FindEntryThatContains(file_vm_addr); 1854 if (entry && entry->data) 1855 { 1856 Variable *variable = entry->data; 1857 SymbolContextScope *scc = variable->GetSymbolContextScope(); 1858 if (scc) 1859 { 1860 scc->CalculateSymbolContext(&sc); 1861 sc.variable = variable; 1862 } 1863 return sc.GetResolvedMask(); 1864 } 1865 } 1866 } 1867 else 1868 { 1869 uint32_t cu_idx = DW_INVALID_INDEX; 1870 DWARFCompileUnit* dwarf_cu = debug_info->GetCompileUnit(cu_offset, &cu_idx).get(); 1871 if (dwarf_cu) 1872 { 1873 sc.comp_unit = GetCompUnitForDWARFCompUnit(dwarf_cu, cu_idx); 1874 if (sc.comp_unit) 1875 { 1876 resolved |= eSymbolContextCompUnit; 1877 1878 bool force_check_line_table = false; 1879 if (resolve_scope & (eSymbolContextFunction | eSymbolContextBlock)) 1880 { 1881 DWARFDebugInfoEntry *function_die = NULL; 1882 DWARFDebugInfoEntry *block_die = NULL; 1883 if (resolve_scope & eSymbolContextBlock) 1884 { 1885 dwarf_cu->LookupAddress(file_vm_addr, &function_die, &block_die); 1886 } 1887 else 1888 { 1889 dwarf_cu->LookupAddress(file_vm_addr, &function_die, NULL); 1890 } 1891 1892 if (function_die != NULL) 1893 { 1894 sc.function = sc.comp_unit->FindFunctionByUID (MakeUserID(function_die->GetOffset())).get(); 1895 if (sc.function == NULL) 1896 sc.function = ParseCompileUnitFunction(sc, dwarf_cu, function_die); 1897 } 1898 else 1899 { 1900 // We might have had a compile unit that had discontiguous 1901 // address ranges where the gaps are symbols that don't have 1902 // any debug info. Discontiguous compile unit address ranges 1903 // should only happen when there aren't other functions from 1904 // other compile units in these gaps. This helps keep the size 1905 // of the aranges down. 1906 force_check_line_table = true; 1907 } 1908 1909 if (sc.function != NULL) 1910 { 1911 resolved |= eSymbolContextFunction; 1912 1913 if (resolve_scope & eSymbolContextBlock) 1914 { 1915 Block& block = sc.function->GetBlock (true); 1916 1917 if (block_die != NULL) 1918 sc.block = block.FindBlockByID (MakeUserID(block_die->GetOffset())); 1919 else 1920 sc.block = block.FindBlockByID (MakeUserID(function_die->GetOffset())); 1921 if (sc.block) 1922 resolved |= eSymbolContextBlock; 1923 } 1924 } 1925 } 1926 1927 if ((resolve_scope & eSymbolContextLineEntry) || force_check_line_table) 1928 { 1929 LineTable *line_table = sc.comp_unit->GetLineTable(); 1930 if (line_table != NULL) 1931 { 1932 // And address that makes it into this function should be in terms 1933 // of this debug file if there is no debug map, or it will be an 1934 // address in the .o file which needs to be fixed up to be in terms 1935 // of the debug map executable. Either way, calling FixupAddress() 1936 // will work for us. 1937 Address exe_so_addr (so_addr); 1938 if (FixupAddress(exe_so_addr)) 1939 { 1940 if (line_table->FindLineEntryByAddress (exe_so_addr, sc.line_entry)) 1941 { 1942 resolved |= eSymbolContextLineEntry; 1943 } 1944 } 1945 } 1946 } 1947 1948 if (force_check_line_table && !(resolved & eSymbolContextLineEntry)) 1949 { 1950 // We might have had a compile unit that had discontiguous 1951 // address ranges where the gaps are symbols that don't have 1952 // any debug info. Discontiguous compile unit address ranges 1953 // should only happen when there aren't other functions from 1954 // other compile units in these gaps. This helps keep the size 1955 // of the aranges down. 1956 sc.comp_unit = NULL; 1957 resolved &= ~eSymbolContextCompUnit; 1958 } 1959 } 1960 else 1961 { 1962 GetObjectFile()->GetModule()->ReportWarning ("0x%8.8x: compile unit %u failed to create a valid lldb_private::CompileUnit class.", 1963 cu_offset, 1964 cu_idx); 1965 } 1966 } 1967 } 1968 } 1969 } 1970 return resolved; 1971 } 1972 1973 1974 1975 uint32_t 1976 SymbolFileDWARF::ResolveSymbolContext(const FileSpec& file_spec, uint32_t line, bool check_inlines, uint32_t resolve_scope, SymbolContextList& sc_list) 1977 { 1978 const uint32_t prev_size = sc_list.GetSize(); 1979 if (resolve_scope & eSymbolContextCompUnit) 1980 { 1981 DWARFDebugInfo* debug_info = DebugInfo(); 1982 if (debug_info) 1983 { 1984 uint32_t cu_idx; 1985 DWARFCompileUnit* dwarf_cu = NULL; 1986 1987 for (cu_idx = 0; (dwarf_cu = debug_info->GetCompileUnitAtIndex(cu_idx)) != NULL; ++cu_idx) 1988 { 1989 CompileUnit *dc_cu = GetCompUnitForDWARFCompUnit(dwarf_cu, cu_idx); 1990 const bool full_match = (bool)file_spec.GetDirectory(); 1991 bool file_spec_matches_cu_file_spec = dc_cu != NULL && FileSpec::Equal(file_spec, *dc_cu, full_match); 1992 if (check_inlines || file_spec_matches_cu_file_spec) 1993 { 1994 SymbolContext sc (m_obj_file->GetModule()); 1995 sc.comp_unit = GetCompUnitForDWARFCompUnit(dwarf_cu, cu_idx); 1996 if (sc.comp_unit) 1997 { 1998 uint32_t file_idx = UINT32_MAX; 1999 2000 // If we are looking for inline functions only and we don't 2001 // find it in the support files, we are done. 2002 if (check_inlines) 2003 { 2004 file_idx = sc.comp_unit->GetSupportFiles().FindFileIndex (1, file_spec, true); 2005 if (file_idx == UINT32_MAX) 2006 continue; 2007 } 2008 2009 if (line != 0) 2010 { 2011 LineTable *line_table = sc.comp_unit->GetLineTable(); 2012 2013 if (line_table != NULL && line != 0) 2014 { 2015 // We will have already looked up the file index if 2016 // we are searching for inline entries. 2017 if (!check_inlines) 2018 file_idx = sc.comp_unit->GetSupportFiles().FindFileIndex (1, file_spec, true); 2019 2020 if (file_idx != UINT32_MAX) 2021 { 2022 uint32_t found_line; 2023 uint32_t line_idx = line_table->FindLineEntryIndexByFileIndex (0, file_idx, line, false, &sc.line_entry); 2024 found_line = sc.line_entry.line; 2025 2026 while (line_idx != UINT32_MAX) 2027 { 2028 sc.function = NULL; 2029 sc.block = NULL; 2030 if (resolve_scope & (eSymbolContextFunction | eSymbolContextBlock)) 2031 { 2032 const lldb::addr_t file_vm_addr = sc.line_entry.range.GetBaseAddress().GetFileAddress(); 2033 if (file_vm_addr != LLDB_INVALID_ADDRESS) 2034 { 2035 DWARFDebugInfoEntry *function_die = NULL; 2036 DWARFDebugInfoEntry *block_die = NULL; 2037 dwarf_cu->LookupAddress(file_vm_addr, &function_die, resolve_scope & eSymbolContextBlock ? &block_die : NULL); 2038 2039 if (function_die != NULL) 2040 { 2041 sc.function = sc.comp_unit->FindFunctionByUID (MakeUserID(function_die->GetOffset())).get(); 2042 if (sc.function == NULL) 2043 sc.function = ParseCompileUnitFunction(sc, dwarf_cu, function_die); 2044 } 2045 2046 if (sc.function != NULL) 2047 { 2048 Block& block = sc.function->GetBlock (true); 2049 2050 if (block_die != NULL) 2051 sc.block = block.FindBlockByID (MakeUserID(block_die->GetOffset())); 2052 else if (function_die != NULL) 2053 sc.block = block.FindBlockByID (MakeUserID(function_die->GetOffset())); 2054 } 2055 } 2056 } 2057 2058 sc_list.Append(sc); 2059 line_idx = line_table->FindLineEntryIndexByFileIndex (line_idx + 1, file_idx, found_line, true, &sc.line_entry); 2060 } 2061 } 2062 } 2063 else if (file_spec_matches_cu_file_spec && !check_inlines) 2064 { 2065 // only append the context if we aren't looking for inline call sites 2066 // by file and line and if the file spec matches that of the compile unit 2067 sc_list.Append(sc); 2068 } 2069 } 2070 else if (file_spec_matches_cu_file_spec && !check_inlines) 2071 { 2072 // only append the context if we aren't looking for inline call sites 2073 // by file and line and if the file spec matches that of the compile unit 2074 sc_list.Append(sc); 2075 } 2076 2077 if (!check_inlines) 2078 break; 2079 } 2080 } 2081 } 2082 } 2083 } 2084 return sc_list.GetSize() - prev_size; 2085 } 2086 2087 void 2088 SymbolFileDWARF::Index () 2089 { 2090 if (m_indexed) 2091 return; 2092 m_indexed = true; 2093 Timer scoped_timer (__PRETTY_FUNCTION__, 2094 "SymbolFileDWARF::Index (%s)", 2095 GetObjectFile()->GetFileSpec().GetFilename().AsCString("<Unknown>")); 2096 2097 DWARFDebugInfo* debug_info = DebugInfo(); 2098 if (debug_info) 2099 { 2100 uint32_t cu_idx = 0; 2101 const uint32_t num_compile_units = GetNumCompileUnits(); 2102 for (cu_idx = 0; cu_idx < num_compile_units; ++cu_idx) 2103 { 2104 DWARFCompileUnit* dwarf_cu = debug_info->GetCompileUnitAtIndex(cu_idx); 2105 2106 bool clear_dies = dwarf_cu->ExtractDIEsIfNeeded (false) > 1; 2107 2108 dwarf_cu->Index (cu_idx, 2109 m_function_basename_index, 2110 m_function_fullname_index, 2111 m_function_method_index, 2112 m_function_selector_index, 2113 m_objc_class_selectors_index, 2114 m_global_index, 2115 m_type_index, 2116 m_namespace_index); 2117 2118 // Keep memory down by clearing DIEs if this generate function 2119 // caused them to be parsed 2120 if (clear_dies) 2121 dwarf_cu->ClearDIEs (true); 2122 } 2123 2124 m_function_basename_index.Finalize(); 2125 m_function_fullname_index.Finalize(); 2126 m_function_method_index.Finalize(); 2127 m_function_selector_index.Finalize(); 2128 m_objc_class_selectors_index.Finalize(); 2129 m_global_index.Finalize(); 2130 m_type_index.Finalize(); 2131 m_namespace_index.Finalize(); 2132 2133 #if defined (ENABLE_DEBUG_PRINTF) 2134 StreamFile s(stdout, false); 2135 s.Printf ("DWARF index for '%s':", 2136 GetObjectFile()->GetFileSpec().GetPath().c_str()); 2137 s.Printf("\nFunction basenames:\n"); m_function_basename_index.Dump (&s); 2138 s.Printf("\nFunction fullnames:\n"); m_function_fullname_index.Dump (&s); 2139 s.Printf("\nFunction methods:\n"); m_function_method_index.Dump (&s); 2140 s.Printf("\nFunction selectors:\n"); m_function_selector_index.Dump (&s); 2141 s.Printf("\nObjective C class selectors:\n"); m_objc_class_selectors_index.Dump (&s); 2142 s.Printf("\nGlobals and statics:\n"); m_global_index.Dump (&s); 2143 s.Printf("\nTypes:\n"); m_type_index.Dump (&s); 2144 s.Printf("\nNamespaces:\n") m_namespace_index.Dump (&s); 2145 #endif 2146 } 2147 } 2148 2149 bool 2150 SymbolFileDWARF::DeclContextMatchesThisSymbolFile (const lldb_private::CompilerDeclContext *decl_ctx) 2151 { 2152 if (decl_ctx == nullptr || !decl_ctx->IsValid()) 2153 { 2154 // Invalid namespace decl which means we aren't matching only things 2155 // in this symbol file, so return true to indicate it matches this 2156 // symbol file. 2157 return true; 2158 } 2159 2160 if ((TypeSystem *)&GetClangASTContext() == decl_ctx->GetTypeSystem()) 2161 return true; // The type systems match, return true 2162 2163 // The namespace AST was valid, and it does not match... 2164 Log *log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2165 2166 if (log) 2167 GetObjectFile()->GetModule()->LogMessage(log, "Valid namespace does not match symbol file"); 2168 2169 return false; 2170 } 2171 2172 uint32_t 2173 SymbolFileDWARF::FindGlobalVariables (const ConstString &name, const CompilerDeclContext *parent_decl_ctx, bool append, uint32_t max_matches, VariableList& variables) 2174 { 2175 Log *log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2176 2177 if (log) 2178 GetObjectFile()->GetModule()->LogMessage (log, 2179 "SymbolFileDWARF::FindGlobalVariables (name=\"%s\", parent_decl_ctx=%p, append=%u, max_matches=%u, variables)", 2180 name.GetCString(), 2181 static_cast<const void*>(parent_decl_ctx), 2182 append, max_matches); 2183 2184 if (!DeclContextMatchesThisSymbolFile(parent_decl_ctx)) 2185 return 0; 2186 2187 DWARFDebugInfo* info = DebugInfo(); 2188 if (info == NULL) 2189 return 0; 2190 2191 // If we aren't appending the results to this list, then clear the list 2192 if (!append) 2193 variables.Clear(); 2194 2195 // Remember how many variables are in the list before we search in case 2196 // we are appending the results to a variable list. 2197 const uint32_t original_size = variables.GetSize(); 2198 2199 DIEArray die_offsets; 2200 2201 if (m_using_apple_tables) 2202 { 2203 if (m_apple_names_ap.get()) 2204 { 2205 const char *name_cstr = name.GetCString(); 2206 llvm::StringRef basename; 2207 llvm::StringRef context; 2208 2209 if (!CPPLanguageRuntime::ExtractContextAndIdentifier(name_cstr, context, basename)) 2210 basename = name_cstr; 2211 2212 m_apple_names_ap->FindByName (basename.data(), die_offsets); 2213 } 2214 } 2215 else 2216 { 2217 // Index the DWARF if we haven't already 2218 if (!m_indexed) 2219 Index (); 2220 2221 m_global_index.Find (name, die_offsets); 2222 } 2223 2224 const size_t num_die_matches = die_offsets.size(); 2225 if (num_die_matches) 2226 { 2227 SymbolContext sc; 2228 sc.module_sp = m_obj_file->GetModule(); 2229 assert (sc.module_sp); 2230 2231 DWARFDebugInfo* debug_info = DebugInfo(); 2232 DWARFCompileUnit* dwarf_cu = NULL; 2233 const DWARFDebugInfoEntry* die = NULL; 2234 bool done = false; 2235 for (size_t i=0; i<num_die_matches && !done; ++i) 2236 { 2237 const dw_offset_t die_offset = die_offsets[i]; 2238 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2239 2240 if (die) 2241 { 2242 switch (die->Tag()) 2243 { 2244 default: 2245 case DW_TAG_subprogram: 2246 case DW_TAG_inlined_subroutine: 2247 case DW_TAG_try_block: 2248 case DW_TAG_catch_block: 2249 break; 2250 2251 case DW_TAG_variable: 2252 { 2253 sc.comp_unit = GetCompUnitForDWARFCompUnit(dwarf_cu, UINT32_MAX); 2254 2255 if (parent_decl_ctx) 2256 { 2257 TypeSystem *type_system = GetTypeSystemForLanguage(dwarf_cu->GetLanguageType()); 2258 2259 if (type_system) 2260 { 2261 CompilerDeclContext actual_parent_decl_ctx = type_system->GetDeclContextContainingUIDFromDWARF (this, dwarf_cu, die); 2262 if (!actual_parent_decl_ctx || actual_parent_decl_ctx != *parent_decl_ctx) 2263 continue; 2264 } 2265 } 2266 2267 ParseVariables(sc, dwarf_cu, LLDB_INVALID_ADDRESS, die, false, false, &variables); 2268 2269 if (variables.GetSize() - original_size >= max_matches) 2270 done = true; 2271 } 2272 break; 2273 } 2274 } 2275 else 2276 { 2277 if (m_using_apple_tables) 2278 { 2279 GetObjectFile()->GetModule()->ReportErrorIfModifyDetected ("the DWARF debug information has been modified (.apple_names accelerator table had bad die 0x%8.8x for '%s')\n", 2280 die_offset, name.GetCString()); 2281 } 2282 } 2283 } 2284 } 2285 2286 // Return the number of variable that were appended to the list 2287 const uint32_t num_matches = variables.GetSize() - original_size; 2288 if (log && num_matches > 0) 2289 { 2290 GetObjectFile()->GetModule()->LogMessage (log, 2291 "SymbolFileDWARF::FindGlobalVariables (name=\"%s\", parent_decl_ctx=%p, append=%u, max_matches=%u, variables) => %u", 2292 name.GetCString(), 2293 static_cast<const void*>(parent_decl_ctx), 2294 append, max_matches, 2295 num_matches); 2296 } 2297 return num_matches; 2298 } 2299 2300 uint32_t 2301 SymbolFileDWARF::FindGlobalVariables(const RegularExpression& regex, bool append, uint32_t max_matches, VariableList& variables) 2302 { 2303 Log *log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2304 2305 if (log) 2306 { 2307 GetObjectFile()->GetModule()->LogMessage (log, 2308 "SymbolFileDWARF::FindGlobalVariables (regex=\"%s\", append=%u, max_matches=%u, variables)", 2309 regex.GetText(), append, 2310 max_matches); 2311 } 2312 2313 DWARFDebugInfo* info = DebugInfo(); 2314 if (info == NULL) 2315 return 0; 2316 2317 // If we aren't appending the results to this list, then clear the list 2318 if (!append) 2319 variables.Clear(); 2320 2321 // Remember how many variables are in the list before we search in case 2322 // we are appending the results to a variable list. 2323 const uint32_t original_size = variables.GetSize(); 2324 2325 DIEArray die_offsets; 2326 2327 if (m_using_apple_tables) 2328 { 2329 if (m_apple_names_ap.get()) 2330 { 2331 DWARFMappedHash::DIEInfoArray hash_data_array; 2332 if (m_apple_names_ap->AppendAllDIEsThatMatchingRegex (regex, hash_data_array)) 2333 DWARFMappedHash::ExtractDIEArray (hash_data_array, die_offsets); 2334 } 2335 } 2336 else 2337 { 2338 // Index the DWARF if we haven't already 2339 if (!m_indexed) 2340 Index (); 2341 2342 m_global_index.Find (regex, die_offsets); 2343 } 2344 2345 SymbolContext sc; 2346 sc.module_sp = m_obj_file->GetModule(); 2347 assert (sc.module_sp); 2348 2349 DWARFCompileUnit* dwarf_cu = NULL; 2350 const DWARFDebugInfoEntry* die = NULL; 2351 const size_t num_matches = die_offsets.size(); 2352 if (num_matches) 2353 { 2354 DWARFDebugInfo* debug_info = DebugInfo(); 2355 for (size_t i=0; i<num_matches; ++i) 2356 { 2357 const dw_offset_t die_offset = die_offsets[i]; 2358 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2359 2360 if (die) 2361 { 2362 sc.comp_unit = GetCompUnitForDWARFCompUnit(dwarf_cu, UINT32_MAX); 2363 2364 ParseVariables(sc, dwarf_cu, LLDB_INVALID_ADDRESS, die, false, false, &variables); 2365 2366 if (variables.GetSize() - original_size >= max_matches) 2367 break; 2368 } 2369 else 2370 { 2371 if (m_using_apple_tables) 2372 { 2373 GetObjectFile()->GetModule()->ReportErrorIfModifyDetected ("the DWARF debug information has been modified (.apple_names accelerator table had bad die 0x%8.8x for regex '%s')\n", 2374 die_offset, regex.GetText()); 2375 } 2376 } 2377 } 2378 } 2379 2380 // Return the number of variable that were appended to the list 2381 return variables.GetSize() - original_size; 2382 } 2383 2384 2385 bool 2386 SymbolFileDWARF::ResolveFunction (dw_offset_t die_offset, 2387 DWARFCompileUnit *&dwarf_cu, 2388 bool include_inlines, 2389 SymbolContextList& sc_list) 2390 { 2391 const DWARFDebugInfoEntry *die = DebugInfo()->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2392 return ResolveFunction (dwarf_cu, die, include_inlines, sc_list); 2393 } 2394 2395 2396 bool 2397 SymbolFileDWARF::ResolveFunction (DWARFCompileUnit *cu, 2398 const DWARFDebugInfoEntry *die, 2399 bool include_inlines, 2400 SymbolContextList& sc_list) 2401 { 2402 SymbolContext sc; 2403 2404 if (die == NULL) 2405 return false; 2406 2407 // If we were passed a die that is not a function, just return false... 2408 if (! (die->Tag() == DW_TAG_subprogram || (include_inlines && die->Tag() == DW_TAG_inlined_subroutine))) 2409 return false; 2410 2411 const DWARFDebugInfoEntry* inlined_die = NULL; 2412 if (die->Tag() == DW_TAG_inlined_subroutine) 2413 { 2414 inlined_die = die; 2415 2416 while ((die = die->GetParent()) != NULL) 2417 { 2418 if (die->Tag() == DW_TAG_subprogram) 2419 break; 2420 } 2421 } 2422 assert (die && die->Tag() == DW_TAG_subprogram); 2423 if (GetFunction (cu, die, sc)) 2424 { 2425 Address addr; 2426 // Parse all blocks if needed 2427 if (inlined_die) 2428 { 2429 Block &function_block = sc.function->GetBlock (true); 2430 sc.block = function_block.FindBlockByID (MakeUserID(inlined_die->GetOffset())); 2431 if (sc.block == NULL) 2432 sc.block = function_block.FindBlockByID (inlined_die->GetOffset()); 2433 if (sc.block == NULL || sc.block->GetStartAddress (addr) == false) 2434 addr.Clear(); 2435 } 2436 else 2437 { 2438 sc.block = NULL; 2439 addr = sc.function->GetAddressRange().GetBaseAddress(); 2440 } 2441 2442 if (addr.IsValid()) 2443 { 2444 sc_list.Append(sc); 2445 return true; 2446 } 2447 } 2448 2449 return false; 2450 } 2451 2452 void 2453 SymbolFileDWARF::FindFunctions (const ConstString &name, 2454 const NameToDIE &name_to_die, 2455 bool include_inlines, 2456 SymbolContextList& sc_list) 2457 { 2458 DIEArray die_offsets; 2459 if (name_to_die.Find (name, die_offsets)) 2460 { 2461 ParseFunctions (die_offsets, include_inlines, sc_list); 2462 } 2463 } 2464 2465 2466 void 2467 SymbolFileDWARF::FindFunctions (const RegularExpression ®ex, 2468 const NameToDIE &name_to_die, 2469 bool include_inlines, 2470 SymbolContextList& sc_list) 2471 { 2472 DIEArray die_offsets; 2473 if (name_to_die.Find (regex, die_offsets)) 2474 { 2475 ParseFunctions (die_offsets, include_inlines, sc_list); 2476 } 2477 } 2478 2479 2480 void 2481 SymbolFileDWARF::FindFunctions (const RegularExpression ®ex, 2482 const DWARFMappedHash::MemoryTable &memory_table, 2483 bool include_inlines, 2484 SymbolContextList& sc_list) 2485 { 2486 DIEArray die_offsets; 2487 DWARFMappedHash::DIEInfoArray hash_data_array; 2488 if (memory_table.AppendAllDIEsThatMatchingRegex (regex, hash_data_array)) 2489 { 2490 DWARFMappedHash::ExtractDIEArray (hash_data_array, die_offsets); 2491 ParseFunctions (die_offsets, include_inlines, sc_list); 2492 } 2493 } 2494 2495 void 2496 SymbolFileDWARF::ParseFunctions (const DIEArray &die_offsets, 2497 bool include_inlines, 2498 SymbolContextList& sc_list) 2499 { 2500 const size_t num_matches = die_offsets.size(); 2501 if (num_matches) 2502 { 2503 DWARFCompileUnit* dwarf_cu = NULL; 2504 for (size_t i=0; i<num_matches; ++i) 2505 { 2506 const dw_offset_t die_offset = die_offsets[i]; 2507 ResolveFunction (die_offset, dwarf_cu, include_inlines, sc_list); 2508 } 2509 } 2510 } 2511 2512 bool 2513 SymbolFileDWARF::FunctionDieMatchesPartialName (const DWARFDebugInfoEntry* die, 2514 const DWARFCompileUnit *dwarf_cu, 2515 uint32_t name_type_mask, 2516 const char *partial_name, 2517 const char *base_name_start, 2518 const char *base_name_end) 2519 { 2520 // If we are looking only for methods, throw away all the ones that are or aren't in C++ classes: 2521 if (name_type_mask == eFunctionNameTypeMethod || name_type_mask == eFunctionNameTypeBase) 2522 { 2523 const DWARFDebugInfoEntry *decl_ctx_die = GetDeclContextDIEContainingDIE (dwarf_cu, die); 2524 2525 if (decl_ctx_die == nullptr) 2526 return false; 2527 2528 const dw_tag_t decl_ctx_tag = decl_ctx_die->Tag(); 2529 2530 bool is_cxx_method = (decl_ctx_tag == DW_TAG_structure_type) || (decl_ctx_tag == DW_TAG_class_type); 2531 2532 if (name_type_mask == eFunctionNameTypeMethod) 2533 { 2534 if (is_cxx_method == false) 2535 return false; 2536 } 2537 2538 if (name_type_mask == eFunctionNameTypeBase) 2539 { 2540 if (is_cxx_method == true) 2541 return false; 2542 } 2543 } 2544 2545 // Now we need to check whether the name we got back for this type matches the extra specifications 2546 // that were in the name we're looking up: 2547 if (base_name_start != partial_name || *base_name_end != '\0') 2548 { 2549 // First see if the stuff to the left matches the full name. To do that let's see if 2550 // we can pull out the mips linkage name attribute: 2551 2552 Mangled best_name; 2553 DWARFDebugInfoEntry::Attributes attributes; 2554 DWARFFormValue form_value; 2555 die->GetAttributes(this, dwarf_cu, DWARFFormValue::FixedFormSizes(), attributes); 2556 uint32_t idx = attributes.FindAttributeIndex(DW_AT_MIPS_linkage_name); 2557 if (idx == UINT32_MAX) 2558 idx = attributes.FindAttributeIndex(DW_AT_linkage_name); 2559 if (idx != UINT32_MAX) 2560 { 2561 if (attributes.ExtractFormValueAtIndex(this, idx, form_value)) 2562 { 2563 const char *mangled_name = form_value.AsCString(this); 2564 if (mangled_name) 2565 best_name.SetValue (ConstString(mangled_name), true); 2566 } 2567 } 2568 2569 if (!best_name) 2570 { 2571 idx = attributes.FindAttributeIndex(DW_AT_name); 2572 if (idx != UINT32_MAX && attributes.ExtractFormValueAtIndex(this, idx, form_value)) 2573 { 2574 const char *name = form_value.AsCString(this); 2575 best_name.SetValue (ConstString(name), false); 2576 } 2577 } 2578 2579 const LanguageType cu_language = const_cast<DWARFCompileUnit *>(dwarf_cu)->GetLanguageType(); 2580 if (best_name.GetDemangledName(cu_language)) 2581 { 2582 const char *demangled = best_name.GetDemangledName(cu_language).GetCString(); 2583 if (demangled) 2584 { 2585 std::string name_no_parens(partial_name, base_name_end - partial_name); 2586 const char *partial_in_demangled = strstr (demangled, name_no_parens.c_str()); 2587 if (partial_in_demangled == NULL) 2588 return false; 2589 else 2590 { 2591 // Sort out the case where our name is something like "Process::Destroy" and the match is 2592 // "SBProcess::Destroy" - that shouldn't be a match. We should really always match on 2593 // namespace boundaries... 2594 2595 if (partial_name[0] == ':' && partial_name[1] == ':') 2596 { 2597 // The partial name was already on a namespace boundary so all matches are good. 2598 return true; 2599 } 2600 else if (partial_in_demangled == demangled) 2601 { 2602 // They both start the same, so this is an good match. 2603 return true; 2604 } 2605 else 2606 { 2607 if (partial_in_demangled - demangled == 1) 2608 { 2609 // Only one character difference, can't be a namespace boundary... 2610 return false; 2611 } 2612 else if (*(partial_in_demangled - 1) == ':' && *(partial_in_demangled - 2) == ':') 2613 { 2614 // We are on a namespace boundary, so this is also good. 2615 return true; 2616 } 2617 else 2618 return false; 2619 } 2620 } 2621 } 2622 } 2623 } 2624 2625 return true; 2626 } 2627 2628 bool 2629 SymbolFileDWARF::DIEInDeclContext (const CompilerDeclContext *decl_ctx, 2630 DWARFCompileUnit *cu, 2631 const DWARFDebugInfoEntry *die) 2632 { 2633 // If we have no parent decl context to match this DIE matches, and if the parent 2634 // decl context isn't valid, we aren't trying to look for any particular decl 2635 // context so any die matches. 2636 if (decl_ctx == nullptr || !decl_ctx->IsValid()) 2637 return true; 2638 2639 if (cu && die) 2640 { 2641 TypeSystem *type_system = GetTypeSystemForLanguage(cu->GetLanguageType()); 2642 2643 if (type_system) 2644 { 2645 CompilerDeclContext actual_decl_ctx = type_system->GetDeclContextContainingUIDFromDWARF (this, cu, die); 2646 if (actual_decl_ctx) 2647 return actual_decl_ctx == *decl_ctx; 2648 } 2649 } 2650 return false; 2651 } 2652 2653 uint32_t 2654 SymbolFileDWARF::FindFunctions (const ConstString &name, 2655 const CompilerDeclContext *parent_decl_ctx, 2656 uint32_t name_type_mask, 2657 bool include_inlines, 2658 bool append, 2659 SymbolContextList& sc_list) 2660 { 2661 Timer scoped_timer (__PRETTY_FUNCTION__, 2662 "SymbolFileDWARF::FindFunctions (name = '%s')", 2663 name.AsCString()); 2664 2665 // eFunctionNameTypeAuto should be pre-resolved by a call to Module::PrepareForFunctionNameLookup() 2666 assert ((name_type_mask & eFunctionNameTypeAuto) == 0); 2667 2668 Log *log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2669 2670 if (log) 2671 { 2672 GetObjectFile()->GetModule()->LogMessage (log, 2673 "SymbolFileDWARF::FindFunctions (name=\"%s\", name_type_mask=0x%x, append=%u, sc_list)", 2674 name.GetCString(), 2675 name_type_mask, 2676 append); 2677 } 2678 2679 // If we aren't appending the results to this list, then clear the list 2680 if (!append) 2681 sc_list.Clear(); 2682 2683 if (!DeclContextMatchesThisSymbolFile(parent_decl_ctx)) 2684 return 0; 2685 2686 // If name is empty then we won't find anything. 2687 if (name.IsEmpty()) 2688 return 0; 2689 2690 // Remember how many sc_list are in the list before we search in case 2691 // we are appending the results to a variable list. 2692 2693 const char *name_cstr = name.GetCString(); 2694 2695 const uint32_t original_size = sc_list.GetSize(); 2696 2697 DWARFDebugInfo* info = DebugInfo(); 2698 if (info == NULL) 2699 return 0; 2700 2701 DWARFCompileUnit *dwarf_cu = NULL; 2702 std::set<const DWARFDebugInfoEntry *> resolved_dies; 2703 if (m_using_apple_tables) 2704 { 2705 if (m_apple_names_ap.get()) 2706 { 2707 2708 DIEArray die_offsets; 2709 2710 uint32_t num_matches = 0; 2711 2712 if (name_type_mask & eFunctionNameTypeFull) 2713 { 2714 // If they asked for the full name, match what they typed. At some point we may 2715 // want to canonicalize this (strip double spaces, etc. For now, we just add all the 2716 // dies that we find by exact match. 2717 num_matches = m_apple_names_ap->FindByName (name_cstr, die_offsets); 2718 for (uint32_t i = 0; i < num_matches; i++) 2719 { 2720 const dw_offset_t die_offset = die_offsets[i]; 2721 const DWARFDebugInfoEntry *die = info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2722 if (die) 2723 { 2724 if (!DIEInDeclContext(parent_decl_ctx, dwarf_cu, die)) 2725 continue; // The containing decl contexts don't match 2726 2727 if (resolved_dies.find(die) == resolved_dies.end()) 2728 { 2729 if (ResolveFunction (dwarf_cu, die, include_inlines, sc_list)) 2730 resolved_dies.insert(die); 2731 } 2732 } 2733 else 2734 { 2735 GetObjectFile()->GetModule()->ReportErrorIfModifyDetected ("the DWARF debug information has been modified (.apple_names accelerator table had bad die 0x%8.8x for '%s')", 2736 die_offset, name_cstr); 2737 } 2738 } 2739 } 2740 2741 if (name_type_mask & eFunctionNameTypeSelector) 2742 { 2743 if (parent_decl_ctx && parent_decl_ctx->IsValid()) 2744 return 0; // no selectors in namespaces 2745 2746 num_matches = m_apple_names_ap->FindByName (name_cstr, die_offsets); 2747 // Now make sure these are actually ObjC methods. In this case we can simply look up the name, 2748 // and if it is an ObjC method name, we're good. 2749 2750 for (uint32_t i = 0; i < num_matches; i++) 2751 { 2752 const dw_offset_t die_offset = die_offsets[i]; 2753 const DWARFDebugInfoEntry* die = info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2754 if (die) 2755 { 2756 const char *die_name = die->GetName(this, dwarf_cu); 2757 if (ObjCLanguageRuntime::IsPossibleObjCMethodName(die_name)) 2758 { 2759 if (resolved_dies.find(die) == resolved_dies.end()) 2760 { 2761 if (ResolveFunction (dwarf_cu, die, include_inlines, sc_list)) 2762 resolved_dies.insert(die); 2763 } 2764 } 2765 } 2766 else 2767 { 2768 GetObjectFile()->GetModule()->ReportError ("the DWARF debug information has been modified (.apple_names accelerator table had bad die 0x%8.8x for '%s')", 2769 die_offset, name_cstr); 2770 } 2771 } 2772 die_offsets.clear(); 2773 } 2774 2775 if (((name_type_mask & eFunctionNameTypeMethod) && !parent_decl_ctx) || name_type_mask & eFunctionNameTypeBase) 2776 { 2777 // The apple_names table stores just the "base name" of C++ methods in the table. So we have to 2778 // extract the base name, look that up, and if there is any other information in the name we were 2779 // passed in we have to post-filter based on that. 2780 2781 // FIXME: Arrange the logic above so that we don't calculate the base name twice: 2782 num_matches = m_apple_names_ap->FindByName (name_cstr, die_offsets); 2783 2784 for (uint32_t i = 0; i < num_matches; i++) 2785 { 2786 const dw_offset_t die_offset = die_offsets[i]; 2787 const DWARFDebugInfoEntry* die = info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2788 if (die) 2789 { 2790 if (!DIEInDeclContext(parent_decl_ctx, dwarf_cu, die)) 2791 continue; // The containing decl contexts don't match 2792 2793 2794 // If we get to here, the die is good, and we should add it: 2795 if (resolved_dies.find(die) == resolved_dies.end()) 2796 if (ResolveFunction (dwarf_cu, die, include_inlines, sc_list)) 2797 { 2798 bool keep_die = true; 2799 if ((name_type_mask & (eFunctionNameTypeBase|eFunctionNameTypeMethod)) != (eFunctionNameTypeBase|eFunctionNameTypeMethod)) 2800 { 2801 // We are looking for either basenames or methods, so we need to 2802 // trim out the ones we won't want by looking at the type 2803 SymbolContext sc; 2804 if (sc_list.GetLastContext(sc)) 2805 { 2806 if (sc.block) 2807 { 2808 // We have an inlined function 2809 } 2810 else if (sc.function) 2811 { 2812 Type *type = sc.function->GetType(); 2813 2814 if (type) 2815 { 2816 CompilerDeclContext decl_ctx = GetDeclContextContainingUID (type->GetID()); 2817 if (decl_ctx.IsStructUnionOrClass()) 2818 { 2819 if (name_type_mask & eFunctionNameTypeBase) 2820 { 2821 sc_list.RemoveContextAtIndex(sc_list.GetSize()-1); 2822 keep_die = false; 2823 } 2824 } 2825 else 2826 { 2827 if (name_type_mask & eFunctionNameTypeMethod) 2828 { 2829 sc_list.RemoveContextAtIndex(sc_list.GetSize()-1); 2830 keep_die = false; 2831 } 2832 } 2833 } 2834 else 2835 { 2836 GetObjectFile()->GetModule()->ReportWarning ("function at die offset 0x%8.8x had no function type", 2837 die_offset); 2838 } 2839 } 2840 } 2841 } 2842 if (keep_die) 2843 resolved_dies.insert(die); 2844 } 2845 } 2846 else 2847 { 2848 GetObjectFile()->GetModule()->ReportErrorIfModifyDetected ("the DWARF debug information has been modified (.apple_names accelerator table had bad die 0x%8.8x for '%s')", 2849 die_offset, name_cstr); 2850 } 2851 } 2852 die_offsets.clear(); 2853 } 2854 } 2855 } 2856 else 2857 { 2858 2859 // Index the DWARF if we haven't already 2860 if (!m_indexed) 2861 Index (); 2862 2863 if (name_type_mask & eFunctionNameTypeFull) 2864 { 2865 FindFunctions (name, m_function_fullname_index, include_inlines, sc_list); 2866 2867 // FIXME Temporary workaround for global/anonymous namespace 2868 // functions debugging FreeBSD and Linux binaries. 2869 // If we didn't find any functions in the global namespace try 2870 // looking in the basename index but ignore any returned 2871 // functions that have a namespace but keep functions which 2872 // have an anonymous namespace 2873 // TODO: The arch in the object file isn't correct for MSVC 2874 // binaries on windows, we should find a way to make it 2875 // correct and handle those symbols as well. 2876 if (sc_list.GetSize() == 0) 2877 { 2878 ArchSpec arch; 2879 if (!parent_decl_ctx && 2880 GetObjectFile()->GetArchitecture(arch) && 2881 (arch.GetTriple().isOSFreeBSD() || arch.GetTriple().isOSLinux() || 2882 arch.GetMachine() == llvm::Triple::hexagon)) 2883 { 2884 SymbolContextList temp_sc_list; 2885 FindFunctions (name, m_function_basename_index, include_inlines, temp_sc_list); 2886 SymbolContext sc; 2887 for (uint32_t i = 0; i < temp_sc_list.GetSize(); i++) 2888 { 2889 if (temp_sc_list.GetContextAtIndex(i, sc)) 2890 { 2891 ConstString mangled_name = sc.GetFunctionName(Mangled::ePreferMangled); 2892 ConstString demangled_name = sc.GetFunctionName(Mangled::ePreferDemangled); 2893 // Mangled names on Linux and FreeBSD are of the form: 2894 // _ZN18function_namespace13function_nameEv. 2895 if (strncmp(mangled_name.GetCString(), "_ZN", 3) || 2896 !strncmp(demangled_name.GetCString(), "(anonymous namespace)", 21)) 2897 { 2898 sc_list.Append(sc); 2899 } 2900 } 2901 } 2902 } 2903 } 2904 } 2905 DIEArray die_offsets; 2906 DWARFCompileUnit *dwarf_cu = NULL; 2907 2908 if (name_type_mask & eFunctionNameTypeBase) 2909 { 2910 uint32_t num_base = m_function_basename_index.Find(name, die_offsets); 2911 for (uint32_t i = 0; i < num_base; i++) 2912 { 2913 const DWARFDebugInfoEntry* die = info->GetDIEPtrWithCompileUnitHint (die_offsets[i], &dwarf_cu); 2914 if (die) 2915 { 2916 if (!DIEInDeclContext(parent_decl_ctx, dwarf_cu, die)) 2917 continue; // The containing decl contexts don't match 2918 2919 // If we get to here, the die is good, and we should add it: 2920 if (resolved_dies.find(die) == resolved_dies.end()) 2921 { 2922 if (ResolveFunction (dwarf_cu, die, include_inlines, sc_list)) 2923 resolved_dies.insert(die); 2924 } 2925 } 2926 } 2927 die_offsets.clear(); 2928 } 2929 2930 if (name_type_mask & eFunctionNameTypeMethod) 2931 { 2932 if (parent_decl_ctx && parent_decl_ctx->IsValid()) 2933 return 0; // no methods in namespaces 2934 2935 uint32_t num_base = m_function_method_index.Find(name, die_offsets); 2936 { 2937 for (uint32_t i = 0; i < num_base; i++) 2938 { 2939 const DWARFDebugInfoEntry* die = info->GetDIEPtrWithCompileUnitHint (die_offsets[i], &dwarf_cu); 2940 if (die) 2941 { 2942 // If we get to here, the die is good, and we should add it: 2943 if (resolved_dies.find(die) == resolved_dies.end()) 2944 { 2945 if (ResolveFunction (dwarf_cu, die, include_inlines, sc_list)) 2946 resolved_dies.insert(die); 2947 } 2948 } 2949 } 2950 } 2951 die_offsets.clear(); 2952 } 2953 2954 if ((name_type_mask & eFunctionNameTypeSelector) && (!parent_decl_ctx || !parent_decl_ctx->IsValid())) 2955 { 2956 FindFunctions (name, m_function_selector_index, include_inlines, sc_list); 2957 } 2958 2959 } 2960 2961 // Return the number of variable that were appended to the list 2962 const uint32_t num_matches = sc_list.GetSize() - original_size; 2963 2964 if (log && num_matches > 0) 2965 { 2966 GetObjectFile()->GetModule()->LogMessage (log, 2967 "SymbolFileDWARF::FindFunctions (name=\"%s\", name_type_mask=0x%x, include_inlines=%d, append=%u, sc_list) => %u", 2968 name.GetCString(), 2969 name_type_mask, 2970 include_inlines, 2971 append, 2972 num_matches); 2973 } 2974 return num_matches; 2975 } 2976 2977 uint32_t 2978 SymbolFileDWARF::FindFunctions(const RegularExpression& regex, bool include_inlines, bool append, SymbolContextList& sc_list) 2979 { 2980 Timer scoped_timer (__PRETTY_FUNCTION__, 2981 "SymbolFileDWARF::FindFunctions (regex = '%s')", 2982 regex.GetText()); 2983 2984 Log *log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2985 2986 if (log) 2987 { 2988 GetObjectFile()->GetModule()->LogMessage (log, 2989 "SymbolFileDWARF::FindFunctions (regex=\"%s\", append=%u, sc_list)", 2990 regex.GetText(), 2991 append); 2992 } 2993 2994 2995 // If we aren't appending the results to this list, then clear the list 2996 if (!append) 2997 sc_list.Clear(); 2998 2999 // Remember how many sc_list are in the list before we search in case 3000 // we are appending the results to a variable list. 3001 uint32_t original_size = sc_list.GetSize(); 3002 3003 if (m_using_apple_tables) 3004 { 3005 if (m_apple_names_ap.get()) 3006 FindFunctions (regex, *m_apple_names_ap, include_inlines, sc_list); 3007 } 3008 else 3009 { 3010 // Index the DWARF if we haven't already 3011 if (!m_indexed) 3012 Index (); 3013 3014 FindFunctions (regex, m_function_basename_index, include_inlines, sc_list); 3015 3016 FindFunctions (regex, m_function_fullname_index, include_inlines, sc_list); 3017 } 3018 3019 // Return the number of variable that were appended to the list 3020 return sc_list.GetSize() - original_size; 3021 } 3022 3023 uint32_t 3024 SymbolFileDWARF::FindTypes (const SymbolContext& sc, 3025 const ConstString &name, 3026 const CompilerDeclContext *parent_decl_ctx, 3027 bool append, 3028 uint32_t max_matches, 3029 TypeList& types) 3030 { 3031 DWARFDebugInfo* info = DebugInfo(); 3032 if (info == NULL) 3033 return 0; 3034 3035 Log *log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 3036 3037 if (log) 3038 { 3039 if (parent_decl_ctx) 3040 GetObjectFile()->GetModule()->LogMessage (log, 3041 "SymbolFileDWARF::FindTypes (sc, name=\"%s\", parent_decl_ctx = %p (\"%s\"), append=%u, max_matches=%u, type_list)", 3042 name.GetCString(), 3043 static_cast<const void*>(parent_decl_ctx), 3044 parent_decl_ctx->GetName().AsCString("<NULL>"), 3045 append, max_matches); 3046 else 3047 GetObjectFile()->GetModule()->LogMessage (log, 3048 "SymbolFileDWARF::FindTypes (sc, name=\"%s\", parent_decl_ctx = NULL, append=%u, max_matches=%u, type_list)", 3049 name.GetCString(), append, 3050 max_matches); 3051 } 3052 3053 // If we aren't appending the results to this list, then clear the list 3054 if (!append) 3055 types.Clear(); 3056 3057 if (!DeclContextMatchesThisSymbolFile(parent_decl_ctx)) 3058 return 0; 3059 3060 DIEArray die_offsets; 3061 3062 if (m_using_apple_tables) 3063 { 3064 if (m_apple_types_ap.get()) 3065 { 3066 const char *name_cstr = name.GetCString(); 3067 m_apple_types_ap->FindByName (name_cstr, die_offsets); 3068 } 3069 } 3070 else 3071 { 3072 if (!m_indexed) 3073 Index (); 3074 3075 m_type_index.Find (name, die_offsets); 3076 } 3077 3078 const size_t num_die_matches = die_offsets.size(); 3079 3080 if (num_die_matches) 3081 { 3082 const uint32_t initial_types_size = types.GetSize(); 3083 DWARFCompileUnit* dwarf_cu = NULL; 3084 const DWARFDebugInfoEntry* die = NULL; 3085 DWARFDebugInfo* debug_info = DebugInfo(); 3086 for (size_t i=0; i<num_die_matches; ++i) 3087 { 3088 const dw_offset_t die_offset = die_offsets[i]; 3089 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 3090 3091 if (die) 3092 { 3093 if (!DIEInDeclContext(parent_decl_ctx, dwarf_cu, die)) 3094 continue; // The containing decl contexts don't match 3095 3096 Type *matching_type = ResolveType (dwarf_cu, die); 3097 if (matching_type) 3098 { 3099 // We found a type pointer, now find the shared pointer form our type list 3100 types.InsertUnique (matching_type->shared_from_this()); 3101 if (types.GetSize() >= max_matches) 3102 break; 3103 } 3104 } 3105 else 3106 { 3107 if (m_using_apple_tables) 3108 { 3109 GetObjectFile()->GetModule()->ReportErrorIfModifyDetected ("the DWARF debug information has been modified (.apple_types accelerator table had bad die 0x%8.8x for '%s')\n", 3110 die_offset, name.GetCString()); 3111 } 3112 } 3113 3114 } 3115 const uint32_t num_matches = types.GetSize() - initial_types_size; 3116 if (log && num_matches) 3117 { 3118 if (parent_decl_ctx) 3119 { 3120 GetObjectFile()->GetModule()->LogMessage (log, 3121 "SymbolFileDWARF::FindTypes (sc, name=\"%s\", parent_decl_ctx = %p (\"%s\"), append=%u, max_matches=%u, type_list) => %u", 3122 name.GetCString(), 3123 static_cast<const void*>(parent_decl_ctx), 3124 parent_decl_ctx->GetName().AsCString("<NULL>"), 3125 append, max_matches, 3126 num_matches); 3127 } 3128 else 3129 { 3130 GetObjectFile()->GetModule()->LogMessage (log, 3131 "SymbolFileDWARF::FindTypes (sc, name=\"%s\", parent_decl_ctx = NULL, append=%u, max_matches=%u, type_list) => %u", 3132 name.GetCString(), 3133 append, max_matches, 3134 num_matches); 3135 } 3136 } 3137 return num_matches; 3138 } 3139 return 0; 3140 } 3141 3142 3143 CompilerDeclContext 3144 SymbolFileDWARF::FindNamespace (const SymbolContext& sc, 3145 const ConstString &name, 3146 const CompilerDeclContext *parent_decl_ctx) 3147 { 3148 Log *log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 3149 3150 if (log) 3151 { 3152 GetObjectFile()->GetModule()->LogMessage (log, 3153 "SymbolFileDWARF::FindNamespace (sc, name=\"%s\")", 3154 name.GetCString()); 3155 } 3156 3157 CompilerDeclContext namespace_decl_ctx; 3158 3159 if (!DeclContextMatchesThisSymbolFile(parent_decl_ctx)) 3160 return namespace_decl_ctx; 3161 3162 3163 DWARFDebugInfo* info = DebugInfo(); 3164 if (info) 3165 { 3166 DIEArray die_offsets; 3167 3168 // Index if we already haven't to make sure the compile units 3169 // get indexed and make their global DIE index list 3170 if (m_using_apple_tables) 3171 { 3172 if (m_apple_namespaces_ap.get()) 3173 { 3174 const char *name_cstr = name.GetCString(); 3175 m_apple_namespaces_ap->FindByName (name_cstr, die_offsets); 3176 } 3177 } 3178 else 3179 { 3180 if (!m_indexed) 3181 Index (); 3182 3183 m_namespace_index.Find (name, die_offsets); 3184 } 3185 3186 DWARFCompileUnit* dwarf_cu = NULL; 3187 const DWARFDebugInfoEntry* die = NULL; 3188 const size_t num_matches = die_offsets.size(); 3189 if (num_matches) 3190 { 3191 DWARFDebugInfo* debug_info = DebugInfo(); 3192 for (size_t i=0; i<num_matches; ++i) 3193 { 3194 const dw_offset_t die_offset = die_offsets[i]; 3195 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 3196 3197 if (die) 3198 { 3199 if (!DIEInDeclContext(parent_decl_ctx, dwarf_cu, die)) 3200 continue; // The containing decl contexts don't match 3201 3202 TypeSystem *type_system = GetTypeSystemForLanguage(dwarf_cu->GetLanguageType()); 3203 3204 if (type_system) 3205 { 3206 namespace_decl_ctx = type_system->GetDeclContextForUIDFromDWARF(this, dwarf_cu, die); 3207 if (namespace_decl_ctx) 3208 break; 3209 } 3210 } 3211 else 3212 { 3213 if (m_using_apple_tables) 3214 { 3215 GetObjectFile()->GetModule()->ReportErrorIfModifyDetected ("the DWARF debug information has been modified (.apple_namespaces accelerator table had bad die 0x%8.8x for '%s')\n", 3216 die_offset, name.GetCString()); 3217 } 3218 } 3219 3220 } 3221 } 3222 } 3223 if (log && namespace_decl_ctx) 3224 { 3225 GetObjectFile()->GetModule()->LogMessage (log, 3226 "SymbolFileDWARF::FindNamespace (sc, name=\"%s\") => CompilerDeclContext(%p/%p) \"%s\"", 3227 name.GetCString(), 3228 static_cast<const void*>(namespace_decl_ctx.GetTypeSystem()), 3229 static_cast<const void*>(namespace_decl_ctx.GetOpaqueDeclContext()), 3230 namespace_decl_ctx.GetName().AsCString("<NULL>")); 3231 } 3232 3233 return namespace_decl_ctx; 3234 } 3235 3236 uint32_t 3237 SymbolFileDWARF::FindTypes(std::vector<dw_offset_t> die_offsets, uint32_t max_matches, TypeList& types) 3238 { 3239 // Remember how many sc_list are in the list before we search in case 3240 // we are appending the results to a variable list. 3241 uint32_t original_size = types.GetSize(); 3242 3243 const uint32_t num_die_offsets = die_offsets.size(); 3244 // Parse all of the types we found from the pubtypes matches 3245 uint32_t i; 3246 uint32_t num_matches = 0; 3247 for (i = 0; i < num_die_offsets; ++i) 3248 { 3249 Type *matching_type = ResolveTypeUID (die_offsets[i]); 3250 if (matching_type) 3251 { 3252 // We found a type pointer, now find the shared pointer form our type list 3253 types.InsertUnique (matching_type->shared_from_this()); 3254 ++num_matches; 3255 if (num_matches >= max_matches) 3256 break; 3257 } 3258 } 3259 3260 // Return the number of variable that were appended to the list 3261 return types.GetSize() - original_size; 3262 } 3263 3264 3265 TypeSP 3266 SymbolFileDWARF::GetTypeForDIE (DWARFCompileUnit *dwarf_cu, const DWARFDebugInfoEntry* die) 3267 { 3268 TypeSP type_sp; 3269 if (die != NULL) 3270 { 3271 assert(dwarf_cu != NULL); 3272 Type *type_ptr = m_die_to_type.lookup (die); 3273 if (type_ptr == NULL) 3274 { 3275 CompileUnit* lldb_cu = GetCompUnitForDWARFCompUnit(dwarf_cu); 3276 assert (lldb_cu); 3277 SymbolContext sc(lldb_cu); 3278 type_sp = ParseType(sc, dwarf_cu, die, NULL); 3279 } 3280 else if (type_ptr != DIE_IS_BEING_PARSED) 3281 { 3282 // Grab the existing type from the master types lists 3283 type_sp = type_ptr->shared_from_this(); 3284 } 3285 3286 } 3287 return type_sp; 3288 } 3289 3290 3291 const DWARFDebugInfoEntry * 3292 SymbolFileDWARF::GetDeclContextDIEContainingDIE (const DWARFCompileUnit *cu, const DWARFDebugInfoEntry *die) 3293 { 3294 if (cu && die) 3295 { 3296 const DWARFDebugInfoEntry * const decl_die = die; 3297 3298 while (die != NULL) 3299 { 3300 // If this is the original DIE that we are searching for a declaration 3301 // for, then don't look in the cache as we don't want our own decl 3302 // context to be our decl context... 3303 if (decl_die != die) 3304 { 3305 switch (die->Tag()) 3306 { 3307 case DW_TAG_compile_unit: 3308 case DW_TAG_namespace: 3309 case DW_TAG_structure_type: 3310 case DW_TAG_union_type: 3311 case DW_TAG_class_type: 3312 return die; 3313 3314 default: 3315 break; 3316 } 3317 } 3318 3319 dw_offset_t die_offset = die->GetAttributeValueAsReference(this, cu, DW_AT_specification, DW_INVALID_OFFSET); 3320 if (die_offset != DW_INVALID_OFFSET) 3321 { 3322 DWARFCompileUnit *spec_cu = const_cast<DWARFCompileUnit *>(cu); 3323 const DWARFDebugInfoEntry *spec_die = DebugInfo()->GetDIEPtrWithCompileUnitHint (die_offset, &spec_cu); 3324 const DWARFDebugInfoEntry *spec_die_decl_ctx_die = GetDeclContextDIEContainingDIE (spec_cu, spec_die); 3325 if (spec_die_decl_ctx_die) 3326 return spec_die_decl_ctx_die; 3327 } 3328 3329 die_offset = die->GetAttributeValueAsReference(this, cu, DW_AT_abstract_origin, DW_INVALID_OFFSET); 3330 if (die_offset != DW_INVALID_OFFSET) 3331 { 3332 DWARFCompileUnit *abs_cu = const_cast<DWARFCompileUnit *>(cu); 3333 const DWARFDebugInfoEntry *abs_die = DebugInfo()->GetDIEPtrWithCompileUnitHint (die_offset, &abs_cu); 3334 const DWARFDebugInfoEntry *abs_die_decl_ctx_die = GetDeclContextDIEContainingDIE (abs_cu, abs_die); 3335 if (abs_die_decl_ctx_die) 3336 return abs_die_decl_ctx_die; 3337 } 3338 3339 die = die->GetParent(); 3340 } 3341 } 3342 return NULL; 3343 } 3344 3345 3346 Symbol * 3347 SymbolFileDWARF::GetObjCClassSymbol (const ConstString &objc_class_name) 3348 { 3349 Symbol *objc_class_symbol = NULL; 3350 if (m_obj_file) 3351 { 3352 Symtab *symtab = m_obj_file->GetSymtab (); 3353 if (symtab) 3354 { 3355 objc_class_symbol = symtab->FindFirstSymbolWithNameAndType (objc_class_name, 3356 eSymbolTypeObjCClass, 3357 Symtab::eDebugNo, 3358 Symtab::eVisibilityAny); 3359 } 3360 } 3361 return objc_class_symbol; 3362 } 3363 3364 // Some compilers don't emit the DW_AT_APPLE_objc_complete_type attribute. If they don't 3365 // then we can end up looking through all class types for a complete type and never find 3366 // the full definition. We need to know if this attribute is supported, so we determine 3367 // this here and cache th result. We also need to worry about the debug map DWARF file 3368 // if we are doing darwin DWARF in .o file debugging. 3369 bool 3370 SymbolFileDWARF::Supports_DW_AT_APPLE_objc_complete_type (DWARFCompileUnit *cu) 3371 { 3372 if (m_supports_DW_AT_APPLE_objc_complete_type == eLazyBoolCalculate) 3373 { 3374 m_supports_DW_AT_APPLE_objc_complete_type = eLazyBoolNo; 3375 if (cu && cu->Supports_DW_AT_APPLE_objc_complete_type()) 3376 m_supports_DW_AT_APPLE_objc_complete_type = eLazyBoolYes; 3377 else 3378 { 3379 DWARFDebugInfo* debug_info = DebugInfo(); 3380 const uint32_t num_compile_units = GetNumCompileUnits(); 3381 for (uint32_t cu_idx = 0; cu_idx < num_compile_units; ++cu_idx) 3382 { 3383 DWARFCompileUnit* dwarf_cu = debug_info->GetCompileUnitAtIndex(cu_idx); 3384 if (dwarf_cu != cu && dwarf_cu->Supports_DW_AT_APPLE_objc_complete_type()) 3385 { 3386 m_supports_DW_AT_APPLE_objc_complete_type = eLazyBoolYes; 3387 break; 3388 } 3389 } 3390 } 3391 if (m_supports_DW_AT_APPLE_objc_complete_type == eLazyBoolNo && GetDebugMapSymfile ()) 3392 return m_debug_map_symfile->Supports_DW_AT_APPLE_objc_complete_type (this); 3393 } 3394 return m_supports_DW_AT_APPLE_objc_complete_type == eLazyBoolYes; 3395 } 3396 3397 // This function can be used when a DIE is found that is a forward declaration 3398 // DIE and we want to try and find a type that has the complete definition. 3399 TypeSP 3400 SymbolFileDWARF::FindCompleteObjCDefinitionTypeForDIE (const DWARFDebugInfoEntry *die, 3401 const ConstString &type_name, 3402 bool must_be_implementation) 3403 { 3404 3405 TypeSP type_sp; 3406 3407 if (!type_name || (must_be_implementation && !GetObjCClassSymbol (type_name))) 3408 return type_sp; 3409 3410 DIEArray die_offsets; 3411 3412 if (m_using_apple_tables) 3413 { 3414 if (m_apple_types_ap.get()) 3415 { 3416 const char *name_cstr = type_name.GetCString(); 3417 m_apple_types_ap->FindCompleteObjCClassByName (name_cstr, die_offsets, must_be_implementation); 3418 } 3419 } 3420 else 3421 { 3422 if (!m_indexed) 3423 Index (); 3424 3425 m_type_index.Find (type_name, die_offsets); 3426 } 3427 3428 const size_t num_matches = die_offsets.size(); 3429 3430 DWARFCompileUnit* type_cu = NULL; 3431 const DWARFDebugInfoEntry* type_die = NULL; 3432 if (num_matches) 3433 { 3434 DWARFDebugInfo* debug_info = DebugInfo(); 3435 for (size_t i=0; i<num_matches; ++i) 3436 { 3437 const dw_offset_t die_offset = die_offsets[i]; 3438 type_die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &type_cu); 3439 3440 if (type_die) 3441 { 3442 bool try_resolving_type = false; 3443 3444 // Don't try and resolve the DIE we are looking for with the DIE itself! 3445 if (type_die != die) 3446 { 3447 switch (type_die->Tag()) 3448 { 3449 case DW_TAG_class_type: 3450 case DW_TAG_structure_type: 3451 try_resolving_type = true; 3452 break; 3453 default: 3454 break; 3455 } 3456 } 3457 3458 if (try_resolving_type) 3459 { 3460 if (must_be_implementation && type_cu->Supports_DW_AT_APPLE_objc_complete_type()) 3461 try_resolving_type = type_die->GetAttributeValueAsUnsigned (this, type_cu, DW_AT_APPLE_objc_complete_type, 0); 3462 3463 if (try_resolving_type) 3464 { 3465 Type *resolved_type = ResolveType (type_cu, type_die, false); 3466 if (resolved_type && resolved_type != DIE_IS_BEING_PARSED) 3467 { 3468 DEBUG_PRINTF ("resolved 0x%8.8" PRIx64 " from %s to 0x%8.8" PRIx64 " (cu 0x%8.8" PRIx64 ")\n", 3469 MakeUserID(die->GetOffset()), 3470 m_obj_file->GetFileSpec().GetFilename().AsCString("<Unknown>"), 3471 MakeUserID(type_die->GetOffset()), 3472 MakeUserID(type_cu->GetOffset())); 3473 3474 if (die) 3475 m_die_to_type[die] = resolved_type; 3476 type_sp = resolved_type->shared_from_this(); 3477 break; 3478 } 3479 } 3480 } 3481 } 3482 else 3483 { 3484 if (m_using_apple_tables) 3485 { 3486 GetObjectFile()->GetModule()->ReportErrorIfModifyDetected ("the DWARF debug information has been modified (.apple_types accelerator table had bad die 0x%8.8x for '%s')\n", 3487 die_offset, type_name.GetCString()); 3488 } 3489 } 3490 3491 } 3492 } 3493 return type_sp; 3494 } 3495 3496 3497 //---------------------------------------------------------------------- 3498 // This function helps to ensure that the declaration contexts match for 3499 // two different DIEs. Often times debug information will refer to a 3500 // forward declaration of a type (the equivalent of "struct my_struct;". 3501 // There will often be a declaration of that type elsewhere that has the 3502 // full definition. When we go looking for the full type "my_struct", we 3503 // will find one or more matches in the accelerator tables and we will 3504 // then need to make sure the type was in the same declaration context 3505 // as the original DIE. This function can efficiently compare two DIEs 3506 // and will return true when the declaration context matches, and false 3507 // when they don't. 3508 //---------------------------------------------------------------------- 3509 bool 3510 SymbolFileDWARF::DIEDeclContextsMatch (DWARFCompileUnit* cu1, const DWARFDebugInfoEntry *die1, 3511 DWARFCompileUnit* cu2, const DWARFDebugInfoEntry *die2) 3512 { 3513 if (die1 == die2) 3514 return true; 3515 3516 #if defined (LLDB_CONFIGURATION_DEBUG) 3517 // You can't and shouldn't call this function with a compile unit from 3518 // two different SymbolFileDWARF instances. 3519 assert (DebugInfo()->ContainsCompileUnit (cu1)); 3520 assert (DebugInfo()->ContainsCompileUnit (cu2)); 3521 #endif 3522 3523 DWARFDIECollection decl_ctx_1; 3524 DWARFDIECollection decl_ctx_2; 3525 //The declaration DIE stack is a stack of the declaration context 3526 // DIEs all the way back to the compile unit. If a type "T" is 3527 // declared inside a class "B", and class "B" is declared inside 3528 // a class "A" and class "A" is in a namespace "lldb", and the 3529 // namespace is in a compile unit, there will be a stack of DIEs: 3530 // 3531 // [0] DW_TAG_class_type for "B" 3532 // [1] DW_TAG_class_type for "A" 3533 // [2] DW_TAG_namespace for "lldb" 3534 // [3] DW_TAG_compile_unit for the source file. 3535 // 3536 // We grab both contexts and make sure that everything matches 3537 // all the way back to the compiler unit. 3538 3539 // First lets grab the decl contexts for both DIEs 3540 die1->GetDeclContextDIEs (this, cu1, decl_ctx_1); 3541 die2->GetDeclContextDIEs (this, cu2, decl_ctx_2); 3542 // Make sure the context arrays have the same size, otherwise 3543 // we are done 3544 const size_t count1 = decl_ctx_1.Size(); 3545 const size_t count2 = decl_ctx_2.Size(); 3546 if (count1 != count2) 3547 return false; 3548 3549 // Make sure the DW_TAG values match all the way back up the 3550 // compile unit. If they don't, then we are done. 3551 const DWARFDebugInfoEntry *decl_ctx_die1; 3552 const DWARFDebugInfoEntry *decl_ctx_die2; 3553 size_t i; 3554 for (i=0; i<count1; i++) 3555 { 3556 decl_ctx_die1 = decl_ctx_1.GetDIEPtrAtIndex (i); 3557 decl_ctx_die2 = decl_ctx_2.GetDIEPtrAtIndex (i); 3558 if (decl_ctx_die1->Tag() != decl_ctx_die2->Tag()) 3559 return false; 3560 } 3561 #if defined LLDB_CONFIGURATION_DEBUG 3562 3563 // Make sure the top item in the decl context die array is always 3564 // DW_TAG_compile_unit. If it isn't then something went wrong in 3565 // the DWARFDebugInfoEntry::GetDeclContextDIEs() function... 3566 assert (decl_ctx_1.GetDIEPtrAtIndex (count1 - 1)->Tag() == DW_TAG_compile_unit); 3567 3568 #endif 3569 // Always skip the compile unit when comparing by only iterating up to 3570 // "count - 1". Here we compare the names as we go. 3571 for (i=0; i<count1 - 1; i++) 3572 { 3573 decl_ctx_die1 = decl_ctx_1.GetDIEPtrAtIndex (i); 3574 decl_ctx_die2 = decl_ctx_2.GetDIEPtrAtIndex (i); 3575 const char *name1 = decl_ctx_die1->GetName(this, cu1); 3576 const char *name2 = decl_ctx_die2->GetName(this, cu2); 3577 // If the string was from a DW_FORM_strp, then the pointer will often 3578 // be the same! 3579 if (name1 == name2) 3580 continue; 3581 3582 // Name pointers are not equal, so only compare the strings 3583 // if both are not NULL. 3584 if (name1 && name2) 3585 { 3586 // If the strings don't compare, we are done... 3587 if (strcmp(name1, name2) != 0) 3588 return false; 3589 } 3590 else 3591 { 3592 // One name was NULL while the other wasn't 3593 return false; 3594 } 3595 } 3596 // We made it through all of the checks and the declaration contexts 3597 // are equal. 3598 return true; 3599 } 3600 3601 3602 TypeSP 3603 SymbolFileDWARF::FindDefinitionTypeForDWARFDeclContext (const DWARFDeclContext &dwarf_decl_ctx) 3604 { 3605 TypeSP type_sp; 3606 3607 const uint32_t dwarf_decl_ctx_count = dwarf_decl_ctx.GetSize(); 3608 if (dwarf_decl_ctx_count > 0) 3609 { 3610 const ConstString type_name(dwarf_decl_ctx[0].name); 3611 const dw_tag_t tag = dwarf_decl_ctx[0].tag; 3612 3613 if (type_name) 3614 { 3615 Log *log (LogChannelDWARF::GetLogIfAny(DWARF_LOG_TYPE_COMPLETION|DWARF_LOG_LOOKUPS)); 3616 if (log) 3617 { 3618 GetObjectFile()->GetModule()->LogMessage (log, 3619 "SymbolFileDWARF::FindDefinitionTypeForDWARFDeclContext(tag=%s, qualified-name='%s')", 3620 DW_TAG_value_to_name(dwarf_decl_ctx[0].tag), 3621 dwarf_decl_ctx.GetQualifiedName()); 3622 } 3623 3624 DIEArray die_offsets; 3625 3626 if (m_using_apple_tables) 3627 { 3628 if (m_apple_types_ap.get()) 3629 { 3630 const bool has_tag = m_apple_types_ap->GetHeader().header_data.ContainsAtom (DWARFMappedHash::eAtomTypeTag); 3631 const bool has_qualified_name_hash = m_apple_types_ap->GetHeader().header_data.ContainsAtom (DWARFMappedHash::eAtomTypeQualNameHash); 3632 if (has_tag && has_qualified_name_hash) 3633 { 3634 const char *qualified_name = dwarf_decl_ctx.GetQualifiedName(); 3635 const uint32_t qualified_name_hash = MappedHash::HashStringUsingDJB (qualified_name); 3636 if (log) 3637 GetObjectFile()->GetModule()->LogMessage (log,"FindByNameAndTagAndQualifiedNameHash()"); 3638 m_apple_types_ap->FindByNameAndTagAndQualifiedNameHash (type_name.GetCString(), tag, qualified_name_hash, die_offsets); 3639 } 3640 else if (has_tag) 3641 { 3642 if (log) 3643 GetObjectFile()->GetModule()->LogMessage (log,"FindByNameAndTag()"); 3644 m_apple_types_ap->FindByNameAndTag (type_name.GetCString(), tag, die_offsets); 3645 } 3646 else 3647 { 3648 m_apple_types_ap->FindByName (type_name.GetCString(), die_offsets); 3649 } 3650 } 3651 } 3652 else 3653 { 3654 if (!m_indexed) 3655 Index (); 3656 3657 m_type_index.Find (type_name, die_offsets); 3658 } 3659 3660 const size_t num_matches = die_offsets.size(); 3661 3662 3663 DWARFCompileUnit* type_cu = NULL; 3664 const DWARFDebugInfoEntry* type_die = NULL; 3665 if (num_matches) 3666 { 3667 DWARFDebugInfo* debug_info = DebugInfo(); 3668 for (size_t i=0; i<num_matches; ++i) 3669 { 3670 const dw_offset_t die_offset = die_offsets[i]; 3671 type_die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &type_cu); 3672 3673 if (type_die) 3674 { 3675 bool try_resolving_type = false; 3676 3677 // Don't try and resolve the DIE we are looking for with the DIE itself! 3678 const dw_tag_t type_tag = type_die->Tag(); 3679 // Make sure the tags match 3680 if (type_tag == tag) 3681 { 3682 // The tags match, lets try resolving this type 3683 try_resolving_type = true; 3684 } 3685 else 3686 { 3687 // The tags don't match, but we need to watch our for a 3688 // forward declaration for a struct and ("struct foo") 3689 // ends up being a class ("class foo { ... };") or 3690 // vice versa. 3691 switch (type_tag) 3692 { 3693 case DW_TAG_class_type: 3694 // We had a "class foo", see if we ended up with a "struct foo { ... };" 3695 try_resolving_type = (tag == DW_TAG_structure_type); 3696 break; 3697 case DW_TAG_structure_type: 3698 // We had a "struct foo", see if we ended up with a "class foo { ... };" 3699 try_resolving_type = (tag == DW_TAG_class_type); 3700 break; 3701 default: 3702 // Tags don't match, don't event try to resolve 3703 // using this type whose name matches.... 3704 break; 3705 } 3706 } 3707 3708 if (try_resolving_type) 3709 { 3710 DWARFDeclContext type_dwarf_decl_ctx; 3711 type_die->GetDWARFDeclContext (this, type_cu, type_dwarf_decl_ctx); 3712 3713 if (log) 3714 { 3715 GetObjectFile()->GetModule()->LogMessage (log, 3716 "SymbolFileDWARF::FindDefinitionTypeForDWARFDeclContext(tag=%s, qualified-name='%s') trying die=0x%8.8x (%s)", 3717 DW_TAG_value_to_name(dwarf_decl_ctx[0].tag), 3718 dwarf_decl_ctx.GetQualifiedName(), 3719 type_die->GetOffset(), 3720 type_dwarf_decl_ctx.GetQualifiedName()); 3721 } 3722 3723 // Make sure the decl contexts match all the way up 3724 if (dwarf_decl_ctx == type_dwarf_decl_ctx) 3725 { 3726 Type *resolved_type = ResolveType (type_cu, type_die, false); 3727 if (resolved_type && resolved_type != DIE_IS_BEING_PARSED) 3728 { 3729 type_sp = resolved_type->shared_from_this(); 3730 break; 3731 } 3732 } 3733 } 3734 else 3735 { 3736 if (log) 3737 { 3738 std::string qualified_name; 3739 type_die->GetQualifiedName(this, type_cu, qualified_name); 3740 GetObjectFile()->GetModule()->LogMessage (log, 3741 "SymbolFileDWARF::FindDefinitionTypeForDWARFDeclContext(tag=%s, qualified-name='%s') ignoring die=0x%8.8x (%s)", 3742 DW_TAG_value_to_name(dwarf_decl_ctx[0].tag), 3743 dwarf_decl_ctx.GetQualifiedName(), 3744 type_die->GetOffset(), 3745 qualified_name.c_str()); 3746 } 3747 } 3748 } 3749 else 3750 { 3751 if (m_using_apple_tables) 3752 { 3753 GetObjectFile()->GetModule()->ReportErrorIfModifyDetected ("the DWARF debug information has been modified (.apple_types accelerator table had bad die 0x%8.8x for '%s')\n", 3754 die_offset, type_name.GetCString()); 3755 } 3756 } 3757 3758 } 3759 } 3760 } 3761 } 3762 return type_sp; 3763 } 3764 3765 TypeSP 3766 SymbolFileDWARF::ParseType (const SymbolContext& sc, DWARFCompileUnit* dwarf_cu, const DWARFDebugInfoEntry *die, bool *type_is_new_ptr) 3767 { 3768 TypeSP type_sp; 3769 3770 TypeSystem *type_system = GetTypeSystemForLanguage(dwarf_cu->GetLanguageType()); 3771 3772 if (type_system) 3773 { 3774 Log *log = LogChannelDWARF::GetLogIfAll(DWARF_LOG_DEBUG_INFO); 3775 type_sp = type_system->ParseTypeFromDWARF (sc, this, dwarf_cu, die, log, type_is_new_ptr); 3776 if (type_sp) 3777 { 3778 TypeList* type_list = GetTypeList(); 3779 if (type_list) 3780 type_list->Insert(type_sp); 3781 } 3782 } 3783 3784 return type_sp; 3785 } 3786 3787 size_t 3788 SymbolFileDWARF::ParseTypes 3789 ( 3790 const SymbolContext& sc, 3791 DWARFCompileUnit* dwarf_cu, 3792 const DWARFDebugInfoEntry *die, 3793 bool parse_siblings, 3794 bool parse_children 3795 ) 3796 { 3797 size_t types_added = 0; 3798 while (die != NULL) 3799 { 3800 bool type_is_new = false; 3801 if (ParseType(sc, dwarf_cu, die, &type_is_new).get()) 3802 { 3803 if (type_is_new) 3804 ++types_added; 3805 } 3806 3807 if (parse_children && die->HasChildren()) 3808 { 3809 if (die->Tag() == DW_TAG_subprogram) 3810 { 3811 SymbolContext child_sc(sc); 3812 child_sc.function = sc.comp_unit->FindFunctionByUID(MakeUserID(die->GetOffset())).get(); 3813 types_added += ParseTypes(child_sc, dwarf_cu, die->GetFirstChild(), true, true); 3814 } 3815 else 3816 types_added += ParseTypes(sc, dwarf_cu, die->GetFirstChild(), true, true); 3817 } 3818 3819 if (parse_siblings) 3820 die = die->GetSibling(); 3821 else 3822 die = NULL; 3823 } 3824 return types_added; 3825 } 3826 3827 3828 size_t 3829 SymbolFileDWARF::ParseFunctionBlocks (const SymbolContext &sc) 3830 { 3831 assert(sc.comp_unit && sc.function); 3832 size_t functions_added = 0; 3833 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnit(sc.comp_unit); 3834 if (dwarf_cu) 3835 { 3836 dw_offset_t function_die_offset = sc.function->GetID(); 3837 const DWARFDebugInfoEntry *function_die = dwarf_cu->GetDIEPtr(function_die_offset); 3838 if (function_die) 3839 { 3840 ParseFunctionBlocks(sc, &sc.function->GetBlock (false), dwarf_cu, function_die, LLDB_INVALID_ADDRESS, 0); 3841 } 3842 } 3843 3844 return functions_added; 3845 } 3846 3847 3848 size_t 3849 SymbolFileDWARF::ParseTypes (const SymbolContext &sc) 3850 { 3851 // At least a compile unit must be valid 3852 assert(sc.comp_unit); 3853 size_t types_added = 0; 3854 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnit(sc.comp_unit); 3855 if (dwarf_cu) 3856 { 3857 if (sc.function) 3858 { 3859 dw_offset_t function_die_offset = sc.function->GetID(); 3860 const DWARFDebugInfoEntry *func_die = dwarf_cu->GetDIEPtr(function_die_offset); 3861 if (func_die && func_die->HasChildren()) 3862 { 3863 types_added = ParseTypes(sc, dwarf_cu, func_die->GetFirstChild(), true, true); 3864 } 3865 } 3866 else 3867 { 3868 const DWARFDebugInfoEntry *dwarf_cu_die = dwarf_cu->DIE(); 3869 if (dwarf_cu_die && dwarf_cu_die->HasChildren()) 3870 { 3871 types_added = ParseTypes(sc, dwarf_cu, dwarf_cu_die->GetFirstChild(), true, true); 3872 } 3873 } 3874 } 3875 3876 return types_added; 3877 } 3878 3879 size_t 3880 SymbolFileDWARF::ParseVariablesForContext (const SymbolContext& sc) 3881 { 3882 if (sc.comp_unit != NULL) 3883 { 3884 DWARFDebugInfo* info = DebugInfo(); 3885 if (info == NULL) 3886 return 0; 3887 3888 if (sc.function) 3889 { 3890 DWARFCompileUnit* dwarf_cu = info->GetCompileUnitContainingDIE(sc.function->GetID()).get(); 3891 3892 if (dwarf_cu == NULL) 3893 return 0; 3894 3895 const DWARFDebugInfoEntry *function_die = dwarf_cu->GetDIEPtr(sc.function->GetID()); 3896 3897 dw_addr_t func_lo_pc = function_die->GetAttributeValueAsUnsigned (this, dwarf_cu, DW_AT_low_pc, LLDB_INVALID_ADDRESS); 3898 if (func_lo_pc != LLDB_INVALID_ADDRESS) 3899 { 3900 const size_t num_variables = ParseVariables(sc, dwarf_cu, func_lo_pc, function_die->GetFirstChild(), true, true); 3901 3902 // Let all blocks know they have parse all their variables 3903 sc.function->GetBlock (false).SetDidParseVariables (true, true); 3904 return num_variables; 3905 } 3906 } 3907 else if (sc.comp_unit) 3908 { 3909 DWARFCompileUnit* dwarf_cu = info->GetCompileUnit(sc.comp_unit->GetID()).get(); 3910 3911 if (dwarf_cu == NULL) 3912 return 0; 3913 3914 uint32_t vars_added = 0; 3915 VariableListSP variables (sc.comp_unit->GetVariableList(false)); 3916 3917 if (variables.get() == NULL) 3918 { 3919 variables.reset(new VariableList()); 3920 sc.comp_unit->SetVariableList(variables); 3921 3922 DWARFCompileUnit* match_dwarf_cu = NULL; 3923 const DWARFDebugInfoEntry* die = NULL; 3924 DIEArray die_offsets; 3925 if (m_using_apple_tables) 3926 { 3927 if (m_apple_names_ap.get()) 3928 { 3929 DWARFMappedHash::DIEInfoArray hash_data_array; 3930 if (m_apple_names_ap->AppendAllDIEsInRange (dwarf_cu->GetOffset(), 3931 dwarf_cu->GetNextCompileUnitOffset(), 3932 hash_data_array)) 3933 { 3934 DWARFMappedHash::ExtractDIEArray (hash_data_array, die_offsets); 3935 } 3936 } 3937 } 3938 else 3939 { 3940 // Index if we already haven't to make sure the compile units 3941 // get indexed and make their global DIE index list 3942 if (!m_indexed) 3943 Index (); 3944 3945 m_global_index.FindAllEntriesForCompileUnit (dwarf_cu->GetOffset(), 3946 dwarf_cu->GetNextCompileUnitOffset(), 3947 die_offsets); 3948 } 3949 3950 const size_t num_matches = die_offsets.size(); 3951 if (num_matches) 3952 { 3953 DWARFDebugInfo* debug_info = DebugInfo(); 3954 for (size_t i=0; i<num_matches; ++i) 3955 { 3956 const dw_offset_t die_offset = die_offsets[i]; 3957 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &match_dwarf_cu); 3958 if (die) 3959 { 3960 VariableSP var_sp (ParseVariableDIE(sc, dwarf_cu, die, LLDB_INVALID_ADDRESS)); 3961 if (var_sp) 3962 { 3963 variables->AddVariableIfUnique (var_sp); 3964 ++vars_added; 3965 } 3966 } 3967 else 3968 { 3969 if (m_using_apple_tables) 3970 { 3971 GetObjectFile()->GetModule()->ReportErrorIfModifyDetected ("the DWARF debug information has been modified (.apple_names accelerator table had bad die 0x%8.8x)\n", die_offset); 3972 } 3973 } 3974 3975 } 3976 } 3977 } 3978 return vars_added; 3979 } 3980 } 3981 return 0; 3982 } 3983 3984 VariableSP 3985 SymbolFileDWARF::ParseVariableDIE 3986 ( 3987 const SymbolContext& sc, 3988 DWARFCompileUnit* dwarf_cu, 3989 const DWARFDebugInfoEntry *die, 3990 const lldb::addr_t func_low_pc 3991 ) 3992 { 3993 VariableSP var_sp (m_die_to_variable_sp[die]); 3994 if (var_sp) 3995 return var_sp; // Already been parsed! 3996 3997 const dw_tag_t tag = die->Tag(); 3998 ModuleSP module = GetObjectFile()->GetModule(); 3999 4000 if ((tag == DW_TAG_variable) || 4001 (tag == DW_TAG_constant) || 4002 (tag == DW_TAG_formal_parameter && sc.function)) 4003 { 4004 DWARFDebugInfoEntry::Attributes attributes; 4005 const size_t num_attributes = die->GetAttributes(this, 4006 dwarf_cu, 4007 DWARFFormValue::FixedFormSizes(), 4008 attributes); 4009 if (num_attributes > 0) 4010 { 4011 const char *name = NULL; 4012 const char *mangled = NULL; 4013 Declaration decl; 4014 uint32_t i; 4015 lldb::user_id_t type_uid = LLDB_INVALID_UID; 4016 DWARFExpression location(dwarf_cu); 4017 bool is_external = false; 4018 bool is_artificial = false; 4019 bool location_is_const_value_data = false; 4020 bool has_explicit_location = false; 4021 DWARFFormValue const_value; 4022 //AccessType accessibility = eAccessNone; 4023 4024 for (i=0; i<num_attributes; ++i) 4025 { 4026 dw_attr_t attr = attributes.AttributeAtIndex(i); 4027 DWARFFormValue form_value; 4028 4029 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 4030 { 4031 switch (attr) 4032 { 4033 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 4034 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 4035 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 4036 case DW_AT_name: name = form_value.AsCString(this); break; 4037 case DW_AT_linkage_name: 4038 case DW_AT_MIPS_linkage_name: mangled = form_value.AsCString(this); break; 4039 case DW_AT_type: type_uid = form_value.Reference(); break; 4040 case DW_AT_external: is_external = form_value.Boolean(); break; 4041 case DW_AT_const_value: 4042 // If we have already found a DW_AT_location attribute, ignore this attribute. 4043 if (!has_explicit_location) 4044 { 4045 location_is_const_value_data = true; 4046 // The constant value will be either a block, a data value or a string. 4047 const DWARFDataExtractor& debug_info_data = get_debug_info_data(); 4048 if (DWARFFormValue::IsBlockForm(form_value.Form())) 4049 { 4050 // Retrieve the value as a block expression. 4051 uint32_t block_offset = form_value.BlockData() - debug_info_data.GetDataStart(); 4052 uint32_t block_length = form_value.Unsigned(); 4053 location.CopyOpcodeData(module, debug_info_data, block_offset, block_length); 4054 } 4055 else if (DWARFFormValue::IsDataForm(form_value.Form())) 4056 { 4057 // Retrieve the value as a data expression. 4058 DWARFFormValue::FixedFormSizes fixed_form_sizes = 4059 DWARFFormValue::GetFixedFormSizesForAddressSize ( 4060 attributes.CompileUnitAtIndex(i)->GetAddressByteSize(), 4061 attributes.CompileUnitAtIndex(i)->IsDWARF64()); 4062 uint32_t data_offset = attributes.DIEOffsetAtIndex(i); 4063 uint32_t data_length = fixed_form_sizes.GetSize(form_value.Form()); 4064 if (data_length == 0) 4065 { 4066 const uint8_t *data_pointer = form_value.BlockData(); 4067 if (data_pointer) 4068 { 4069 form_value.Unsigned(); 4070 } 4071 else if (DWARFFormValue::IsDataForm(form_value.Form())) 4072 { 4073 // we need to get the byte size of the type later after we create the variable 4074 const_value = form_value; 4075 } 4076 } 4077 else 4078 location.CopyOpcodeData(module, debug_info_data, data_offset, data_length); 4079 } 4080 else 4081 { 4082 // Retrieve the value as a string expression. 4083 if (form_value.Form() == DW_FORM_strp) 4084 { 4085 DWARFFormValue::FixedFormSizes fixed_form_sizes = 4086 DWARFFormValue::GetFixedFormSizesForAddressSize ( 4087 attributes.CompileUnitAtIndex(i)->GetAddressByteSize(), 4088 attributes.CompileUnitAtIndex(i)->IsDWARF64()); 4089 uint32_t data_offset = attributes.DIEOffsetAtIndex(i); 4090 uint32_t data_length = fixed_form_sizes.GetSize(form_value.Form()); 4091 location.CopyOpcodeData(module, debug_info_data, data_offset, data_length); 4092 } 4093 else 4094 { 4095 const char *str = form_value.AsCString(this); 4096 uint32_t string_offset = str - (const char *)debug_info_data.GetDataStart(); 4097 uint32_t string_length = strlen(str) + 1; 4098 location.CopyOpcodeData(module, debug_info_data, string_offset, string_length); 4099 } 4100 } 4101 } 4102 break; 4103 case DW_AT_location: 4104 { 4105 location_is_const_value_data = false; 4106 has_explicit_location = true; 4107 if (form_value.BlockData()) 4108 { 4109 const DWARFDataExtractor& debug_info_data = get_debug_info_data(); 4110 4111 uint32_t block_offset = form_value.BlockData() - debug_info_data.GetDataStart(); 4112 uint32_t block_length = form_value.Unsigned(); 4113 location.CopyOpcodeData(module, get_debug_info_data(), block_offset, block_length); 4114 } 4115 else 4116 { 4117 const DWARFDataExtractor& debug_loc_data = get_debug_loc_data(); 4118 const dw_offset_t debug_loc_offset = form_value.Unsigned(); 4119 4120 size_t loc_list_length = DWARFLocationList::Size(debug_loc_data, debug_loc_offset); 4121 if (loc_list_length > 0) 4122 { 4123 location.CopyOpcodeData(module, debug_loc_data, debug_loc_offset, loc_list_length); 4124 assert (func_low_pc != LLDB_INVALID_ADDRESS); 4125 location.SetLocationListSlide (func_low_pc - attributes.CompileUnitAtIndex(i)->GetBaseAddress()); 4126 } 4127 } 4128 } 4129 break; 4130 4131 case DW_AT_artificial: is_artificial = form_value.Boolean(); break; 4132 case DW_AT_accessibility: break; //accessibility = DW_ACCESS_to_AccessType(form_value.Unsigned()); break; 4133 case DW_AT_declaration: 4134 case DW_AT_description: 4135 case DW_AT_endianity: 4136 case DW_AT_segment: 4137 case DW_AT_start_scope: 4138 case DW_AT_visibility: 4139 default: 4140 case DW_AT_abstract_origin: 4141 case DW_AT_sibling: 4142 case DW_AT_specification: 4143 break; 4144 } 4145 } 4146 } 4147 4148 const DWARFDebugInfoEntry *parent_context_die = GetDeclContextDIEContainingDIE(dwarf_cu, die); 4149 bool is_static_member = die->GetParent()->Tag() == DW_TAG_compile_unit && (parent_context_die->Tag() == DW_TAG_class_type || parent_context_die->Tag() == DW_TAG_structure_type); 4150 4151 ValueType scope = eValueTypeInvalid; 4152 4153 const DWARFDebugInfoEntry *sc_parent_die = GetParentSymbolContextDIE(die); 4154 dw_tag_t parent_tag = sc_parent_die ? sc_parent_die->Tag() : 0; 4155 SymbolContextScope * symbol_context_scope = NULL; 4156 4157 if (!mangled) 4158 { 4159 // LLDB relies on the mangled name (DW_TAG_linkage_name or DW_AT_MIPS_linkage_name) to 4160 // generate fully qualified names of global variables with commands like "frame var j". 4161 // For example, if j were an int variable holding a value 4 and declared in a namespace 4162 // B which in turn is contained in a namespace A, the command "frame var j" returns 4163 // "(int) A::B::j = 4". If the compiler does not emit a linkage name, we should be able 4164 // to generate a fully qualified name from the declaration context. 4165 if (die->GetParent()->Tag() == DW_TAG_compile_unit && 4166 LanguageRuntime::LanguageIsCPlusPlus(dwarf_cu->GetLanguageType())) 4167 { 4168 DWARFDeclContext decl_ctx; 4169 4170 die->GetDWARFDeclContext(this, dwarf_cu, decl_ctx); 4171 mangled = decl_ctx.GetQualifiedNameAsConstString().GetCString(); 4172 } 4173 } 4174 4175 // DWARF doesn't specify if a DW_TAG_variable is a local, global 4176 // or static variable, so we have to do a little digging by 4177 // looking at the location of a variable to see if it contains 4178 // a DW_OP_addr opcode _somewhere_ in the definition. I say 4179 // somewhere because clang likes to combine small global variables 4180 // into the same symbol and have locations like: 4181 // DW_OP_addr(0x1000), DW_OP_constu(2), DW_OP_plus 4182 // So if we don't have a DW_TAG_formal_parameter, we can look at 4183 // the location to see if it contains a DW_OP_addr opcode, and 4184 // then we can correctly classify our variables. 4185 if (tag == DW_TAG_formal_parameter) 4186 scope = eValueTypeVariableArgument; 4187 else 4188 { 4189 bool op_error = false; 4190 // Check if the location has a DW_OP_addr with any address value... 4191 lldb::addr_t location_DW_OP_addr = LLDB_INVALID_ADDRESS; 4192 if (!location_is_const_value_data) 4193 { 4194 location_DW_OP_addr = location.GetLocation_DW_OP_addr (0, op_error); 4195 if (op_error) 4196 { 4197 StreamString strm; 4198 location.DumpLocationForAddress (&strm, eDescriptionLevelFull, 0, 0, NULL); 4199 GetObjectFile()->GetModule()->ReportError ("0x%8.8x: %s has an invalid location: %s", die->GetOffset(), DW_TAG_value_to_name(die->Tag()), strm.GetString().c_str()); 4200 } 4201 } 4202 4203 if (location_DW_OP_addr != LLDB_INVALID_ADDRESS) 4204 { 4205 if (is_external) 4206 scope = eValueTypeVariableGlobal; 4207 else 4208 scope = eValueTypeVariableStatic; 4209 4210 4211 SymbolFileDWARFDebugMap *debug_map_symfile = GetDebugMapSymfile (); 4212 4213 if (debug_map_symfile) 4214 { 4215 // When leaving the DWARF in the .o files on darwin, 4216 // when we have a global variable that wasn't initialized, 4217 // the .o file might not have allocated a virtual 4218 // address for the global variable. In this case it will 4219 // have created a symbol for the global variable 4220 // that is undefined/data and external and the value will 4221 // be the byte size of the variable. When we do the 4222 // address map in SymbolFileDWARFDebugMap we rely on 4223 // having an address, we need to do some magic here 4224 // so we can get the correct address for our global 4225 // variable. The address for all of these entries 4226 // will be zero, and there will be an undefined symbol 4227 // in this object file, and the executable will have 4228 // a matching symbol with a good address. So here we 4229 // dig up the correct address and replace it in the 4230 // location for the variable, and set the variable's 4231 // symbol context scope to be that of the main executable 4232 // so the file address will resolve correctly. 4233 bool linked_oso_file_addr = false; 4234 if (is_external && location_DW_OP_addr == 0) 4235 { 4236 // we have a possible uninitialized extern global 4237 ConstString const_name(mangled ? mangled : name); 4238 ObjectFile *debug_map_objfile = debug_map_symfile->GetObjectFile(); 4239 if (debug_map_objfile) 4240 { 4241 Symtab *debug_map_symtab = debug_map_objfile->GetSymtab(); 4242 if (debug_map_symtab) 4243 { 4244 Symbol *exe_symbol = debug_map_symtab->FindFirstSymbolWithNameAndType (const_name, 4245 eSymbolTypeData, 4246 Symtab::eDebugYes, 4247 Symtab::eVisibilityExtern); 4248 if (exe_symbol) 4249 { 4250 if (exe_symbol->ValueIsAddress()) 4251 { 4252 const addr_t exe_file_addr = exe_symbol->GetAddressRef().GetFileAddress(); 4253 if (exe_file_addr != LLDB_INVALID_ADDRESS) 4254 { 4255 if (location.Update_DW_OP_addr (exe_file_addr)) 4256 { 4257 linked_oso_file_addr = true; 4258 symbol_context_scope = exe_symbol; 4259 } 4260 } 4261 } 4262 } 4263 } 4264 } 4265 } 4266 4267 if (!linked_oso_file_addr) 4268 { 4269 // The DW_OP_addr is not zero, but it contains a .o file address which 4270 // needs to be linked up correctly. 4271 const lldb::addr_t exe_file_addr = debug_map_symfile->LinkOSOFileAddress(this, location_DW_OP_addr); 4272 if (exe_file_addr != LLDB_INVALID_ADDRESS) 4273 { 4274 // Update the file address for this variable 4275 location.Update_DW_OP_addr (exe_file_addr); 4276 } 4277 else 4278 { 4279 // Variable didn't make it into the final executable 4280 return var_sp; 4281 } 4282 } 4283 } 4284 } 4285 else 4286 { 4287 scope = eValueTypeVariableLocal; 4288 } 4289 } 4290 4291 if (symbol_context_scope == NULL) 4292 { 4293 switch (parent_tag) 4294 { 4295 case DW_TAG_subprogram: 4296 case DW_TAG_inlined_subroutine: 4297 case DW_TAG_lexical_block: 4298 if (sc.function) 4299 { 4300 symbol_context_scope = sc.function->GetBlock(true).FindBlockByID(MakeUserID(sc_parent_die->GetOffset())); 4301 if (symbol_context_scope == NULL) 4302 symbol_context_scope = sc.function; 4303 } 4304 break; 4305 4306 default: 4307 symbol_context_scope = sc.comp_unit; 4308 break; 4309 } 4310 } 4311 4312 if (symbol_context_scope) 4313 { 4314 SymbolFileTypeSP type_sp(new SymbolFileType(*this, type_uid)); 4315 4316 if (const_value.Form() && type_sp && type_sp->GetType()) 4317 location.CopyOpcodeData(const_value.Unsigned(), type_sp->GetType()->GetByteSize(), dwarf_cu->GetAddressByteSize()); 4318 4319 var_sp.reset (new Variable (MakeUserID(die->GetOffset()), 4320 name, 4321 mangled, 4322 type_sp, 4323 scope, 4324 symbol_context_scope, 4325 &decl, 4326 location, 4327 is_external, 4328 is_artificial, 4329 is_static_member)); 4330 4331 var_sp->SetLocationIsConstantValueData (location_is_const_value_data); 4332 } 4333 else 4334 { 4335 // Not ready to parse this variable yet. It might be a global 4336 // or static variable that is in a function scope and the function 4337 // in the symbol context wasn't filled in yet 4338 return var_sp; 4339 } 4340 } 4341 // Cache var_sp even if NULL (the variable was just a specification or 4342 // was missing vital information to be able to be displayed in the debugger 4343 // (missing location due to optimization, etc)) so we don't re-parse 4344 // this DIE over and over later... 4345 m_die_to_variable_sp[die] = var_sp; 4346 } 4347 return var_sp; 4348 } 4349 4350 4351 const DWARFDebugInfoEntry * 4352 SymbolFileDWARF::FindBlockContainingSpecification (dw_offset_t func_die_offset, 4353 dw_offset_t spec_block_die_offset, 4354 DWARFCompileUnit **result_die_cu_handle) 4355 { 4356 // Give the concrete function die specified by "func_die_offset", find the 4357 // concrete block whose DW_AT_specification or DW_AT_abstract_origin points 4358 // to "spec_block_die_offset" 4359 DWARFDebugInfo* info = DebugInfo(); 4360 4361 const DWARFDebugInfoEntry *die = info->GetDIEPtrWithCompileUnitHint(func_die_offset, result_die_cu_handle); 4362 if (die) 4363 { 4364 assert (*result_die_cu_handle); 4365 return FindBlockContainingSpecification (*result_die_cu_handle, die, spec_block_die_offset, result_die_cu_handle); 4366 } 4367 return NULL; 4368 } 4369 4370 4371 const DWARFDebugInfoEntry * 4372 SymbolFileDWARF::FindBlockContainingSpecification(DWARFCompileUnit* dwarf_cu, 4373 const DWARFDebugInfoEntry *die, 4374 dw_offset_t spec_block_die_offset, 4375 DWARFCompileUnit **result_die_cu_handle) 4376 { 4377 if (die) 4378 { 4379 switch (die->Tag()) 4380 { 4381 case DW_TAG_subprogram: 4382 case DW_TAG_inlined_subroutine: 4383 case DW_TAG_lexical_block: 4384 { 4385 if (die->GetAttributeValueAsReference (this, dwarf_cu, DW_AT_specification, DW_INVALID_OFFSET) == spec_block_die_offset) 4386 { 4387 *result_die_cu_handle = dwarf_cu; 4388 return die; 4389 } 4390 4391 if (die->GetAttributeValueAsReference (this, dwarf_cu, DW_AT_abstract_origin, DW_INVALID_OFFSET) == spec_block_die_offset) 4392 { 4393 *result_die_cu_handle = dwarf_cu; 4394 return die; 4395 } 4396 } 4397 break; 4398 } 4399 4400 // Give the concrete function die specified by "func_die_offset", find the 4401 // concrete block whose DW_AT_specification or DW_AT_abstract_origin points 4402 // to "spec_block_die_offset" 4403 for (const DWARFDebugInfoEntry *child_die = die->GetFirstChild(); child_die != NULL; child_die = child_die->GetSibling()) 4404 { 4405 const DWARFDebugInfoEntry *result_die = FindBlockContainingSpecification (dwarf_cu, 4406 child_die, 4407 spec_block_die_offset, 4408 result_die_cu_handle); 4409 if (result_die) 4410 return result_die; 4411 } 4412 } 4413 4414 *result_die_cu_handle = NULL; 4415 return NULL; 4416 } 4417 4418 size_t 4419 SymbolFileDWARF::ParseVariables 4420 ( 4421 const SymbolContext& sc, 4422 DWARFCompileUnit* dwarf_cu, 4423 const lldb::addr_t func_low_pc, 4424 const DWARFDebugInfoEntry *orig_die, 4425 bool parse_siblings, 4426 bool parse_children, 4427 VariableList* cc_variable_list 4428 ) 4429 { 4430 if (orig_die == NULL) 4431 return 0; 4432 4433 VariableListSP variable_list_sp; 4434 4435 size_t vars_added = 0; 4436 const DWARFDebugInfoEntry *die = orig_die; 4437 while (die != NULL) 4438 { 4439 dw_tag_t tag = die->Tag(); 4440 4441 // Check to see if we have already parsed this variable or constant? 4442 if (m_die_to_variable_sp[die]) 4443 { 4444 if (cc_variable_list) 4445 cc_variable_list->AddVariableIfUnique (m_die_to_variable_sp[die]); 4446 } 4447 else 4448 { 4449 // We haven't already parsed it, lets do that now. 4450 if ((tag == DW_TAG_variable) || 4451 (tag == DW_TAG_constant) || 4452 (tag == DW_TAG_formal_parameter && sc.function)) 4453 { 4454 if (variable_list_sp.get() == NULL) 4455 { 4456 const DWARFDebugInfoEntry *sc_parent_die = GetParentSymbolContextDIE(orig_die); 4457 dw_tag_t parent_tag = sc_parent_die ? sc_parent_die->Tag() : 0; 4458 switch (parent_tag) 4459 { 4460 case DW_TAG_compile_unit: 4461 if (sc.comp_unit != NULL) 4462 { 4463 variable_list_sp = sc.comp_unit->GetVariableList(false); 4464 if (variable_list_sp.get() == NULL) 4465 { 4466 variable_list_sp.reset(new VariableList()); 4467 sc.comp_unit->SetVariableList(variable_list_sp); 4468 } 4469 } 4470 else 4471 { 4472 GetObjectFile()->GetModule()->ReportError ("parent 0x%8.8" PRIx64 " %s with no valid compile unit in symbol context for 0x%8.8" PRIx64 " %s.\n", 4473 MakeUserID(sc_parent_die->GetOffset()), 4474 DW_TAG_value_to_name (parent_tag), 4475 MakeUserID(orig_die->GetOffset()), 4476 DW_TAG_value_to_name (orig_die->Tag())); 4477 } 4478 break; 4479 4480 case DW_TAG_subprogram: 4481 case DW_TAG_inlined_subroutine: 4482 case DW_TAG_lexical_block: 4483 if (sc.function != NULL) 4484 { 4485 // Check to see if we already have parsed the variables for the given scope 4486 4487 Block *block = sc.function->GetBlock(true).FindBlockByID(MakeUserID(sc_parent_die->GetOffset())); 4488 if (block == NULL) 4489 { 4490 // This must be a specification or abstract origin with 4491 // a concrete block counterpart in the current function. We need 4492 // to find the concrete block so we can correctly add the 4493 // variable to it 4494 DWARFCompileUnit *concrete_block_die_cu = dwarf_cu; 4495 const DWARFDebugInfoEntry *concrete_block_die = FindBlockContainingSpecification (sc.function->GetID(), 4496 sc_parent_die->GetOffset(), 4497 &concrete_block_die_cu); 4498 if (concrete_block_die) 4499 block = sc.function->GetBlock(true).FindBlockByID(MakeUserID(concrete_block_die->GetOffset())); 4500 } 4501 4502 if (block != NULL) 4503 { 4504 const bool can_create = false; 4505 variable_list_sp = block->GetBlockVariableList (can_create); 4506 if (variable_list_sp.get() == NULL) 4507 { 4508 variable_list_sp.reset(new VariableList()); 4509 block->SetVariableList(variable_list_sp); 4510 } 4511 } 4512 } 4513 break; 4514 4515 default: 4516 GetObjectFile()->GetModule()->ReportError ("didn't find appropriate parent DIE for variable list for 0x%8.8" PRIx64 " %s.\n", 4517 MakeUserID(orig_die->GetOffset()), 4518 DW_TAG_value_to_name (orig_die->Tag())); 4519 break; 4520 } 4521 } 4522 4523 if (variable_list_sp) 4524 { 4525 VariableSP var_sp (ParseVariableDIE(sc, dwarf_cu, die, func_low_pc)); 4526 if (var_sp) 4527 { 4528 variable_list_sp->AddVariableIfUnique (var_sp); 4529 if (cc_variable_list) 4530 cc_variable_list->AddVariableIfUnique (var_sp); 4531 ++vars_added; 4532 } 4533 } 4534 } 4535 } 4536 4537 bool skip_children = (sc.function == NULL && tag == DW_TAG_subprogram); 4538 4539 if (!skip_children && parse_children && die->HasChildren()) 4540 { 4541 vars_added += ParseVariables(sc, dwarf_cu, func_low_pc, die->GetFirstChild(), true, true, cc_variable_list); 4542 } 4543 4544 if (parse_siblings) 4545 die = die->GetSibling(); 4546 else 4547 die = NULL; 4548 } 4549 return vars_added; 4550 } 4551 4552 //------------------------------------------------------------------ 4553 // PluginInterface protocol 4554 //------------------------------------------------------------------ 4555 ConstString 4556 SymbolFileDWARF::GetPluginName() 4557 { 4558 return GetPluginNameStatic(); 4559 } 4560 4561 uint32_t 4562 SymbolFileDWARF::GetPluginVersion() 4563 { 4564 return 1; 4565 } 4566 4567 void 4568 SymbolFileDWARF::DumpIndexes () 4569 { 4570 StreamFile s(stdout, false); 4571 4572 s.Printf ("DWARF index for (%s) '%s':", 4573 GetObjectFile()->GetModule()->GetArchitecture().GetArchitectureName(), 4574 GetObjectFile()->GetFileSpec().GetPath().c_str()); 4575 s.Printf("\nFunction basenames:\n"); m_function_basename_index.Dump (&s); 4576 s.Printf("\nFunction fullnames:\n"); m_function_fullname_index.Dump (&s); 4577 s.Printf("\nFunction methods:\n"); m_function_method_index.Dump (&s); 4578 s.Printf("\nFunction selectors:\n"); m_function_selector_index.Dump (&s); 4579 s.Printf("\nObjective C class selectors:\n"); m_objc_class_selectors_index.Dump (&s); 4580 s.Printf("\nGlobals and statics:\n"); m_global_index.Dump (&s); 4581 s.Printf("\nTypes:\n"); m_type_index.Dump (&s); 4582 s.Printf("\nNamespaces:\n"); m_namespace_index.Dump (&s); 4583 } 4584 4585 4586 SymbolFileDWARFDebugMap * 4587 SymbolFileDWARF::GetDebugMapSymfile () 4588 { 4589 if (m_debug_map_symfile == NULL && !m_debug_map_module_wp.expired()) 4590 { 4591 lldb::ModuleSP module_sp (m_debug_map_module_wp.lock()); 4592 if (module_sp) 4593 { 4594 SymbolVendor *sym_vendor = module_sp->GetSymbolVendor(); 4595 if (sym_vendor) 4596 m_debug_map_symfile = (SymbolFileDWARFDebugMap *)sym_vendor->GetSymbolFile(); 4597 } 4598 } 4599 return m_debug_map_symfile; 4600 } 4601 4602 4603