* symtab.h (SYMBOL_SET_LINKAGE_NAME): Update comment.
[deliverable/binutils-gdb.git] / gdb / elfread.c
index 76af9dcd7c3eb4bee032e3ee828426b1ce8c0ebf..29b7c0c92914f5945da691d7600bc45b86ece861 100644 (file)
@@ -1,7 +1,7 @@
 /* Read ELF (Executable and Linking Format) object files for GDB.
 
    Copyright (C) 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
-   2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008
+   2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
    Free Software Foundation, Inc.
 
    Written by Fred Fish at Cygnus Support.
@@ -108,13 +108,23 @@ elf_symfile_segments (bfd *abfd)
       for (j = 0; j < num_segments; j++)
        if (segments[j]->p_memsz > 0
            && vma >= segments[j]->p_vaddr
-           && vma < segments[j]->p_vaddr + segments[j]->p_memsz)
+           && (vma - segments[j]->p_vaddr) < segments[j]->p_memsz)
          {
            data->segment_info[i] = j + 1;
            break;
          }
 
-      if (bfd_get_section_size (sect) > 0 && j == num_segments)
+      /* We should have found a segment for every non-empty section.
+        If we haven't, we will not relocate this section by any
+        offsets we apply to the segments.  As an exception, do not
+        warn about SHT_NOBITS sections; in normal ELF execution
+        environments, SHT_NOBITS means zero-initialized and belongs
+        in a segment, but in no-OS environments some tools (e.g. ARM
+        RealView) use SHT_NOBITS for uninitialized data.  Since it is
+        uninitialized, it doesn't need a program header.  Such
+        binaries are not relocatable.  */
+      if (bfd_get_section_size (sect) > 0 && j == num_segments
+         && (bfd_get_section_flags (abfd, sect) & SEC_LOAD) != 0)
        warning (_("Loadable segment \"%s\" outside of ELF segments"),
                 bfd_section_name (abfd, sect));
     }
@@ -172,7 +182,7 @@ record_minimal_symbol (char *name, CORE_ADDR address,
     address = gdbarch_smash_text_address (gdbarch, address);
 
   return prim_record_minimal_symbol_and_info
-    (name, address, ms_type, NULL, bfd_section->index, bfd_section, objfile);
+    (name, address, ms_type, bfd_section->index, bfd_section, objfile);
 }
 
 /*
@@ -221,8 +231,9 @@ elf_symtab_read (struct objfile *objfile, int type,
   /* If filesym is nonzero, it points to a file symbol, but we haven't
      seen any section info for it yet.  */
   asymbol *filesym = 0;
-  /* Name of filesym, as saved on the objfile_obstack.  */
-  char *filesymname = obsavestring ("", 0, &objfile->objfile_obstack);
+  /* Name of filesym.  This is either a constant string or is saved on
+     the objfile's obstack.  */
+  char *filesymname = "";
   struct dbx_symfile_info *dbx = objfile->deprecated_sym_stab_info;
   int stripped = (bfd_get_symcount (objfile->obfd) == 0);
 
@@ -324,8 +335,10 @@ elf_symtab_read (struct objfile *objfile, int type,
             interested in will have a section. */
          /* Bfd symbols are section relative. */
          symaddr = sym->value + sym->section->vma;
-         /* Relocate all non-absolute symbols by the section offset.  */
-         if (sym->section != &bfd_abs_section)
+         /* Relocate all non-absolute and non-TLS symbols by the
+            section offset.  */
+         if (sym->section != &bfd_abs_section
+             && !(sym->section->flags & SEC_THREAD_LOCAL))
            {
              symaddr += offset;
            }
@@ -425,10 +438,11 @@ elf_symtab_read (struct objfile *objfile, int type,
                          int max_index;
                          size_t size;
 
-                         max_index 
-                           = max (SECT_OFF_BSS (objfile),
-                                  max (SECT_OFF_DATA (objfile),
-                                       SECT_OFF_RODATA (objfile)));
+                         max_index = SECT_OFF_BSS (objfile);
+                         if (objfile->sect_index_data > max_index)
+                           max_index = objfile->sect_index_data;
+                         if (objfile->sect_index_rodata > max_index)
+                           max_index = objfile->sect_index_rodata;
 
                          /* max_index is the largest index we'll
                             use into this array, so we must
@@ -521,6 +535,34 @@ elf_symtab_read (struct objfile *objfile, int type,
          if (msym != NULL)
            msym->filename = filesymname;
          gdbarch_elf_make_msymbol_special (gdbarch, sym, msym);
+
+         /* For @plt symbols, also record a trampoline to the
+            destination symbol.  The @plt symbol will be used in
+            disassembly, and the trampoline will be used when we are
+            trying to find the target.  */
+         if (msym && ms_type == mst_text && type == ST_SYNTHETIC)
+           {
+             int len = strlen (sym->name);
+
+             if (len > 4 && strcmp (sym->name + len - 4, "@plt") == 0)
+               {
+                 char *base_name = xmalloc (len - 4 + 1);
+                 struct minimal_symbol *mtramp;
+
+                 memcpy (base_name, sym->name, len - 4);
+                 base_name[len - 4] = '\0';
+                 mtramp = record_minimal_symbol (base_name, symaddr,
+                                                 mst_solib_trampoline,
+                                                 sym->section, objfile);
+                 xfree (base_name);
+                 if (mtramp)
+                   {
+                     MSYMBOL_SIZE (mtramp) = MSYMBOL_SIZE (msym);
+                     mtramp->filename = filesymname;
+                     gdbarch_elf_make_msymbol_special (gdbarch, sym, mtramp);
+                   }
+               }
+           }
        }
     }
 }
This page took 0.025803 seconds and 4 git commands to generate.