[Lldb-commits] [lldb] r181841 - <rdar://problem/13748253>

Greg Clayton gclayton at apple.com
Tue May 14 15:19:37 PDT 2013


Author: gclayton
Date: Tue May 14 17:19:37 2013
New Revision: 181841

URL: http://llvm.org/viewvc/llvm-project?rev=181841&view=rev
Log:
<rdar://problem/13748253>

Combine N_GSYM stab entries with their non-stab counterpart (data symbols) to make the symbol table smaller with less duplicate named symbols.


Modified:
    lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp

Modified: lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp?rev=181841&r1=181840&r2=181841&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp (original)
+++ lldb/trunk/source/Plugins/ObjectFile/Mach-O/ObjectFileMachO.cpp Tue May 14 17:19:37 2013
@@ -1712,8 +1712,10 @@ ObjectFileMachO::ParseSymtab (bool minim
         std::vector<uint32_t> N_COMM_indexes;
         typedef std::map <uint64_t, uint32_t> ValueToSymbolIndexMap;
         typedef std::map <uint32_t, uint32_t> NListIndexToSymbolIndexMap;
+        typedef std::map <const char *, uint32_t> ConstNameToSymbolIndexMap;
         ValueToSymbolIndexMap N_FUN_addr_to_sym_idx;
         ValueToSymbolIndexMap N_STSYM_addr_to_sym_idx;
+        ConstNameToSymbolIndexMap N_GSYM_name_to_sym_idx;
         // Any symbols that get merged into another will get an entry
         // in this map so we know
         NListIndexToSymbolIndexMap m_nlist_idx_to_sym_idx;
@@ -1970,6 +1972,7 @@ ObjectFileMachO::ParseSymtab (bool minim
                                             bool add_nlist = true;
                                             bool is_debug = ((nlist.n_type & NlistMaskStab) != 0);
                                             bool demangled_is_synthesized = false;
+                                            bool is_gsym = false;
 
                                             assert (sym_idx < num_syms);
 
@@ -1997,6 +2000,7 @@ ObjectFileMachO::ParseSymtab (bool minim
                                                             add_nlist = false;
                                                         else
                                                         {
+                                                            is_gsym = true;
                                                             sym[sym_idx].SetExternal(true);
                                                             if (nlist.n_value != 0)
                                                                 symbol_section = section_info.GetSection (nlist.n_sect, nlist.n_value);
@@ -2510,53 +2514,10 @@ ObjectFileMachO::ParseSymtab (bool minim
 
                                                     if (symbol_name)
                                                     {
-                                                        sym[sym_idx].GetMangled().SetValue(ConstString(symbol_name), symbol_name_is_mangled);
-                                                    }
-                                                }
-
-                                                if (is_debug == false)
-                                                {
-                                                    if (type == eSymbolTypeCode)
-                                                    {
-                                                        // See if we can find a N_FUN entry for any code symbols.
-                                                        // If we do find a match, and the name matches, then we
-                                                        // can merge the two into just the function symbol to avoid
-                                                        // duplicate entries in the symbol table
-                                                        ValueToSymbolIndexMap::const_iterator pos = N_FUN_addr_to_sym_idx.find (nlist.n_value);
-                                                        if (pos != N_FUN_addr_to_sym_idx.end())
-                                                        {
-                                                            if ((symbol_name_is_mangled == true && sym[sym_idx].GetMangled().GetMangledName() == sym[pos->second].GetMangled().GetMangledName()) ||
-                                                                (symbol_name_is_mangled == false && sym[sym_idx].GetMangled().GetDemangledName() == sym[pos->second].GetMangled().GetDemangledName()))
-                                                            {
-                                                                m_nlist_idx_to_sym_idx[nlist_idx] = pos->second;
-                                                                // We just need the flags from the linker symbol, so put these flags
-                                                                // into the N_FUN flags to avoid duplicate symbols in the symbol table
-                                                                sym[pos->second].SetFlags (nlist.n_type << 16 | nlist.n_desc);
-                                                                sym[sym_idx].Clear();
-                                                                continue;
-                                                            }
-                                                        }
-                                                    }
-                                                    else if (type == eSymbolTypeData)
-                                                    {
-                                                        // See if we can find a N_STSYM entry for any data symbols.
-                                                        // If we do find a match, and the name matches, then we
-                                                        // can merge the two into just the Static symbol to avoid
-                                                        // duplicate entries in the symbol table
-                                                        ValueToSymbolIndexMap::const_iterator pos = N_STSYM_addr_to_sym_idx.find (nlist.n_value);
-                                                        if (pos != N_STSYM_addr_to_sym_idx.end())
-                                                        {
-                                                            if ((symbol_name_is_mangled == true && sym[sym_idx].GetMangled().GetMangledName() == sym[pos->second].GetMangled().GetMangledName()) ||
-                                                                (symbol_name_is_mangled == false && sym[sym_idx].GetMangled().GetDemangledName() == sym[pos->second].GetMangled().GetDemangledName()))
-                                                            {
-                                                                m_nlist_idx_to_sym_idx[nlist_idx] = pos->second;
-                                                                // We just need the flags from the linker symbol, so put these flags
-                                                                // into the N_STSYM flags to avoid duplicate symbols in the symbol table
-                                                                sym[pos->second].SetFlags (nlist.n_type << 16 | nlist.n_desc);
-                                                                sym[sym_idx].Clear();
-                                                                continue;
-                                                            }
-                                                        }
+                                                        ConstString const_symbol_name(symbol_name);
+                                                        if (is_gsym)
+                                                            N_GSYM_name_to_sym_idx[const_symbol_name.GetCString()] = sym_idx;
+                                                        sym[sym_idx].GetMangled().SetValue(const_symbol_name, symbol_name_is_mangled);
                                                     }
                                                 }
                                                 if (symbol_section)
@@ -2612,6 +2573,71 @@ ObjectFileMachO::ParseSymtab (bool minim
                                                     symbol_value -= section_file_addr;
                                                 }
 
+                                                if (is_debug == false)
+                                                {
+                                                    if (type == eSymbolTypeCode)
+                                                    {
+                                                        // See if we can find a N_FUN entry for any code symbols.
+                                                        // If we do find a match, and the name matches, then we
+                                                        // can merge the two into just the function symbol to avoid
+                                                        // duplicate entries in the symbol table
+                                                        ValueToSymbolIndexMap::const_iterator pos = N_FUN_addr_to_sym_idx.find (nlist.n_value);
+                                                        if (pos != N_FUN_addr_to_sym_idx.end())
+                                                        {
+                                                            if ((symbol_name_is_mangled == true && sym[sym_idx].GetMangled().GetMangledName() == sym[pos->second].GetMangled().GetMangledName()) ||
+                                                                (symbol_name_is_mangled == false && sym[sym_idx].GetMangled().GetDemangledName() == sym[pos->second].GetMangled().GetDemangledName()))
+                                                            {
+                                                                m_nlist_idx_to_sym_idx[nlist_idx] = pos->second;
+                                                                // We just need the flags from the linker symbol, so put these flags
+                                                                // into the N_FUN flags to avoid duplicate symbols in the symbol table
+                                                                sym[pos->second].SetFlags (nlist.n_type << 16 | nlist.n_desc);
+                                                                sym[sym_idx].Clear();
+                                                                continue;
+                                                            }
+                                                        }
+                                                    }
+                                                    else if (type == eSymbolTypeData)
+                                                    {
+                                                        // See if we can find a N_STSYM entry for any data symbols.
+                                                        // If we do find a match, and the name matches, then we
+                                                        // can merge the two into just the Static symbol to avoid
+                                                        // duplicate entries in the symbol table
+                                                        ValueToSymbolIndexMap::const_iterator pos = N_STSYM_addr_to_sym_idx.find (nlist.n_value);
+                                                        if (pos != N_STSYM_addr_to_sym_idx.end())
+                                                        {
+                                                            if ((symbol_name_is_mangled == true && sym[sym_idx].GetMangled().GetMangledName() == sym[pos->second].GetMangled().GetMangledName()) ||
+                                                                (symbol_name_is_mangled == false && sym[sym_idx].GetMangled().GetDemangledName() == sym[pos->second].GetMangled().GetDemangledName()))
+                                                            {
+                                                                m_nlist_idx_to_sym_idx[nlist_idx] = pos->second;
+                                                                // We just need the flags from the linker symbol, so put these flags
+                                                                // into the N_STSYM flags to avoid duplicate symbols in the symbol table
+                                                                sym[pos->second].SetFlags (nlist.n_type << 16 | nlist.n_desc);
+                                                                sym[sym_idx].Clear();
+                                                                continue;
+                                                            }
+                                                        }
+                                                        else
+                                                        {
+                                                            // Combine N_GSYM stab entries with the non stab symbol
+                                                            ConstNameToSymbolIndexMap::const_iterator pos = N_GSYM_name_to_sym_idx.find(sym[sym_idx].GetMangled().GetMangledName().GetCString());
+                                                            if (pos != N_GSYM_name_to_sym_idx.end())
+                                                            {
+                                                                const uint32_t GSYM_sym_idx = pos->second;
+                                                                m_nlist_idx_to_sym_idx[nlist_idx] = GSYM_sym_idx;
+                                                                // Copy the address, because often the N_GSYM address has an invalid address of zero
+                                                                // when the global is a common symbol
+                                                                sym[GSYM_sym_idx].GetAddress().SetSection (symbol_section);
+                                                                sym[GSYM_sym_idx].GetAddress().SetOffset (symbol_value);
+                                                                // We just need the flags from the linker symbol, so put these flags
+                                                                // into the N_STSYM flags to avoid duplicate symbols in the symbol table
+                                                                sym[GSYM_sym_idx].SetFlags (nlist.n_type << 16 | nlist.n_desc);
+                                                                sym[sym_idx].Clear();
+                                                                continue;
+                                                            }
+                                                        }
+                                                    }
+                                                }
+
                                                 sym[sym_idx].SetID (nlist_idx);
                                                 sym[sym_idx].SetType (type);
                                                 sym[sym_idx].GetAddress().SetSection (symbol_section);
@@ -2711,6 +2737,7 @@ ObjectFileMachO::ParseSymtab (bool minim
             SectionSP symbol_section;
             lldb::addr_t symbol_byte_size = 0;
             bool add_nlist = true;
+            bool is_gsym = false;
             bool is_debug = ((nlist.n_type & NlistMaskStab) != 0);
             bool demangled_is_synthesized = false;
 
@@ -2740,6 +2767,7 @@ ObjectFileMachO::ParseSymtab (bool minim
                         add_nlist = false;
                     else
                     {
+                        is_gsym = true;
                         sym[sym_idx].SetExternal(true);
                         if (nlist.n_value != 0)
                             symbol_section = section_info.GetSection (nlist.n_sect, nlist.n_value);
@@ -3258,8 +3286,58 @@ ObjectFileMachO::ParseSymtab (bool minim
 
                     if (symbol_name)
                     {
-                        sym[sym_idx].GetMangled().SetValue(ConstString(symbol_name), symbol_name_is_mangled);
+                        ConstString const_symbol_name(symbol_name);
+                        if (is_gsym)
+                            N_GSYM_name_to_sym_idx[const_symbol_name.GetCString()] = sym_idx;
+                        sym[sym_idx].GetMangled().SetValue(const_symbol_name, symbol_name_is_mangled);
+                    }
+                }
+                if (symbol_section)
+                {
+                    const addr_t section_file_addr = symbol_section->GetFileAddress();
+                    if (symbol_byte_size == 0 && function_starts_count > 0)
+                    {
+                        addr_t symbol_lookup_file_addr = nlist.n_value;
+                        // Do an exact address match for non-ARM addresses, else get the closest since
+                        // the symbol might be a thumb symbol which has an address with bit zero set
+                        FunctionStarts::Entry *func_start_entry = function_starts.FindEntry (symbol_lookup_file_addr, !is_arm);
+                        if (is_arm && func_start_entry)
+                        {
+                            // Verify that the function start address is the symbol address (ARM)
+                            // or the symbol address + 1 (thumb)
+                            if (func_start_entry->addr != symbol_lookup_file_addr &&
+                                func_start_entry->addr != (symbol_lookup_file_addr + 1))
+                            {
+                                // Not the right entry, NULL it out...
+                                func_start_entry = NULL;
+                            }
+                        }
+                        if (func_start_entry)
+                        {
+                            func_start_entry->data = true;
+
+                            addr_t symbol_file_addr = func_start_entry->addr;
+                            if (is_arm)
+                                symbol_file_addr &= 0xfffffffffffffffeull;
+
+                            const FunctionStarts::Entry *next_func_start_entry = function_starts.FindNextEntry (func_start_entry);
+                            const addr_t section_end_file_addr = section_file_addr + symbol_section->GetByteSize();
+                            if (next_func_start_entry)
+                            {
+                                addr_t next_symbol_file_addr = next_func_start_entry->addr;
+                                // Be sure the clear the Thumb address bit when we calculate the size
+                                // from the current and next address
+                                if (is_arm)
+                                    next_symbol_file_addr &= 0xfffffffffffffffeull;
+                                symbol_byte_size = std::min<lldb::addr_t>(next_symbol_file_addr - symbol_file_addr, section_end_file_addr - symbol_file_addr);
+                            }
+                            else
+                            {
+                                symbol_byte_size = section_end_file_addr - symbol_file_addr;
+                            }
+                        }
                     }
+                    symbol_value -= section_file_addr;
                 }
 
                 if (is_debug == false)
@@ -3305,54 +3383,26 @@ ObjectFileMachO::ParseSymtab (bool minim
                                 continue;
                             }
                         }
-                    }
-                }
-                if (symbol_section)
-                {
-                    const addr_t section_file_addr = symbol_section->GetFileAddress();
-                    if (symbol_byte_size == 0 && function_starts_count > 0)
-                    {
-                        addr_t symbol_lookup_file_addr = nlist.n_value;
-                        // Do an exact address match for non-ARM addresses, else get the closest since
-                        // the symbol might be a thumb symbol which has an address with bit zero set
-                        FunctionStarts::Entry *func_start_entry = function_starts.FindEntry (symbol_lookup_file_addr, !is_arm);
-                        if (is_arm && func_start_entry)
+                        else
                         {
-                            // Verify that the function start address is the symbol address (ARM)
-                            // or the symbol address + 1 (thumb)
-                            if (func_start_entry->addr != symbol_lookup_file_addr &&
-                                func_start_entry->addr != (symbol_lookup_file_addr + 1))
+                            // Combine N_GSYM stab entries with the non stab symbol
+                            ConstNameToSymbolIndexMap::const_iterator pos = N_GSYM_name_to_sym_idx.find(sym[sym_idx].GetMangled().GetMangledName().GetCString());
+                            if (pos != N_GSYM_name_to_sym_idx.end())
                             {
-                                // Not the right entry, NULL it out...
-                                func_start_entry = NULL;
-                            }
-                        }
-                        if (func_start_entry)
-                        {
-                            func_start_entry->data = true;
-
-                            addr_t symbol_file_addr = func_start_entry->addr;
-                            if (is_arm)
-                                symbol_file_addr &= 0xfffffffffffffffeull;
-
-                            const FunctionStarts::Entry *next_func_start_entry = function_starts.FindNextEntry (func_start_entry);
-                            const addr_t section_end_file_addr = section_file_addr + symbol_section->GetByteSize();
-                            if (next_func_start_entry)
-                            {
-                                addr_t next_symbol_file_addr = next_func_start_entry->addr;
-                                // Be sure the clear the Thumb address bit when we calculate the size
-                                // from the current and next address
-                                if (is_arm)
-                                    next_symbol_file_addr &= 0xfffffffffffffffeull;
-                                symbol_byte_size = std::min<lldb::addr_t>(next_symbol_file_addr - symbol_file_addr, section_end_file_addr - symbol_file_addr);
-                            }
-                            else
-                            {
-                                symbol_byte_size = section_end_file_addr - symbol_file_addr;
+                                const uint32_t GSYM_sym_idx = pos->second;
+                                m_nlist_idx_to_sym_idx[nlist_idx] = GSYM_sym_idx;
+                                // Copy the address, because often the N_GSYM address has an invalid address of zero
+                                // when the global is a common symbol
+                                sym[GSYM_sym_idx].GetAddress().SetSection (symbol_section);
+                                sym[GSYM_sym_idx].GetAddress().SetOffset (symbol_value);
+                                // We just need the flags from the linker symbol, so put these flags
+                                // into the N_STSYM flags to avoid duplicate symbols in the symbol table
+                                sym[GSYM_sym_idx].SetFlags (nlist.n_type << 16 | nlist.n_desc);
+                                sym[sym_idx].Clear();
+                                continue;
                             }
                         }
                     }
-                    symbol_value -= section_file_addr;
                 }
 
                 sym[sym_idx].SetID (nlist_idx);





More information about the lldb-commits mailing list