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