X-Git-Url: http://git.efficios.com/?a=blobdiff_plain;f=gdb%2Felfread.c;h=44b793d8f14b4d42901acb764c8b8e0f16d526e8;hb=4bdb25fe6902963ca9cf91d6b2688cf888527bf8;hp=9d35febc2f97ec79594442c4f8ab8d2ac9dfb11c;hpb=99d89cdea6c296bdd94ce532350d139d3900ff78;p=deliverable%2Fbinutils-gdb.git diff --git a/gdb/elfread.c b/gdb/elfread.c index 9d35febc2f..44b793d8f1 100644 --- a/gdb/elfread.c +++ b/gdb/elfread.c @@ -29,7 +29,6 @@ #include "symfile.h" #include "objfiles.h" #include "stabsread.h" -#include "gdb-stabs.h" #include "complaints.h" #include "demangle.h" #include "psympriv.h" @@ -47,6 +46,9 @@ #include "build-id.h" #include "location.h" #include "auxv.h" +#include "mdebugread.h" +#include "ctfread.h" +#include "gdbsupport/gdb_string_view.h" /* Forward declarations. */ extern const struct sym_fns elf_sym_fns_gdb_index; @@ -61,11 +63,16 @@ struct elfinfo { asection *stabsect; /* Section pointer for .stab section */ asection *mdebugsect; /* Section pointer for .mdebug section */ + asection *ctfsect; /* Section pointer for .ctf section */ }; +/* Type for per-BFD data. */ + +typedef std::vector> elfread_data; + /* Per-BFD data for probe info. */ -static const struct bfd_data *probe_key = NULL; +static const struct bfd_key probe_key; /* Minimal symbols located at the GOT entries for .plt - that is the real pointer where the given entry will jump to. It gets updated by the real @@ -121,7 +128,7 @@ elf_symfile_segments (bfd *abfd) { int j; - if ((bfd_get_section_flags (abfd, sect) & SEC_ALLOC) == 0) + if ((bfd_section_flags (sect) & SEC_ALLOC) == 0) continue; Elf_Internal_Shdr *this_hdr = &elf_section_data (sect)->this_hdr; @@ -142,10 +149,10 @@ elf_symfile_segments (bfd *abfd) 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) + if (bfd_section_size (sect) > 0 && j == num_segments + && (bfd_section_flags (sect) & SEC_LOAD) != 0) warning (_("Loadable section \"%s\" outside of ELF segments"), - bfd_section_name (abfd, sect)); + bfd_section_name (sect)); } return data; @@ -184,11 +191,15 @@ elf_locate_sections (bfd *ignore_abfd, asection *sectp, void *eip) { ei->mdebugsect = sectp; } + else if (strcmp (sectp->name, ".ctf") == 0) + { + ei->ctfsect = sectp; + } } static struct minimal_symbol * record_minimal_symbol (minimal_symbol_reader &reader, - const char *name, int name_len, bool copy_name, + gdb::string_view name, bool copy_name, CORE_ADDR address, enum minimal_symbol_type ms_type, asection *bfd_section, struct objfile *objfile) @@ -199,10 +210,16 @@ record_minimal_symbol (minimal_symbol_reader &reader, || ms_type == mst_text_gnu_ifunc) address = gdbarch_addr_bits_remove (gdbarch, address); - return reader.record_full (name, name_len, copy_name, address, - ms_type, - gdb_bfd_section_index (objfile->obfd, - bfd_section)); + struct minimal_symbol *result + = reader.record_full (name, copy_name, address, + ms_type, + gdb_bfd_section_index (objfile->obfd, + bfd_section)); + if ((objfile->flags & OBJF_MAINLINE) == 0 + && (ms_type == mst_data || ms_type == mst_bss)) + result->maybe_copied = 1; + + return result; } /* Read the symbol table of an ELF file. @@ -285,12 +302,12 @@ elf_symtab_read (minimal_symbol_reader &reader, covers the stub's address. */ for (sect = abfd->sections; sect != NULL; sect = sect->next) { - if ((bfd_get_section_flags (abfd, sect) & SEC_ALLOC) == 0) + if ((bfd_section_flags (sect) & SEC_ALLOC) == 0) continue; - if (symaddr >= bfd_get_section_vma (abfd, sect) - && symaddr < bfd_get_section_vma (abfd, sect) - + bfd_get_section_size (sect)) + if (symaddr >= bfd_section_vma (sect) + && symaddr < bfd_section_vma (sect) + + bfd_section_size (sect)) break; } if (!sect) @@ -314,7 +331,7 @@ elf_symtab_read (minimal_symbol_reader &reader, continue; msym = record_minimal_symbol - (reader, sym->name, strlen (sym->name), copy_names, + (reader, sym->name, copy_names, symaddr, mst_solib_trampoline, sect, objfile); if (msym != NULL) { @@ -333,8 +350,8 @@ elf_symtab_read (minimal_symbol_reader &reader, if (sym->flags & BSF_FILE) { filesymname - = (const char *) bcache (sym->name, strlen (sym->name) + 1, - objfile->per_bfd->filename_cache); + = ((const char *) objfile->per_bfd->filename_cache.insert + (sym->name, strlen (sym->name) + 1)); } else if (sym->flags & BSF_SECTION_SYM) continue; @@ -458,7 +475,7 @@ elf_symtab_read (minimal_symbol_reader &reader, continue; /* Skip this symbol. */ } msym = record_minimal_symbol - (reader, sym->name, strlen (sym->name), copy_names, symaddr, + (reader, sym->name, copy_names, symaddr, ms_type, sym->section, objfile); if (msym) @@ -487,8 +504,10 @@ elf_symtab_read (minimal_symbol_reader &reader, { int len = atsign - sym->name; - record_minimal_symbol (reader, sym->name, len, true, symaddr, - ms_type, sym->section, objfile); + record_minimal_symbol (reader, + gdb::string_view (sym->name, len), + true, symaddr, ms_type, sym->section, + objfile); } } @@ -504,10 +523,9 @@ elf_symtab_read (minimal_symbol_reader &reader, { struct minimal_symbol *mtramp; - mtramp = record_minimal_symbol (reader, sym->name, len - 4, - true, symaddr, - mst_solib_trampoline, - sym->section, objfile); + mtramp = record_minimal_symbol + (reader, gdb::string_view (sym->name, len - 4), true, + symaddr, mst_solib_trampoline, sym->section, objfile); if (mtramp) { SET_MSYMBOL_SIZE (mtramp, MSYMBOL_SIZE (msym)); @@ -587,9 +605,9 @@ elf_rel_plt_read (minimal_symbol_reader &reader, if (section == NULL) return false; - return (bfd_get_section_vma (obfd, section) <= address - && (address < bfd_get_section_vma (obfd, section) - + bfd_get_section_size (section))); + return (bfd_section_vma (section) <= address + && (address < bfd_section_vma (section) + + bfd_section_size (section))); }; reloc_count = relplt->size / elf_section_data (relplt)->this_hdr.sh_entsize; @@ -623,8 +641,7 @@ elf_rel_plt_read (minimal_symbol_reader &reader, string_buffer.assign (name); string_buffer.append (got_suffix, got_suffix + got_suffix_len); - msym = record_minimal_symbol (reader, string_buffer.c_str (), - string_buffer.size (), + msym = record_minimal_symbol (reader, string_buffer, true, address, mst_slot_got_plt, msym_section, objfile); if (msym) @@ -634,7 +651,8 @@ elf_rel_plt_read (minimal_symbol_reader &reader, /* The data pointer is htab_t for gnu_ifunc_record_cache_unchecked. */ -static const struct objfile_data *elf_objfile_gnu_ifunc_cache_data; +static const struct objfile_key + elf_objfile_gnu_ifunc_cache_data; /* Map function names to CORE_ADDR in elf_objfile_gnu_ifunc_cache_data. */ @@ -696,7 +714,7 @@ elf_gnu_ifunc_record_cache (const char *name, CORE_ADDR addr) /* If .plt jumps back to .plt the symbol is still deferred for later resolution and it has no use for GDB. */ - const char *target_name = MSYMBOL_LINKAGE_NAME (msym.minsym); + const char *target_name = msym.minsym->linkage_name (); size_t len = strlen (target_name); /* Note we check the symbol's name instead of checking whether the @@ -705,15 +723,13 @@ elf_gnu_ifunc_record_cache (const char *name, CORE_ADDR addr) if (len > 4 && strcmp (target_name + len - 4, "@plt") == 0) return 0; - htab = (htab_t) objfile_data (objfile, elf_objfile_gnu_ifunc_cache_data); + htab = elf_objfile_gnu_ifunc_cache_data.get (objfile); if (htab == NULL) { - htab = htab_create_alloc_ex (1, elf_gnu_ifunc_cache_hash, - elf_gnu_ifunc_cache_eq, - NULL, &objfile->objfile_obstack, - hashtab_obstack_allocate, - dummy_obstack_deallocate); - set_objfile_data (objfile, elf_objfile_gnu_ifunc_cache_data, htab); + htab = htab_create_alloc (1, elf_gnu_ifunc_cache_hash, + elf_gnu_ifunc_cache_eq, + NULL, xcalloc, xfree); + elf_objfile_gnu_ifunc_cache_data.set (objfile, htab); } entry_local.addr = addr; @@ -758,13 +774,13 @@ elf_gnu_ifunc_record_cache (const char *name, CORE_ADDR addr) static int elf_gnu_ifunc_resolve_by_cache (const char *name, CORE_ADDR *addr_p) { - for (objfile *objfile : all_objfiles (current_program_space)) + for (objfile *objfile : current_program_space->objfiles ()) { htab_t htab; struct elf_gnu_ifunc_cache *entry_p; void **slot; - htab = (htab_t) objfile_data (objfile, elf_objfile_gnu_ifunc_cache_data); + htab = elf_objfile_gnu_ifunc_cache_data.get (objfile); if (htab == NULL) continue; @@ -803,7 +819,7 @@ elf_gnu_ifunc_resolve_by_got (const char *name, CORE_ADDR *addr_p) name_got_plt = (char *) alloca (strlen (name) + got_suffix_len + 1); sprintf (name_got_plt, "%s" SYMBOL_GOT_PLT_SUFFIX, name); - for (objfile *objfile : all_objfiles (current_program_space)) + for (objfile *objfile : current_program_space->objfiles ()) { bfd *obfd = objfile->obfd; struct gdbarch *gdbarch = get_objfile_arch (objfile); @@ -847,21 +863,21 @@ elf_gnu_ifunc_resolve_by_got (const char *name, CORE_ADDR *addr_p) /* Try to find the target resolved function entry address of a STT_GNU_IFUNC function NAME. If the address is found it is stored to *ADDR_P (if ADDR_P - is not NULL) and the function returns 1. It returns 0 otherwise. + is not NULL) and the function returns true. It returns false otherwise. Both the elf_objfile_gnu_ifunc_cache_data hash table and SYMBOL_GOT_PLT_SUFFIX locations are searched by this function. */ -static int +static bool elf_gnu_ifunc_resolve_name (const char *name, CORE_ADDR *addr_p) { if (elf_gnu_ifunc_resolve_by_cache (name, addr_p)) - return 1; + return true; if (elf_gnu_ifunc_resolve_by_got (name, addr_p)) - return 1; + return true; - return 0; + return false; } /* Call STT_GNU_IFUNC - a function returning addresss of a real function to @@ -1035,7 +1051,6 @@ elf_read_minimal_symbols (struct objfile *objfile, int symfile_flags, long symcount = 0, dynsymcount = 0, synthcount, storage_needed; asymbol **symbol_table = NULL, **dyn_symbol_table = NULL; asymbol *synthsyms; - struct dbx_symfile_info *dbx; if (symtab_create_debug) { @@ -1051,7 +1066,8 @@ elf_read_minimal_symbols (struct objfile *objfile, int symfile_flags, go away once all types of symbols are in the per-BFD object. */ if (objfile->per_bfd->minsyms_read && ei->stabsect == NULL - && ei->mdebugsect == NULL) + && ei->mdebugsect == NULL + && ei->ctfsect == NULL) { if (symtab_create_debug) fprintf_unfiltered (gdb_stdlog, @@ -1061,10 +1077,6 @@ elf_read_minimal_symbols (struct objfile *objfile, int symfile_flags, minimal_symbol_reader reader (objfile); - /* Allocate struct to keep track of the symfile. */ - dbx = XCNEW (struct dbx_symfile_info); - set_objfile_data (objfile, dbx_objfile_data_key, dbx); - /* Process the normal ELF symbol table first. */ storage_needed = bfd_get_symtab_upper_bound (objfile->obfd); @@ -1196,6 +1208,7 @@ elf_symfile_read (struct objfile *objfile, symfile_add_flags symfile_flags) { bfd *abfd = objfile->obfd; struct elfinfo ei; + bool has_dwarf2 = true; memset ((char *) &ei, 0, sizeof (ei)); if (!(objfile->flags & OBJF_READNEVER)) @@ -1238,10 +1251,10 @@ elf_symfile_read (struct objfile *objfile, symfile_add_flags symfile_flags) elfstab_build_psymtabs (objfile, ei.stabsect, str_sect->filepos, - bfd_section_size (abfd, str_sect)); + bfd_section_size (str_sect)); } - if (dwarf2_has_info (objfile, NULL)) + if (dwarf2_has_info (objfile, NULL, true)) { dw_index_kind index_kind; @@ -1298,6 +1311,14 @@ elf_symfile_read (struct objfile *objfile, symfile_add_flags symfile_flags) symbol_file_add_separate (debug_bfd.get (), debugfile.c_str (), symfile_flags, objfile); } + else + has_dwarf2 = false; + } + + /* Read the CTF section only if there is no DWARF info. */ + if (!has_dwarf2 && ei.ctfsect) + { + elfctf_build_psymtabs (objfile); } } @@ -1312,15 +1333,11 @@ read_psyms (struct objfile *objfile) /* Initialize anything that needs initializing when a completely new symbol file is specified (not just adding some symbols from another file, e.g. a - shared library). - - We reinitialize buildsym, since we may be reading stabs from an ELF - file. */ + shared library). */ static void elf_new_init (struct objfile *ignore) { - stabsread_new_init (); } /* Perform any local cleanups required when we are done with a particular @@ -1346,43 +1363,24 @@ elf_symfile_init (struct objfile *objfile) /* Implementation of `sym_get_probes', as documented in symfile.h. */ -static const std::vector & +static const elfread_data & elf_get_probes (struct objfile *objfile) { - std::vector *probes_per_bfd; - - /* Have we parsed this objfile's probes already? */ - probes_per_bfd = (std::vector *) bfd_data (objfile->obfd, probe_key); + elfread_data *probes_per_bfd = probe_key.get (objfile->obfd); if (probes_per_bfd == NULL) { - probes_per_bfd = new std::vector; + probes_per_bfd = probe_key.emplace (objfile->obfd); /* Here we try to gather information about all types of probes from the objfile. */ for (const static_probe_ops *ops : all_static_probe_ops) ops->get_probes (probes_per_bfd, objfile); - - set_bfd_data (objfile->obfd, probe_key, probes_per_bfd); } return *probes_per_bfd; } -/* Helper function used to free the space allocated for storing SystemTap - probe information. */ - -static void -probe_key_free (bfd *abfd, void *d) -{ - std::vector *probes = (std::vector *) d; - - for (probe *p : *probes) - delete p; - - delete probes; -} - /* Implementation `sym_probe_fns', as documented in symfile.h. */ @@ -1436,7 +1434,7 @@ const struct sym_fns elf_sym_fns_gdb_index = elf_symfile_read, /* read a symbol file into symtab */ NULL, /* sym_read_psymbols */ elf_symfile_finish, /* finished with file, cleanup */ - default_symfile_offsets, /* Translate ext. to int. relocatin */ + default_symfile_offsets, /* Translate ext. to int. relocation */ elf_symfile_segments, /* Get segment information from a file. */ NULL, default_symfile_relocate, /* Relocate a debug section. */ @@ -1453,7 +1451,7 @@ const struct sym_fns elf_sym_fns_debug_names = elf_symfile_read, /* read a symbol file into symtab */ NULL, /* sym_read_psymbols */ elf_symfile_finish, /* finished with file, cleanup */ - default_symfile_offsets, /* Translate ext. to int. relocatin */ + default_symfile_offsets, /* Translate ext. to int. relocation */ elf_symfile_segments, /* Get segment information from a file. */ NULL, default_symfile_relocate, /* Relocate a debug section. */ @@ -1474,9 +1472,7 @@ static const struct gnu_ifunc_fns elf_gnu_ifunc_fns = void _initialize_elfread (void) { - probe_key = register_bfd_data_with_cleanup (NULL, probe_key_free); add_symtab_fns (bfd_target_elf_flavour, &elf_sym_fns); - elf_objfile_gnu_ifunc_cache_data = register_objfile_data (); gnu_ifunc_fns_p = &elf_gnu_ifunc_fns; }