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/Basic/Builtins.h" 18 #include "clang/Basic/IdentifierTable.h" 19 #include "clang/Basic/LangOptions.h" 20 #include "clang/Basic/SourceManager.h" 21 #include "clang/Basic/TargetInfo.h" 22 #include "clang/Basic/Specifiers.h" 23 #include "clang/Sema/DeclSpec.h" 24 25 #include "llvm/Support/Casting.h" 26 27 #include "lldb/Core/Module.h" 28 #include "lldb/Core/PluginManager.h" 29 #include "lldb/Core/RegularExpression.h" 30 #include "lldb/Core/Scalar.h" 31 #include "lldb/Core/Section.h" 32 #include "lldb/Core/StreamFile.h" 33 #include "lldb/Core/StreamString.h" 34 #include "lldb/Core/Timer.h" 35 #include "lldb/Core/Value.h" 36 37 #include "lldb/Host/Host.h" 38 39 #include "lldb/Symbol/Block.h" 40 #include "lldb/Symbol/ClangExternalASTSourceCallbacks.h" 41 #include "lldb/Symbol/CompileUnit.h" 42 #include "lldb/Symbol/LineTable.h" 43 #include "lldb/Symbol/ObjectFile.h" 44 #include "lldb/Symbol/SymbolVendor.h" 45 #include "lldb/Symbol/VariableList.h" 46 47 #include "lldb/Target/ObjCLanguageRuntime.h" 48 #include "lldb/Target/CPPLanguageRuntime.h" 49 50 #include "DWARFCompileUnit.h" 51 #include "DWARFDebugAbbrev.h" 52 #include "DWARFDebugAranges.h" 53 #include "DWARFDebugInfo.h" 54 #include "DWARFDebugInfoEntry.h" 55 #include "DWARFDebugLine.h" 56 #include "DWARFDebugPubnames.h" 57 #include "DWARFDebugRanges.h" 58 #include "DWARFDIECollection.h" 59 #include "DWARFFormValue.h" 60 #include "DWARFLocationList.h" 61 #include "LogChannelDWARF.h" 62 #include "SymbolFileDWARFDebugMap.h" 63 64 #include <map> 65 66 //#define ENABLE_DEBUG_PRINTF // COMMENT OUT THIS LINE PRIOR TO CHECKIN 67 68 #ifdef ENABLE_DEBUG_PRINTF 69 #include <stdio.h> 70 #define DEBUG_PRINTF(fmt, ...) printf(fmt, ## __VA_ARGS__) 71 #else 72 #define DEBUG_PRINTF(fmt, ...) 73 #endif 74 75 #define DIE_IS_BEING_PARSED ((lldb_private::Type*)1) 76 77 using namespace lldb; 78 using namespace lldb_private; 79 80 81 static AccessType 82 DW_ACCESS_to_AccessType (uint32_t dwarf_accessibility) 83 { 84 switch (dwarf_accessibility) 85 { 86 case DW_ACCESS_public: return eAccessPublic; 87 case DW_ACCESS_private: return eAccessPrivate; 88 case DW_ACCESS_protected: return eAccessProtected; 89 default: break; 90 } 91 return eAccessNone; 92 } 93 94 void 95 SymbolFileDWARF::Initialize() 96 { 97 LogChannelDWARF::Initialize(); 98 PluginManager::RegisterPlugin (GetPluginNameStatic(), 99 GetPluginDescriptionStatic(), 100 CreateInstance); 101 } 102 103 void 104 SymbolFileDWARF::Terminate() 105 { 106 PluginManager::UnregisterPlugin (CreateInstance); 107 LogChannelDWARF::Initialize(); 108 } 109 110 111 const char * 112 SymbolFileDWARF::GetPluginNameStatic() 113 { 114 return "dwarf"; 115 } 116 117 const char * 118 SymbolFileDWARF::GetPluginDescriptionStatic() 119 { 120 return "DWARF and DWARF3 debug symbol file reader."; 121 } 122 123 124 SymbolFile* 125 SymbolFileDWARF::CreateInstance (ObjectFile* obj_file) 126 { 127 return new SymbolFileDWARF(obj_file); 128 } 129 130 TypeList * 131 SymbolFileDWARF::GetTypeList () 132 { 133 if (m_debug_map_symfile) 134 return m_debug_map_symfile->GetTypeList(); 135 return m_obj_file->GetModule()->GetTypeList(); 136 137 } 138 139 //---------------------------------------------------------------------- 140 // Gets the first parent that is a lexical block, function or inlined 141 // subroutine, or compile unit. 142 //---------------------------------------------------------------------- 143 static const DWARFDebugInfoEntry * 144 GetParentSymbolContextDIE(const DWARFDebugInfoEntry *child_die) 145 { 146 const DWARFDebugInfoEntry *die; 147 for (die = child_die->GetParent(); die != NULL; die = die->GetParent()) 148 { 149 dw_tag_t tag = die->Tag(); 150 151 switch (tag) 152 { 153 case DW_TAG_compile_unit: 154 case DW_TAG_subprogram: 155 case DW_TAG_inlined_subroutine: 156 case DW_TAG_lexical_block: 157 return die; 158 } 159 } 160 return NULL; 161 } 162 163 164 SymbolFileDWARF::SymbolFileDWARF(ObjectFile* objfile) : 165 SymbolFile (objfile), 166 UserID (0), // Used by SymbolFileDWARFDebugMap to when this class parses .o files to contain the .o file index/ID 167 m_debug_map_symfile (NULL), 168 m_clang_tu_decl (NULL), 169 m_flags(), 170 m_data_debug_abbrev (), 171 m_data_debug_aranges (), 172 m_data_debug_frame (), 173 m_data_debug_info (), 174 m_data_debug_line (), 175 m_data_debug_loc (), 176 m_data_debug_ranges (), 177 m_data_debug_str (), 178 m_data_apple_names (), 179 m_data_apple_types (), 180 m_data_apple_namespaces (), 181 m_abbr(), 182 m_info(), 183 m_line(), 184 m_apple_names_ap (), 185 m_apple_types_ap (), 186 m_apple_namespaces_ap (), 187 m_apple_objc_ap (), 188 m_function_basename_index(), 189 m_function_fullname_index(), 190 m_function_method_index(), 191 m_function_selector_index(), 192 m_objc_class_selectors_index(), 193 m_global_index(), 194 m_type_index(), 195 m_namespace_index(), 196 m_indexed (false), 197 m_is_external_ast_source (false), 198 m_using_apple_tables (false), 199 m_ranges(), 200 m_unique_ast_type_map () 201 { 202 } 203 204 SymbolFileDWARF::~SymbolFileDWARF() 205 { 206 if (m_is_external_ast_source) 207 m_obj_file->GetModule()->GetClangASTContext().RemoveExternalSource (); 208 } 209 210 static const ConstString & 211 GetDWARFMachOSegmentName () 212 { 213 static ConstString g_dwarf_section_name ("__DWARF"); 214 return g_dwarf_section_name; 215 } 216 217 UniqueDWARFASTTypeMap & 218 SymbolFileDWARF::GetUniqueDWARFASTTypeMap () 219 { 220 if (m_debug_map_symfile) 221 return m_debug_map_symfile->GetUniqueDWARFASTTypeMap (); 222 return m_unique_ast_type_map; 223 } 224 225 ClangASTContext & 226 SymbolFileDWARF::GetClangASTContext () 227 { 228 if (m_debug_map_symfile) 229 return m_debug_map_symfile->GetClangASTContext (); 230 231 ClangASTContext &ast = m_obj_file->GetModule()->GetClangASTContext(); 232 if (!m_is_external_ast_source) 233 { 234 m_is_external_ast_source = true; 235 llvm::OwningPtr<clang::ExternalASTSource> ast_source_ap ( 236 new ClangExternalASTSourceCallbacks (SymbolFileDWARF::CompleteTagDecl, 237 SymbolFileDWARF::CompleteObjCInterfaceDecl, 238 SymbolFileDWARF::FindExternalVisibleDeclsByName, 239 this)); 240 241 ast.SetExternalSource (ast_source_ap); 242 } 243 return ast; 244 } 245 246 void 247 SymbolFileDWARF::InitializeObject() 248 { 249 // Install our external AST source callbacks so we can complete Clang types. 250 Module *module = m_obj_file->GetModule(); 251 if (module) 252 { 253 const SectionList *section_list = m_obj_file->GetSectionList(); 254 255 const Section* section = section_list->FindSectionByName(GetDWARFMachOSegmentName ()).get(); 256 257 // Memory map the DWARF mach-o segment so we have everything mmap'ed 258 // to keep our heap memory usage down. 259 if (section) 260 section->MemoryMapSectionDataFromObjectFile(m_obj_file, m_dwarf_data); 261 } 262 get_apple_names_data(); 263 if (m_data_apple_names.GetByteSize() > 0) 264 { 265 m_apple_names_ap.reset (new DWARFMappedHash::MemoryTable (m_data_apple_names, get_debug_str_data(), ".apple_names")); 266 if (m_apple_names_ap->IsValid()) 267 m_using_apple_tables = true; 268 else 269 m_apple_names_ap.reset(); 270 } 271 get_apple_types_data(); 272 if (m_data_apple_types.GetByteSize() > 0) 273 { 274 m_apple_types_ap.reset (new DWARFMappedHash::MemoryTable (m_data_apple_types, get_debug_str_data(), ".apple_types")); 275 if (m_apple_types_ap->IsValid()) 276 m_using_apple_tables = true; 277 else 278 m_apple_types_ap.reset(); 279 } 280 281 get_apple_namespaces_data(); 282 if (m_data_apple_namespaces.GetByteSize() > 0) 283 { 284 m_apple_namespaces_ap.reset (new DWARFMappedHash::MemoryTable (m_data_apple_namespaces, get_debug_str_data(), ".apple_namespaces")); 285 if (m_apple_namespaces_ap->IsValid()) 286 m_using_apple_tables = true; 287 else 288 m_apple_namespaces_ap.reset(); 289 } 290 291 get_apple_objc_data(); 292 if (m_data_apple_objc.GetByteSize() > 0) 293 { 294 m_apple_objc_ap.reset (new DWARFMappedHash::MemoryTable (m_data_apple_objc, get_debug_str_data(), ".apple_objc")); 295 if (m_apple_objc_ap->IsValid()) 296 m_using_apple_tables = true; 297 else 298 m_apple_objc_ap.reset(); 299 } 300 } 301 302 bool 303 SymbolFileDWARF::SupportedVersion(uint16_t version) 304 { 305 return version == 2 || version == 3; 306 } 307 308 uint32_t 309 SymbolFileDWARF::GetAbilities () 310 { 311 uint32_t abilities = 0; 312 if (m_obj_file != NULL) 313 { 314 const Section* section = NULL; 315 const SectionList *section_list = m_obj_file->GetSectionList(); 316 if (section_list == NULL) 317 return 0; 318 319 uint64_t debug_abbrev_file_size = 0; 320 uint64_t debug_aranges_file_size = 0; 321 uint64_t debug_frame_file_size = 0; 322 uint64_t debug_info_file_size = 0; 323 uint64_t debug_line_file_size = 0; 324 uint64_t debug_loc_file_size = 0; 325 uint64_t debug_macinfo_file_size = 0; 326 uint64_t debug_pubnames_file_size = 0; 327 uint64_t debug_pubtypes_file_size = 0; 328 uint64_t debug_ranges_file_size = 0; 329 uint64_t debug_str_file_size = 0; 330 331 section = section_list->FindSectionByName(GetDWARFMachOSegmentName ()).get(); 332 333 if (section) 334 section_list = §ion->GetChildren (); 335 336 section = section_list->FindSectionByType (eSectionTypeDWARFDebugInfo, true).get(); 337 if (section != NULL) 338 { 339 debug_info_file_size = section->GetByteSize(); 340 341 section = section_list->FindSectionByType (eSectionTypeDWARFDebugAbbrev, true).get(); 342 if (section) 343 debug_abbrev_file_size = section->GetByteSize(); 344 else 345 m_flags.Set (flagsGotDebugAbbrevData); 346 347 section = section_list->FindSectionByType (eSectionTypeDWARFDebugAranges, true).get(); 348 if (section) 349 debug_aranges_file_size = section->GetByteSize(); 350 else 351 m_flags.Set (flagsGotDebugArangesData); 352 353 section = section_list->FindSectionByType (eSectionTypeDWARFDebugFrame, true).get(); 354 if (section) 355 debug_frame_file_size = section->GetByteSize(); 356 else 357 m_flags.Set (flagsGotDebugFrameData); 358 359 section = section_list->FindSectionByType (eSectionTypeDWARFDebugLine, true).get(); 360 if (section) 361 debug_line_file_size = section->GetByteSize(); 362 else 363 m_flags.Set (flagsGotDebugLineData); 364 365 section = section_list->FindSectionByType (eSectionTypeDWARFDebugLoc, true).get(); 366 if (section) 367 debug_loc_file_size = section->GetByteSize(); 368 else 369 m_flags.Set (flagsGotDebugLocData); 370 371 section = section_list->FindSectionByType (eSectionTypeDWARFDebugMacInfo, true).get(); 372 if (section) 373 debug_macinfo_file_size = section->GetByteSize(); 374 else 375 m_flags.Set (flagsGotDebugMacInfoData); 376 377 section = section_list->FindSectionByType (eSectionTypeDWARFDebugPubNames, true).get(); 378 if (section) 379 debug_pubnames_file_size = section->GetByteSize(); 380 else 381 m_flags.Set (flagsGotDebugPubNamesData); 382 383 section = section_list->FindSectionByType (eSectionTypeDWARFDebugPubTypes, true).get(); 384 if (section) 385 debug_pubtypes_file_size = section->GetByteSize(); 386 else 387 m_flags.Set (flagsGotDebugPubTypesData); 388 389 section = section_list->FindSectionByType (eSectionTypeDWARFDebugRanges, true).get(); 390 if (section) 391 debug_ranges_file_size = section->GetByteSize(); 392 else 393 m_flags.Set (flagsGotDebugRangesData); 394 395 section = section_list->FindSectionByType (eSectionTypeDWARFDebugStr, true).get(); 396 if (section) 397 debug_str_file_size = section->GetByteSize(); 398 else 399 m_flags.Set (flagsGotDebugStrData); 400 } 401 402 if (debug_abbrev_file_size > 0 && debug_info_file_size > 0) 403 abilities |= CompileUnits | Functions | Blocks | GlobalVariables | LocalVariables | VariableTypes; 404 405 if (debug_line_file_size > 0) 406 abilities |= LineTables; 407 408 if (debug_aranges_file_size > 0) 409 abilities |= AddressAcceleratorTable; 410 411 if (debug_pubnames_file_size > 0) 412 abilities |= FunctionAcceleratorTable; 413 414 if (debug_pubtypes_file_size > 0) 415 abilities |= TypeAcceleratorTable; 416 417 if (debug_macinfo_file_size > 0) 418 abilities |= MacroInformation; 419 420 if (debug_frame_file_size > 0) 421 abilities |= CallFrameInformation; 422 } 423 return abilities; 424 } 425 426 const DataExtractor& 427 SymbolFileDWARF::GetCachedSectionData (uint32_t got_flag, SectionType sect_type, DataExtractor &data) 428 { 429 if (m_flags.IsClear (got_flag)) 430 { 431 m_flags.Set (got_flag); 432 const SectionList *section_list = m_obj_file->GetSectionList(); 433 if (section_list) 434 { 435 Section *section = section_list->FindSectionByType(sect_type, true).get(); 436 if (section) 437 { 438 // See if we memory mapped the DWARF segment? 439 if (m_dwarf_data.GetByteSize()) 440 { 441 data.SetData(m_dwarf_data, section->GetOffset (), section->GetByteSize()); 442 } 443 else 444 { 445 if (section->ReadSectionDataFromObjectFile(m_obj_file, data) == 0) 446 data.Clear(); 447 } 448 } 449 } 450 } 451 return data; 452 } 453 454 const DataExtractor& 455 SymbolFileDWARF::get_debug_abbrev_data() 456 { 457 return GetCachedSectionData (flagsGotDebugAbbrevData, eSectionTypeDWARFDebugAbbrev, m_data_debug_abbrev); 458 } 459 460 const DataExtractor& 461 SymbolFileDWARF::get_debug_aranges_data() 462 { 463 return GetCachedSectionData (flagsGotDebugArangesData, eSectionTypeDWARFDebugAranges, m_data_debug_aranges); 464 } 465 466 const DataExtractor& 467 SymbolFileDWARF::get_debug_frame_data() 468 { 469 return GetCachedSectionData (flagsGotDebugFrameData, eSectionTypeDWARFDebugFrame, m_data_debug_frame); 470 } 471 472 const DataExtractor& 473 SymbolFileDWARF::get_debug_info_data() 474 { 475 return GetCachedSectionData (flagsGotDebugInfoData, eSectionTypeDWARFDebugInfo, m_data_debug_info); 476 } 477 478 const DataExtractor& 479 SymbolFileDWARF::get_debug_line_data() 480 { 481 return GetCachedSectionData (flagsGotDebugLineData, eSectionTypeDWARFDebugLine, m_data_debug_line); 482 } 483 484 const DataExtractor& 485 SymbolFileDWARF::get_debug_loc_data() 486 { 487 return GetCachedSectionData (flagsGotDebugLocData, eSectionTypeDWARFDebugLoc, m_data_debug_loc); 488 } 489 490 const DataExtractor& 491 SymbolFileDWARF::get_debug_ranges_data() 492 { 493 return GetCachedSectionData (flagsGotDebugRangesData, eSectionTypeDWARFDebugRanges, m_data_debug_ranges); 494 } 495 496 const DataExtractor& 497 SymbolFileDWARF::get_debug_str_data() 498 { 499 return GetCachedSectionData (flagsGotDebugStrData, eSectionTypeDWARFDebugStr, m_data_debug_str); 500 } 501 502 const DataExtractor& 503 SymbolFileDWARF::get_apple_names_data() 504 { 505 return GetCachedSectionData (flagsGotAppleNamesData, eSectionTypeDWARFAppleNames, m_data_apple_names); 506 } 507 508 const DataExtractor& 509 SymbolFileDWARF::get_apple_types_data() 510 { 511 return GetCachedSectionData (flagsGotAppleTypesData, eSectionTypeDWARFAppleTypes, m_data_apple_types); 512 } 513 514 const DataExtractor& 515 SymbolFileDWARF::get_apple_namespaces_data() 516 { 517 return GetCachedSectionData (flagsGotAppleNamespacesData, eSectionTypeDWARFAppleNamespaces, m_data_apple_namespaces); 518 } 519 520 const DataExtractor& 521 SymbolFileDWARF::get_apple_objc_data() 522 { 523 return GetCachedSectionData (flagsGotAppleObjCData, eSectionTypeDWARFAppleObjC, m_data_apple_objc); 524 } 525 526 527 DWARFDebugAbbrev* 528 SymbolFileDWARF::DebugAbbrev() 529 { 530 if (m_abbr.get() == NULL) 531 { 532 const DataExtractor &debug_abbrev_data = get_debug_abbrev_data(); 533 if (debug_abbrev_data.GetByteSize() > 0) 534 { 535 m_abbr.reset(new DWARFDebugAbbrev()); 536 if (m_abbr.get()) 537 m_abbr->Parse(debug_abbrev_data); 538 } 539 } 540 return m_abbr.get(); 541 } 542 543 const DWARFDebugAbbrev* 544 SymbolFileDWARF::DebugAbbrev() const 545 { 546 return m_abbr.get(); 547 } 548 549 550 DWARFDebugInfo* 551 SymbolFileDWARF::DebugInfo() 552 { 553 if (m_info.get() == NULL) 554 { 555 Timer scoped_timer(__PRETTY_FUNCTION__, "%s this = %p", __PRETTY_FUNCTION__, this); 556 if (get_debug_info_data().GetByteSize() > 0) 557 { 558 m_info.reset(new DWARFDebugInfo()); 559 if (m_info.get()) 560 { 561 m_info->SetDwarfData(this); 562 } 563 } 564 } 565 return m_info.get(); 566 } 567 568 const DWARFDebugInfo* 569 SymbolFileDWARF::DebugInfo() const 570 { 571 return m_info.get(); 572 } 573 574 DWARFCompileUnit* 575 SymbolFileDWARF::GetDWARFCompileUnitForUID(lldb::user_id_t cu_uid) 576 { 577 DWARFDebugInfo* info = DebugInfo(); 578 if (info && UserIDMatches(cu_uid)) 579 return info->GetCompileUnit((dw_offset_t)cu_uid).get(); 580 return NULL; 581 } 582 583 584 DWARFDebugRanges* 585 SymbolFileDWARF::DebugRanges() 586 { 587 if (m_ranges.get() == NULL) 588 { 589 Timer scoped_timer(__PRETTY_FUNCTION__, "%s this = %p", __PRETTY_FUNCTION__, this); 590 if (get_debug_ranges_data().GetByteSize() > 0) 591 { 592 m_ranges.reset(new DWARFDebugRanges()); 593 if (m_ranges.get()) 594 m_ranges->Extract(this); 595 } 596 } 597 return m_ranges.get(); 598 } 599 600 const DWARFDebugRanges* 601 SymbolFileDWARF::DebugRanges() const 602 { 603 return m_ranges.get(); 604 } 605 606 bool 607 SymbolFileDWARF::ParseCompileUnit (DWARFCompileUnit* curr_cu, CompUnitSP& compile_unit_sp) 608 { 609 if (curr_cu != NULL) 610 { 611 const DWARFDebugInfoEntry * cu_die = curr_cu->GetCompileUnitDIEOnly (); 612 if (cu_die) 613 { 614 const char * cu_die_name = cu_die->GetName(this, curr_cu); 615 const char * cu_comp_dir = cu_die->GetAttributeValueAsString(this, curr_cu, DW_AT_comp_dir, NULL); 616 LanguageType cu_language = (LanguageType)cu_die->GetAttributeValueAsUnsigned(this, curr_cu, DW_AT_language, 0); 617 if (cu_die_name) 618 { 619 FileSpec cu_file_spec; 620 621 if (cu_die_name[0] == '/' || cu_comp_dir == NULL || cu_comp_dir[0] == '\0') 622 { 623 // If we have a full path to the compile unit, we don't need to resolve 624 // the file. This can be expensive e.g. when the source files are NFS mounted. 625 cu_file_spec.SetFile (cu_die_name, false); 626 } 627 else 628 { 629 std::string fullpath(cu_comp_dir); 630 if (*fullpath.rbegin() != '/') 631 fullpath += '/'; 632 fullpath += cu_die_name; 633 cu_file_spec.SetFile (fullpath.c_str(), false); 634 } 635 636 compile_unit_sp.reset(new CompileUnit (m_obj_file->GetModule(), 637 curr_cu, 638 cu_file_spec, 639 MakeUserID(curr_cu->GetOffset()), 640 cu_language)); 641 if (compile_unit_sp.get()) 642 { 643 curr_cu->SetUserData(compile_unit_sp.get()); 644 return true; 645 } 646 } 647 } 648 } 649 return false; 650 } 651 652 uint32_t 653 SymbolFileDWARF::GetNumCompileUnits() 654 { 655 DWARFDebugInfo* info = DebugInfo(); 656 if (info) 657 return info->GetNumCompileUnits(); 658 return 0; 659 } 660 661 CompUnitSP 662 SymbolFileDWARF::ParseCompileUnitAtIndex(uint32_t cu_idx) 663 { 664 CompUnitSP comp_unit; 665 DWARFDebugInfo* info = DebugInfo(); 666 if (info) 667 { 668 DWARFCompileUnit* curr_cu = info->GetCompileUnitAtIndex(cu_idx); 669 if (curr_cu != NULL) 670 { 671 // Our symbol vendor shouldn't be asking us to add a compile unit that 672 // has already been added to it, which this DWARF plug-in knows as it 673 // stores the lldb compile unit (CompileUnit) pointer in each 674 // DWARFCompileUnit object when it gets added. 675 assert(curr_cu->GetUserData() == NULL); 676 ParseCompileUnit(curr_cu, comp_unit); 677 } 678 } 679 return comp_unit; 680 } 681 682 static void 683 AddRangesToBlock (Block& block, 684 DWARFDebugRanges::RangeList& ranges, 685 addr_t block_base_addr) 686 { 687 const size_t num_ranges = ranges.GetSize(); 688 for (size_t i = 0; i<num_ranges; ++i) 689 { 690 const DWARFDebugRanges::Range &range = ranges.GetEntryRef (i); 691 const addr_t range_base = range.GetRangeBase(); 692 assert (range_base >= block_base_addr); 693 block.AddRange(Block::Range (range_base - block_base_addr, range.GetByteSize()));; 694 } 695 block.FinalizeRanges (); 696 } 697 698 699 Function * 700 SymbolFileDWARF::ParseCompileUnitFunction (const SymbolContext& sc, DWARFCompileUnit* dwarf_cu, const DWARFDebugInfoEntry *die) 701 { 702 DWARFDebugRanges::RangeList func_ranges; 703 const char *name = NULL; 704 const char *mangled = NULL; 705 int decl_file = 0; 706 int decl_line = 0; 707 int decl_column = 0; 708 int call_file = 0; 709 int call_line = 0; 710 int call_column = 0; 711 DWARFExpression frame_base; 712 713 assert (die->Tag() == DW_TAG_subprogram); 714 715 if (die->Tag() != DW_TAG_subprogram) 716 return NULL; 717 718 if (die->GetDIENamesAndRanges(this, dwarf_cu, name, mangled, func_ranges, decl_file, decl_line, decl_column, call_file, call_line, call_column, &frame_base)) 719 { 720 // Union of all ranges in the function DIE (if the function is discontiguous) 721 AddressRange func_range; 722 lldb::addr_t lowest_func_addr = func_ranges.GetMinRangeBase (0); 723 lldb::addr_t highest_func_addr = func_ranges.GetMaxRangeEnd (0); 724 if (lowest_func_addr != LLDB_INVALID_ADDRESS && lowest_func_addr <= highest_func_addr) 725 { 726 func_range.GetBaseAddress().ResolveAddressUsingFileSections (lowest_func_addr, m_obj_file->GetSectionList()); 727 if (func_range.GetBaseAddress().IsValid()) 728 func_range.SetByteSize(highest_func_addr - lowest_func_addr); 729 } 730 731 if (func_range.GetBaseAddress().IsValid()) 732 { 733 Mangled func_name; 734 if (mangled) 735 func_name.SetValue(mangled, true); 736 else if (name) 737 func_name.SetValue(name, false); 738 739 FunctionSP func_sp; 740 std::auto_ptr<Declaration> decl_ap; 741 if (decl_file != 0 || decl_line != 0 || decl_column != 0) 742 decl_ap.reset(new Declaration (sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(decl_file), 743 decl_line, 744 decl_column)); 745 746 // Supply the type _only_ if it has already been parsed 747 Type *func_type = m_die_to_type.lookup (die); 748 749 assert(func_type == NULL || func_type != DIE_IS_BEING_PARSED); 750 751 func_range.GetBaseAddress().ResolveLinkedAddress(); 752 753 const user_id_t func_user_id = MakeUserID(die->GetOffset()); 754 func_sp.reset(new Function (sc.comp_unit, 755 func_user_id, // UserID is the DIE offset 756 func_user_id, 757 func_name, 758 func_type, 759 func_range)); // first address range 760 761 if (func_sp.get() != NULL) 762 { 763 if (frame_base.IsValid()) 764 func_sp->GetFrameBaseExpression() = frame_base; 765 sc.comp_unit->AddFunction(func_sp); 766 return func_sp.get(); 767 } 768 } 769 } 770 return NULL; 771 } 772 773 size_t 774 SymbolFileDWARF::ParseCompileUnitFunctions(const SymbolContext &sc) 775 { 776 assert (sc.comp_unit); 777 size_t functions_added = 0; 778 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnitForUID(sc.comp_unit->GetID()); 779 if (dwarf_cu) 780 { 781 DWARFDIECollection function_dies; 782 const size_t num_funtions = dwarf_cu->AppendDIEsWithTag (DW_TAG_subprogram, function_dies); 783 size_t func_idx; 784 for (func_idx = 0; func_idx < num_funtions; ++func_idx) 785 { 786 const DWARFDebugInfoEntry *die = function_dies.GetDIEPtrAtIndex(func_idx); 787 if (sc.comp_unit->FindFunctionByUID (MakeUserID(die->GetOffset())).get() == NULL) 788 { 789 if (ParseCompileUnitFunction(sc, dwarf_cu, die)) 790 ++functions_added; 791 } 792 } 793 //FixupTypes(); 794 } 795 return functions_added; 796 } 797 798 bool 799 SymbolFileDWARF::ParseCompileUnitSupportFiles (const SymbolContext& sc, FileSpecList& support_files) 800 { 801 assert (sc.comp_unit); 802 DWARFCompileUnit* curr_cu = GetDWARFCompileUnitForUID(sc.comp_unit->GetID()); 803 assert (curr_cu); 804 const DWARFDebugInfoEntry * cu_die = curr_cu->GetCompileUnitDIEOnly(); 805 806 if (cu_die) 807 { 808 const char * cu_comp_dir = cu_die->GetAttributeValueAsString(this, curr_cu, DW_AT_comp_dir, NULL); 809 dw_offset_t stmt_list = cu_die->GetAttributeValueAsUnsigned(this, curr_cu, DW_AT_stmt_list, DW_INVALID_OFFSET); 810 811 // All file indexes in DWARF are one based and a file of index zero is 812 // supposed to be the compile unit itself. 813 support_files.Append (*sc.comp_unit); 814 815 return DWARFDebugLine::ParseSupportFiles(get_debug_line_data(), cu_comp_dir, stmt_list, support_files); 816 } 817 return false; 818 } 819 820 struct ParseDWARFLineTableCallbackInfo 821 { 822 LineTable* line_table; 823 const SectionList *section_list; 824 lldb::addr_t prev_sect_file_base_addr; 825 lldb::addr_t curr_sect_file_base_addr; 826 bool is_oso_for_debug_map; 827 bool prev_in_final_executable; 828 DWARFDebugLine::Row prev_row; 829 SectionSP prev_section_sp; 830 SectionSP curr_section_sp; 831 }; 832 833 //---------------------------------------------------------------------- 834 // ParseStatementTableCallback 835 //---------------------------------------------------------------------- 836 static void 837 ParseDWARFLineTableCallback(dw_offset_t offset, const DWARFDebugLine::State& state, void* userData) 838 { 839 LineTable* line_table = ((ParseDWARFLineTableCallbackInfo*)userData)->line_table; 840 if (state.row == DWARFDebugLine::State::StartParsingLineTable) 841 { 842 // Just started parsing the line table 843 } 844 else if (state.row == DWARFDebugLine::State::DoneParsingLineTable) 845 { 846 // Done parsing line table, nothing to do for the cleanup 847 } 848 else 849 { 850 ParseDWARFLineTableCallbackInfo* info = (ParseDWARFLineTableCallbackInfo*)userData; 851 // We have a new row, lets append it 852 853 if (info->curr_section_sp.get() == NULL || info->curr_section_sp->ContainsFileAddress(state.address) == false) 854 { 855 info->prev_section_sp = info->curr_section_sp; 856 info->prev_sect_file_base_addr = info->curr_sect_file_base_addr; 857 // If this is an end sequence entry, then we subtract one from the 858 // address to make sure we get an address that is not the end of 859 // a section. 860 if (state.end_sequence && state.address != 0) 861 info->curr_section_sp = info->section_list->FindSectionContainingFileAddress (state.address - 1); 862 else 863 info->curr_section_sp = info->section_list->FindSectionContainingFileAddress (state.address); 864 865 if (info->curr_section_sp.get()) 866 info->curr_sect_file_base_addr = info->curr_section_sp->GetFileAddress (); 867 else 868 info->curr_sect_file_base_addr = 0; 869 } 870 if (info->curr_section_sp.get()) 871 { 872 lldb::addr_t curr_line_section_offset = state.address - info->curr_sect_file_base_addr; 873 // Check for the fancy section magic to determine if we 874 875 if (info->is_oso_for_debug_map) 876 { 877 // When this is a debug map object file that contains DWARF 878 // (referenced from an N_OSO debug map nlist entry) we will have 879 // a file address in the file range for our section from the 880 // original .o file, and a load address in the executable that 881 // contains the debug map. 882 // 883 // If the sections for the file range and load range are 884 // different, we have a remapped section for the function and 885 // this address is resolved. If they are the same, then the 886 // function for this address didn't make it into the final 887 // executable. 888 bool curr_in_final_executable = info->curr_section_sp->GetLinkedSection () != NULL; 889 890 // If we are doing DWARF with debug map, then we need to carefully 891 // add each line table entry as there may be gaps as functions 892 // get moved around or removed. 893 if (!info->prev_row.end_sequence && info->prev_section_sp.get()) 894 { 895 if (info->prev_in_final_executable) 896 { 897 bool terminate_previous_entry = false; 898 if (!curr_in_final_executable) 899 { 900 // Check for the case where the previous line entry 901 // in a function made it into the final executable, 902 // yet the current line entry falls in a function 903 // that didn't. The line table used to be contiguous 904 // through this address range but now it isn't. We 905 // need to terminate the previous line entry so 906 // that we can reconstruct the line range correctly 907 // for it and to keep the line table correct. 908 terminate_previous_entry = true; 909 } 910 else if (info->curr_section_sp.get() != info->prev_section_sp.get()) 911 { 912 // Check for cases where the line entries used to be 913 // contiguous address ranges, but now they aren't. 914 // This can happen when order files specify the 915 // ordering of the functions. 916 lldb::addr_t prev_line_section_offset = info->prev_row.address - info->prev_sect_file_base_addr; 917 Section *curr_sect = info->curr_section_sp.get(); 918 Section *prev_sect = info->prev_section_sp.get(); 919 assert (curr_sect->GetLinkedSection()); 920 assert (prev_sect->GetLinkedSection()); 921 lldb::addr_t object_file_addr_delta = state.address - info->prev_row.address; 922 lldb::addr_t curr_linked_file_addr = curr_sect->GetLinkedFileAddress() + curr_line_section_offset; 923 lldb::addr_t prev_linked_file_addr = prev_sect->GetLinkedFileAddress() + prev_line_section_offset; 924 lldb::addr_t linked_file_addr_delta = curr_linked_file_addr - prev_linked_file_addr; 925 if (object_file_addr_delta != linked_file_addr_delta) 926 terminate_previous_entry = true; 927 } 928 929 if (terminate_previous_entry) 930 { 931 line_table->InsertLineEntry (info->prev_section_sp, 932 state.address - info->prev_sect_file_base_addr, 933 info->prev_row.line, 934 info->prev_row.column, 935 info->prev_row.file, 936 false, // is_stmt 937 false, // basic_block 938 false, // state.prologue_end 939 false, // state.epilogue_begin 940 true); // end_sequence); 941 } 942 } 943 } 944 945 if (curr_in_final_executable) 946 { 947 line_table->InsertLineEntry (info->curr_section_sp, 948 curr_line_section_offset, 949 state.line, 950 state.column, 951 state.file, 952 state.is_stmt, 953 state.basic_block, 954 state.prologue_end, 955 state.epilogue_begin, 956 state.end_sequence); 957 info->prev_section_sp = info->curr_section_sp; 958 } 959 else 960 { 961 // If the current address didn't make it into the final 962 // executable, the current section will be the __text 963 // segment in the .o file, so we need to clear this so 964 // we can catch the next function that did make it into 965 // the final executable. 966 info->prev_section_sp.reset(); 967 info->curr_section_sp.reset(); 968 } 969 970 info->prev_in_final_executable = curr_in_final_executable; 971 } 972 else 973 { 974 // We are not in an object file that contains DWARF for an 975 // N_OSO, this is just a normal DWARF file. The DWARF spec 976 // guarantees that the addresses will be in increasing order 977 // so, since we store line tables in file address order, we 978 // can always just append the line entry without needing to 979 // search for the correct insertion point (we don't need to 980 // use LineEntry::InsertLineEntry()). 981 line_table->AppendLineEntry (info->curr_section_sp, 982 curr_line_section_offset, 983 state.line, 984 state.column, 985 state.file, 986 state.is_stmt, 987 state.basic_block, 988 state.prologue_end, 989 state.epilogue_begin, 990 state.end_sequence); 991 } 992 } 993 994 info->prev_row = state; 995 } 996 } 997 998 bool 999 SymbolFileDWARF::ParseCompileUnitLineTable (const SymbolContext &sc) 1000 { 1001 assert (sc.comp_unit); 1002 if (sc.comp_unit->GetLineTable() != NULL) 1003 return true; 1004 1005 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnitForUID(sc.comp_unit->GetID()); 1006 if (dwarf_cu) 1007 { 1008 const DWARFDebugInfoEntry *dwarf_cu_die = dwarf_cu->GetCompileUnitDIEOnly(); 1009 const dw_offset_t cu_line_offset = dwarf_cu_die->GetAttributeValueAsUnsigned(this, dwarf_cu, DW_AT_stmt_list, DW_INVALID_OFFSET); 1010 if (cu_line_offset != DW_INVALID_OFFSET) 1011 { 1012 std::auto_ptr<LineTable> line_table_ap(new LineTable(sc.comp_unit)); 1013 if (line_table_ap.get()) 1014 { 1015 ParseDWARFLineTableCallbackInfo info = { 1016 line_table_ap.get(), 1017 m_obj_file->GetSectionList(), 1018 0, 1019 0, 1020 m_debug_map_symfile != NULL, 1021 false, 1022 DWARFDebugLine::Row(), 1023 SectionSP(), 1024 SectionSP() 1025 }; 1026 uint32_t offset = cu_line_offset; 1027 DWARFDebugLine::ParseStatementTable(get_debug_line_data(), &offset, ParseDWARFLineTableCallback, &info); 1028 sc.comp_unit->SetLineTable(line_table_ap.release()); 1029 return true; 1030 } 1031 } 1032 } 1033 return false; 1034 } 1035 1036 size_t 1037 SymbolFileDWARF::ParseFunctionBlocks 1038 ( 1039 const SymbolContext& sc, 1040 Block *parent_block, 1041 DWARFCompileUnit* dwarf_cu, 1042 const DWARFDebugInfoEntry *die, 1043 addr_t subprogram_low_pc, 1044 uint32_t depth 1045 ) 1046 { 1047 size_t blocks_added = 0; 1048 while (die != NULL) 1049 { 1050 dw_tag_t tag = die->Tag(); 1051 1052 switch (tag) 1053 { 1054 case DW_TAG_inlined_subroutine: 1055 case DW_TAG_subprogram: 1056 case DW_TAG_lexical_block: 1057 { 1058 Block *block = NULL; 1059 if (tag == DW_TAG_subprogram) 1060 { 1061 // Skip any DW_TAG_subprogram DIEs that are inside 1062 // of a normal or inlined functions. These will be 1063 // parsed on their own as separate entities. 1064 1065 if (depth > 0) 1066 break; 1067 1068 block = parent_block; 1069 } 1070 else 1071 { 1072 BlockSP block_sp(new Block (MakeUserID(die->GetOffset()))); 1073 parent_block->AddChild(block_sp); 1074 block = block_sp.get(); 1075 } 1076 DWARFDebugRanges::RangeList ranges; 1077 const char *name = NULL; 1078 const char *mangled_name = NULL; 1079 1080 int decl_file = 0; 1081 int decl_line = 0; 1082 int decl_column = 0; 1083 int call_file = 0; 1084 int call_line = 0; 1085 int call_column = 0; 1086 if (die->GetDIENamesAndRanges (this, 1087 dwarf_cu, 1088 name, 1089 mangled_name, 1090 ranges, 1091 decl_file, decl_line, decl_column, 1092 call_file, call_line, call_column)) 1093 { 1094 if (tag == DW_TAG_subprogram) 1095 { 1096 assert (subprogram_low_pc == LLDB_INVALID_ADDRESS); 1097 subprogram_low_pc = ranges.GetMinRangeBase(0); 1098 } 1099 else if (tag == DW_TAG_inlined_subroutine) 1100 { 1101 // We get called here for inlined subroutines in two ways. 1102 // The first time is when we are making the Function object 1103 // for this inlined concrete instance. Since we're creating a top level block at 1104 // here, the subprogram_low_pc will be LLDB_INVALID_ADDRESS. So we need to 1105 // adjust the containing address. 1106 // The second time is when we are parsing the blocks inside the function that contains 1107 // the inlined concrete instance. Since these will be blocks inside the containing "real" 1108 // function the offset will be for that function. 1109 if (subprogram_low_pc == LLDB_INVALID_ADDRESS) 1110 { 1111 subprogram_low_pc = ranges.GetMinRangeBase(0); 1112 } 1113 } 1114 1115 AddRangesToBlock (*block, ranges, subprogram_low_pc); 1116 1117 if (tag != DW_TAG_subprogram && (name != NULL || mangled_name != NULL)) 1118 { 1119 std::auto_ptr<Declaration> decl_ap; 1120 if (decl_file != 0 || decl_line != 0 || decl_column != 0) 1121 decl_ap.reset(new Declaration(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(decl_file), 1122 decl_line, decl_column)); 1123 1124 std::auto_ptr<Declaration> call_ap; 1125 if (call_file != 0 || call_line != 0 || call_column != 0) 1126 call_ap.reset(new Declaration(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(call_file), 1127 call_line, call_column)); 1128 1129 block->SetInlinedFunctionInfo (name, mangled_name, decl_ap.get(), call_ap.get()); 1130 } 1131 1132 ++blocks_added; 1133 1134 if (die->HasChildren()) 1135 { 1136 blocks_added += ParseFunctionBlocks (sc, 1137 block, 1138 dwarf_cu, 1139 die->GetFirstChild(), 1140 subprogram_low_pc, 1141 depth + 1); 1142 } 1143 } 1144 } 1145 break; 1146 default: 1147 break; 1148 } 1149 1150 // Only parse siblings of the block if we are not at depth zero. A depth 1151 // of zero indicates we are currently parsing the top level 1152 // DW_TAG_subprogram DIE 1153 1154 if (depth == 0) 1155 die = NULL; 1156 else 1157 die = die->GetSibling(); 1158 } 1159 return blocks_added; 1160 } 1161 1162 bool 1163 SymbolFileDWARF::ParseTemplateParameterInfos (DWARFCompileUnit* dwarf_cu, 1164 const DWARFDebugInfoEntry *parent_die, 1165 ClangASTContext::TemplateParameterInfos &template_param_infos) 1166 { 1167 1168 if (parent_die == NULL) 1169 return NULL; 1170 1171 const uint8_t *fixed_form_sizes = DWARFFormValue::GetFixedFormSizesForAddressSize (dwarf_cu->GetAddressByteSize()); 1172 1173 Args template_parameter_names; 1174 for (const DWARFDebugInfoEntry *die = parent_die->GetFirstChild(); 1175 die != NULL; 1176 die = die->GetSibling()) 1177 { 1178 const dw_tag_t tag = die->Tag(); 1179 1180 switch (tag) 1181 { 1182 case DW_TAG_template_type_parameter: 1183 case DW_TAG_template_value_parameter: 1184 { 1185 DWARFDebugInfoEntry::Attributes attributes; 1186 const size_t num_attributes = die->GetAttributes (this, 1187 dwarf_cu, 1188 fixed_form_sizes, 1189 attributes); 1190 const char *name = NULL; 1191 Type *lldb_type = NULL; 1192 clang_type_t clang_type = NULL; 1193 uint64_t uval64 = 0; 1194 bool uval64_valid = false; 1195 if (num_attributes > 0) 1196 { 1197 DWARFFormValue form_value; 1198 for (size_t i=0; i<num_attributes; ++i) 1199 { 1200 const dw_attr_t attr = attributes.AttributeAtIndex(i); 1201 1202 switch (attr) 1203 { 1204 case DW_AT_name: 1205 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 1206 name = form_value.AsCString(&get_debug_str_data()); 1207 break; 1208 1209 case DW_AT_type: 1210 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 1211 { 1212 const dw_offset_t type_die_offset = form_value.Reference(dwarf_cu); 1213 lldb_type = ResolveTypeUID(type_die_offset); 1214 if (lldb_type) 1215 clang_type = lldb_type->GetClangForwardType(); 1216 } 1217 break; 1218 1219 case DW_AT_const_value: 1220 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 1221 { 1222 uval64_valid = true; 1223 uval64 = form_value.Unsigned(); 1224 } 1225 break; 1226 default: 1227 break; 1228 } 1229 } 1230 1231 if (name && lldb_type && clang_type) 1232 { 1233 bool is_signed = false; 1234 template_param_infos.names.push_back(name); 1235 clang::QualType clang_qual_type (clang::QualType::getFromOpaquePtr (clang_type)); 1236 if (tag == DW_TAG_template_value_parameter && ClangASTContext::IsIntegerType (clang_type, is_signed) && uval64_valid) 1237 { 1238 llvm::APInt apint (lldb_type->GetByteSize() * 8, uval64, is_signed); 1239 template_param_infos.args.push_back (clang::TemplateArgument (llvm::APSInt(apint), clang_qual_type)); 1240 } 1241 else 1242 { 1243 template_param_infos.args.push_back (clang::TemplateArgument (clang_qual_type)); 1244 } 1245 } 1246 else 1247 { 1248 return false; 1249 } 1250 1251 } 1252 } 1253 break; 1254 1255 default: 1256 break; 1257 } 1258 } 1259 if (template_param_infos.args.empty()) 1260 return false; 1261 return template_param_infos.args.size() == template_param_infos.names.size(); 1262 } 1263 1264 clang::ClassTemplateDecl * 1265 SymbolFileDWARF::ParseClassTemplateDecl (clang::DeclContext *decl_ctx, 1266 lldb::AccessType access_type, 1267 const char *parent_name, 1268 int tag_decl_kind, 1269 const ClangASTContext::TemplateParameterInfos &template_param_infos) 1270 { 1271 if (template_param_infos.IsValid()) 1272 { 1273 std::string template_basename(parent_name); 1274 template_basename.erase (template_basename.find('<')); 1275 ClangASTContext &ast = GetClangASTContext(); 1276 1277 return ast.CreateClassTemplateDecl (decl_ctx, 1278 access_type, 1279 template_basename.c_str(), 1280 tag_decl_kind, 1281 template_param_infos); 1282 } 1283 return NULL; 1284 } 1285 1286 size_t 1287 SymbolFileDWARF::ParseChildMembers 1288 ( 1289 const SymbolContext& sc, 1290 DWARFCompileUnit* dwarf_cu, 1291 const DWARFDebugInfoEntry *parent_die, 1292 clang_type_t class_clang_type, 1293 const LanguageType class_language, 1294 std::vector<clang::CXXBaseSpecifier *>& base_classes, 1295 std::vector<int>& member_accessibilities, 1296 DWARFDIECollection& member_function_dies, 1297 AccessType& default_accessibility, 1298 bool &is_a_class 1299 ) 1300 { 1301 if (parent_die == NULL) 1302 return 0; 1303 1304 size_t count = 0; 1305 const DWARFDebugInfoEntry *die; 1306 const uint8_t *fixed_form_sizes = DWARFFormValue::GetFixedFormSizesForAddressSize (dwarf_cu->GetAddressByteSize()); 1307 uint32_t member_idx = 0; 1308 1309 for (die = parent_die->GetFirstChild(); die != NULL; die = die->GetSibling()) 1310 { 1311 dw_tag_t tag = die->Tag(); 1312 1313 switch (tag) 1314 { 1315 case DW_TAG_member: 1316 { 1317 DWARFDebugInfoEntry::Attributes attributes; 1318 const size_t num_attributes = die->GetAttributes (this, 1319 dwarf_cu, 1320 fixed_form_sizes, 1321 attributes); 1322 if (num_attributes > 0) 1323 { 1324 Declaration decl; 1325 //DWARFExpression location; 1326 const char *name = NULL; 1327 bool is_artificial = false; 1328 lldb::user_id_t encoding_uid = LLDB_INVALID_UID; 1329 AccessType accessibility = eAccessNone; 1330 //off_t member_offset = 0; 1331 size_t byte_size = 0; 1332 size_t bit_offset = 0; 1333 size_t bit_size = 0; 1334 uint32_t i; 1335 for (i=0; i<num_attributes && !is_artificial; ++i) 1336 { 1337 const dw_attr_t attr = attributes.AttributeAtIndex(i); 1338 DWARFFormValue form_value; 1339 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 1340 { 1341 switch (attr) 1342 { 1343 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 1344 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 1345 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 1346 case DW_AT_name: name = form_value.AsCString(&get_debug_str_data()); break; 1347 case DW_AT_type: encoding_uid = form_value.Reference(dwarf_cu); break; 1348 case DW_AT_bit_offset: bit_offset = form_value.Unsigned(); break; 1349 case DW_AT_bit_size: bit_size = form_value.Unsigned(); break; 1350 case DW_AT_byte_size: byte_size = form_value.Unsigned(); break; 1351 case DW_AT_data_member_location: 1352 // if (form_value.BlockData()) 1353 // { 1354 // Value initialValue(0); 1355 // Value memberOffset(0); 1356 // const DataExtractor& debug_info_data = get_debug_info_data(); 1357 // uint32_t block_length = form_value.Unsigned(); 1358 // uint32_t block_offset = form_value.BlockData() - debug_info_data.GetDataStart(); 1359 // if (DWARFExpression::Evaluate(NULL, NULL, debug_info_data, NULL, NULL, block_offset, block_length, eRegisterKindDWARF, &initialValue, memberOffset, NULL)) 1360 // { 1361 // member_offset = memberOffset.ResolveValue(NULL, NULL).UInt(); 1362 // } 1363 // } 1364 break; 1365 1366 case DW_AT_accessibility: accessibility = DW_ACCESS_to_AccessType (form_value.Unsigned()); break; 1367 case DW_AT_artificial: is_artificial = form_value.Unsigned() != 0; break; 1368 case DW_AT_declaration: 1369 case DW_AT_description: 1370 case DW_AT_mutable: 1371 case DW_AT_visibility: 1372 default: 1373 case DW_AT_sibling: 1374 break; 1375 } 1376 } 1377 } 1378 1379 // Clang has a DWARF generation bug where sometimes it 1380 // represents fields that are references with bad byte size 1381 // and bit size/offset information such as: 1382 // 1383 // DW_AT_byte_size( 0x00 ) 1384 // DW_AT_bit_size( 0x40 ) 1385 // DW_AT_bit_offset( 0xffffffffffffffc0 ) 1386 // 1387 // So check the bit offset to make sure it is sane, and if 1388 // the values are not sane, remove them. If we don't do this 1389 // then we will end up with a crash if we try to use this 1390 // type in an expression when clang becomes unhappy with its 1391 // recycled debug info. 1392 1393 if (bit_offset > 128) 1394 { 1395 bit_size = 0; 1396 bit_offset = 0; 1397 } 1398 1399 // FIXME: Make Clang ignore Objective-C accessibility for expressions 1400 if (class_language == eLanguageTypeObjC || 1401 class_language == eLanguageTypeObjC_plus_plus) 1402 accessibility = eAccessNone; 1403 1404 if (member_idx == 0 && !is_artificial && name && (strstr (name, "_vptr$") == name)) 1405 { 1406 // Not all compilers will mark the vtable pointer 1407 // member as artificial (llvm-gcc). We can't have 1408 // the virtual members in our classes otherwise it 1409 // throws off all child offsets since we end up 1410 // having and extra pointer sized member in our 1411 // class layouts. 1412 is_artificial = true; 1413 } 1414 1415 if (is_artificial == false) 1416 { 1417 Type *member_type = ResolveTypeUID(encoding_uid); 1418 if (member_type) 1419 { 1420 if (accessibility == eAccessNone) 1421 accessibility = default_accessibility; 1422 member_accessibilities.push_back(accessibility); 1423 1424 GetClangASTContext().AddFieldToRecordType (class_clang_type, 1425 name, 1426 member_type->GetClangLayoutType(), 1427 accessibility, 1428 bit_size); 1429 } 1430 else 1431 { 1432 if (name) 1433 ReportError ("0x%8.8llx: DW_TAG_member '%s' refers to type 0x%8.8llx which was unable to be parsed", 1434 MakeUserID(die->GetOffset()), 1435 name, 1436 encoding_uid); 1437 else 1438 ReportError ("0x%8.8llx: DW_TAG_member refers to type 0x%8.8llx which was unable to be parsed", 1439 MakeUserID(die->GetOffset()), 1440 encoding_uid); 1441 } 1442 } 1443 } 1444 ++member_idx; 1445 } 1446 break; 1447 1448 case DW_TAG_subprogram: 1449 // Let the type parsing code handle this one for us. 1450 member_function_dies.Append (die); 1451 break; 1452 1453 case DW_TAG_inheritance: 1454 { 1455 is_a_class = true; 1456 if (default_accessibility == eAccessNone) 1457 default_accessibility = eAccessPrivate; 1458 // TODO: implement DW_TAG_inheritance type parsing 1459 DWARFDebugInfoEntry::Attributes attributes; 1460 const size_t num_attributes = die->GetAttributes (this, 1461 dwarf_cu, 1462 fixed_form_sizes, 1463 attributes); 1464 if (num_attributes > 0) 1465 { 1466 Declaration decl; 1467 DWARFExpression location; 1468 lldb::user_id_t encoding_uid = LLDB_INVALID_UID; 1469 AccessType accessibility = default_accessibility; 1470 bool is_virtual = false; 1471 bool is_base_of_class = true; 1472 off_t member_offset = 0; 1473 uint32_t i; 1474 for (i=0; i<num_attributes; ++i) 1475 { 1476 const dw_attr_t attr = attributes.AttributeAtIndex(i); 1477 DWARFFormValue form_value; 1478 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 1479 { 1480 switch (attr) 1481 { 1482 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 1483 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 1484 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 1485 case DW_AT_type: encoding_uid = form_value.Reference(dwarf_cu); break; 1486 case DW_AT_data_member_location: 1487 if (form_value.BlockData()) 1488 { 1489 Value initialValue(0); 1490 Value memberOffset(0); 1491 const DataExtractor& debug_info_data = get_debug_info_data(); 1492 uint32_t block_length = form_value.Unsigned(); 1493 uint32_t block_offset = form_value.BlockData() - debug_info_data.GetDataStart(); 1494 if (DWARFExpression::Evaluate (NULL, 1495 NULL, 1496 NULL, 1497 NULL, 1498 NULL, 1499 debug_info_data, 1500 block_offset, 1501 block_length, 1502 eRegisterKindDWARF, 1503 &initialValue, 1504 memberOffset, 1505 NULL)) 1506 { 1507 member_offset = memberOffset.ResolveValue(NULL, NULL).UInt(); 1508 } 1509 } 1510 break; 1511 1512 case DW_AT_accessibility: 1513 accessibility = DW_ACCESS_to_AccessType(form_value.Unsigned()); 1514 break; 1515 1516 case DW_AT_virtuality: is_virtual = form_value.Unsigned() != 0; break; 1517 default: 1518 case DW_AT_sibling: 1519 break; 1520 } 1521 } 1522 } 1523 1524 Type *base_class_type = ResolveTypeUID(encoding_uid); 1525 assert(base_class_type); 1526 1527 clang_type_t base_class_clang_type = base_class_type->GetClangFullType(); 1528 assert (base_class_clang_type); 1529 if (class_language == eLanguageTypeObjC) 1530 { 1531 GetClangASTContext().SetObjCSuperClass(class_clang_type, base_class_clang_type); 1532 } 1533 else 1534 { 1535 base_classes.push_back (GetClangASTContext().CreateBaseClassSpecifier (base_class_clang_type, 1536 accessibility, 1537 is_virtual, 1538 is_base_of_class)); 1539 } 1540 } 1541 } 1542 break; 1543 1544 default: 1545 break; 1546 } 1547 } 1548 return count; 1549 } 1550 1551 1552 clang::DeclContext* 1553 SymbolFileDWARF::GetClangDeclContextContainingTypeUID (lldb::user_id_t type_uid) 1554 { 1555 DWARFDebugInfo* debug_info = DebugInfo(); 1556 if (debug_info && UserIDMatches(type_uid)) 1557 { 1558 DWARFCompileUnitSP cu_sp; 1559 const DWARFDebugInfoEntry* die = debug_info->GetDIEPtr(type_uid, &cu_sp); 1560 if (die) 1561 return GetClangDeclContextContainingDIE (cu_sp.get(), die, NULL); 1562 } 1563 return NULL; 1564 } 1565 1566 clang::DeclContext* 1567 SymbolFileDWARF::GetClangDeclContextForTypeUID (const lldb_private::SymbolContext &sc, lldb::user_id_t type_uid) 1568 { 1569 if (UserIDMatches(type_uid)) 1570 return GetClangDeclContextForDIEOffset (sc, type_uid); 1571 return NULL; 1572 } 1573 1574 Type* 1575 SymbolFileDWARF::ResolveTypeUID (lldb::user_id_t type_uid) 1576 { 1577 if (UserIDMatches(type_uid)) 1578 { 1579 DWARFDebugInfo* debug_info = DebugInfo(); 1580 if (debug_info) 1581 { 1582 DWARFCompileUnitSP cu_sp; 1583 const DWARFDebugInfoEntry* type_die = debug_info->GetDIEPtr(type_uid, &cu_sp); 1584 if (type_die != NULL) 1585 { 1586 // We might be coming in in the middle of a type tree (a class 1587 // withing a class, an enum within a class), so parse any needed 1588 // parent DIEs before we get to this one... 1589 const DWARFDebugInfoEntry *decl_ctx_die = GetDeclContextDIEContainingDIE (cu_sp.get(), type_die); 1590 switch (decl_ctx_die->Tag()) 1591 { 1592 case DW_TAG_structure_type: 1593 case DW_TAG_union_type: 1594 case DW_TAG_class_type: 1595 ResolveType(cu_sp.get(), decl_ctx_die); 1596 break; 1597 } 1598 return ResolveType (cu_sp.get(), type_die); 1599 } 1600 } 1601 } 1602 return NULL; 1603 } 1604 1605 // This function is used when SymbolFileDWARFDebugMap owns a bunch of 1606 // SymbolFileDWARF objects to detect if this DWARF file is the one that 1607 // can resolve a clang_type. 1608 bool 1609 SymbolFileDWARF::HasForwardDeclForClangType (lldb::clang_type_t clang_type) 1610 { 1611 clang_type_t clang_type_no_qualifiers = ClangASTType::RemoveFastQualifiers(clang_type); 1612 const DWARFDebugInfoEntry* die = m_forward_decl_clang_type_to_die.lookup (clang_type_no_qualifiers); 1613 return die != NULL; 1614 } 1615 1616 1617 lldb::clang_type_t 1618 SymbolFileDWARF::ResolveClangOpaqueTypeDefinition (lldb::clang_type_t clang_type) 1619 { 1620 // We have a struct/union/class/enum that needs to be fully resolved. 1621 clang_type_t clang_type_no_qualifiers = ClangASTType::RemoveFastQualifiers(clang_type); 1622 const DWARFDebugInfoEntry* die = m_forward_decl_clang_type_to_die.lookup (clang_type_no_qualifiers); 1623 if (die == NULL) 1624 { 1625 // We have already resolved this type... 1626 return clang_type; 1627 } 1628 // Once we start resolving this type, remove it from the forward declaration 1629 // map in case anyone child members or other types require this type to get resolved. 1630 // The type will get resolved when all of the calls to SymbolFileDWARF::ResolveClangOpaqueTypeDefinition 1631 // are done. 1632 m_forward_decl_clang_type_to_die.erase (clang_type_no_qualifiers); 1633 1634 1635 // Disable external storage for this type so we don't get anymore 1636 // clang::ExternalASTSource queries for this type. 1637 ClangASTContext::SetHasExternalStorage (clang_type, false); 1638 1639 DWARFDebugInfo* debug_info = DebugInfo(); 1640 1641 DWARFCompileUnit *curr_cu = debug_info->GetCompileUnitContainingDIE (die->GetOffset()).get(); 1642 Type *type = m_die_to_type.lookup (die); 1643 1644 const dw_tag_t tag = die->Tag(); 1645 1646 DEBUG_PRINTF ("0x%8.8llx: %s (\"%s\") - resolve forward declaration...\n", 1647 MakeUserID(die->GetOffset()), 1648 DW_TAG_value_to_name(tag), 1649 type->GetName().AsCString()); 1650 assert (clang_type); 1651 DWARFDebugInfoEntry::Attributes attributes; 1652 1653 ClangASTContext &ast = GetClangASTContext(); 1654 1655 switch (tag) 1656 { 1657 case DW_TAG_structure_type: 1658 case DW_TAG_union_type: 1659 case DW_TAG_class_type: 1660 ast.StartTagDeclarationDefinition (clang_type); 1661 if (die->HasChildren()) 1662 { 1663 LanguageType class_language = eLanguageTypeUnknown; 1664 bool is_objc_class = ClangASTContext::IsObjCClassType (clang_type); 1665 if (is_objc_class) 1666 class_language = eLanguageTypeObjC; 1667 1668 int tag_decl_kind = -1; 1669 AccessType default_accessibility = eAccessNone; 1670 if (tag == DW_TAG_structure_type) 1671 { 1672 tag_decl_kind = clang::TTK_Struct; 1673 default_accessibility = eAccessPublic; 1674 } 1675 else if (tag == DW_TAG_union_type) 1676 { 1677 tag_decl_kind = clang::TTK_Union; 1678 default_accessibility = eAccessPublic; 1679 } 1680 else if (tag == DW_TAG_class_type) 1681 { 1682 tag_decl_kind = clang::TTK_Class; 1683 default_accessibility = eAccessPrivate; 1684 } 1685 1686 SymbolContext sc(GetCompUnitForDWARFCompUnit(curr_cu)); 1687 std::vector<clang::CXXBaseSpecifier *> base_classes; 1688 std::vector<int> member_accessibilities; 1689 bool is_a_class = false; 1690 // Parse members and base classes first 1691 DWARFDIECollection member_function_dies; 1692 1693 ParseChildMembers (sc, 1694 curr_cu, 1695 die, 1696 clang_type, 1697 class_language, 1698 base_classes, 1699 member_accessibilities, 1700 member_function_dies, 1701 default_accessibility, 1702 is_a_class); 1703 1704 // Now parse any methods if there were any... 1705 size_t num_functions = member_function_dies.Size(); 1706 if (num_functions > 0) 1707 { 1708 for (size_t i=0; i<num_functions; ++i) 1709 { 1710 ResolveType(curr_cu, member_function_dies.GetDIEPtrAtIndex(i)); 1711 } 1712 } 1713 1714 if (class_language == eLanguageTypeObjC) 1715 { 1716 std::string class_str (ClangASTType::GetTypeNameForOpaqueQualType(clang_type)); 1717 if (!class_str.empty()) 1718 { 1719 1720 DIEArray method_die_offsets; 1721 if (m_using_apple_tables) 1722 { 1723 if (m_apple_objc_ap.get()) 1724 m_apple_objc_ap->FindByName(class_str.c_str(), method_die_offsets); 1725 } 1726 else 1727 { 1728 if (!m_indexed) 1729 Index (); 1730 1731 ConstString class_name (class_str.c_str()); 1732 m_objc_class_selectors_index.Find (class_name, method_die_offsets); 1733 } 1734 1735 if (!method_die_offsets.empty()) 1736 { 1737 DWARFDebugInfo* debug_info = DebugInfo(); 1738 1739 DWARFCompileUnit* method_cu = NULL; 1740 const size_t num_matches = method_die_offsets.size(); 1741 for (size_t i=0; i<num_matches; ++i) 1742 { 1743 const dw_offset_t die_offset = method_die_offsets[i]; 1744 DWARFDebugInfoEntry *method_die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &method_cu); 1745 1746 if (method_die) 1747 ResolveType (method_cu, method_die); 1748 else 1749 { 1750 if (m_using_apple_tables) 1751 { 1752 ReportError (".apple_objc accelerator table had bad die 0x%8.8x for '%s'\n", 1753 die_offset, class_str.c_str()); 1754 } 1755 } 1756 } 1757 } 1758 } 1759 } 1760 1761 // If we have a DW_TAG_structure_type instead of a DW_TAG_class_type we 1762 // need to tell the clang type it is actually a class. 1763 if (class_language != eLanguageTypeObjC) 1764 { 1765 if (is_a_class && tag_decl_kind != clang::TTK_Class) 1766 ast.SetTagTypeKind (clang_type, clang::TTK_Class); 1767 } 1768 1769 // Since DW_TAG_structure_type gets used for both classes 1770 // and structures, we may need to set any DW_TAG_member 1771 // fields to have a "private" access if none was specified. 1772 // When we parsed the child members we tracked that actual 1773 // accessibility value for each DW_TAG_member in the 1774 // "member_accessibilities" array. If the value for the 1775 // member is zero, then it was set to the "default_accessibility" 1776 // which for structs was "public". Below we correct this 1777 // by setting any fields to "private" that weren't correctly 1778 // set. 1779 if (is_a_class && !member_accessibilities.empty()) 1780 { 1781 // This is a class and all members that didn't have 1782 // their access specified are private. 1783 ast.SetDefaultAccessForRecordFields (clang_type, 1784 eAccessPrivate, 1785 &member_accessibilities.front(), 1786 member_accessibilities.size()); 1787 } 1788 1789 if (!base_classes.empty()) 1790 { 1791 ast.SetBaseClassesForClassType (clang_type, 1792 &base_classes.front(), 1793 base_classes.size()); 1794 1795 // Clang will copy each CXXBaseSpecifier in "base_classes" 1796 // so we have to free them all. 1797 ClangASTContext::DeleteBaseClassSpecifiers (&base_classes.front(), 1798 base_classes.size()); 1799 } 1800 1801 } 1802 ast.CompleteTagDeclarationDefinition (clang_type); 1803 return clang_type; 1804 1805 case DW_TAG_enumeration_type: 1806 ast.StartTagDeclarationDefinition (clang_type); 1807 if (die->HasChildren()) 1808 { 1809 SymbolContext sc(GetCompUnitForDWARFCompUnit(curr_cu)); 1810 ParseChildEnumerators(sc, clang_type, type->GetByteSize(), curr_cu, die); 1811 } 1812 ast.CompleteTagDeclarationDefinition (clang_type); 1813 return clang_type; 1814 1815 default: 1816 assert(false && "not a forward clang type decl!"); 1817 break; 1818 } 1819 return NULL; 1820 } 1821 1822 Type* 1823 SymbolFileDWARF::ResolveType (DWARFCompileUnit* curr_cu, const DWARFDebugInfoEntry* type_die, bool assert_not_being_parsed) 1824 { 1825 if (type_die != NULL) 1826 { 1827 Type *type = m_die_to_type.lookup (type_die); 1828 if (type == NULL) 1829 type = GetTypeForDIE (curr_cu, type_die).get(); 1830 if (assert_not_being_parsed) 1831 assert (type != DIE_IS_BEING_PARSED); 1832 return type; 1833 } 1834 return NULL; 1835 } 1836 1837 CompileUnit* 1838 SymbolFileDWARF::GetCompUnitForDWARFCompUnit (DWARFCompileUnit* curr_cu, uint32_t cu_idx) 1839 { 1840 // Check if the symbol vendor already knows about this compile unit? 1841 if (curr_cu->GetUserData() == NULL) 1842 { 1843 // The symbol vendor doesn't know about this compile unit, we 1844 // need to parse and add it to the symbol vendor object. 1845 CompUnitSP dc_cu; 1846 ParseCompileUnit(curr_cu, dc_cu); 1847 if (dc_cu.get()) 1848 { 1849 // Figure out the compile unit index if we weren't given one 1850 if (cu_idx == UINT32_MAX) 1851 DebugInfo()->GetCompileUnit(curr_cu->GetOffset(), &cu_idx); 1852 1853 m_obj_file->GetModule()->GetSymbolVendor()->SetCompileUnitAtIndex(dc_cu, cu_idx); 1854 1855 if (m_debug_map_symfile) 1856 m_debug_map_symfile->SetCompileUnit(this, dc_cu); 1857 } 1858 } 1859 return (CompileUnit*)curr_cu->GetUserData(); 1860 } 1861 1862 bool 1863 SymbolFileDWARF::GetFunction (DWARFCompileUnit* curr_cu, const DWARFDebugInfoEntry* func_die, SymbolContext& sc) 1864 { 1865 sc.Clear(); 1866 // Check if the symbol vendor already knows about this compile unit? 1867 sc.comp_unit = GetCompUnitForDWARFCompUnit(curr_cu, UINT32_MAX); 1868 1869 sc.function = sc.comp_unit->FindFunctionByUID (MakeUserID(func_die->GetOffset())).get(); 1870 if (sc.function == NULL) 1871 sc.function = ParseCompileUnitFunction(sc, curr_cu, func_die); 1872 1873 if (sc.function) 1874 { 1875 sc.module_sp = sc.function->CalculateSymbolContextModule(); 1876 return true; 1877 } 1878 1879 return false; 1880 } 1881 1882 uint32_t 1883 SymbolFileDWARF::ResolveSymbolContext (const Address& so_addr, uint32_t resolve_scope, SymbolContext& sc) 1884 { 1885 Timer scoped_timer(__PRETTY_FUNCTION__, 1886 "SymbolFileDWARF::ResolveSymbolContext (so_addr = { section = %p, offset = 0x%llx }, resolve_scope = 0x%8.8x)", 1887 so_addr.GetSection(), 1888 so_addr.GetOffset(), 1889 resolve_scope); 1890 uint32_t resolved = 0; 1891 if (resolve_scope & ( eSymbolContextCompUnit | 1892 eSymbolContextFunction | 1893 eSymbolContextBlock | 1894 eSymbolContextLineEntry)) 1895 { 1896 lldb::addr_t file_vm_addr = so_addr.GetFileAddress(); 1897 1898 DWARFDebugInfo* debug_info = DebugInfo(); 1899 if (debug_info) 1900 { 1901 dw_offset_t cu_offset = debug_info->GetCompileUnitAranges().FindAddress(file_vm_addr); 1902 if (cu_offset != DW_INVALID_OFFSET) 1903 { 1904 uint32_t cu_idx; 1905 DWARFCompileUnit* curr_cu = debug_info->GetCompileUnit(cu_offset, &cu_idx).get(); 1906 if (curr_cu) 1907 { 1908 sc.comp_unit = GetCompUnitForDWARFCompUnit(curr_cu, cu_idx); 1909 assert(sc.comp_unit != NULL); 1910 resolved |= eSymbolContextCompUnit; 1911 1912 if (resolve_scope & eSymbolContextLineEntry) 1913 { 1914 LineTable *line_table = sc.comp_unit->GetLineTable(); 1915 if (line_table == NULL) 1916 { 1917 if (ParseCompileUnitLineTable(sc)) 1918 line_table = sc.comp_unit->GetLineTable(); 1919 } 1920 if (line_table != NULL) 1921 { 1922 if (so_addr.IsLinkedAddress()) 1923 { 1924 Address linked_addr (so_addr); 1925 linked_addr.ResolveLinkedAddress(); 1926 if (line_table->FindLineEntryByAddress (linked_addr, sc.line_entry)) 1927 { 1928 resolved |= eSymbolContextLineEntry; 1929 } 1930 } 1931 else if (line_table->FindLineEntryByAddress (so_addr, sc.line_entry)) 1932 { 1933 resolved |= eSymbolContextLineEntry; 1934 } 1935 } 1936 } 1937 1938 if (resolve_scope & (eSymbolContextFunction | eSymbolContextBlock)) 1939 { 1940 DWARFDebugInfoEntry *function_die = NULL; 1941 DWARFDebugInfoEntry *block_die = NULL; 1942 if (resolve_scope & eSymbolContextBlock) 1943 { 1944 curr_cu->LookupAddress(file_vm_addr, &function_die, &block_die); 1945 } 1946 else 1947 { 1948 curr_cu->LookupAddress(file_vm_addr, &function_die, NULL); 1949 } 1950 1951 if (function_die != NULL) 1952 { 1953 sc.function = sc.comp_unit->FindFunctionByUID (MakeUserID(function_die->GetOffset())).get(); 1954 if (sc.function == NULL) 1955 sc.function = ParseCompileUnitFunction(sc, curr_cu, function_die); 1956 } 1957 1958 if (sc.function != NULL) 1959 { 1960 resolved |= eSymbolContextFunction; 1961 1962 if (resolve_scope & eSymbolContextBlock) 1963 { 1964 Block& block = sc.function->GetBlock (true); 1965 1966 if (block_die != NULL) 1967 sc.block = block.FindBlockByID (MakeUserID(block_die->GetOffset())); 1968 else 1969 sc.block = block.FindBlockByID (MakeUserID(function_die->GetOffset())); 1970 if (sc.block) 1971 resolved |= eSymbolContextBlock; 1972 } 1973 } 1974 } 1975 } 1976 } 1977 } 1978 } 1979 return resolved; 1980 } 1981 1982 1983 1984 uint32_t 1985 SymbolFileDWARF::ResolveSymbolContext(const FileSpec& file_spec, uint32_t line, bool check_inlines, uint32_t resolve_scope, SymbolContextList& sc_list) 1986 { 1987 const uint32_t prev_size = sc_list.GetSize(); 1988 if (resolve_scope & eSymbolContextCompUnit) 1989 { 1990 DWARFDebugInfo* debug_info = DebugInfo(); 1991 if (debug_info) 1992 { 1993 uint32_t cu_idx; 1994 DWARFCompileUnit* curr_cu = NULL; 1995 1996 for (cu_idx = 0; (curr_cu = debug_info->GetCompileUnitAtIndex(cu_idx)) != NULL; ++cu_idx) 1997 { 1998 CompileUnit *dc_cu = GetCompUnitForDWARFCompUnit(curr_cu, cu_idx); 1999 bool file_spec_matches_cu_file_spec = dc_cu != NULL && FileSpec::Compare(file_spec, *dc_cu, false) == 0; 2000 if (check_inlines || file_spec_matches_cu_file_spec) 2001 { 2002 SymbolContext sc (m_obj_file->GetModule()); 2003 sc.comp_unit = GetCompUnitForDWARFCompUnit(curr_cu, cu_idx); 2004 assert(sc.comp_unit != NULL); 2005 2006 uint32_t file_idx = UINT32_MAX; 2007 2008 // If we are looking for inline functions only and we don't 2009 // find it in the support files, we are done. 2010 if (check_inlines) 2011 { 2012 file_idx = sc.comp_unit->GetSupportFiles().FindFileIndex (1, file_spec, true); 2013 if (file_idx == UINT32_MAX) 2014 continue; 2015 } 2016 2017 if (line != 0) 2018 { 2019 LineTable *line_table = sc.comp_unit->GetLineTable(); 2020 2021 if (line_table != NULL && line != 0) 2022 { 2023 // We will have already looked up the file index if 2024 // we are searching for inline entries. 2025 if (!check_inlines) 2026 file_idx = sc.comp_unit->GetSupportFiles().FindFileIndex (1, file_spec, true); 2027 2028 if (file_idx != UINT32_MAX) 2029 { 2030 uint32_t found_line; 2031 uint32_t line_idx = line_table->FindLineEntryIndexByFileIndex (0, file_idx, line, false, &sc.line_entry); 2032 found_line = sc.line_entry.line; 2033 2034 while (line_idx != UINT32_MAX) 2035 { 2036 sc.function = NULL; 2037 sc.block = NULL; 2038 if (resolve_scope & (eSymbolContextFunction | eSymbolContextBlock)) 2039 { 2040 const lldb::addr_t file_vm_addr = sc.line_entry.range.GetBaseAddress().GetFileAddress(); 2041 if (file_vm_addr != LLDB_INVALID_ADDRESS) 2042 { 2043 DWARFDebugInfoEntry *function_die = NULL; 2044 DWARFDebugInfoEntry *block_die = NULL; 2045 curr_cu->LookupAddress(file_vm_addr, &function_die, resolve_scope & eSymbolContextBlock ? &block_die : NULL); 2046 2047 if (function_die != NULL) 2048 { 2049 sc.function = sc.comp_unit->FindFunctionByUID (MakeUserID(function_die->GetOffset())).get(); 2050 if (sc.function == NULL) 2051 sc.function = ParseCompileUnitFunction(sc, curr_cu, function_die); 2052 } 2053 2054 if (sc.function != NULL) 2055 { 2056 Block& block = sc.function->GetBlock (true); 2057 2058 if (block_die != NULL) 2059 sc.block = block.FindBlockByID (MakeUserID(block_die->GetOffset())); 2060 else 2061 sc.block = block.FindBlockByID (MakeUserID(function_die->GetOffset())); 2062 } 2063 } 2064 } 2065 2066 sc_list.Append(sc); 2067 line_idx = line_table->FindLineEntryIndexByFileIndex (line_idx + 1, file_idx, found_line, true, &sc.line_entry); 2068 } 2069 } 2070 } 2071 else if (file_spec_matches_cu_file_spec && !check_inlines) 2072 { 2073 // only append the context if we aren't looking for inline call sites 2074 // by file and line and if the file spec matches that of the compile unit 2075 sc_list.Append(sc); 2076 } 2077 } 2078 else if (file_spec_matches_cu_file_spec && !check_inlines) 2079 { 2080 // only append the context if we aren't looking for inline call sites 2081 // by file and line and if the file spec matches that of the compile unit 2082 sc_list.Append(sc); 2083 } 2084 2085 if (!check_inlines) 2086 break; 2087 } 2088 } 2089 } 2090 } 2091 return sc_list.GetSize() - prev_size; 2092 } 2093 2094 void 2095 SymbolFileDWARF::Index () 2096 { 2097 if (m_indexed) 2098 return; 2099 m_indexed = true; 2100 Timer scoped_timer (__PRETTY_FUNCTION__, 2101 "SymbolFileDWARF::Index (%s)", 2102 GetObjectFile()->GetFileSpec().GetFilename().AsCString()); 2103 2104 DWARFDebugInfo* debug_info = DebugInfo(); 2105 if (debug_info) 2106 { 2107 uint32_t cu_idx = 0; 2108 const uint32_t num_compile_units = GetNumCompileUnits(); 2109 for (cu_idx = 0; cu_idx < num_compile_units; ++cu_idx) 2110 { 2111 DWARFCompileUnit* curr_cu = debug_info->GetCompileUnitAtIndex(cu_idx); 2112 2113 bool clear_dies = curr_cu->ExtractDIEsIfNeeded (false) > 1; 2114 2115 curr_cu->Index (cu_idx, 2116 m_function_basename_index, 2117 m_function_fullname_index, 2118 m_function_method_index, 2119 m_function_selector_index, 2120 m_objc_class_selectors_index, 2121 m_global_index, 2122 m_type_index, 2123 m_namespace_index); 2124 2125 // Keep memory down by clearing DIEs if this generate function 2126 // caused them to be parsed 2127 if (clear_dies) 2128 curr_cu->ClearDIEs (true); 2129 } 2130 2131 m_function_basename_index.Finalize(); 2132 m_function_fullname_index.Finalize(); 2133 m_function_method_index.Finalize(); 2134 m_function_selector_index.Finalize(); 2135 m_objc_class_selectors_index.Finalize(); 2136 m_global_index.Finalize(); 2137 m_type_index.Finalize(); 2138 m_namespace_index.Finalize(); 2139 2140 #if defined (ENABLE_DEBUG_PRINTF) 2141 StreamFile s(stdout, false); 2142 s.Printf ("DWARF index for '%s/%s':", 2143 GetObjectFile()->GetFileSpec().GetDirectory().AsCString(), 2144 GetObjectFile()->GetFileSpec().GetFilename().AsCString()); 2145 s.Printf("\nFunction basenames:\n"); m_function_basename_index.Dump (&s); 2146 s.Printf("\nFunction fullnames:\n"); m_function_fullname_index.Dump (&s); 2147 s.Printf("\nFunction methods:\n"); m_function_method_index.Dump (&s); 2148 s.Printf("\nFunction selectors:\n"); m_function_selector_index.Dump (&s); 2149 s.Printf("\nObjective C class selectors:\n"); m_objc_class_selectors_index.Dump (&s); 2150 s.Printf("\nGlobals and statics:\n"); m_global_index.Dump (&s); 2151 s.Printf("\nTypes:\n"); m_type_index.Dump (&s); 2152 s.Printf("\nNamepaces:\n"); m_namespace_index.Dump (&s); 2153 #endif 2154 } 2155 } 2156 2157 bool 2158 SymbolFileDWARF::NamespaceDeclMatchesThisSymbolFile (const ClangNamespaceDecl *namespace_decl) 2159 { 2160 if (namespace_decl == NULL) 2161 { 2162 // Invalid namespace decl which means we aren't matching only things 2163 // in this symbol file, so return true to indicate it matches this 2164 // symbol file. 2165 return true; 2166 } 2167 2168 clang::ASTContext *namespace_ast = namespace_decl->GetASTContext(); 2169 2170 if (namespace_ast == NULL) 2171 return true; // No AST in the "namespace_decl", return true since it 2172 // could then match any symbol file, including this one 2173 2174 if (namespace_ast == GetClangASTContext().getASTContext()) 2175 return true; // The ASTs match, return true 2176 2177 // The namespace AST was valid, and it does not match... 2178 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2179 2180 if (log) 2181 log->Printf("Valid namespace does not match symbol file"); 2182 2183 return false; 2184 } 2185 2186 bool 2187 SymbolFileDWARF::DIEIsInNamespace (const ClangNamespaceDecl *namespace_decl, 2188 DWARFCompileUnit* cu, 2189 const DWARFDebugInfoEntry* die) 2190 { 2191 // No namespace specified, so the answesr i 2192 if (namespace_decl == NULL) 2193 return true; 2194 2195 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2196 2197 const DWARFDebugInfoEntry *decl_ctx_die = GetDeclContextDIEContainingDIE (cu, die); 2198 if (decl_ctx_die) 2199 { 2200 2201 clang::NamespaceDecl *clang_namespace_decl = namespace_decl->GetNamespaceDecl(); 2202 if (clang_namespace_decl) 2203 { 2204 if (decl_ctx_die->Tag() != DW_TAG_namespace) 2205 { 2206 if (log) 2207 log->Printf("Found a match, but its parent is not a namespace"); 2208 return false; 2209 } 2210 2211 DeclContextToDIEMap::iterator pos = m_decl_ctx_to_die.find(clang_namespace_decl); 2212 2213 if (pos == m_decl_ctx_to_die.end()) 2214 { 2215 if (log) 2216 log->Printf("Found a match in a namespace, but its parent is not the requested namespace"); 2217 2218 return false; 2219 } 2220 2221 return pos->second.count (decl_ctx_die); 2222 } 2223 else 2224 { 2225 // We have a namespace_decl that was not NULL but it contained 2226 // a NULL "clang::NamespaceDecl", so this means the global namespace 2227 // So as long the the contained decl context DIE isn't a namespace 2228 // we should be ok. 2229 if (decl_ctx_die->Tag() != DW_TAG_namespace) 2230 return true; 2231 } 2232 } 2233 2234 if (log) 2235 log->Printf("Found a match, but its parent doesn't exist"); 2236 2237 return false; 2238 } 2239 uint32_t 2240 SymbolFileDWARF::FindGlobalVariables (const ConstString &name, const lldb_private::ClangNamespaceDecl *namespace_decl, bool append, uint32_t max_matches, VariableList& variables) 2241 { 2242 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2243 2244 if (log) 2245 { 2246 log->Printf ("SymbolFileDWARF::FindGlobalVariables (file=\"%s/%s\", name=\"%s\", append=%u, max_matches=%u, variables)", 2247 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 2248 m_obj_file->GetFileSpec().GetFilename().GetCString(), 2249 name.GetCString(), append, max_matches); 2250 } 2251 2252 if (!NamespaceDeclMatchesThisSymbolFile(namespace_decl)) 2253 return 0; 2254 2255 DWARFDebugInfo* info = DebugInfo(); 2256 if (info == NULL) 2257 return 0; 2258 2259 // If we aren't appending the results to this list, then clear the list 2260 if (!append) 2261 variables.Clear(); 2262 2263 // Remember how many variables are in the list before we search in case 2264 // we are appending the results to a variable list. 2265 const uint32_t original_size = variables.GetSize(); 2266 2267 DIEArray die_offsets; 2268 2269 if (m_using_apple_tables) 2270 { 2271 if (m_apple_names_ap.get()) 2272 { 2273 const char *name_cstr = name.GetCString(); 2274 const char *base_name_start; 2275 const char *base_name_end = NULL; 2276 2277 if (!CPPLanguageRuntime::StripNamespacesFromVariableName(name_cstr, base_name_start, base_name_end)) 2278 base_name_start = name_cstr; 2279 2280 m_apple_names_ap->FindByName (base_name_start, die_offsets); 2281 } 2282 } 2283 else 2284 { 2285 // Index the DWARF if we haven't already 2286 if (!m_indexed) 2287 Index (); 2288 2289 m_global_index.Find (name, die_offsets); 2290 } 2291 2292 const size_t num_matches = die_offsets.size(); 2293 if (num_matches) 2294 { 2295 SymbolContext sc; 2296 sc.module_sp = m_obj_file->GetModule(); 2297 assert (sc.module_sp); 2298 2299 DWARFDebugInfo* debug_info = DebugInfo(); 2300 DWARFCompileUnit* dwarf_cu = NULL; 2301 const DWARFDebugInfoEntry* die = NULL; 2302 for (size_t i=0; i<num_matches; ++i) 2303 { 2304 const dw_offset_t die_offset = die_offsets[i]; 2305 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2306 2307 if (die) 2308 { 2309 sc.comp_unit = GetCompUnitForDWARFCompUnit(dwarf_cu, UINT32_MAX); 2310 assert(sc.comp_unit != NULL); 2311 2312 if (namespace_decl && !DIEIsInNamespace (namespace_decl, dwarf_cu, die)) 2313 continue; 2314 2315 ParseVariables(sc, dwarf_cu, LLDB_INVALID_ADDRESS, die, false, false, &variables); 2316 2317 if (variables.GetSize() - original_size >= max_matches) 2318 break; 2319 } 2320 else 2321 { 2322 if (m_using_apple_tables) 2323 { 2324 ReportError (".apple_names accelerator table had bad die 0x%8.8x for '%s'\n", 2325 die_offset, name.GetCString()); 2326 } 2327 } 2328 } 2329 } 2330 2331 // Return the number of variable that were appended to the list 2332 return variables.GetSize() - original_size; 2333 } 2334 2335 uint32_t 2336 SymbolFileDWARF::FindGlobalVariables(const RegularExpression& regex, bool append, uint32_t max_matches, VariableList& variables) 2337 { 2338 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2339 2340 if (log) 2341 { 2342 log->Printf ("SymbolFileDWARF::FindGlobalVariables (file=\"%s/%s\", regex=\"%s\", append=%u, max_matches=%u, variables)", 2343 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 2344 m_obj_file->GetFileSpec().GetFilename().GetCString(), 2345 regex.GetText(), append, max_matches); 2346 } 2347 2348 DWARFDebugInfo* info = DebugInfo(); 2349 if (info == NULL) 2350 return 0; 2351 2352 // If we aren't appending the results to this list, then clear the list 2353 if (!append) 2354 variables.Clear(); 2355 2356 // Remember how many variables are in the list before we search in case 2357 // we are appending the results to a variable list. 2358 const uint32_t original_size = variables.GetSize(); 2359 2360 DIEArray die_offsets; 2361 2362 if (m_using_apple_tables) 2363 { 2364 if (m_apple_names_ap.get()) 2365 m_apple_names_ap->AppendAllDIEsThatMatchingRegex (regex, die_offsets); 2366 } 2367 else 2368 { 2369 // Index the DWARF if we haven't already 2370 if (!m_indexed) 2371 Index (); 2372 2373 m_global_index.Find (regex, die_offsets); 2374 } 2375 2376 SymbolContext sc; 2377 sc.module_sp = m_obj_file->GetModule(); 2378 assert (sc.module_sp); 2379 2380 DWARFCompileUnit* dwarf_cu = NULL; 2381 const DWARFDebugInfoEntry* die = NULL; 2382 const size_t num_matches = die_offsets.size(); 2383 if (num_matches) 2384 { 2385 DWARFDebugInfo* debug_info = DebugInfo(); 2386 for (size_t i=0; i<num_matches; ++i) 2387 { 2388 const dw_offset_t die_offset = die_offsets[i]; 2389 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2390 2391 if (die) 2392 { 2393 sc.comp_unit = GetCompUnitForDWARFCompUnit(dwarf_cu, UINT32_MAX); 2394 2395 ParseVariables(sc, dwarf_cu, LLDB_INVALID_ADDRESS, die, false, false, &variables); 2396 2397 if (variables.GetSize() - original_size >= max_matches) 2398 break; 2399 } 2400 else 2401 { 2402 if (m_using_apple_tables) 2403 { 2404 ReportError (".apple_names accelerator table had bad die 0x%8.8x for regex '%s'\n", 2405 die_offset, regex.GetText()); 2406 } 2407 } 2408 } 2409 } 2410 2411 // Return the number of variable that were appended to the list 2412 return variables.GetSize() - original_size; 2413 } 2414 2415 2416 bool 2417 SymbolFileDWARF::ResolveFunction (dw_offset_t die_offset, 2418 DWARFCompileUnit *&dwarf_cu, 2419 SymbolContextList& sc_list) 2420 { 2421 const DWARFDebugInfoEntry *die = DebugInfo()->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2422 return ResolveFunction (dwarf_cu, die, sc_list); 2423 } 2424 2425 2426 bool 2427 SymbolFileDWARF::ResolveFunction (DWARFCompileUnit *cu, 2428 const DWARFDebugInfoEntry *die, 2429 SymbolContextList& sc_list) 2430 { 2431 SymbolContext sc; 2432 2433 if (die == NULL) 2434 return false; 2435 2436 // If we were passed a die that is not a function, just return false... 2437 if (die->Tag() != DW_TAG_subprogram && die->Tag() != DW_TAG_inlined_subroutine) 2438 return false; 2439 2440 const DWARFDebugInfoEntry* inlined_die = NULL; 2441 if (die->Tag() == DW_TAG_inlined_subroutine) 2442 { 2443 inlined_die = die; 2444 2445 while ((die = die->GetParent()) != NULL) 2446 { 2447 if (die->Tag() == DW_TAG_subprogram) 2448 break; 2449 } 2450 } 2451 assert (die->Tag() == DW_TAG_subprogram); 2452 if (GetFunction (cu, die, sc)) 2453 { 2454 Address addr; 2455 // Parse all blocks if needed 2456 if (inlined_die) 2457 { 2458 sc.block = sc.function->GetBlock (true).FindBlockByID (MakeUserID(inlined_die->GetOffset())); 2459 assert (sc.block != NULL); 2460 if (sc.block->GetStartAddress (addr) == false) 2461 addr.Clear(); 2462 } 2463 else 2464 { 2465 sc.block = NULL; 2466 addr = sc.function->GetAddressRange().GetBaseAddress(); 2467 } 2468 2469 if (addr.IsValid()) 2470 { 2471 2472 // We found the function, so we should find the line table 2473 // and line table entry as well 2474 LineTable *line_table = sc.comp_unit->GetLineTable(); 2475 if (line_table == NULL) 2476 { 2477 if (ParseCompileUnitLineTable(sc)) 2478 line_table = sc.comp_unit->GetLineTable(); 2479 } 2480 if (line_table != NULL) 2481 line_table->FindLineEntryByAddress (addr, sc.line_entry); 2482 2483 sc_list.Append(sc); 2484 return true; 2485 } 2486 } 2487 2488 return false; 2489 } 2490 2491 void 2492 SymbolFileDWARF::FindFunctions (const ConstString &name, 2493 const NameToDIE &name_to_die, 2494 SymbolContextList& sc_list) 2495 { 2496 DIEArray die_offsets; 2497 if (name_to_die.Find (name, die_offsets)) 2498 { 2499 ParseFunctions (die_offsets, sc_list); 2500 } 2501 } 2502 2503 2504 void 2505 SymbolFileDWARF::FindFunctions (const RegularExpression ®ex, 2506 const NameToDIE &name_to_die, 2507 SymbolContextList& sc_list) 2508 { 2509 DIEArray die_offsets; 2510 if (name_to_die.Find (regex, die_offsets)) 2511 { 2512 ParseFunctions (die_offsets, sc_list); 2513 } 2514 } 2515 2516 2517 void 2518 SymbolFileDWARF::FindFunctions (const RegularExpression ®ex, 2519 const DWARFMappedHash::MemoryTable &memory_table, 2520 SymbolContextList& sc_list) 2521 { 2522 DIEArray die_offsets; 2523 if (memory_table.AppendAllDIEsThatMatchingRegex (regex, die_offsets)) 2524 { 2525 ParseFunctions (die_offsets, sc_list); 2526 } 2527 } 2528 2529 void 2530 SymbolFileDWARF::ParseFunctions (const DIEArray &die_offsets, 2531 SymbolContextList& sc_list) 2532 { 2533 const size_t num_matches = die_offsets.size(); 2534 if (num_matches) 2535 { 2536 SymbolContext sc; 2537 2538 DWARFCompileUnit* dwarf_cu = NULL; 2539 for (size_t i=0; i<num_matches; ++i) 2540 { 2541 const dw_offset_t die_offset = die_offsets[i]; 2542 ResolveFunction (die_offset, dwarf_cu, sc_list); 2543 } 2544 } 2545 } 2546 2547 bool 2548 SymbolFileDWARF::FunctionDieMatchesPartialName (const DWARFDebugInfoEntry* die, 2549 const DWARFCompileUnit *dwarf_cu, 2550 uint32_t name_type_mask, 2551 const char *partial_name, 2552 const char *base_name_start, 2553 const char *base_name_end) 2554 { 2555 // If we are looking only for methods, throw away all the ones that aren't in C++ classes: 2556 if (name_type_mask == eFunctionNameTypeMethod 2557 || name_type_mask == eFunctionNameTypeBase) 2558 { 2559 clang::DeclContext *containing_decl_ctx = GetClangDeclContextContainingDIEOffset(die->GetOffset()); 2560 if (!containing_decl_ctx) 2561 return false; 2562 2563 bool is_cxx_method = DeclKindIsCXXClass(containing_decl_ctx->getDeclKind()); 2564 2565 if (!is_cxx_method && name_type_mask == eFunctionNameTypeMethod) 2566 return false; 2567 if (is_cxx_method && name_type_mask == eFunctionNameTypeBase) 2568 return false; 2569 } 2570 2571 // Now we need to check whether the name we got back for this type matches the extra specifications 2572 // that were in the name we're looking up: 2573 if (base_name_start != partial_name || *base_name_end != '\0') 2574 { 2575 // First see if the stuff to the left matches the full name. To do that let's see if 2576 // we can pull out the mips linkage name attribute: 2577 2578 Mangled best_name; 2579 2580 DWARFDebugInfoEntry::Attributes attributes; 2581 die->GetAttributes(this, dwarf_cu, NULL, attributes); 2582 uint32_t idx = attributes.FindAttributeIndex(DW_AT_MIPS_linkage_name); 2583 if (idx != UINT32_MAX) 2584 { 2585 DWARFFormValue form_value; 2586 if (attributes.ExtractFormValueAtIndex(this, idx, form_value)) 2587 { 2588 const char *name = form_value.AsCString(&get_debug_str_data()); 2589 best_name.SetValue (name, true); 2590 } 2591 } 2592 if (best_name) 2593 { 2594 const char *demangled = best_name.GetDemangledName().GetCString(); 2595 if (demangled) 2596 { 2597 std::string name_no_parens(partial_name, base_name_end - partial_name); 2598 if (strstr (demangled, name_no_parens.c_str()) == NULL) 2599 return false; 2600 } 2601 } 2602 } 2603 2604 return true; 2605 } 2606 2607 uint32_t 2608 SymbolFileDWARF::FindFunctions (const ConstString &name, 2609 const lldb_private::ClangNamespaceDecl *namespace_decl, 2610 uint32_t name_type_mask, 2611 bool append, 2612 SymbolContextList& sc_list) 2613 { 2614 Timer scoped_timer (__PRETTY_FUNCTION__, 2615 "SymbolFileDWARF::FindFunctions (name = '%s')", 2616 name.AsCString()); 2617 2618 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2619 2620 if (log) 2621 { 2622 log->Printf ("SymbolFileDWARF::FindFunctions (file=\"%s/%s\", name=\"%s\", name_type_mask=0x%x, append=%u, sc_list)", 2623 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 2624 m_obj_file->GetFileSpec().GetFilename().GetCString(), 2625 name.GetCString(), name_type_mask, append); 2626 } 2627 2628 // If we aren't appending the results to this list, then clear the list 2629 if (!append) 2630 sc_list.Clear(); 2631 2632 if (!NamespaceDeclMatchesThisSymbolFile(namespace_decl)) 2633 return 0; 2634 2635 // If name is empty then we won't find anything. 2636 if (name.IsEmpty()) 2637 return 0; 2638 2639 // Remember how many sc_list are in the list before we search in case 2640 // we are appending the results to a variable list. 2641 2642 const uint32_t original_size = sc_list.GetSize(); 2643 2644 const char *name_cstr = name.GetCString(); 2645 uint32_t effective_name_type_mask = eFunctionNameTypeNone; 2646 const char *base_name_start = name_cstr; 2647 const char *base_name_end = name_cstr + strlen(name_cstr); 2648 2649 if (name_type_mask & eFunctionNameTypeAuto) 2650 { 2651 if (CPPLanguageRuntime::IsCPPMangledName (name_cstr)) 2652 effective_name_type_mask = eFunctionNameTypeFull; 2653 else if (ObjCLanguageRuntime::IsPossibleObjCMethodName (name_cstr)) 2654 effective_name_type_mask = eFunctionNameTypeFull; 2655 else 2656 { 2657 if (ObjCLanguageRuntime::IsPossibleObjCSelector(name_cstr)) 2658 effective_name_type_mask |= eFunctionNameTypeSelector; 2659 2660 if (CPPLanguageRuntime::IsPossibleCPPCall(name_cstr, base_name_start, base_name_end)) 2661 effective_name_type_mask |= (eFunctionNameTypeMethod | eFunctionNameTypeBase); 2662 } 2663 } 2664 else 2665 { 2666 effective_name_type_mask = name_type_mask; 2667 if (effective_name_type_mask & eFunctionNameTypeMethod || name_type_mask & eFunctionNameTypeBase) 2668 { 2669 // If they've asked for a CPP method or function name and it can't be that, we don't 2670 // even need to search for CPP methods or names. 2671 if (!CPPLanguageRuntime::IsPossibleCPPCall(name_cstr, base_name_start, base_name_end)) 2672 { 2673 effective_name_type_mask &= ~(eFunctionNameTypeMethod | eFunctionNameTypeBase); 2674 if (effective_name_type_mask == eFunctionNameTypeNone) 2675 return 0; 2676 } 2677 } 2678 2679 if (effective_name_type_mask & eFunctionNameTypeSelector) 2680 { 2681 if (!ObjCLanguageRuntime::IsPossibleObjCSelector(name_cstr)) 2682 { 2683 effective_name_type_mask &= ~(eFunctionNameTypeSelector); 2684 if (effective_name_type_mask == eFunctionNameTypeNone) 2685 return 0; 2686 } 2687 } 2688 } 2689 2690 DWARFDebugInfo* info = DebugInfo(); 2691 if (info == NULL) 2692 return 0; 2693 2694 DWARFCompileUnit *dwarf_cu = NULL; 2695 if (m_using_apple_tables) 2696 { 2697 if (m_apple_names_ap.get()) 2698 { 2699 2700 DIEArray die_offsets; 2701 2702 uint32_t num_matches = 0; 2703 2704 if (effective_name_type_mask & eFunctionNameTypeFull) 2705 { 2706 // If they asked for the full name, match what they typed. At some point we may 2707 // want to canonicalize this (strip double spaces, etc. For now, we just add all the 2708 // dies that we find by exact match. 2709 num_matches = m_apple_names_ap->FindByName (name_cstr, die_offsets); 2710 for (uint32_t i = 0; i < num_matches; i++) 2711 { 2712 const dw_offset_t die_offset = die_offsets[i]; 2713 const DWARFDebugInfoEntry *die = info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2714 if (die) 2715 { 2716 if (namespace_decl && !DIEIsInNamespace (namespace_decl, dwarf_cu, die)) 2717 continue; 2718 2719 ResolveFunction (dwarf_cu, die, sc_list); 2720 } 2721 else 2722 { 2723 ReportError (".apple_names accelerator table had bad die 0x%8.8x for '%s'\n", 2724 die_offset, name_cstr); 2725 } 2726 } 2727 } 2728 else 2729 { 2730 if (effective_name_type_mask & eFunctionNameTypeSelector) 2731 { 2732 if (namespace_decl && *namespace_decl) 2733 return 0; // no selectors in namespaces 2734 2735 num_matches = m_apple_names_ap->FindByName (name_cstr, die_offsets); 2736 // Now make sure these are actually ObjC methods. In this case we can simply look up the name, 2737 // and if it is an ObjC method name, we're good. 2738 2739 for (uint32_t i = 0; i < num_matches; i++) 2740 { 2741 const dw_offset_t die_offset = die_offsets[i]; 2742 const DWARFDebugInfoEntry* die = info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2743 if (die) 2744 { 2745 const char *die_name = die->GetName(this, dwarf_cu); 2746 if (ObjCLanguageRuntime::IsPossibleObjCMethodName(die_name)) 2747 ResolveFunction (dwarf_cu, die, sc_list); 2748 } 2749 else 2750 { 2751 ReportError (".apple_names accelerator table had bad die 0x%8.8x for '%s'\n", 2752 die_offset, name_cstr); 2753 } 2754 } 2755 die_offsets.clear(); 2756 } 2757 2758 if (effective_name_type_mask & eFunctionNameTypeMethod 2759 || effective_name_type_mask & eFunctionNameTypeBase) 2760 { 2761 if ((effective_name_type_mask & eFunctionNameTypeMethod) && 2762 (namespace_decl && *namespace_decl)) 2763 return 0; // no methods in namespaces 2764 2765 // The apple_names table stores just the "base name" of C++ methods in the table. So we have to 2766 // extract the base name, look that up, and if there is any other information in the name we were 2767 // passed in we have to post-filter based on that. 2768 2769 // FIXME: Arrange the logic above so that we don't calculate the base name twice: 2770 std::string base_name(base_name_start, base_name_end - base_name_start); 2771 num_matches = m_apple_names_ap->FindByName (base_name.c_str(), die_offsets); 2772 2773 for (uint32_t i = 0; i < num_matches; i++) 2774 { 2775 const dw_offset_t die_offset = die_offsets[i]; 2776 const DWARFDebugInfoEntry* die = info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 2777 if (die) 2778 { 2779 if (namespace_decl && !DIEIsInNamespace (namespace_decl, dwarf_cu, die)) 2780 continue; 2781 2782 if (!FunctionDieMatchesPartialName(die, 2783 dwarf_cu, 2784 effective_name_type_mask, 2785 name_cstr, 2786 base_name_start, 2787 base_name_end)) 2788 continue; 2789 2790 // If we get to here, the die is good, and we should add it: 2791 ResolveFunction (dwarf_cu, die, sc_list); 2792 } 2793 else 2794 { 2795 ReportError (".apple_names accelerator table had bad die 0x%8.8x for '%s'\n", 2796 die_offset, name_cstr); 2797 } 2798 } 2799 die_offsets.clear(); 2800 } 2801 } 2802 } 2803 } 2804 else 2805 { 2806 2807 // Index the DWARF if we haven't already 2808 if (!m_indexed) 2809 Index (); 2810 2811 if (name_type_mask & eFunctionNameTypeFull) 2812 FindFunctions (name, m_function_fullname_index, sc_list); 2813 2814 std::string base_name(base_name_start, base_name_end - base_name_start); 2815 ConstString base_name_const(base_name.c_str()); 2816 DIEArray die_offsets; 2817 DWARFCompileUnit *dwarf_cu = NULL; 2818 2819 if (effective_name_type_mask & eFunctionNameTypeBase) 2820 { 2821 uint32_t num_base = m_function_basename_index.Find(base_name_const, die_offsets); 2822 for (uint32_t i = 0; i < num_base; i++) 2823 { 2824 const DWARFDebugInfoEntry* die = info->GetDIEPtrWithCompileUnitHint (die_offsets[i], &dwarf_cu); 2825 if (die) 2826 { 2827 if (namespace_decl && !DIEIsInNamespace (namespace_decl, dwarf_cu, die)) 2828 continue; 2829 2830 if (!FunctionDieMatchesPartialName(die, 2831 dwarf_cu, 2832 effective_name_type_mask, 2833 name_cstr, 2834 base_name_start, 2835 base_name_end)) 2836 continue; 2837 2838 // If we get to here, the die is good, and we should add it: 2839 ResolveFunction (dwarf_cu, die, sc_list); 2840 } 2841 } 2842 die_offsets.clear(); 2843 } 2844 2845 if (effective_name_type_mask & eFunctionNameTypeMethod) 2846 { 2847 if (namespace_decl && *namespace_decl) 2848 return 0; // no methods in namespaces 2849 2850 uint32_t num_base = m_function_method_index.Find(base_name_const, die_offsets); 2851 { 2852 for (uint32_t i = 0; i < num_base; i++) 2853 { 2854 const DWARFDebugInfoEntry* die = info->GetDIEPtrWithCompileUnitHint (die_offsets[i], &dwarf_cu); 2855 if (die) 2856 { 2857 if (!FunctionDieMatchesPartialName(die, 2858 dwarf_cu, 2859 effective_name_type_mask, 2860 name_cstr, 2861 base_name_start, 2862 base_name_end)) 2863 continue; 2864 2865 // If we get to here, the die is good, and we should add it: 2866 ResolveFunction (dwarf_cu, die, sc_list); 2867 } 2868 } 2869 } 2870 die_offsets.clear(); 2871 } 2872 2873 if ((effective_name_type_mask & eFunctionNameTypeSelector) && (!namespace_decl || !*namespace_decl)) 2874 { 2875 FindFunctions (name, m_function_selector_index, sc_list); 2876 } 2877 2878 } 2879 2880 // Return the number of variable that were appended to the list 2881 return sc_list.GetSize() - original_size; 2882 } 2883 2884 uint32_t 2885 SymbolFileDWARF::FindFunctions(const RegularExpression& regex, bool append, SymbolContextList& sc_list) 2886 { 2887 Timer scoped_timer (__PRETTY_FUNCTION__, 2888 "SymbolFileDWARF::FindFunctions (regex = '%s')", 2889 regex.GetText()); 2890 2891 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2892 2893 if (log) 2894 { 2895 log->Printf ("SymbolFileDWARF::FindFunctions (file=\"%s/%s\", regex=\"%s\"append=%u, sc_list)", 2896 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 2897 m_obj_file->GetFileSpec().GetFilename().GetCString(), 2898 regex.GetText(), append); 2899 } 2900 2901 2902 // If we aren't appending the results to this list, then clear the list 2903 if (!append) 2904 sc_list.Clear(); 2905 2906 // Remember how many sc_list are in the list before we search in case 2907 // we are appending the results to a variable list. 2908 uint32_t original_size = sc_list.GetSize(); 2909 2910 if (m_using_apple_tables) 2911 { 2912 if (m_apple_names_ap.get()) 2913 FindFunctions (regex, *m_apple_names_ap, sc_list); 2914 } 2915 else 2916 { 2917 // Index the DWARF if we haven't already 2918 if (!m_indexed) 2919 Index (); 2920 2921 FindFunctions (regex, m_function_basename_index, sc_list); 2922 2923 FindFunctions (regex, m_function_fullname_index, sc_list); 2924 } 2925 2926 // Return the number of variable that were appended to the list 2927 return sc_list.GetSize() - original_size; 2928 } 2929 2930 void 2931 SymbolFileDWARF::ReportError (const char *format, ...) 2932 { 2933 ::fprintf (stderr, 2934 "error: %s/%s ", 2935 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 2936 m_obj_file->GetFileSpec().GetFilename().GetCString()); 2937 2938 if (m_obj_file->GetModule()->GetObjectName()) 2939 ::fprintf (stderr, "(%s) ", m_obj_file->GetModule()->GetObjectName().GetCString()); 2940 2941 va_list args; 2942 va_start (args, format); 2943 vfprintf (stderr, format, args); 2944 va_end (args); 2945 } 2946 2947 void 2948 SymbolFileDWARF::ReportWarning (const char *format, ...) 2949 { 2950 ::fprintf (stderr, 2951 "warning: %s/%s ", 2952 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 2953 m_obj_file->GetFileSpec().GetFilename().GetCString()); 2954 2955 if (m_obj_file->GetModule()->GetObjectName()) 2956 ::fprintf (stderr, "(%s) ", m_obj_file->GetModule()->GetObjectName().GetCString()); 2957 2958 va_list args; 2959 va_start (args, format); 2960 vfprintf (stderr, format, args); 2961 va_end (args); 2962 } 2963 2964 uint32_t 2965 SymbolFileDWARF::FindTypes(const SymbolContext& sc, const ConstString &name, const lldb_private::ClangNamespaceDecl *namespace_decl, bool append, uint32_t max_matches, TypeList& types) 2966 { 2967 DWARFDebugInfo* info = DebugInfo(); 2968 if (info == NULL) 2969 return 0; 2970 2971 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 2972 2973 if (log) 2974 { 2975 log->Printf ("SymbolFileDWARF::FindTypes (file=\"%s/%s\", sc, name=\"%s\", append=%u, max_matches=%u, type_list)", 2976 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 2977 m_obj_file->GetFileSpec().GetFilename().GetCString(), 2978 name.GetCString(), append, max_matches); 2979 } 2980 2981 // If we aren't appending the results to this list, then clear the list 2982 if (!append) 2983 types.Clear(); 2984 2985 if (!NamespaceDeclMatchesThisSymbolFile(namespace_decl)) 2986 return 0; 2987 2988 DIEArray die_offsets; 2989 2990 if (m_using_apple_tables) 2991 { 2992 if (m_apple_types_ap.get()) 2993 { 2994 const char *name_cstr = name.GetCString(); 2995 m_apple_types_ap->FindByName (name_cstr, die_offsets); 2996 } 2997 } 2998 else 2999 { 3000 if (!m_indexed) 3001 Index (); 3002 3003 m_type_index.Find (name, die_offsets); 3004 } 3005 3006 3007 const size_t num_matches = die_offsets.size(); 3008 3009 if (num_matches) 3010 { 3011 const uint32_t initial_types_size = types.GetSize(); 3012 DWARFCompileUnit* dwarf_cu = NULL; 3013 const DWARFDebugInfoEntry* die = NULL; 3014 DWARFDebugInfo* debug_info = DebugInfo(); 3015 for (size_t i=0; i<num_matches; ++i) 3016 { 3017 const dw_offset_t die_offset = die_offsets[i]; 3018 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 3019 3020 if (die) 3021 { 3022 if (namespace_decl && !DIEIsInNamespace (namespace_decl, dwarf_cu, die)) 3023 continue; 3024 3025 Type *matching_type = ResolveType (dwarf_cu, die); 3026 if (matching_type) 3027 { 3028 // We found a type pointer, now find the shared pointer form our type list 3029 types.InsertUnique (TypeSP (matching_type)); 3030 if (types.GetSize() >= max_matches) 3031 break; 3032 } 3033 } 3034 else 3035 { 3036 if (m_using_apple_tables) 3037 { 3038 ReportError (".apple_types accelerator table had bad die 0x%8.8x for '%s'\n", 3039 die_offset, name.GetCString()); 3040 } 3041 } 3042 3043 } 3044 return types.GetSize() - initial_types_size; 3045 } 3046 return 0; 3047 } 3048 3049 3050 ClangNamespaceDecl 3051 SymbolFileDWARF::FindNamespace (const SymbolContext& sc, 3052 const ConstString &name, 3053 const lldb_private::ClangNamespaceDecl *parent_namespace_decl) 3054 { 3055 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_LOOKUPS)); 3056 3057 if (log) 3058 { 3059 log->Printf ("SymbolFileDWARF::FindNamespace (file=\"%s/%s\", sc, name=\"%s\")", 3060 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 3061 m_obj_file->GetFileSpec().GetFilename().GetCString(), 3062 name.GetCString()); 3063 } 3064 3065 if (!NamespaceDeclMatchesThisSymbolFile(parent_namespace_decl)) 3066 return ClangNamespaceDecl(); 3067 3068 ClangNamespaceDecl namespace_decl; 3069 DWARFDebugInfo* info = DebugInfo(); 3070 if (info) 3071 { 3072 DIEArray die_offsets; 3073 3074 // Index if we already haven't to make sure the compile units 3075 // get indexed and make their global DIE index list 3076 if (m_using_apple_tables) 3077 { 3078 if (m_apple_namespaces_ap.get()) 3079 { 3080 const char *name_cstr = name.GetCString(); 3081 m_apple_namespaces_ap->FindByName (name_cstr, die_offsets); 3082 } 3083 } 3084 else 3085 { 3086 if (!m_indexed) 3087 Index (); 3088 3089 m_namespace_index.Find (name, die_offsets); 3090 } 3091 3092 DWARFCompileUnit* dwarf_cu = NULL; 3093 const DWARFDebugInfoEntry* die = NULL; 3094 const size_t num_matches = die_offsets.size(); 3095 if (num_matches) 3096 { 3097 DWARFDebugInfo* debug_info = DebugInfo(); 3098 for (size_t i=0; i<num_matches; ++i) 3099 { 3100 const dw_offset_t die_offset = die_offsets[i]; 3101 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 3102 3103 if (die) 3104 { 3105 if (parent_namespace_decl && !DIEIsInNamespace (parent_namespace_decl, dwarf_cu, die)) 3106 continue; 3107 3108 clang::NamespaceDecl *clang_namespace_decl = ResolveNamespaceDIE (dwarf_cu, die); 3109 if (clang_namespace_decl) 3110 { 3111 namespace_decl.SetASTContext (GetClangASTContext().getASTContext()); 3112 namespace_decl.SetNamespaceDecl (clang_namespace_decl); 3113 } 3114 } 3115 else 3116 { 3117 if (m_using_apple_tables) 3118 { 3119 ReportError (".apple_namespaces accelerator table had bad die 0x%8.8x for '%s'\n", 3120 die_offset, name.GetCString()); 3121 } 3122 } 3123 3124 } 3125 } 3126 } 3127 return namespace_decl; 3128 } 3129 3130 uint32_t 3131 SymbolFileDWARF::FindTypes(std::vector<dw_offset_t> die_offsets, uint32_t max_matches, TypeList& types) 3132 { 3133 // Remember how many sc_list are in the list before we search in case 3134 // we are appending the results to a variable list. 3135 uint32_t original_size = types.GetSize(); 3136 3137 const uint32_t num_die_offsets = die_offsets.size(); 3138 // Parse all of the types we found from the pubtypes matches 3139 uint32_t i; 3140 uint32_t num_matches = 0; 3141 for (i = 0; i < num_die_offsets; ++i) 3142 { 3143 Type *matching_type = ResolveTypeUID (die_offsets[i]); 3144 if (matching_type) 3145 { 3146 // We found a type pointer, now find the shared pointer form our type list 3147 types.InsertUnique (TypeSP (matching_type)); 3148 ++num_matches; 3149 if (num_matches >= max_matches) 3150 break; 3151 } 3152 } 3153 3154 // Return the number of variable that were appended to the list 3155 return types.GetSize() - original_size; 3156 } 3157 3158 3159 size_t 3160 SymbolFileDWARF::ParseChildParameters (const SymbolContext& sc, 3161 clang::DeclContext *containing_decl_ctx, 3162 TypeSP& type_sp, 3163 DWARFCompileUnit* dwarf_cu, 3164 const DWARFDebugInfoEntry *parent_die, 3165 bool skip_artificial, 3166 bool &is_static, 3167 TypeList* type_list, 3168 std::vector<clang_type_t>& function_param_types, 3169 std::vector<clang::ParmVarDecl*>& function_param_decls, 3170 unsigned &type_quals) 3171 { 3172 if (parent_die == NULL) 3173 return 0; 3174 3175 const uint8_t *fixed_form_sizes = DWARFFormValue::GetFixedFormSizesForAddressSize (dwarf_cu->GetAddressByteSize()); 3176 3177 size_t arg_idx = 0; 3178 const DWARFDebugInfoEntry *die; 3179 for (die = parent_die->GetFirstChild(); die != NULL; die = die->GetSibling()) 3180 { 3181 dw_tag_t tag = die->Tag(); 3182 switch (tag) 3183 { 3184 case DW_TAG_formal_parameter: 3185 { 3186 DWARFDebugInfoEntry::Attributes attributes; 3187 const size_t num_attributes = die->GetAttributes(this, dwarf_cu, fixed_form_sizes, attributes); 3188 if (num_attributes > 0) 3189 { 3190 const char *name = NULL; 3191 Declaration decl; 3192 dw_offset_t param_type_die_offset = DW_INVALID_OFFSET; 3193 bool is_artificial = false; 3194 // one of None, Auto, Register, Extern, Static, PrivateExtern 3195 3196 clang::StorageClass storage = clang::SC_None; 3197 uint32_t i; 3198 for (i=0; i<num_attributes; ++i) 3199 { 3200 const dw_attr_t attr = attributes.AttributeAtIndex(i); 3201 DWARFFormValue form_value; 3202 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 3203 { 3204 switch (attr) 3205 { 3206 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 3207 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 3208 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 3209 case DW_AT_name: name = form_value.AsCString(&get_debug_str_data()); break; 3210 case DW_AT_type: param_type_die_offset = form_value.Reference(dwarf_cu); break; 3211 case DW_AT_artificial: is_artificial = form_value.Unsigned() != 0; break; 3212 case DW_AT_location: 3213 // if (form_value.BlockData()) 3214 // { 3215 // const DataExtractor& debug_info_data = debug_info(); 3216 // uint32_t block_length = form_value.Unsigned(); 3217 // DataExtractor location(debug_info_data, form_value.BlockData() - debug_info_data.GetDataStart(), block_length); 3218 // } 3219 // else 3220 // { 3221 // } 3222 // break; 3223 case DW_AT_const_value: 3224 case DW_AT_default_value: 3225 case DW_AT_description: 3226 case DW_AT_endianity: 3227 case DW_AT_is_optional: 3228 case DW_AT_segment: 3229 case DW_AT_variable_parameter: 3230 default: 3231 case DW_AT_abstract_origin: 3232 case DW_AT_sibling: 3233 break; 3234 } 3235 } 3236 } 3237 3238 bool skip = false; 3239 if (skip_artificial) 3240 { 3241 if (is_artificial) 3242 { 3243 // In order to determine if a C++ member function is 3244 // "const" we have to look at the const-ness of "this"... 3245 // Ugly, but that 3246 if (arg_idx == 0) 3247 { 3248 if (DeclKindIsCXXClass(containing_decl_ctx->getDeclKind())) 3249 { 3250 // Often times compilers omit the "this" name for the 3251 // specification DIEs, so we can't rely upon the name 3252 // being in the formal parameter DIE... 3253 if (name == NULL || ::strcmp(name, "this")==0) 3254 { 3255 Type *this_type = ResolveTypeUID (param_type_die_offset); 3256 if (this_type) 3257 { 3258 uint32_t encoding_mask = this_type->GetEncodingMask(); 3259 if (encoding_mask & Type::eEncodingIsPointerUID) 3260 { 3261 is_static = false; 3262 3263 if (encoding_mask & (1u << Type::eEncodingIsConstUID)) 3264 type_quals |= clang::Qualifiers::Const; 3265 if (encoding_mask & (1u << Type::eEncodingIsVolatileUID)) 3266 type_quals |= clang::Qualifiers::Volatile; 3267 } 3268 } 3269 } 3270 } 3271 } 3272 skip = true; 3273 } 3274 else 3275 { 3276 3277 // HACK: Objective C formal parameters "self" and "_cmd" 3278 // are not marked as artificial in the DWARF... 3279 CompileUnit *curr_cu = GetCompUnitForDWARFCompUnit(dwarf_cu, UINT32_MAX); 3280 if (curr_cu && (curr_cu->GetLanguage() == eLanguageTypeObjC || curr_cu->GetLanguage() == eLanguageTypeObjC_plus_plus)) 3281 { 3282 if (name && name[0] && (strcmp (name, "self") == 0 || strcmp (name, "_cmd") == 0)) 3283 skip = true; 3284 } 3285 } 3286 } 3287 3288 if (!skip) 3289 { 3290 Type *type = ResolveTypeUID(param_type_die_offset); 3291 if (type) 3292 { 3293 function_param_types.push_back (type->GetClangForwardType()); 3294 3295 clang::ParmVarDecl *param_var_decl = GetClangASTContext().CreateParameterDeclaration (name, type->GetClangForwardType(), storage); 3296 assert(param_var_decl); 3297 function_param_decls.push_back(param_var_decl); 3298 } 3299 } 3300 } 3301 arg_idx++; 3302 } 3303 break; 3304 3305 default: 3306 break; 3307 } 3308 } 3309 return arg_idx; 3310 } 3311 3312 size_t 3313 SymbolFileDWARF::ParseChildEnumerators 3314 ( 3315 const SymbolContext& sc, 3316 clang_type_t enumerator_clang_type, 3317 uint32_t enumerator_byte_size, 3318 DWARFCompileUnit* dwarf_cu, 3319 const DWARFDebugInfoEntry *parent_die 3320 ) 3321 { 3322 if (parent_die == NULL) 3323 return 0; 3324 3325 size_t enumerators_added = 0; 3326 const DWARFDebugInfoEntry *die; 3327 const uint8_t *fixed_form_sizes = DWARFFormValue::GetFixedFormSizesForAddressSize (dwarf_cu->GetAddressByteSize()); 3328 3329 for (die = parent_die->GetFirstChild(); die != NULL; die = die->GetSibling()) 3330 { 3331 const dw_tag_t tag = die->Tag(); 3332 if (tag == DW_TAG_enumerator) 3333 { 3334 DWARFDebugInfoEntry::Attributes attributes; 3335 const size_t num_child_attributes = die->GetAttributes(this, dwarf_cu, fixed_form_sizes, attributes); 3336 if (num_child_attributes > 0) 3337 { 3338 const char *name = NULL; 3339 bool got_value = false; 3340 int64_t enum_value = 0; 3341 Declaration decl; 3342 3343 uint32_t i; 3344 for (i=0; i<num_child_attributes; ++i) 3345 { 3346 const dw_attr_t attr = attributes.AttributeAtIndex(i); 3347 DWARFFormValue form_value; 3348 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 3349 { 3350 switch (attr) 3351 { 3352 case DW_AT_const_value: 3353 got_value = true; 3354 enum_value = form_value.Unsigned(); 3355 break; 3356 3357 case DW_AT_name: 3358 name = form_value.AsCString(&get_debug_str_data()); 3359 break; 3360 3361 case DW_AT_description: 3362 default: 3363 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 3364 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 3365 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 3366 case DW_AT_sibling: 3367 break; 3368 } 3369 } 3370 } 3371 3372 if (name && name[0] && got_value) 3373 { 3374 GetClangASTContext().AddEnumerationValueToEnumerationType (enumerator_clang_type, 3375 enumerator_clang_type, 3376 decl, 3377 name, 3378 enum_value, 3379 enumerator_byte_size * 8); 3380 ++enumerators_added; 3381 } 3382 } 3383 } 3384 } 3385 return enumerators_added; 3386 } 3387 3388 void 3389 SymbolFileDWARF::ParseChildArrayInfo 3390 ( 3391 const SymbolContext& sc, 3392 DWARFCompileUnit* dwarf_cu, 3393 const DWARFDebugInfoEntry *parent_die, 3394 int64_t& first_index, 3395 std::vector<uint64_t>& element_orders, 3396 uint32_t& byte_stride, 3397 uint32_t& bit_stride 3398 ) 3399 { 3400 if (parent_die == NULL) 3401 return; 3402 3403 const DWARFDebugInfoEntry *die; 3404 const uint8_t *fixed_form_sizes = DWARFFormValue::GetFixedFormSizesForAddressSize (dwarf_cu->GetAddressByteSize()); 3405 for (die = parent_die->GetFirstChild(); die != NULL; die = die->GetSibling()) 3406 { 3407 const dw_tag_t tag = die->Tag(); 3408 switch (tag) 3409 { 3410 case DW_TAG_enumerator: 3411 { 3412 DWARFDebugInfoEntry::Attributes attributes; 3413 const size_t num_child_attributes = die->GetAttributes(this, dwarf_cu, fixed_form_sizes, attributes); 3414 if (num_child_attributes > 0) 3415 { 3416 const char *name = NULL; 3417 bool got_value = false; 3418 int64_t enum_value = 0; 3419 3420 uint32_t i; 3421 for (i=0; i<num_child_attributes; ++i) 3422 { 3423 const dw_attr_t attr = attributes.AttributeAtIndex(i); 3424 DWARFFormValue form_value; 3425 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 3426 { 3427 switch (attr) 3428 { 3429 case DW_AT_const_value: 3430 got_value = true; 3431 enum_value = form_value.Unsigned(); 3432 break; 3433 3434 case DW_AT_name: 3435 name = form_value.AsCString(&get_debug_str_data()); 3436 break; 3437 3438 case DW_AT_description: 3439 default: 3440 case DW_AT_decl_file: 3441 case DW_AT_decl_line: 3442 case DW_AT_decl_column: 3443 case DW_AT_sibling: 3444 break; 3445 } 3446 } 3447 } 3448 } 3449 } 3450 break; 3451 3452 case DW_TAG_subrange_type: 3453 { 3454 DWARFDebugInfoEntry::Attributes attributes; 3455 const size_t num_child_attributes = die->GetAttributes(this, dwarf_cu, fixed_form_sizes, attributes); 3456 if (num_child_attributes > 0) 3457 { 3458 const char *name = NULL; 3459 bool got_value = false; 3460 uint64_t byte_size = 0; 3461 int64_t enum_value = 0; 3462 uint64_t num_elements = 0; 3463 uint64_t lower_bound = 0; 3464 uint64_t upper_bound = 0; 3465 uint32_t i; 3466 for (i=0; i<num_child_attributes; ++i) 3467 { 3468 const dw_attr_t attr = attributes.AttributeAtIndex(i); 3469 DWARFFormValue form_value; 3470 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 3471 { 3472 switch (attr) 3473 { 3474 case DW_AT_const_value: 3475 got_value = true; 3476 enum_value = form_value.Unsigned(); 3477 break; 3478 3479 case DW_AT_name: 3480 name = form_value.AsCString(&get_debug_str_data()); 3481 break; 3482 3483 case DW_AT_count: 3484 num_elements = form_value.Unsigned(); 3485 break; 3486 3487 case DW_AT_bit_stride: 3488 bit_stride = form_value.Unsigned(); 3489 break; 3490 3491 case DW_AT_byte_stride: 3492 byte_stride = form_value.Unsigned(); 3493 break; 3494 3495 case DW_AT_byte_size: 3496 byte_size = form_value.Unsigned(); 3497 break; 3498 3499 case DW_AT_lower_bound: 3500 lower_bound = form_value.Unsigned(); 3501 break; 3502 3503 case DW_AT_upper_bound: 3504 upper_bound = form_value.Unsigned(); 3505 break; 3506 3507 default: 3508 case DW_AT_abstract_origin: 3509 case DW_AT_accessibility: 3510 case DW_AT_allocated: 3511 case DW_AT_associated: 3512 case DW_AT_data_location: 3513 case DW_AT_declaration: 3514 case DW_AT_description: 3515 case DW_AT_sibling: 3516 case DW_AT_threads_scaled: 3517 case DW_AT_type: 3518 case DW_AT_visibility: 3519 break; 3520 } 3521 } 3522 } 3523 3524 if (upper_bound > lower_bound) 3525 num_elements = upper_bound - lower_bound + 1; 3526 3527 if (num_elements > 0) 3528 element_orders.push_back (num_elements); 3529 } 3530 } 3531 break; 3532 } 3533 } 3534 } 3535 3536 TypeSP 3537 SymbolFileDWARF::GetTypeForDIE (DWARFCompileUnit *curr_cu, const DWARFDebugInfoEntry* die) 3538 { 3539 TypeSP type_sp; 3540 if (die != NULL) 3541 { 3542 assert(curr_cu != NULL); 3543 Type *type_ptr = m_die_to_type.lookup (die); 3544 if (type_ptr == NULL) 3545 { 3546 CompileUnit* lldb_cu = GetCompUnitForDWARFCompUnit(curr_cu); 3547 assert (lldb_cu); 3548 SymbolContext sc(lldb_cu); 3549 type_sp = ParseType(sc, curr_cu, die, NULL); 3550 } 3551 else if (type_ptr != DIE_IS_BEING_PARSED) 3552 { 3553 // Grab the existing type from the master types lists 3554 type_sp = type_ptr; 3555 } 3556 3557 } 3558 return type_sp; 3559 } 3560 3561 clang::DeclContext * 3562 SymbolFileDWARF::GetClangDeclContextContainingDIEOffset (dw_offset_t die_offset) 3563 { 3564 if (die_offset != DW_INVALID_OFFSET) 3565 { 3566 DWARFCompileUnitSP cu_sp; 3567 const DWARFDebugInfoEntry* die = DebugInfo()->GetDIEPtr(die_offset, &cu_sp); 3568 return GetClangDeclContextContainingDIE (cu_sp.get(), die, NULL); 3569 } 3570 return NULL; 3571 } 3572 3573 clang::DeclContext * 3574 SymbolFileDWARF::GetClangDeclContextForDIEOffset (const SymbolContext &sc, dw_offset_t die_offset) 3575 { 3576 if (die_offset != DW_INVALID_OFFSET) 3577 { 3578 DWARFDebugInfo* debug_info = DebugInfo(); 3579 if (debug_info) 3580 { 3581 DWARFCompileUnitSP cu_sp; 3582 const DWARFDebugInfoEntry* die = debug_info->GetDIEPtr(die_offset, &cu_sp); 3583 if (die) 3584 return GetClangDeclContextForDIE (sc, cu_sp.get(), die); 3585 } 3586 } 3587 return NULL; 3588 } 3589 3590 clang::NamespaceDecl * 3591 SymbolFileDWARF::ResolveNamespaceDIE (DWARFCompileUnit *curr_cu, const DWARFDebugInfoEntry *die) 3592 { 3593 if (die && die->Tag() == DW_TAG_namespace) 3594 { 3595 // See if we already parsed this namespace DIE and associated it with a 3596 // uniqued namespace declaration 3597 clang::NamespaceDecl *namespace_decl = static_cast<clang::NamespaceDecl *>(m_die_to_decl_ctx[die]); 3598 if (namespace_decl) 3599 return namespace_decl; 3600 else 3601 { 3602 const char *namespace_name = die->GetAttributeValueAsString(this, curr_cu, DW_AT_name, NULL); 3603 clang::DeclContext *containing_decl_ctx = GetClangDeclContextContainingDIE (curr_cu, die, NULL); 3604 namespace_decl = GetClangASTContext().GetUniqueNamespaceDeclaration (namespace_name, containing_decl_ctx); 3605 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_DEBUG_INFO)); 3606 if (log) 3607 { 3608 const char *object_name = m_obj_file->GetModule()->GetObjectName().GetCString(); 3609 if (namespace_name) 3610 { 3611 log->Printf ("ASTContext => %p: 0x%8.8llx: DW_TAG_namespace with DW_AT_name(\"%s\") => clang::NamespaceDecl * %p in %s/%s%s%s%s (original = %p)", 3612 GetClangASTContext().getASTContext(), 3613 MakeUserID(die->GetOffset()), 3614 namespace_name, 3615 namespace_decl, 3616 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 3617 m_obj_file->GetFileSpec().GetFilename().GetCString(), 3618 object_name ? "(" : "", 3619 object_name ? object_name : "", 3620 object_name ? "(" : "", 3621 namespace_decl->getOriginalNamespace()); 3622 } 3623 else 3624 { 3625 log->Printf ("ASTContext => %p: 0x%8.8llx: DW_TAG_namespace (anonymous) => clang::NamespaceDecl * %p in %s/%s%s%s%s (original = %p)", 3626 GetClangASTContext().getASTContext(), 3627 MakeUserID(die->GetOffset()), 3628 namespace_decl, 3629 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 3630 m_obj_file->GetFileSpec().GetFilename().GetCString(), 3631 object_name ? "(" : "", 3632 object_name ? object_name : "", 3633 object_name ? "(" : "", 3634 namespace_decl->getOriginalNamespace()); 3635 } 3636 } 3637 3638 if (namespace_decl) 3639 LinkDeclContextToDIE((clang::DeclContext*)namespace_decl, die); 3640 return namespace_decl; 3641 } 3642 } 3643 return NULL; 3644 } 3645 3646 clang::DeclContext * 3647 SymbolFileDWARF::GetClangDeclContextForDIE (const SymbolContext &sc, DWARFCompileUnit *curr_cu, const DWARFDebugInfoEntry *die) 3648 { 3649 clang::DeclContext *clang_decl_ctx = GetCachedClangDeclContextForDIE (die); 3650 if (clang_decl_ctx) 3651 return clang_decl_ctx; 3652 // If this DIE has a specification, or an abstract origin, then trace to those. 3653 3654 dw_offset_t die_offset = die->GetAttributeValueAsReference(this, curr_cu, DW_AT_specification, DW_INVALID_OFFSET); 3655 if (die_offset != DW_INVALID_OFFSET) 3656 return GetClangDeclContextForDIEOffset (sc, die_offset); 3657 3658 die_offset = die->GetAttributeValueAsReference(this, curr_cu, DW_AT_abstract_origin, DW_INVALID_OFFSET); 3659 if (die_offset != DW_INVALID_OFFSET) 3660 return GetClangDeclContextForDIEOffset (sc, die_offset); 3661 3662 // This is the DIE we want. Parse it, then query our map. 3663 3664 ParseType(sc, curr_cu, die, NULL); 3665 3666 clang_decl_ctx = GetCachedClangDeclContextForDIE (die); 3667 3668 return clang_decl_ctx; 3669 } 3670 3671 clang::DeclContext * 3672 SymbolFileDWARF::GetClangDeclContextContainingDIE (DWARFCompileUnit *cu, const DWARFDebugInfoEntry *die, const DWARFDebugInfoEntry **decl_ctx_die_copy) 3673 { 3674 if (m_clang_tu_decl == NULL) 3675 m_clang_tu_decl = GetClangASTContext().getASTContext()->getTranslationUnitDecl(); 3676 3677 const DWARFDebugInfoEntry *decl_ctx_die = GetDeclContextDIEContainingDIE (cu, die); 3678 3679 if (decl_ctx_die_copy) 3680 *decl_ctx_die_copy = decl_ctx_die; 3681 3682 if (decl_ctx_die) 3683 { 3684 3685 DIEToDeclContextMap::iterator pos = m_die_to_decl_ctx.find (decl_ctx_die); 3686 if (pos != m_die_to_decl_ctx.end()) 3687 return pos->second; 3688 3689 switch (decl_ctx_die->Tag()) 3690 { 3691 case DW_TAG_compile_unit: 3692 return m_clang_tu_decl; 3693 3694 case DW_TAG_namespace: 3695 return ResolveNamespaceDIE (cu, decl_ctx_die); 3696 break; 3697 3698 case DW_TAG_structure_type: 3699 case DW_TAG_union_type: 3700 case DW_TAG_class_type: 3701 { 3702 Type* type = ResolveType (cu, decl_ctx_die); 3703 if (type) 3704 { 3705 clang::DeclContext *decl_ctx = ClangASTContext::GetDeclContextForType (type->GetClangForwardType ()); 3706 if (decl_ctx) 3707 { 3708 LinkDeclContextToDIE (decl_ctx, decl_ctx_die); 3709 if (decl_ctx) 3710 return decl_ctx; 3711 } 3712 } 3713 } 3714 break; 3715 3716 default: 3717 break; 3718 } 3719 } 3720 return m_clang_tu_decl; 3721 } 3722 3723 3724 const DWARFDebugInfoEntry * 3725 SymbolFileDWARF::GetDeclContextDIEContainingDIE (DWARFCompileUnit *cu, const DWARFDebugInfoEntry *die) 3726 { 3727 if (cu && die) 3728 { 3729 const DWARFDebugInfoEntry * const decl_die = die; 3730 3731 while (die != NULL) 3732 { 3733 // If this is the original DIE that we are searching for a declaration 3734 // for, then don't look in the cache as we don't want our own decl 3735 // context to be our decl context... 3736 if (decl_die != die) 3737 { 3738 switch (die->Tag()) 3739 { 3740 case DW_TAG_compile_unit: 3741 case DW_TAG_namespace: 3742 case DW_TAG_structure_type: 3743 case DW_TAG_union_type: 3744 case DW_TAG_class_type: 3745 return die; 3746 3747 default: 3748 break; 3749 } 3750 } 3751 3752 dw_offset_t die_offset = die->GetAttributeValueAsReference(this, cu, DW_AT_specification, DW_INVALID_OFFSET); 3753 if (die_offset != DW_INVALID_OFFSET) 3754 { 3755 DWARFCompileUnit *spec_cu = cu; 3756 const DWARFDebugInfoEntry *spec_die = DebugInfo()->GetDIEPtrWithCompileUnitHint (die_offset, &spec_cu); 3757 const DWARFDebugInfoEntry *spec_die_decl_ctx_die = GetDeclContextDIEContainingDIE (spec_cu, spec_die); 3758 if (spec_die_decl_ctx_die) 3759 return spec_die_decl_ctx_die; 3760 } 3761 3762 die_offset = die->GetAttributeValueAsReference(this, cu, DW_AT_abstract_origin, DW_INVALID_OFFSET); 3763 if (die_offset != DW_INVALID_OFFSET) 3764 { 3765 DWARFCompileUnit *abs_cu = cu; 3766 const DWARFDebugInfoEntry *abs_die = DebugInfo()->GetDIEPtrWithCompileUnitHint (die_offset, &abs_cu); 3767 const DWARFDebugInfoEntry *abs_die_decl_ctx_die = GetDeclContextDIEContainingDIE (abs_cu, abs_die); 3768 if (abs_die_decl_ctx_die) 3769 return abs_die_decl_ctx_die; 3770 } 3771 3772 die = die->GetParent(); 3773 } 3774 } 3775 return NULL; 3776 } 3777 3778 3779 3780 // This function can be used when a DIE is found that is a forward declaration 3781 // DIE and we want to try and find a type that has the complete definition. 3782 TypeSP 3783 SymbolFileDWARF::FindDefinitionTypeForDIE (DWARFCompileUnit* cu, 3784 const DWARFDebugInfoEntry *die, 3785 const ConstString &type_name) 3786 { 3787 TypeSP type_sp; 3788 3789 if (cu == NULL || die == NULL || !type_name) 3790 return type_sp; 3791 3792 DIEArray die_offsets; 3793 3794 if (m_using_apple_tables) 3795 { 3796 if (m_apple_types_ap.get()) 3797 { 3798 const char *name_cstr = type_name.GetCString(); 3799 m_apple_types_ap->FindByName (name_cstr, die_offsets); 3800 } 3801 } 3802 else 3803 { 3804 if (!m_indexed) 3805 Index (); 3806 3807 m_type_index.Find (type_name, die_offsets); 3808 } 3809 3810 3811 const size_t num_matches = die_offsets.size(); 3812 3813 const dw_tag_t type_tag = die->Tag(); 3814 3815 DWARFCompileUnit* type_cu = NULL; 3816 const DWARFDebugInfoEntry* type_die = NULL; 3817 if (num_matches) 3818 { 3819 DWARFDebugInfo* debug_info = DebugInfo(); 3820 for (size_t i=0; i<num_matches; ++i) 3821 { 3822 const dw_offset_t die_offset = die_offsets[i]; 3823 type_die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &type_cu); 3824 3825 if (type_die) 3826 { 3827 if (type_die != die && type_die->Tag() == type_tag) 3828 { 3829 // Hold off on comparing parent DIE tags until 3830 // we know what happens with stuff in namespaces 3831 // for gcc and clang... 3832 //DWARFDebugInfoEntry *parent_die = die->GetParent(); 3833 //DWARFDebugInfoEntry *parent_type_die = type_die->GetParent(); 3834 //if (parent_die->Tag() == parent_type_die->Tag()) 3835 { 3836 Type *resolved_type = ResolveType (type_cu, type_die, false); 3837 if (resolved_type && resolved_type != DIE_IS_BEING_PARSED) 3838 { 3839 DEBUG_PRINTF ("resolved 0x%8.8llx (cu 0x%8.8llx) from %s to 0x%8.8llx (cu 0x%8.8llx)\n", 3840 MakeUserID(die->GetOffset()), 3841 MakeUserID(curr_cu->GetOffset()), 3842 m_obj_file->GetFileSpec().GetFilename().AsCString(), 3843 MakeUserID(type_die->GetOffset()), 3844 MakeUserID(type_cu->GetOffset())); 3845 3846 m_die_to_type[die] = resolved_type; 3847 type_sp = resolved_type; 3848 break; 3849 } 3850 } 3851 } 3852 } 3853 else 3854 { 3855 if (m_using_apple_tables) 3856 { 3857 ReportError (".apple_types accelerator table had bad die 0x%8.8x for '%s'\n", 3858 die_offset, type_name.GetCString()); 3859 } 3860 } 3861 3862 } 3863 } 3864 return type_sp; 3865 } 3866 3867 TypeSP 3868 SymbolFileDWARF::ParseType (const SymbolContext& sc, DWARFCompileUnit* dwarf_cu, const DWARFDebugInfoEntry *die, bool *type_is_new_ptr) 3869 { 3870 TypeSP type_sp; 3871 3872 if (type_is_new_ptr) 3873 *type_is_new_ptr = false; 3874 3875 AccessType accessibility = eAccessNone; 3876 if (die != NULL) 3877 { 3878 LogSP log (LogChannelDWARF::GetLogIfAll(DWARF_LOG_DEBUG_INFO)); 3879 if (log && dwarf_cu) 3880 { 3881 StreamString s; 3882 die->DumpLocation (this, dwarf_cu, s); 3883 log->Printf ("SymbolFileDwarf::%s %s", __FUNCTION__, s.GetData()); 3884 3885 } 3886 3887 Type *type_ptr = m_die_to_type.lookup (die); 3888 TypeList* type_list = GetTypeList(); 3889 if (type_ptr == NULL) 3890 { 3891 ClangASTContext &ast = GetClangASTContext(); 3892 if (type_is_new_ptr) 3893 *type_is_new_ptr = true; 3894 3895 const dw_tag_t tag = die->Tag(); 3896 3897 bool is_forward_declaration = false; 3898 DWARFDebugInfoEntry::Attributes attributes; 3899 const char *type_name_cstr = NULL; 3900 ConstString type_name_const_str; 3901 Type::ResolveState resolve_state = Type::eResolveStateUnresolved; 3902 size_t byte_size = 0; 3903 bool byte_size_valid = false; 3904 Declaration decl; 3905 3906 Type::EncodingDataType encoding_data_type = Type::eEncodingIsUID; 3907 clang_type_t clang_type = NULL; 3908 3909 dw_attr_t attr; 3910 3911 switch (tag) 3912 { 3913 case DW_TAG_base_type: 3914 case DW_TAG_pointer_type: 3915 case DW_TAG_reference_type: 3916 case DW_TAG_typedef: 3917 case DW_TAG_const_type: 3918 case DW_TAG_restrict_type: 3919 case DW_TAG_volatile_type: 3920 case DW_TAG_unspecified_type: 3921 { 3922 // Set a bit that lets us know that we are currently parsing this 3923 m_die_to_type[die] = DIE_IS_BEING_PARSED; 3924 3925 const size_t num_attributes = die->GetAttributes(this, dwarf_cu, NULL, attributes); 3926 uint32_t encoding = 0; 3927 lldb::user_id_t encoding_uid = LLDB_INVALID_UID; 3928 3929 if (num_attributes > 0) 3930 { 3931 uint32_t i; 3932 for (i=0; i<num_attributes; ++i) 3933 { 3934 attr = attributes.AttributeAtIndex(i); 3935 DWARFFormValue form_value; 3936 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 3937 { 3938 switch (attr) 3939 { 3940 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 3941 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 3942 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 3943 case DW_AT_name: 3944 3945 type_name_cstr = form_value.AsCString(&get_debug_str_data()); 3946 // Work around a bug in llvm-gcc where they give a name to a reference type which doesn't 3947 // include the "&"... 3948 if (tag == DW_TAG_reference_type) 3949 { 3950 if (strchr (type_name_cstr, '&') == NULL) 3951 type_name_cstr = NULL; 3952 } 3953 if (type_name_cstr) 3954 type_name_const_str.SetCString(type_name_cstr); 3955 break; 3956 case DW_AT_byte_size: byte_size = form_value.Unsigned(); byte_size_valid = true; break; 3957 case DW_AT_encoding: encoding = form_value.Unsigned(); break; 3958 case DW_AT_type: encoding_uid = form_value.Reference(dwarf_cu); break; 3959 default: 3960 case DW_AT_sibling: 3961 break; 3962 } 3963 } 3964 } 3965 } 3966 3967 DEBUG_PRINTF ("0x%8.8llx: %s (\"%s\") type => 0x%8.8x\n", MakeUserID(die->GetOffset()), DW_TAG_value_to_name(tag), type_name_cstr, encoding_uid); 3968 3969 switch (tag) 3970 { 3971 default: 3972 break; 3973 3974 case DW_TAG_unspecified_type: 3975 if (strcmp(type_name_cstr, "nullptr_t") == 0) 3976 { 3977 resolve_state = Type::eResolveStateFull; 3978 clang_type = ast.getASTContext()->NullPtrTy.getAsOpaquePtr(); 3979 break; 3980 } 3981 // Fall through to base type below in case we can handle the type there... 3982 3983 case DW_TAG_base_type: 3984 resolve_state = Type::eResolveStateFull; 3985 clang_type = ast.GetBuiltinTypeForDWARFEncodingAndBitSize (type_name_cstr, 3986 encoding, 3987 byte_size * 8); 3988 break; 3989 3990 case DW_TAG_pointer_type: encoding_data_type = Type::eEncodingIsPointerUID; break; 3991 case DW_TAG_reference_type: encoding_data_type = Type::eEncodingIsLValueReferenceUID; break; 3992 case DW_TAG_typedef: encoding_data_type = Type::eEncodingIsTypedefUID; break; 3993 case DW_TAG_const_type: encoding_data_type = Type::eEncodingIsConstUID; break; 3994 case DW_TAG_restrict_type: encoding_data_type = Type::eEncodingIsRestrictUID; break; 3995 case DW_TAG_volatile_type: encoding_data_type = Type::eEncodingIsVolatileUID; break; 3996 } 3997 3998 if (type_name_cstr != NULL && sc.comp_unit != NULL && 3999 (sc.comp_unit->GetLanguage() == eLanguageTypeObjC || sc.comp_unit->GetLanguage() == eLanguageTypeObjC_plus_plus)) 4000 { 4001 static ConstString g_objc_type_name_id("id"); 4002 static ConstString g_objc_type_name_Class("Class"); 4003 static ConstString g_objc_type_name_selector("SEL"); 4004 4005 if (type_name_const_str == g_objc_type_name_id) 4006 { 4007 clang_type = ast.GetBuiltInType_objc_id(); 4008 resolve_state = Type::eResolveStateFull; 4009 4010 } 4011 else if (type_name_const_str == g_objc_type_name_Class) 4012 { 4013 clang_type = ast.GetBuiltInType_objc_Class(); 4014 resolve_state = Type::eResolveStateFull; 4015 } 4016 else if (type_name_const_str == g_objc_type_name_selector) 4017 { 4018 clang_type = ast.GetBuiltInType_objc_selector(); 4019 resolve_state = Type::eResolveStateFull; 4020 } 4021 } 4022 4023 type_sp.reset( new Type (MakeUserID(die->GetOffset()), 4024 this, 4025 type_name_const_str, 4026 byte_size, 4027 NULL, 4028 encoding_uid, 4029 encoding_data_type, 4030 &decl, 4031 clang_type, 4032 resolve_state)); 4033 4034 m_die_to_type[die] = type_sp.get(); 4035 4036 // Type* encoding_type = GetUniquedTypeForDIEOffset(encoding_uid, type_sp, NULL, 0, 0, false); 4037 // if (encoding_type != NULL) 4038 // { 4039 // if (encoding_type != DIE_IS_BEING_PARSED) 4040 // type_sp->SetEncodingType(encoding_type); 4041 // else 4042 // m_indirect_fixups.push_back(type_sp.get()); 4043 // } 4044 } 4045 break; 4046 4047 case DW_TAG_structure_type: 4048 case DW_TAG_union_type: 4049 case DW_TAG_class_type: 4050 { 4051 // Set a bit that lets us know that we are currently parsing this 4052 m_die_to_type[die] = DIE_IS_BEING_PARSED; 4053 4054 LanguageType class_language = eLanguageTypeUnknown; 4055 //bool struct_is_class = false; 4056 const size_t num_attributes = die->GetAttributes(this, dwarf_cu, NULL, attributes); 4057 if (num_attributes > 0) 4058 { 4059 uint32_t i; 4060 for (i=0; i<num_attributes; ++i) 4061 { 4062 attr = attributes.AttributeAtIndex(i); 4063 DWARFFormValue form_value; 4064 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 4065 { 4066 switch (attr) 4067 { 4068 case DW_AT_decl_file: 4069 decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); 4070 break; 4071 4072 case DW_AT_decl_line: 4073 decl.SetLine(form_value.Unsigned()); 4074 break; 4075 4076 case DW_AT_decl_column: 4077 decl.SetColumn(form_value.Unsigned()); 4078 break; 4079 4080 case DW_AT_name: 4081 type_name_cstr = form_value.AsCString(&get_debug_str_data()); 4082 type_name_const_str.SetCString(type_name_cstr); 4083 break; 4084 4085 case DW_AT_byte_size: 4086 byte_size = form_value.Unsigned(); 4087 byte_size_valid = true; 4088 break; 4089 4090 case DW_AT_accessibility: 4091 accessibility = DW_ACCESS_to_AccessType(form_value.Unsigned()); 4092 break; 4093 4094 case DW_AT_declaration: 4095 is_forward_declaration = form_value.Unsigned() != 0; 4096 break; 4097 4098 case DW_AT_APPLE_runtime_class: 4099 class_language = (LanguageType)form_value.Signed(); 4100 break; 4101 4102 case DW_AT_allocated: 4103 case DW_AT_associated: 4104 case DW_AT_data_location: 4105 case DW_AT_description: 4106 case DW_AT_start_scope: 4107 case DW_AT_visibility: 4108 default: 4109 case DW_AT_sibling: 4110 break; 4111 } 4112 } 4113 } 4114 } 4115 4116 UniqueDWARFASTType unique_ast_entry; 4117 if (decl.IsValid()) 4118 { 4119 if (GetUniqueDWARFASTTypeMap().Find (type_name_const_str, 4120 this, 4121 dwarf_cu, 4122 die, 4123 decl, 4124 byte_size_valid ? byte_size : -1, 4125 unique_ast_entry)) 4126 { 4127 // We have already parsed this type or from another 4128 // compile unit. GCC loves to use the "one definition 4129 // rule" which can result in multiple definitions 4130 // of the same class over and over in each compile 4131 // unit. 4132 type_sp = unique_ast_entry.m_type_sp; 4133 if (type_sp) 4134 { 4135 m_die_to_type[die] = type_sp.get(); 4136 return type_sp; 4137 } 4138 } 4139 } 4140 4141 DEBUG_PRINTF ("0x%8.8llx: %s (\"%s\")\n", MakeUserID(die->GetOffset()), DW_TAG_value_to_name(tag), type_name_cstr); 4142 4143 int tag_decl_kind = -1; 4144 AccessType default_accessibility = eAccessNone; 4145 if (tag == DW_TAG_structure_type) 4146 { 4147 tag_decl_kind = clang::TTK_Struct; 4148 default_accessibility = eAccessPublic; 4149 } 4150 else if (tag == DW_TAG_union_type) 4151 { 4152 tag_decl_kind = clang::TTK_Union; 4153 default_accessibility = eAccessPublic; 4154 } 4155 else if (tag == DW_TAG_class_type) 4156 { 4157 tag_decl_kind = clang::TTK_Class; 4158 default_accessibility = eAccessPrivate; 4159 } 4160 4161 4162 if (is_forward_declaration) 4163 { 4164 // We have a forward declaration to a type and we need 4165 // to try and find a full declaration. We look in the 4166 // current type index just in case we have a forward 4167 // declaration followed by an actual declarations in the 4168 // DWARF. If this fails, we need to look elsewhere... 4169 4170 type_sp = FindDefinitionTypeForDIE (dwarf_cu, die, type_name_const_str); 4171 4172 if (!type_sp && m_debug_map_symfile) 4173 { 4174 // We weren't able to find a full declaration in 4175 // this DWARF, see if we have a declaration anywhere 4176 // else... 4177 type_sp = m_debug_map_symfile->FindDefinitionTypeForDIE (dwarf_cu, die, type_name_const_str); 4178 } 4179 4180 if (type_sp) 4181 { 4182 // We found a real definition for this type elsewhere 4183 // so lets use it and cache the fact that we found 4184 // a complete type for this die 4185 m_die_to_type[die] = type_sp.get(); 4186 return type_sp; 4187 } 4188 } 4189 assert (tag_decl_kind != -1); 4190 bool clang_type_was_created = false; 4191 clang_type = m_forward_decl_die_to_clang_type.lookup (die); 4192 if (clang_type == NULL) 4193 { 4194 clang::DeclContext *decl_ctx = GetClangDeclContextContainingDIE (dwarf_cu, die, NULL); 4195 if (accessibility == eAccessNone && decl_ctx) 4196 { 4197 // Check the decl context that contains this class/struct/union. 4198 // If it is a class we must give it an accessability. 4199 const clang::Decl::Kind containing_decl_kind = decl_ctx->getDeclKind(); 4200 if (DeclKindIsCXXClass (containing_decl_kind)) 4201 accessibility = default_accessibility; 4202 } 4203 4204 if (type_name_cstr && strchr (type_name_cstr, '<')) 4205 { 4206 ClangASTContext::TemplateParameterInfos template_param_infos; 4207 if (ParseTemplateParameterInfos (dwarf_cu, die, template_param_infos)) 4208 { 4209 clang::ClassTemplateDecl *class_template_decl = ParseClassTemplateDecl (decl_ctx, 4210 accessibility, 4211 type_name_cstr, 4212 tag_decl_kind, 4213 template_param_infos); 4214 4215 clang::ClassTemplateSpecializationDecl *class_specialization_decl = ast.CreateClassTemplateSpecializationDecl (decl_ctx, 4216 class_template_decl, 4217 tag_decl_kind, 4218 template_param_infos); 4219 clang_type = ast.CreateClassTemplateSpecializationType (class_specialization_decl); 4220 clang_type_was_created = true; 4221 } 4222 } 4223 4224 if (!clang_type_was_created) 4225 { 4226 clang_type_was_created = true; 4227 clang_type = ast.CreateRecordType (decl_ctx, 4228 accessibility, 4229 type_name_cstr, 4230 tag_decl_kind, 4231 class_language); 4232 } 4233 } 4234 4235 // Store a forward declaration to this class type in case any 4236 // parameters in any class methods need it for the clang 4237 // types for function prototypes. 4238 LinkDeclContextToDIE(ClangASTContext::GetDeclContextForType(clang_type), die); 4239 type_sp.reset (new Type (MakeUserID(die->GetOffset()), 4240 this, 4241 type_name_const_str, 4242 byte_size, 4243 NULL, 4244 LLDB_INVALID_UID, 4245 Type::eEncodingIsUID, 4246 &decl, 4247 clang_type, 4248 Type::eResolveStateForward)); 4249 4250 4251 // Add our type to the unique type map so we don't 4252 // end up creating many copies of the same type over 4253 // and over in the ASTContext for our module 4254 unique_ast_entry.m_type_sp = type_sp; 4255 unique_ast_entry.m_symfile = this; 4256 unique_ast_entry.m_cu = dwarf_cu; 4257 unique_ast_entry.m_die = die; 4258 unique_ast_entry.m_declaration = decl; 4259 GetUniqueDWARFASTTypeMap().Insert (type_name_const_str, 4260 unique_ast_entry); 4261 4262 if (die->HasChildren() == false && is_forward_declaration == false) 4263 { 4264 // No children for this struct/union/class, lets finish it 4265 ast.StartTagDeclarationDefinition (clang_type); 4266 ast.CompleteTagDeclarationDefinition (clang_type); 4267 } 4268 else if (clang_type_was_created) 4269 { 4270 // Leave this as a forward declaration until we need 4271 // to know the details of the type. lldb_private::Type 4272 // will automatically call the SymbolFile virtual function 4273 // "SymbolFileDWARF::ResolveClangOpaqueTypeDefinition(Type *)" 4274 // When the definition needs to be defined. 4275 m_forward_decl_die_to_clang_type[die] = clang_type; 4276 m_forward_decl_clang_type_to_die[ClangASTType::RemoveFastQualifiers (clang_type)] = die; 4277 ClangASTContext::SetHasExternalStorage (clang_type, true); 4278 } 4279 } 4280 break; 4281 4282 case DW_TAG_enumeration_type: 4283 { 4284 // Set a bit that lets us know that we are currently parsing this 4285 m_die_to_type[die] = DIE_IS_BEING_PARSED; 4286 4287 lldb::user_id_t encoding_uid = DW_INVALID_OFFSET; 4288 4289 const size_t num_attributes = die->GetAttributes(this, dwarf_cu, NULL, attributes); 4290 if (num_attributes > 0) 4291 { 4292 uint32_t i; 4293 4294 for (i=0; i<num_attributes; ++i) 4295 { 4296 attr = attributes.AttributeAtIndex(i); 4297 DWARFFormValue form_value; 4298 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 4299 { 4300 switch (attr) 4301 { 4302 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 4303 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 4304 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 4305 case DW_AT_name: 4306 type_name_cstr = form_value.AsCString(&get_debug_str_data()); 4307 type_name_const_str.SetCString(type_name_cstr); 4308 break; 4309 case DW_AT_type: encoding_uid = form_value.Reference(dwarf_cu); break; 4310 case DW_AT_byte_size: byte_size = form_value.Unsigned(); byte_size_valid = true; break; 4311 case DW_AT_accessibility: accessibility = DW_ACCESS_to_AccessType(form_value.Unsigned()); break; 4312 case DW_AT_declaration: is_forward_declaration = form_value.Unsigned() != 0; break; 4313 case DW_AT_allocated: 4314 case DW_AT_associated: 4315 case DW_AT_bit_stride: 4316 case DW_AT_byte_stride: 4317 case DW_AT_data_location: 4318 case DW_AT_description: 4319 case DW_AT_start_scope: 4320 case DW_AT_visibility: 4321 case DW_AT_specification: 4322 case DW_AT_abstract_origin: 4323 case DW_AT_sibling: 4324 break; 4325 } 4326 } 4327 } 4328 4329 DEBUG_PRINTF ("0x%8.8llx: %s (\"%s\")\n", MakeUserID(die->GetOffset()), DW_TAG_value_to_name(tag), type_name_cstr); 4330 4331 clang_type_t enumerator_clang_type = NULL; 4332 clang_type = m_forward_decl_die_to_clang_type.lookup (die); 4333 if (clang_type == NULL) 4334 { 4335 enumerator_clang_type = ast.GetBuiltinTypeForDWARFEncodingAndBitSize (NULL, 4336 DW_ATE_signed, 4337 byte_size * 8); 4338 clang_type = ast.CreateEnumerationType (type_name_cstr, 4339 GetClangDeclContextContainingDIE (dwarf_cu, die, NULL), 4340 decl, 4341 enumerator_clang_type); 4342 } 4343 else 4344 { 4345 enumerator_clang_type = ClangASTContext::GetEnumerationIntegerType (clang_type); 4346 assert (enumerator_clang_type != NULL); 4347 } 4348 4349 LinkDeclContextToDIE(ClangASTContext::GetDeclContextForType(clang_type), die); 4350 4351 type_sp.reset( new Type (MakeUserID(die->GetOffset()), 4352 this, 4353 type_name_const_str, 4354 byte_size, 4355 NULL, 4356 encoding_uid, 4357 Type::eEncodingIsUID, 4358 &decl, 4359 clang_type, 4360 Type::eResolveStateForward)); 4361 4362 ast.StartTagDeclarationDefinition (clang_type); 4363 if (die->HasChildren()) 4364 { 4365 SymbolContext cu_sc(GetCompUnitForDWARFCompUnit(dwarf_cu)); 4366 ParseChildEnumerators(cu_sc, clang_type, type_sp->GetByteSize(), dwarf_cu, die); 4367 } 4368 ast.CompleteTagDeclarationDefinition (clang_type); 4369 } 4370 } 4371 break; 4372 4373 case DW_TAG_inlined_subroutine: 4374 case DW_TAG_subprogram: 4375 case DW_TAG_subroutine_type: 4376 { 4377 // Set a bit that lets us know that we are currently parsing this 4378 m_die_to_type[die] = DIE_IS_BEING_PARSED; 4379 4380 const char *mangled = NULL; 4381 dw_offset_t type_die_offset = DW_INVALID_OFFSET; 4382 bool is_variadic = false; 4383 bool is_inline = false; 4384 bool is_static = false; 4385 bool is_virtual = false; 4386 bool is_explicit = false; 4387 bool is_artificial = false; 4388 dw_offset_t specification_die_offset = DW_INVALID_OFFSET; 4389 dw_offset_t abstract_origin_die_offset = DW_INVALID_OFFSET; 4390 4391 unsigned type_quals = 0; 4392 clang::StorageClass storage = clang::SC_None;//, Extern, Static, PrivateExtern 4393 4394 4395 const size_t num_attributes = die->GetAttributes(this, dwarf_cu, NULL, attributes); 4396 if (num_attributes > 0) 4397 { 4398 uint32_t i; 4399 for (i=0; i<num_attributes; ++i) 4400 { 4401 attr = attributes.AttributeAtIndex(i); 4402 DWARFFormValue form_value; 4403 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 4404 { 4405 switch (attr) 4406 { 4407 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 4408 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 4409 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 4410 case DW_AT_name: 4411 type_name_cstr = form_value.AsCString(&get_debug_str_data()); 4412 type_name_const_str.SetCString(type_name_cstr); 4413 break; 4414 4415 case DW_AT_MIPS_linkage_name: mangled = form_value.AsCString(&get_debug_str_data()); break; 4416 case DW_AT_type: type_die_offset = form_value.Reference(dwarf_cu); break; 4417 case DW_AT_accessibility: accessibility = DW_ACCESS_to_AccessType(form_value.Unsigned()); break; 4418 case DW_AT_declaration: is_forward_declaration = form_value.Unsigned() != 0; break; 4419 case DW_AT_inline: is_inline = form_value.Unsigned() != 0; break; 4420 case DW_AT_virtuality: is_virtual = form_value.Unsigned() != 0; break; 4421 case DW_AT_explicit: is_explicit = form_value.Unsigned() != 0; break; 4422 case DW_AT_artificial: is_artificial = form_value.Unsigned() != 0; break; 4423 4424 4425 case DW_AT_external: 4426 if (form_value.Unsigned()) 4427 { 4428 if (storage == clang::SC_None) 4429 storage = clang::SC_Extern; 4430 else 4431 storage = clang::SC_PrivateExtern; 4432 } 4433 break; 4434 4435 case DW_AT_specification: 4436 specification_die_offset = form_value.Reference(dwarf_cu); 4437 break; 4438 4439 case DW_AT_abstract_origin: 4440 abstract_origin_die_offset = form_value.Reference(dwarf_cu); 4441 break; 4442 4443 case DW_AT_allocated: 4444 case DW_AT_associated: 4445 case DW_AT_address_class: 4446 case DW_AT_calling_convention: 4447 case DW_AT_data_location: 4448 case DW_AT_elemental: 4449 case DW_AT_entry_pc: 4450 case DW_AT_frame_base: 4451 case DW_AT_high_pc: 4452 case DW_AT_low_pc: 4453 case DW_AT_object_pointer: 4454 case DW_AT_prototyped: 4455 case DW_AT_pure: 4456 case DW_AT_ranges: 4457 case DW_AT_recursive: 4458 case DW_AT_return_addr: 4459 case DW_AT_segment: 4460 case DW_AT_start_scope: 4461 case DW_AT_static_link: 4462 case DW_AT_trampoline: 4463 case DW_AT_visibility: 4464 case DW_AT_vtable_elem_location: 4465 case DW_AT_description: 4466 case DW_AT_sibling: 4467 break; 4468 } 4469 } 4470 } 4471 } 4472 4473 DEBUG_PRINTF ("0x%8.8llx: %s (\"%s\")\n", MakeUserID(die->GetOffset()), DW_TAG_value_to_name(tag), type_name_cstr); 4474 4475 clang_type_t return_clang_type = NULL; 4476 Type *func_type = NULL; 4477 4478 if (type_die_offset != DW_INVALID_OFFSET) 4479 func_type = ResolveTypeUID(type_die_offset); 4480 4481 if (func_type) 4482 return_clang_type = func_type->GetClangLayoutType(); 4483 else 4484 return_clang_type = ast.GetBuiltInType_void(); 4485 4486 4487 std::vector<clang_type_t> function_param_types; 4488 std::vector<clang::ParmVarDecl*> function_param_decls; 4489 4490 // Parse the function children for the parameters 4491 4492 const DWARFDebugInfoEntry *decl_ctx_die = NULL; 4493 clang::DeclContext *containing_decl_ctx = GetClangDeclContextContainingDIE (dwarf_cu, die, &decl_ctx_die); 4494 const clang::Decl::Kind containing_decl_kind = containing_decl_ctx->getDeclKind(); 4495 4496 const bool is_cxx_method = DeclKindIsCXXClass (containing_decl_kind); 4497 // Start off static. This will be set to false in ParseChildParameters(...) 4498 // if we find a "this" paramters as the first parameter 4499 if (is_cxx_method) 4500 is_static = true; 4501 4502 if (die->HasChildren()) 4503 { 4504 bool skip_artificial = true; 4505 ParseChildParameters (sc, 4506 containing_decl_ctx, 4507 type_sp, 4508 dwarf_cu, 4509 die, 4510 skip_artificial, 4511 is_static, 4512 type_list, 4513 function_param_types, 4514 function_param_decls, 4515 type_quals); 4516 } 4517 4518 // clang_type will get the function prototype clang type after this call 4519 clang_type = ast.CreateFunctionType (return_clang_type, 4520 &function_param_types[0], 4521 function_param_types.size(), 4522 is_variadic, 4523 type_quals); 4524 4525 if (type_name_cstr) 4526 { 4527 bool type_handled = false; 4528 if (tag == DW_TAG_subprogram) 4529 { 4530 if (ObjCLanguageRuntime::IsPossibleObjCMethodName (type_name_cstr)) 4531 { 4532 // We need to find the DW_TAG_class_type or 4533 // DW_TAG_struct_type by name so we can add this 4534 // as a member function of the class. 4535 const char *class_name_start = type_name_cstr + 2; 4536 const char *class_name_end = ::strchr (class_name_start, ' '); 4537 SymbolContext empty_sc; 4538 clang_type_t class_opaque_type = NULL; 4539 if (class_name_start < class_name_end) 4540 { 4541 ConstString class_name (class_name_start, class_name_end - class_name_start); 4542 TypeList types; 4543 const uint32_t match_count = FindTypes (empty_sc, class_name, NULL, true, UINT32_MAX, types); 4544 if (match_count > 0) 4545 { 4546 for (uint32_t i=0; i<match_count; ++i) 4547 { 4548 Type *type = types.GetTypeAtIndex (i).get(); 4549 clang_type_t type_clang_forward_type = type->GetClangForwardType(); 4550 if (ClangASTContext::IsObjCClassType (type_clang_forward_type)) 4551 { 4552 class_opaque_type = type_clang_forward_type; 4553 break; 4554 } 4555 } 4556 } 4557 } 4558 4559 if (class_opaque_type) 4560 { 4561 // If accessibility isn't set to anything valid, assume public for 4562 // now... 4563 if (accessibility == eAccessNone) 4564 accessibility = eAccessPublic; 4565 4566 clang::ObjCMethodDecl *objc_method_decl; 4567 objc_method_decl = ast.AddMethodToObjCObjectType (class_opaque_type, 4568 type_name_cstr, 4569 clang_type, 4570 accessibility); 4571 LinkDeclContextToDIE(ClangASTContext::GetAsDeclContext(objc_method_decl), die); 4572 type_handled = objc_method_decl != NULL; 4573 } 4574 } 4575 else if (is_cxx_method) 4576 { 4577 // Look at the parent of this DIE and see if is is 4578 // a class or struct and see if this is actually a 4579 // C++ method 4580 Type *class_type = ResolveType (dwarf_cu, decl_ctx_die); 4581 if (class_type) 4582 { 4583 if (specification_die_offset != DW_INVALID_OFFSET) 4584 { 4585 // We have a specification which we are going to base our function 4586 // prototype off of, so we need this type to be completed so that the 4587 // m_die_to_decl_ctx for the method in the specification has a valid 4588 // clang decl context. 4589 class_type->GetClangFullType(); 4590 // If we have a specification, then the function type should have been 4591 // made with the specification and not with this die. 4592 DWARFCompileUnitSP spec_cu_sp; 4593 const DWARFDebugInfoEntry* spec_die = DebugInfo()->GetDIEPtr(specification_die_offset, &spec_cu_sp); 4594 clang::DeclContext *spec_clang_decl_ctx = GetCachedClangDeclContextForDIE (spec_die); 4595 if (spec_clang_decl_ctx) 4596 { 4597 LinkDeclContextToDIE(spec_clang_decl_ctx, die); 4598 } 4599 else 4600 { 4601 ReportWarning ("0x%8.8llx: DW_AT_specification(0x%8.8x) has no decl\n", 4602 MakeUserID(die->GetOffset()), 4603 specification_die_offset); 4604 } 4605 type_handled = true; 4606 } 4607 else if (abstract_origin_die_offset != DW_INVALID_OFFSET) 4608 { 4609 // We have a specification which we are going to base our function 4610 // prototype off of, so we need this type to be completed so that the 4611 // m_die_to_decl_ctx for the method in the abstract origin has a valid 4612 // clang decl context. 4613 class_type->GetClangFullType(); 4614 4615 DWARFCompileUnitSP abs_cu_sp; 4616 const DWARFDebugInfoEntry* abs_die = DebugInfo()->GetDIEPtr(abstract_origin_die_offset, &abs_cu_sp); 4617 clang::DeclContext *abs_clang_decl_ctx = GetCachedClangDeclContextForDIE (abs_die); 4618 if (abs_clang_decl_ctx) 4619 { 4620 LinkDeclContextToDIE (abs_clang_decl_ctx, die); 4621 } 4622 else 4623 { 4624 ReportWarning ("0x%8.8llx: DW_AT_abstract_origin(0x%8.8x) has no decl\n", 4625 MakeUserID(die->GetOffset()), 4626 abstract_origin_die_offset); 4627 } 4628 type_handled = true; 4629 } 4630 else 4631 { 4632 clang_type_t class_opaque_type = class_type->GetClangForwardType(); 4633 if (ClangASTContext::IsCXXClassType (class_opaque_type)) 4634 { 4635 if (ClangASTContext::IsBeingDefined (class_opaque_type)) 4636 { 4637 // Neither GCC 4.2 nor clang++ currently set a valid accessibility 4638 // in the DWARF for C++ methods... Default to public for now... 4639 if (accessibility == eAccessNone) 4640 accessibility = eAccessPublic; 4641 4642 if (!is_static && !die->HasChildren()) 4643 { 4644 // We have a C++ member function with no children (this pointer!) 4645 // and clang will get mad if we try and make a function that isn't 4646 // well formed in the DWARF, so we will just skip it... 4647 type_handled = true; 4648 } 4649 else 4650 { 4651 clang::CXXMethodDecl *cxx_method_decl; 4652 // REMOVE THE CRASH DESCRIPTION BELOW 4653 Host::SetCrashDescriptionWithFormat ("SymbolFileDWARF::ParseType() is adding a method %s to class %s in DIE 0x%8.8llx from %s/%s", 4654 type_name_cstr, 4655 class_type->GetName().GetCString(), 4656 MakeUserID(die->GetOffset()), 4657 m_obj_file->GetFileSpec().GetDirectory().GetCString(), 4658 m_obj_file->GetFileSpec().GetFilename().GetCString()); 4659 4660 const bool is_attr_used = false; 4661 4662 cxx_method_decl = ast.AddMethodToCXXRecordType (class_opaque_type, 4663 type_name_cstr, 4664 clang_type, 4665 accessibility, 4666 is_virtual, 4667 is_static, 4668 is_inline, 4669 is_explicit, 4670 is_attr_used, 4671 is_artificial); 4672 LinkDeclContextToDIE(ClangASTContext::GetAsDeclContext(cxx_method_decl), die); 4673 4674 Host::SetCrashDescription (NULL); 4675 4676 type_handled = cxx_method_decl != NULL; 4677 } 4678 } 4679 else 4680 { 4681 // We were asked to parse the type for a method in a class, yet the 4682 // class hasn't been asked to complete itself through the 4683 // clang::ExternalASTSource protocol, so we need to just have the 4684 // class complete itself and do things the right way, then our 4685 // DIE should then have an entry in the m_die_to_type map. First 4686 // we need to modify the m_die_to_type so it doesn't think we are 4687 // trying to parse this DIE anymore... 4688 m_die_to_type[die] = NULL; 4689 4690 // Now we get the full type to force our class type to complete itself 4691 // using the clang::ExternalASTSource protocol which will parse all 4692 // base classes and all methods (including the method for this DIE). 4693 class_type->GetClangFullType(); 4694 4695 // The type for this DIE should have been filled in the function call above 4696 type_ptr = m_die_to_type[die]; 4697 if (type_ptr) 4698 { 4699 type_sp = type_ptr; 4700 break; 4701 } 4702 } 4703 } 4704 } 4705 } 4706 } 4707 } 4708 4709 if (!type_handled) 4710 { 4711 // We just have a function that isn't part of a class 4712 clang::FunctionDecl *function_decl = ast.CreateFunctionDeclaration (containing_decl_ctx, 4713 type_name_cstr, 4714 clang_type, 4715 storage, 4716 is_inline); 4717 4718 // Add the decl to our DIE to decl context map 4719 assert (function_decl); 4720 LinkDeclContextToDIE(function_decl, die); 4721 if (!function_param_decls.empty()) 4722 ast.SetFunctionParameters (function_decl, 4723 &function_param_decls.front(), 4724 function_param_decls.size()); 4725 } 4726 } 4727 type_sp.reset( new Type (MakeUserID(die->GetOffset()), 4728 this, 4729 type_name_const_str, 4730 0, 4731 NULL, 4732 LLDB_INVALID_UID, 4733 Type::eEncodingIsUID, 4734 &decl, 4735 clang_type, 4736 Type::eResolveStateFull)); 4737 assert(type_sp.get()); 4738 } 4739 break; 4740 4741 case DW_TAG_array_type: 4742 { 4743 // Set a bit that lets us know that we are currently parsing this 4744 m_die_to_type[die] = DIE_IS_BEING_PARSED; 4745 4746 lldb::user_id_t type_die_offset = DW_INVALID_OFFSET; 4747 int64_t first_index = 0; 4748 uint32_t byte_stride = 0; 4749 uint32_t bit_stride = 0; 4750 const size_t num_attributes = die->GetAttributes(this, dwarf_cu, NULL, attributes); 4751 4752 if (num_attributes > 0) 4753 { 4754 uint32_t i; 4755 for (i=0; i<num_attributes; ++i) 4756 { 4757 attr = attributes.AttributeAtIndex(i); 4758 DWARFFormValue form_value; 4759 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 4760 { 4761 switch (attr) 4762 { 4763 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 4764 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 4765 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 4766 case DW_AT_name: 4767 type_name_cstr = form_value.AsCString(&get_debug_str_data()); 4768 type_name_const_str.SetCString(type_name_cstr); 4769 break; 4770 4771 case DW_AT_type: type_die_offset = form_value.Reference(dwarf_cu); break; 4772 case DW_AT_byte_size: byte_size = form_value.Unsigned(); byte_size_valid = true; break; 4773 case DW_AT_byte_stride: byte_stride = form_value.Unsigned(); break; 4774 case DW_AT_bit_stride: bit_stride = form_value.Unsigned(); break; 4775 case DW_AT_accessibility: accessibility = DW_ACCESS_to_AccessType(form_value.Unsigned()); break; 4776 case DW_AT_declaration: is_forward_declaration = form_value.Unsigned() != 0; break; 4777 case DW_AT_allocated: 4778 case DW_AT_associated: 4779 case DW_AT_data_location: 4780 case DW_AT_description: 4781 case DW_AT_ordering: 4782 case DW_AT_start_scope: 4783 case DW_AT_visibility: 4784 case DW_AT_specification: 4785 case DW_AT_abstract_origin: 4786 case DW_AT_sibling: 4787 break; 4788 } 4789 } 4790 } 4791 4792 DEBUG_PRINTF ("0x%8.8llx: %s (\"%s\")\n", MakeUserID(die->GetOffset()), DW_TAG_value_to_name(tag), type_name_cstr); 4793 4794 Type *element_type = ResolveTypeUID(type_die_offset); 4795 4796 if (element_type) 4797 { 4798 std::vector<uint64_t> element_orders; 4799 ParseChildArrayInfo(sc, dwarf_cu, die, first_index, element_orders, byte_stride, bit_stride); 4800 // We have an array that claims to have no members, lets give it at least one member... 4801 if (element_orders.empty()) 4802 element_orders.push_back (1); 4803 if (byte_stride == 0 && bit_stride == 0) 4804 byte_stride = element_type->GetByteSize(); 4805 clang_type_t array_element_type = element_type->GetClangFullType(); 4806 uint64_t array_element_bit_stride = byte_stride * 8 + bit_stride; 4807 uint64_t num_elements = 0; 4808 std::vector<uint64_t>::const_reverse_iterator pos; 4809 std::vector<uint64_t>::const_reverse_iterator end = element_orders.rend(); 4810 for (pos = element_orders.rbegin(); pos != end; ++pos) 4811 { 4812 num_elements = *pos; 4813 clang_type = ast.CreateArrayType (array_element_type, 4814 num_elements, 4815 num_elements * array_element_bit_stride); 4816 array_element_type = clang_type; 4817 array_element_bit_stride = array_element_bit_stride * num_elements; 4818 } 4819 ConstString empty_name; 4820 type_sp.reset( new Type (MakeUserID(die->GetOffset()), 4821 this, 4822 empty_name, 4823 array_element_bit_stride / 8, 4824 NULL, 4825 type_die_offset, 4826 Type::eEncodingIsUID, 4827 &decl, 4828 clang_type, 4829 Type::eResolveStateFull)); 4830 type_sp->SetEncodingType (element_type); 4831 } 4832 } 4833 } 4834 break; 4835 4836 case DW_TAG_ptr_to_member_type: 4837 { 4838 dw_offset_t type_die_offset = DW_INVALID_OFFSET; 4839 dw_offset_t containing_type_die_offset = DW_INVALID_OFFSET; 4840 4841 const size_t num_attributes = die->GetAttributes(this, dwarf_cu, NULL, attributes); 4842 4843 if (num_attributes > 0) { 4844 uint32_t i; 4845 for (i=0; i<num_attributes; ++i) 4846 { 4847 attr = attributes.AttributeAtIndex(i); 4848 DWARFFormValue form_value; 4849 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 4850 { 4851 switch (attr) 4852 { 4853 case DW_AT_type: 4854 type_die_offset = form_value.Reference(dwarf_cu); break; 4855 case DW_AT_containing_type: 4856 containing_type_die_offset = form_value.Reference(dwarf_cu); break; 4857 } 4858 } 4859 } 4860 4861 Type *pointee_type = ResolveTypeUID(type_die_offset); 4862 Type *class_type = ResolveTypeUID(containing_type_die_offset); 4863 4864 clang_type_t pointee_clang_type = pointee_type->GetClangForwardType(); 4865 clang_type_t class_clang_type = class_type->GetClangLayoutType(); 4866 4867 clang_type = ast.CreateMemberPointerType(pointee_clang_type, 4868 class_clang_type); 4869 4870 byte_size = ClangASTType::GetClangTypeBitWidth (ast.getASTContext(), 4871 clang_type) / 8; 4872 4873 type_sp.reset( new Type (MakeUserID(die->GetOffset()), 4874 this, 4875 type_name_const_str, 4876 byte_size, 4877 NULL, 4878 LLDB_INVALID_UID, 4879 Type::eEncodingIsUID, 4880 NULL, 4881 clang_type, 4882 Type::eResolveStateForward)); 4883 } 4884 4885 break; 4886 } 4887 default: 4888 assert(false && "Unhandled type tag!"); 4889 break; 4890 } 4891 4892 if (type_sp.get()) 4893 { 4894 const DWARFDebugInfoEntry *sc_parent_die = GetParentSymbolContextDIE(die); 4895 dw_tag_t sc_parent_tag = sc_parent_die ? sc_parent_die->Tag() : 0; 4896 4897 SymbolContextScope * symbol_context_scope = NULL; 4898 if (sc_parent_tag == DW_TAG_compile_unit) 4899 { 4900 symbol_context_scope = sc.comp_unit; 4901 } 4902 else if (sc.function != NULL) 4903 { 4904 symbol_context_scope = sc.function->GetBlock(true).FindBlockByID(MakeUserID(sc_parent_die->GetOffset())); 4905 if (symbol_context_scope == NULL) 4906 symbol_context_scope = sc.function; 4907 } 4908 4909 if (symbol_context_scope != NULL) 4910 { 4911 type_sp->SetSymbolContextScope(symbol_context_scope); 4912 } 4913 4914 // We are ready to put this type into the uniqued list up at the module level 4915 type_list->Insert (type_sp); 4916 4917 m_die_to_type[die] = type_sp.get(); 4918 } 4919 } 4920 else if (type_ptr != DIE_IS_BEING_PARSED) 4921 { 4922 type_sp = type_ptr; 4923 } 4924 } 4925 return type_sp; 4926 } 4927 4928 size_t 4929 SymbolFileDWARF::ParseTypes 4930 ( 4931 const SymbolContext& sc, 4932 DWARFCompileUnit* dwarf_cu, 4933 const DWARFDebugInfoEntry *die, 4934 bool parse_siblings, 4935 bool parse_children 4936 ) 4937 { 4938 size_t types_added = 0; 4939 while (die != NULL) 4940 { 4941 bool type_is_new = false; 4942 if (ParseType(sc, dwarf_cu, die, &type_is_new).get()) 4943 { 4944 if (type_is_new) 4945 ++types_added; 4946 } 4947 4948 if (parse_children && die->HasChildren()) 4949 { 4950 if (die->Tag() == DW_TAG_subprogram) 4951 { 4952 SymbolContext child_sc(sc); 4953 child_sc.function = sc.comp_unit->FindFunctionByUID(MakeUserID(die->GetOffset())).get(); 4954 types_added += ParseTypes(child_sc, dwarf_cu, die->GetFirstChild(), true, true); 4955 } 4956 else 4957 types_added += ParseTypes(sc, dwarf_cu, die->GetFirstChild(), true, true); 4958 } 4959 4960 if (parse_siblings) 4961 die = die->GetSibling(); 4962 else 4963 die = NULL; 4964 } 4965 return types_added; 4966 } 4967 4968 4969 size_t 4970 SymbolFileDWARF::ParseFunctionBlocks (const SymbolContext &sc) 4971 { 4972 assert(sc.comp_unit && sc.function); 4973 size_t functions_added = 0; 4974 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnitForUID(sc.comp_unit->GetID()); 4975 if (dwarf_cu) 4976 { 4977 dw_offset_t function_die_offset = sc.function->GetID(); 4978 const DWARFDebugInfoEntry *function_die = dwarf_cu->GetDIEPtr(function_die_offset); 4979 if (function_die) 4980 { 4981 ParseFunctionBlocks(sc, &sc.function->GetBlock (false), dwarf_cu, function_die, LLDB_INVALID_ADDRESS, 0); 4982 } 4983 } 4984 4985 return functions_added; 4986 } 4987 4988 4989 size_t 4990 SymbolFileDWARF::ParseTypes (const SymbolContext &sc) 4991 { 4992 // At least a compile unit must be valid 4993 assert(sc.comp_unit); 4994 size_t types_added = 0; 4995 DWARFCompileUnit* dwarf_cu = GetDWARFCompileUnitForUID(sc.comp_unit->GetID()); 4996 if (dwarf_cu) 4997 { 4998 if (sc.function) 4999 { 5000 dw_offset_t function_die_offset = sc.function->GetID(); 5001 const DWARFDebugInfoEntry *func_die = dwarf_cu->GetDIEPtr(function_die_offset); 5002 if (func_die && func_die->HasChildren()) 5003 { 5004 types_added = ParseTypes(sc, dwarf_cu, func_die->GetFirstChild(), true, true); 5005 } 5006 } 5007 else 5008 { 5009 const DWARFDebugInfoEntry *dwarf_cu_die = dwarf_cu->DIE(); 5010 if (dwarf_cu_die && dwarf_cu_die->HasChildren()) 5011 { 5012 types_added = ParseTypes(sc, dwarf_cu, dwarf_cu_die->GetFirstChild(), true, true); 5013 } 5014 } 5015 } 5016 5017 return types_added; 5018 } 5019 5020 size_t 5021 SymbolFileDWARF::ParseVariablesForContext (const SymbolContext& sc) 5022 { 5023 if (sc.comp_unit != NULL) 5024 { 5025 DWARFDebugInfo* info = DebugInfo(); 5026 if (info == NULL) 5027 return 0; 5028 5029 uint32_t cu_idx = UINT32_MAX; 5030 DWARFCompileUnit* dwarf_cu = info->GetCompileUnit(sc.comp_unit->GetID(), &cu_idx).get(); 5031 5032 if (dwarf_cu == NULL) 5033 return 0; 5034 5035 if (sc.function) 5036 { 5037 const DWARFDebugInfoEntry *function_die = dwarf_cu->GetDIEPtr(sc.function->GetID()); 5038 5039 dw_addr_t func_lo_pc = function_die->GetAttributeValueAsUnsigned (this, dwarf_cu, DW_AT_low_pc, DW_INVALID_ADDRESS); 5040 assert (func_lo_pc != DW_INVALID_ADDRESS); 5041 5042 const size_t num_variables = ParseVariables(sc, dwarf_cu, func_lo_pc, function_die->GetFirstChild(), true, true); 5043 5044 // Let all blocks know they have parse all their variables 5045 sc.function->GetBlock (false).SetDidParseVariables (true, true); 5046 5047 return num_variables; 5048 } 5049 else if (sc.comp_unit) 5050 { 5051 uint32_t vars_added = 0; 5052 VariableListSP variables (sc.comp_unit->GetVariableList(false)); 5053 5054 if (variables.get() == NULL) 5055 { 5056 variables.reset(new VariableList()); 5057 sc.comp_unit->SetVariableList(variables); 5058 5059 DWARFCompileUnit* match_dwarf_cu = NULL; 5060 const DWARFDebugInfoEntry* die = NULL; 5061 DIEArray die_offsets; 5062 if (m_using_apple_tables) 5063 { 5064 if (m_apple_names_ap.get()) 5065 m_apple_names_ap->AppendAllDIEsInRange (dwarf_cu->GetOffset(), 5066 dwarf_cu->GetNextCompileUnitOffset(), 5067 die_offsets); 5068 } 5069 else 5070 { 5071 // Index if we already haven't to make sure the compile units 5072 // get indexed and make their global DIE index list 5073 if (!m_indexed) 5074 Index (); 5075 5076 m_global_index.FindAllEntriesForCompileUnit (dwarf_cu->GetOffset(), 5077 dwarf_cu->GetNextCompileUnitOffset(), 5078 die_offsets); 5079 } 5080 5081 const size_t num_matches = die_offsets.size(); 5082 if (num_matches) 5083 { 5084 DWARFDebugInfo* debug_info = DebugInfo(); 5085 for (size_t i=0; i<num_matches; ++i) 5086 { 5087 const dw_offset_t die_offset = die_offsets[i]; 5088 die = debug_info->GetDIEPtrWithCompileUnitHint (die_offset, &match_dwarf_cu); 5089 if (die) 5090 { 5091 VariableSP var_sp (ParseVariableDIE(sc, dwarf_cu, die, LLDB_INVALID_ADDRESS)); 5092 if (var_sp) 5093 { 5094 variables->AddVariableIfUnique (var_sp); 5095 ++vars_added; 5096 } 5097 } 5098 else 5099 { 5100 if (m_using_apple_tables) 5101 { 5102 ReportError (".apple_names accelerator table had bad die 0x%8.8x\n", die_offset); 5103 } 5104 } 5105 5106 } 5107 } 5108 } 5109 return vars_added; 5110 } 5111 } 5112 return 0; 5113 } 5114 5115 5116 VariableSP 5117 SymbolFileDWARF::ParseVariableDIE 5118 ( 5119 const SymbolContext& sc, 5120 DWARFCompileUnit* dwarf_cu, 5121 const DWARFDebugInfoEntry *die, 5122 const lldb::addr_t func_low_pc 5123 ) 5124 { 5125 5126 VariableSP var_sp (m_die_to_variable_sp[die]); 5127 if (var_sp) 5128 return var_sp; // Already been parsed! 5129 5130 const dw_tag_t tag = die->Tag(); 5131 5132 if ((tag == DW_TAG_variable) || 5133 (tag == DW_TAG_constant) || 5134 (tag == DW_TAG_formal_parameter && sc.function)) 5135 { 5136 DWARFDebugInfoEntry::Attributes attributes; 5137 const size_t num_attributes = die->GetAttributes(this, dwarf_cu, NULL, attributes); 5138 if (num_attributes > 0) 5139 { 5140 const char *name = NULL; 5141 const char *mangled = NULL; 5142 Declaration decl; 5143 uint32_t i; 5144 Type *var_type = NULL; 5145 DWARFExpression location; 5146 bool is_external = false; 5147 bool is_artificial = false; 5148 bool location_is_const_value_data = false; 5149 AccessType accessibility = eAccessNone; 5150 5151 for (i=0; i<num_attributes; ++i) 5152 { 5153 dw_attr_t attr = attributes.AttributeAtIndex(i); 5154 DWARFFormValue form_value; 5155 if (attributes.ExtractFormValueAtIndex(this, i, form_value)) 5156 { 5157 switch (attr) 5158 { 5159 case DW_AT_decl_file: decl.SetFile(sc.comp_unit->GetSupportFiles().GetFileSpecAtIndex(form_value.Unsigned())); break; 5160 case DW_AT_decl_line: decl.SetLine(form_value.Unsigned()); break; 5161 case DW_AT_decl_column: decl.SetColumn(form_value.Unsigned()); break; 5162 case DW_AT_name: name = form_value.AsCString(&get_debug_str_data()); break; 5163 case DW_AT_MIPS_linkage_name: mangled = form_value.AsCString(&get_debug_str_data()); break; 5164 case DW_AT_type: var_type = ResolveTypeUID(form_value.Reference(dwarf_cu)); break; 5165 case DW_AT_external: is_external = form_value.Unsigned() != 0; break; 5166 case DW_AT_const_value: 5167 location_is_const_value_data = true; 5168 // Fall through... 5169 case DW_AT_location: 5170 { 5171 if (form_value.BlockData()) 5172 { 5173 const DataExtractor& debug_info_data = get_debug_info_data(); 5174 5175 uint32_t block_offset = form_value.BlockData() - debug_info_data.GetDataStart(); 5176 uint32_t block_length = form_value.Unsigned(); 5177 location.SetOpcodeData(get_debug_info_data(), block_offset, block_length); 5178 } 5179 else 5180 { 5181 const DataExtractor& debug_loc_data = get_debug_loc_data(); 5182 const dw_offset_t debug_loc_offset = form_value.Unsigned(); 5183 5184 size_t loc_list_length = DWARFLocationList::Size(debug_loc_data, debug_loc_offset); 5185 if (loc_list_length > 0) 5186 { 5187 location.SetOpcodeData(debug_loc_data, debug_loc_offset, loc_list_length); 5188 assert (func_low_pc != LLDB_INVALID_ADDRESS); 5189 location.SetLocationListSlide (func_low_pc - dwarf_cu->GetBaseAddress()); 5190 } 5191 } 5192 } 5193 break; 5194 5195 case DW_AT_artificial: is_artificial = form_value.Unsigned() != 0; break; 5196 case DW_AT_accessibility: accessibility = DW_ACCESS_to_AccessType(form_value.Unsigned()); break; 5197 case DW_AT_declaration: 5198 case DW_AT_description: 5199 case DW_AT_endianity: 5200 case DW_AT_segment: 5201 case DW_AT_start_scope: 5202 case DW_AT_visibility: 5203 default: 5204 case DW_AT_abstract_origin: 5205 case DW_AT_sibling: 5206 case DW_AT_specification: 5207 break; 5208 } 5209 } 5210 } 5211 5212 if (location.IsValid()) 5213 { 5214 assert(var_type != DIE_IS_BEING_PARSED); 5215 5216 ValueType scope = eValueTypeInvalid; 5217 5218 const DWARFDebugInfoEntry *sc_parent_die = GetParentSymbolContextDIE(die); 5219 dw_tag_t parent_tag = sc_parent_die ? sc_parent_die->Tag() : 0; 5220 5221 if (tag == DW_TAG_formal_parameter) 5222 scope = eValueTypeVariableArgument; 5223 else if (is_external || parent_tag == DW_TAG_compile_unit) 5224 scope = eValueTypeVariableGlobal; 5225 else 5226 scope = eValueTypeVariableLocal; 5227 5228 SymbolContextScope * symbol_context_scope = NULL; 5229 switch (parent_tag) 5230 { 5231 case DW_TAG_subprogram: 5232 case DW_TAG_inlined_subroutine: 5233 case DW_TAG_lexical_block: 5234 if (sc.function) 5235 { 5236 symbol_context_scope = sc.function->GetBlock(true).FindBlockByID(MakeUserID(sc_parent_die->GetOffset())); 5237 if (symbol_context_scope == NULL) 5238 symbol_context_scope = sc.function; 5239 } 5240 break; 5241 5242 default: 5243 symbol_context_scope = sc.comp_unit; 5244 break; 5245 } 5246 5247 if (symbol_context_scope) 5248 { 5249 var_sp.reset (new Variable (MakeUserID(die->GetOffset()), 5250 name, 5251 mangled, 5252 var_type, 5253 scope, 5254 symbol_context_scope, 5255 &decl, 5256 location, 5257 is_external, 5258 is_artificial)); 5259 5260 var_sp->SetLocationIsConstantValueData (location_is_const_value_data); 5261 } 5262 else 5263 { 5264 // Not ready to parse this variable yet. It might be a global 5265 // or static variable that is in a function scope and the function 5266 // in the symbol context wasn't filled in yet 5267 return var_sp; 5268 } 5269 } 5270 } 5271 // Cache var_sp even if NULL (the variable was just a specification or 5272 // was missing vital information to be able to be displayed in the debugger 5273 // (missing location due to optimization, etc)) so we don't re-parse 5274 // this DIE over and over later... 5275 m_die_to_variable_sp[die] = var_sp; 5276 } 5277 return var_sp; 5278 } 5279 5280 5281 const DWARFDebugInfoEntry * 5282 SymbolFileDWARF::FindBlockContainingSpecification (dw_offset_t func_die_offset, 5283 dw_offset_t spec_block_die_offset, 5284 DWARFCompileUnit **result_die_cu_handle) 5285 { 5286 // Give the concrete function die specified by "func_die_offset", find the 5287 // concrete block whose DW_AT_specification or DW_AT_abstract_origin points 5288 // to "spec_block_die_offset" 5289 DWARFDebugInfo* info = DebugInfo(); 5290 5291 const DWARFDebugInfoEntry *die = info->GetDIEPtrWithCompileUnitHint(func_die_offset, result_die_cu_handle); 5292 if (die) 5293 { 5294 assert (*result_die_cu_handle); 5295 return FindBlockContainingSpecification (*result_die_cu_handle, die, spec_block_die_offset, result_die_cu_handle); 5296 } 5297 return NULL; 5298 } 5299 5300 5301 const DWARFDebugInfoEntry * 5302 SymbolFileDWARF::FindBlockContainingSpecification(DWARFCompileUnit* dwarf_cu, 5303 const DWARFDebugInfoEntry *die, 5304 dw_offset_t spec_block_die_offset, 5305 DWARFCompileUnit **result_die_cu_handle) 5306 { 5307 if (die) 5308 { 5309 switch (die->Tag()) 5310 { 5311 case DW_TAG_subprogram: 5312 case DW_TAG_inlined_subroutine: 5313 case DW_TAG_lexical_block: 5314 { 5315 if (die->GetAttributeValueAsReference (this, dwarf_cu, DW_AT_specification, DW_INVALID_OFFSET) == spec_block_die_offset) 5316 { 5317 *result_die_cu_handle = dwarf_cu; 5318 return die; 5319 } 5320 5321 if (die->GetAttributeValueAsReference (this, dwarf_cu, DW_AT_abstract_origin, DW_INVALID_OFFSET) == spec_block_die_offset) 5322 { 5323 *result_die_cu_handle = dwarf_cu; 5324 return die; 5325 } 5326 } 5327 break; 5328 } 5329 5330 // Give the concrete function die specified by "func_die_offset", find the 5331 // concrete block whose DW_AT_specification or DW_AT_abstract_origin points 5332 // to "spec_block_die_offset" 5333 for (const DWARFDebugInfoEntry *child_die = die->GetFirstChild(); child_die != NULL; child_die = child_die->GetSibling()) 5334 { 5335 const DWARFDebugInfoEntry *result_die = FindBlockContainingSpecification (dwarf_cu, 5336 child_die, 5337 spec_block_die_offset, 5338 result_die_cu_handle); 5339 if (result_die) 5340 return result_die; 5341 } 5342 } 5343 5344 *result_die_cu_handle = NULL; 5345 return NULL; 5346 } 5347 5348 size_t 5349 SymbolFileDWARF::ParseVariables 5350 ( 5351 const SymbolContext& sc, 5352 DWARFCompileUnit* dwarf_cu, 5353 const lldb::addr_t func_low_pc, 5354 const DWARFDebugInfoEntry *orig_die, 5355 bool parse_siblings, 5356 bool parse_children, 5357 VariableList* cc_variable_list 5358 ) 5359 { 5360 if (orig_die == NULL) 5361 return 0; 5362 5363 VariableListSP variable_list_sp; 5364 5365 size_t vars_added = 0; 5366 const DWARFDebugInfoEntry *die = orig_die; 5367 while (die != NULL) 5368 { 5369 dw_tag_t tag = die->Tag(); 5370 5371 // Check to see if we have already parsed this variable or constant? 5372 if (m_die_to_variable_sp[die]) 5373 { 5374 if (cc_variable_list) 5375 cc_variable_list->AddVariableIfUnique (m_die_to_variable_sp[die]); 5376 } 5377 else 5378 { 5379 // We haven't already parsed it, lets do that now. 5380 if ((tag == DW_TAG_variable) || 5381 (tag == DW_TAG_constant) || 5382 (tag == DW_TAG_formal_parameter && sc.function)) 5383 { 5384 if (variable_list_sp.get() == NULL) 5385 { 5386 const DWARFDebugInfoEntry *sc_parent_die = GetParentSymbolContextDIE(orig_die); 5387 dw_tag_t parent_tag = sc_parent_die ? sc_parent_die->Tag() : 0; 5388 switch (parent_tag) 5389 { 5390 case DW_TAG_compile_unit: 5391 if (sc.comp_unit != NULL) 5392 { 5393 variable_list_sp = sc.comp_unit->GetVariableList(false); 5394 if (variable_list_sp.get() == NULL) 5395 { 5396 variable_list_sp.reset(new VariableList()); 5397 sc.comp_unit->SetVariableList(variable_list_sp); 5398 } 5399 } 5400 else 5401 { 5402 ReportError ("parent 0x%8.8llx %s with no valid compile unit in symbol context for 0x%8.8llx %s.\n", 5403 MakeUserID(sc_parent_die->GetOffset()), 5404 DW_TAG_value_to_name (parent_tag), 5405 MakeUserID(orig_die->GetOffset()), 5406 DW_TAG_value_to_name (orig_die->Tag())); 5407 } 5408 break; 5409 5410 case DW_TAG_subprogram: 5411 case DW_TAG_inlined_subroutine: 5412 case DW_TAG_lexical_block: 5413 if (sc.function != NULL) 5414 { 5415 // Check to see if we already have parsed the variables for the given scope 5416 5417 Block *block = sc.function->GetBlock(true).FindBlockByID(MakeUserID(sc_parent_die->GetOffset())); 5418 if (block == NULL) 5419 { 5420 // This must be a specification or abstract origin with 5421 // a concrete block couterpart in the current function. We need 5422 // to find the concrete block so we can correctly add the 5423 // variable to it 5424 DWARFCompileUnit *concrete_block_die_cu = dwarf_cu; 5425 const DWARFDebugInfoEntry *concrete_block_die = FindBlockContainingSpecification (sc.function->GetID(), 5426 sc_parent_die->GetOffset(), 5427 &concrete_block_die_cu); 5428 if (concrete_block_die) 5429 block = sc.function->GetBlock(true).FindBlockByID(MakeUserID(concrete_block_die->GetOffset())); 5430 } 5431 5432 if (block != NULL) 5433 { 5434 const bool can_create = false; 5435 variable_list_sp = block->GetBlockVariableList (can_create); 5436 if (variable_list_sp.get() == NULL) 5437 { 5438 variable_list_sp.reset(new VariableList()); 5439 block->SetVariableList(variable_list_sp); 5440 } 5441 } 5442 } 5443 break; 5444 5445 default: 5446 ReportError ("didn't find appropriate parent DIE for variable list for 0x%8.8llx %s.\n", 5447 MakeUserID(orig_die->GetOffset()), 5448 DW_TAG_value_to_name (orig_die->Tag())); 5449 break; 5450 } 5451 } 5452 5453 if (variable_list_sp) 5454 { 5455 VariableSP var_sp (ParseVariableDIE(sc, dwarf_cu, die, func_low_pc)); 5456 if (var_sp) 5457 { 5458 variable_list_sp->AddVariableIfUnique (var_sp); 5459 if (cc_variable_list) 5460 cc_variable_list->AddVariableIfUnique (var_sp); 5461 ++vars_added; 5462 } 5463 } 5464 } 5465 } 5466 5467 bool skip_children = (sc.function == NULL && tag == DW_TAG_subprogram); 5468 5469 if (!skip_children && parse_children && die->HasChildren()) 5470 { 5471 vars_added += ParseVariables(sc, dwarf_cu, func_low_pc, die->GetFirstChild(), true, true, cc_variable_list); 5472 } 5473 5474 if (parse_siblings) 5475 die = die->GetSibling(); 5476 else 5477 die = NULL; 5478 } 5479 return vars_added; 5480 } 5481 5482 //------------------------------------------------------------------ 5483 // PluginInterface protocol 5484 //------------------------------------------------------------------ 5485 const char * 5486 SymbolFileDWARF::GetPluginName() 5487 { 5488 return "SymbolFileDWARF"; 5489 } 5490 5491 const char * 5492 SymbolFileDWARF::GetShortPluginName() 5493 { 5494 return GetPluginNameStatic(); 5495 } 5496 5497 uint32_t 5498 SymbolFileDWARF::GetPluginVersion() 5499 { 5500 return 1; 5501 } 5502 5503 void 5504 SymbolFileDWARF::CompleteTagDecl (void *baton, clang::TagDecl *decl) 5505 { 5506 SymbolFileDWARF *symbol_file_dwarf = (SymbolFileDWARF *)baton; 5507 clang_type_t clang_type = symbol_file_dwarf->GetClangASTContext().GetTypeForDecl (decl); 5508 if (clang_type) 5509 symbol_file_dwarf->ResolveClangOpaqueTypeDefinition (clang_type); 5510 } 5511 5512 void 5513 SymbolFileDWARF::CompleteObjCInterfaceDecl (void *baton, clang::ObjCInterfaceDecl *decl) 5514 { 5515 SymbolFileDWARF *symbol_file_dwarf = (SymbolFileDWARF *)baton; 5516 clang_type_t clang_type = symbol_file_dwarf->GetClangASTContext().GetTypeForDecl (decl); 5517 if (clang_type) 5518 symbol_file_dwarf->ResolveClangOpaqueTypeDefinition (clang_type); 5519 } 5520 5521 void 5522 SymbolFileDWARF::DumpIndexes () 5523 { 5524 StreamFile s(stdout, false); 5525 5526 s.Printf ("DWARF index for (%s) '%s/%s':", 5527 GetObjectFile()->GetModule()->GetArchitecture().GetArchitectureName(), 5528 GetObjectFile()->GetFileSpec().GetDirectory().AsCString(), 5529 GetObjectFile()->GetFileSpec().GetFilename().AsCString()); 5530 s.Printf("\nFunction basenames:\n"); m_function_basename_index.Dump (&s); 5531 s.Printf("\nFunction fullnames:\n"); m_function_fullname_index.Dump (&s); 5532 s.Printf("\nFunction methods:\n"); m_function_method_index.Dump (&s); 5533 s.Printf("\nFunction selectors:\n"); m_function_selector_index.Dump (&s); 5534 s.Printf("\nObjective C class selectors:\n"); m_objc_class_selectors_index.Dump (&s); 5535 s.Printf("\nGlobals and statics:\n"); m_global_index.Dump (&s); 5536 s.Printf("\nTypes:\n"); m_type_index.Dump (&s); 5537 s.Printf("\nNamepaces:\n"); m_namespace_index.Dump (&s); 5538 } 5539 5540 void 5541 SymbolFileDWARF::SearchDeclContext (const clang::DeclContext *decl_context, 5542 const char *name, 5543 llvm::SmallVectorImpl <clang::NamedDecl *> *results) 5544 { 5545 DeclContextToDIEMap::iterator iter = m_decl_ctx_to_die.find(decl_context); 5546 5547 if (iter == m_decl_ctx_to_die.end()) 5548 return; 5549 5550 for (DIEPointerSet::iterator pos = iter->second.begin(), end = iter->second.end(); pos != end; ++pos) 5551 { 5552 const DWARFDebugInfoEntry *context_die = *pos; 5553 5554 if (!results) 5555 return; 5556 5557 DWARFDebugInfo* info = DebugInfo(); 5558 5559 DIEArray die_offsets; 5560 5561 DWARFCompileUnit* dwarf_cu = NULL; 5562 const DWARFDebugInfoEntry* die = NULL; 5563 size_t num_matches = m_type_index.Find (ConstString(name), die_offsets); 5564 5565 if (num_matches) 5566 { 5567 for (size_t i = 0; i < num_matches; ++i) 5568 { 5569 const dw_offset_t die_offset = die_offsets[i]; 5570 die = info->GetDIEPtrWithCompileUnitHint (die_offset, &dwarf_cu); 5571 5572 if (die->GetParent() != context_die) 5573 continue; 5574 5575 Type *matching_type = ResolveType (dwarf_cu, die); 5576 5577 lldb::clang_type_t type = matching_type->GetClangFullType(); 5578 clang::QualType qual_type = clang::QualType::getFromOpaquePtr(type); 5579 5580 if (const clang::TagType *tag_type = llvm::dyn_cast<clang::TagType>(qual_type.getTypePtr())) 5581 { 5582 clang::TagDecl *tag_decl = tag_type->getDecl(); 5583 results->push_back(tag_decl); 5584 } 5585 else if (const clang::TypedefType *typedef_type = llvm::dyn_cast<clang::TypedefType>(qual_type.getTypePtr())) 5586 { 5587 clang::TypedefNameDecl *typedef_decl = typedef_type->getDecl(); 5588 results->push_back(typedef_decl); 5589 } 5590 } 5591 } 5592 } 5593 } 5594 5595 void 5596 SymbolFileDWARF::FindExternalVisibleDeclsByName (void *baton, 5597 const clang::DeclContext *decl_context, 5598 clang::DeclarationName decl_name, 5599 llvm::SmallVectorImpl <clang::NamedDecl *> *results) 5600 { 5601 5602 switch (decl_context->getDeclKind()) 5603 { 5604 case clang::Decl::Namespace: 5605 case clang::Decl::TranslationUnit: 5606 { 5607 SymbolFileDWARF *symbol_file_dwarf = (SymbolFileDWARF *)baton; 5608 symbol_file_dwarf->SearchDeclContext (decl_context, decl_name.getAsString().c_str(), results); 5609 } 5610 break; 5611 default: 5612 break; 5613 } 5614 } 5615