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