X-Git-Url: http://drtracing.org/?a=blobdiff_plain;f=gdb%2Fsymfile.c;h=e417878031db8b7bb8cc52463475ed83b0632408;hb=328d42d87e97c75d6e52800bfd4bc1bfdfb745d2;hp=dd8192a67fbba4f40d2b68a3f8e9b0ad86318d50;hpb=c7e976792002c6a2810f9bb6cc3ad210514eb650;p=deliverable%2Fbinutils-gdb.git diff --git a/gdb/symfile.c b/gdb/symfile.c index dd8192a67f..e417878031 100644 --- a/gdb/symfile.c +++ b/gdb/symfile.c @@ -1,6 +1,6 @@ /* Generic symbol file reading for the GNU debugger, GDB. - Copyright (C) 1990-2020 Free Software Foundation, Inc. + Copyright (C) 1990-2021 Free Software Foundation, Inc. Contributed by Cygnus Support, using pieces from other GDB modules. @@ -69,8 +69,6 @@ #include #include -#include "psymtab.h" - int (*deprecated_ui_load_progress_hook) (const char *section, unsigned long num); void (*deprecated_show_load_progress) (const char *section, @@ -85,8 +83,14 @@ using clear_symtab_users_cleanup = FORWARD_SCOPE_EXIT (clear_symtab_users); /* Global variables owned by this file. */ -int readnow_symbol_files; /* Read full symbols immediately. */ -int readnever_symbol_files; /* Never read full symbols. */ + +/* See symfile.h. */ + +int readnow_symbol_files; + +/* See symfile.h. */ + +int readnever_symbol_files; /* Functions this file defines. */ @@ -187,7 +191,6 @@ increment_reading_symtab (void) } /* Remember the lowest-addressed loadable section we've seen. - This function is called via bfd_map_over_sections. In case of equal vmas, the section with the largest size becomes the lowest-addressed loadable section. @@ -195,11 +198,9 @@ increment_reading_symtab (void) If the vmas and sizes are equal, the last section is considered the lowest-addressed loadable section. */ -void -find_lowest_section (bfd *abfd, asection *sect, void *obj) +static void +find_lowest_section (asection *sect, asection **lowest) { - asection **lowest = (asection **) obj; - if (0 == (bfd_section_flags (sect) & (SEC_ALLOC | SEC_LOAD))) return; if (!*lowest) @@ -215,21 +216,18 @@ find_lowest_section (bfd *abfd, asection *sect, void *obj) an existing section table. */ section_addr_info -build_section_addr_info_from_section_table (const struct target_section *start, - const struct target_section *end) +build_section_addr_info_from_section_table (const target_section_table &table) { - const struct target_section *stp; - section_addr_info sap; - for (stp = start; stp != end; stp++) + for (const target_section &stp : table) { - struct bfd_section *asect = stp->the_bfd_section; + struct bfd_section *asect = stp.the_bfd_section; bfd *abfd = asect->owner; if (bfd_section_flags (asect) & (SEC_ALLOC | SEC_LOAD) - && sap.size () < end - start) - sap.emplace_back (stp->addr, + && sap.size () < table.size ()) + sap.emplace_back (stp.addr, bfd_section_name (asect), gdb_bfd_section_index (abfd, asect)); } @@ -335,22 +333,13 @@ init_objfile_sect_indices (struct objfile *objfile) } } -/* The arguments to place_section. */ - -struct place_section_arg -{ - section_offsets *offsets; - CORE_ADDR lowest; -}; - /* Find a unique offset to use for loadable section SECT if the user did not provide an offset. */ static void -place_section (bfd *abfd, asection *sect, void *obj) +place_section (bfd *abfd, asection *sect, section_offsets &offsets, + CORE_ADDR &lowest) { - struct place_section_arg *arg = (struct place_section_arg *) obj; - section_offsets &offsets = *arg->offsets; CORE_ADDR start_addr; int done; ULONGEST align = ((ULONGEST) 1) << bfd_section_alignment (sect); @@ -364,7 +353,7 @@ place_section (bfd *abfd, asection *sect, void *obj) return; /* Otherwise, let's try to find a place for the section. */ - start_addr = (arg->lowest + align - 1) & -align; + start_addr = (lowest + align - 1) & -align; do { asection *cur_sec; @@ -405,7 +394,7 @@ place_section (bfd *abfd, asection *sect, void *obj) while (!done); offsets[gdb_bfd_section_index (abfd, sect)] = start_addr; - arg->lowest = start_addr + bfd_section_size (sect); + lowest = start_addr + bfd_section_size (sect); } /* Store section_addr_info as prepared (made relative and with SECTINDEX @@ -430,7 +419,7 @@ relative_addr_info_to_section_offsets (section_offsets §ion_offsets, /* Record all sections in offsets. */ /* The section_offsets in the objfile are here filled in using - the BFD index. */ + the BFD index. */ section_offsets[osp->sectindex] = osp->addr; } } @@ -500,7 +489,8 @@ addr_info_make_relative (section_addr_info *addrs, bfd *abfd) /* Find lowest loadable section to be used as starting point for contiguous sections. */ lower_sect = NULL; - bfd_map_over_sections (abfd, find_lowest_section, &lower_sect); + for (asection *iter : gdb_bfd_sections (abfd)) + find_lowest_section (iter, &lower_sect); if (lower_sect == NULL) { warning (_("no loadable sections found in added symbol-file %s"), @@ -645,7 +635,6 @@ default_symfile_offsets (struct objfile *objfile, small. */ if ((bfd_get_file_flags (objfile->obfd) & (EXEC_P | DYNAMIC)) == 0) { - struct place_section_arg arg; bfd *abfd = objfile->obfd; asection *cur_sec; @@ -661,9 +650,10 @@ default_symfile_offsets (struct objfile *objfile, /* Pick non-overlapping offsets for sections the user did not place explicitly. */ - arg.offsets = &objfile->section_offsets; - arg.lowest = 0; - bfd_map_over_sections (objfile->obfd, place_section, &arg); + CORE_ADDR lowest = 0; + for (asection *sect : gdb_bfd_sections (objfile->obfd)) + place_section (objfile->obfd, sect, objfile->section_offsets, + lowest); /* Correctly filling in the section offsets is not quite enough. Relocatable files have two properties that @@ -783,7 +773,7 @@ read_symbols (struct objfile *objfile, symfile_add_flags add_flags) /* find_separate_debug_file_in_section should be called only if there is single binary with no existing separate debug info file. */ - if (!objfile_has_partial_symbols (objfile) + if (!objfile->has_partial_symbols () && objfile->separate_debug_objfile == NULL && objfile->separate_debug_objfile_backlink == NULL) { @@ -801,7 +791,7 @@ read_symbols (struct objfile *objfile, symfile_add_flags add_flags) } } if ((add_flags & SYMFILE_NO_READ) == 0) - require_partial_symbols (objfile, false); + objfile->require_partial_symbols (false); } /* Initialize entry point information for this objfile. */ @@ -821,7 +811,7 @@ init_entry_point_info (struct objfile *objfile) if (bfd_get_file_flags (objfile->obfd) & EXEC_P) { /* Executable file -- record its entry point so we'll recognize - the startup file because it contains the entry point. */ + the startup file because it contains the entry point. */ ei->entry_point = bfd_get_start_address (objfile->obfd); ei->entry_point_p = 1; } @@ -848,10 +838,8 @@ init_entry_point_info (struct objfile *objfile) /* Make certain that the address points at real code, and not a function descriptor. */ - entry_point - = gdbarch_convert_from_func_ptr_addr (objfile->arch (), - entry_point, - current_top_target ()); + entry_point = gdbarch_convert_from_func_ptr_addr + (objfile->arch (), entry_point, current_inferior ()->top_target ()); /* Remove any ISA markers, so that this matches entries in the symbol table. */ @@ -912,6 +900,7 @@ syms_from_objfile_1 (struct objfile *objfile, const int mainline = add_flags & SYMFILE_MAINLINE; objfile_set_sym_fns (objfile, find_sym_fns (objfile->obfd)); + objfile->qf.clear (); if (objfile->sf == NULL) { @@ -938,21 +927,21 @@ syms_from_objfile_1 (struct objfile *objfile, if (mainline) { /* We will modify the main symbol table, make sure that all its users - will be cleaned up if an error occurs during symbol reading. */ + will be cleaned up if an error occurs during symbol reading. */ defer_clear_users.emplace ((symfile_add_flag) 0); /* Since no error yet, throw away the old symbol table. */ - if (symfile_objfile != NULL) + if (current_program_space->symfile_object_file != NULL) { - symfile_objfile->unlink (); - gdb_assert (symfile_objfile == NULL); + current_program_space->symfile_object_file->unlink (); + gdb_assert (current_program_space->symfile_object_file == NULL); } /* Currently we keep symbols from the add-symbol-file command. - If the user wants to get rid of them, they should do "symbol-file" - without arguments first. Not sure this is the best behavior - (PR 2207). */ + If the user wants to get rid of them, they should do "symbol-file" + without arguments first. Not sure this is the best behavior + (PR 2207). */ (*objfile->sf->sym_new_init) (objfile); } @@ -1009,7 +998,7 @@ finish_new_objfile (struct objfile *objfile, symfile_add_flags add_flags) if (add_flags & SYMFILE_MAINLINE) { /* OK, make it the "real" symbol file. */ - symfile_objfile = objfile; + current_program_space->symfile_object_file = objfile; clear_symtab_users (add_flags); } @@ -1051,6 +1040,7 @@ symbol_file_add_with_addrs (bfd *abfd, const char *name, struct objfile *objfile; const int from_tty = add_flags & SYMFILE_VERBOSE; const int mainline = add_flags & SYMFILE_MAINLINE; + const int always_confirm = add_flags & SYMFILE_ALWAYS_CONFIRM; const int should_print = (print_symbol_loading_p (from_tty, mainline, 1) && (readnow_symbol_files || (add_flags & SYMFILE_NO_READ) == 0)); @@ -1069,12 +1059,13 @@ symbol_file_add_with_addrs (bfd *abfd, const char *name, if ((add_flags & SYMFILE_NOT_FILENAME) != 0) flags |= OBJF_NOT_FILENAME; - /* Give user a chance to burp if we'd be + /* Give user a chance to burp if ALWAYS_CONFIRM or we'd be interactively wiping out any existing symbols. */ - if ((have_full_symbols () || have_partial_symbols ()) - && mainline - && from_tty + if (from_tty + && (always_confirm + || ((have_full_symbols () || have_partial_symbols ()) + && mainline)) && !query (_("Load new symbol table from \"%s\"? "), name)) error (_("Not confirmed.")); @@ -1106,8 +1097,7 @@ symbol_file_add_with_addrs (bfd *abfd, const char *name, printf_filtered (_("Expanding full symbols from %ps...\n"), styled_string (file_name_style.style (), name)); - if (objfile->sf) - objfile->sf->qf->expand_all_symtabs (objfile); + objfile->expand_all_symtabs (); } /* Note that we only print a message if we have no symbols and have @@ -1172,7 +1162,7 @@ struct objfile * symbol_file_add_from_bfd (bfd *abfd, const char *name, symfile_add_flags add_flags, section_addr_info *addrs, - objfile_flags flags, struct objfile *parent) + objfile_flags flags, struct objfile *parent) { return symbol_file_add_with_addrs (abfd, name, add_flags, addrs, flags, parent); @@ -1228,9 +1218,9 @@ symbol_file_clear (int from_tty) { if ((have_full_symbols () || have_partial_symbols ()) && from_tty - && (symfile_objfile + && (current_program_space->symfile_object_file ? !query (_("Discard symbol table from `%s'? "), - objfile_name (symfile_objfile)) + objfile_name (current_program_space->symfile_object_file)) : !query (_("Discard symbol table? ")))) error (_("Not confirmed.")); @@ -1242,7 +1232,7 @@ symbol_file_clear (int from_tty) clear_symtab_users (0); - gdb_assert (symfile_objfile == NULL); + gdb_assert (current_program_space->symfile_object_file == NULL); if (from_tty) printf_filtered (_("No symbol file now.\n")); } @@ -1851,16 +1841,6 @@ load_command (const char *arg, int from_tty) static int validate_download = 0; -/* Callback service function for generic_load (bfd_map_over_sections). */ - -static void -add_section_size_callback (bfd *abfd, asection *asec, void *data) -{ - bfd_size_type *sum = (bfd_size_type *) data; - - *sum += bfd_section_size (asec); -} - /* Opaque data for load_progress. */ struct load_progress_data { @@ -1975,12 +1955,12 @@ load_progress (ULONGEST bytes, void *untyped_arg) totals->total_size); } -/* Callback service function for generic_load (bfd_map_over_sections). */ +/* Service function for generic_load. */ static void -load_section_callback (bfd *abfd, asection *asec, void *data) +load_one_section (bfd *abfd, asection *asec, + struct load_section_data *args) { - struct load_section_data *args = (struct load_section_data *) data; bfd_size_type size = bfd_section_size (asec); const char *sect_name = bfd_section_name (asec); @@ -2005,7 +1985,7 @@ load_section_callback (bfd *abfd, asection *asec, void *data) static void print_transfer_performance (struct ui_file *stream, unsigned long data_count, unsigned long write_count, - std::chrono::steady_clock::duration d); + std::chrono::steady_clock::duration d); /* See symfile.h. */ @@ -2030,9 +2010,9 @@ generic_load (const char *args, int from_tty) cbdata.load_offset = strtoulst (argv[1], &endptr, 0); /* If the last word was not a valid number then - treat it as a file name with spaces in. */ + treat it as a file name with spaces in. */ if (argv[1] == endptr) - error (_("Invalid download offset:%s."), argv[1]); + error (_("Invalid download offset:%s."), argv[1]); if (argv[2] != NULL) error (_("Too many parameters.")); @@ -2049,10 +2029,11 @@ generic_load (const char *args, int from_tty) bfd_errmsg (bfd_get_error ())); } - bfd_map_over_sections (loadfile_bfd.get (), add_section_size_callback, - (void *) &total_progress.total_size); + for (asection *asec : gdb_bfd_sections (loadfile_bfd)) + total_progress.total_size += bfd_section_size (asec); - bfd_map_over_sections (loadfile_bfd.get (), load_section_callback, &cbdata); + for (asection *asec : gdb_bfd_sections (loadfile_bfd)) + load_one_section (loadfile_bfd.get (), asec, &cbdata); using namespace std::chrono; @@ -2308,10 +2289,10 @@ add_symbol_file_command (const char *args, int from_tty) addr = parse_and_eval_address (val); /* Here we store the section offsets in the order they were - entered on the command line. Every array element is - assigned an ascending section index to preserve the above - order over an unstable sorting algorithm. This dummy - index is not used for any other purpose. + entered on the command line. Every array element is + assigned an ascending section index to preserve the above + order over an unstable sorting algorithm. This dummy + index is not used for any other purpose. */ section_addrs.emplace_back (addr, sec, section_addrs.size ()); printf_filtered ("\t%s_addr = %s\n", sec, @@ -2344,7 +2325,7 @@ add_symbol_file_command (const char *args, int from_tty) if (seen_offset) set_objfile_default_section_offset (objf, section_addrs, offset); - add_target_sections_of_objfile (objf); + current_program_space->add_target_sections (objf); /* Getting new symbols may change our opinion about what is frameless. */ @@ -2481,9 +2462,9 @@ reread_symbols (void) /* We need to do this whenever any symbols go away. */ clear_symtab_users_cleanup defer_clear_users (0); - if (exec_bfd != NULL + if (current_program_space->exec_bfd () != NULL && filename_cmp (bfd_get_filename (objfile->obfd), - bfd_get_filename (exec_bfd)) == 0) + bfd_get_filename (current_program_space->exec_bfd ())) == 0) { /* Reload EXEC_BFD without asking anything. */ @@ -2537,12 +2518,15 @@ reread_symbols (void) error (_("Can't read symbols from %s: %s."), objfile_name (objfile), bfd_errmsg (bfd_get_error ())); - objfile->reset_psymtabs (); - /* NB: after this call to obstack_free, objfiles_changed will need to be called (see discussion below). */ obstack_free (&objfile->objfile_obstack, 0); objfile->sections = NULL; + objfile->section_offsets.clear (); + objfile->sect_index_bss = -1; + objfile->sect_index_data = -1; + objfile->sect_index_rodata = -1; + objfile->sect_index_text = -1; objfile->compunit_symtabs = NULL; objfile->template_symbols = NULL; objfile->static_links.reset (nullptr); @@ -2565,13 +2549,14 @@ reread_symbols (void) based on whether .gdb_index is present, and we need it to start over. PR symtab/15885 */ objfile_set_sym_fns (objfile, find_sym_fns (objfile->obfd)); + objfile->qf.clear (); build_objfile_section_table (objfile); /* What the hell is sym_new_init for, anyway? The concept of distinguishing between the main file and additional files in this way seems rather dubious. */ - if (objfile == symfile_objfile) + if (objfile == current_program_space->symfile_object_file) { (*objfile->sf->sym_new_init) (objfile); } @@ -2597,6 +2582,9 @@ reread_symbols (void) objfiles_changed (); + /* Recompute section offsets and section indices. */ + objfile->sf->sym_offsets (objfile, {}); + read_symbols (objfile, 0); if (!objfile_has_symbols (objfile)) @@ -2639,7 +2627,7 @@ reread_symbols (void) gdb::observers::new_objfile.notify (iter); /* At least one objfile has changed, so we can consider that - the executable we're debugging has changed too. */ + the executable we're debugging has changed too. */ gdb::observers::executable_changed.notify (); } } @@ -2662,6 +2650,7 @@ static std::vector filename_language_table; void add_filename_language (const char *ext, enum language lang) { + gdb_assert (ext != nullptr); filename_language_table.emplace_back (ext, lang); } @@ -2994,7 +2983,7 @@ section_is_mapped (struct obj_section *osect) return 0; /* overlay debugging off */ case ovly_auto: /* overlay debugging automatic */ /* Unles there is a gdbarch_overlay_update function, - there's really nothing useful to do here (can't really go auto). */ + there's really nothing useful to do here (can't really go auto). */ gdbarch = osect->objfile->arch (); if (gdbarch_overlay_update_p (gdbarch)) { @@ -3396,8 +3385,7 @@ enum ovly_index static void simple_free_overlay_table (void) { - if (cache_ovly_table) - xfree (cache_ovly_table); + xfree (cache_ovly_table); cache_novlys = 0; cache_ovly_table = NULL; cache_ovly_table_base = 0; @@ -3436,8 +3424,8 @@ simple_read_overlay_table (void) if (! novlys_msym.minsym) { error (_("Error reading inferior's overlay table: " - "couldn't find `_novlys' variable\n" - "in inferior. Use `overlay manual' mode.")); + "couldn't find `_novlys' variable\n" + "in inferior. Use `overlay manual' mode.")); return 0; } @@ -3445,8 +3433,8 @@ simple_read_overlay_table (void) if (! ovly_table_msym.minsym) { error (_("Error reading inferior's overlay table: couldn't find " - "`_ovly_table' array\n" - "in inferior. Use `overlay manual' mode.")); + "`_ovly_table' array\n" + "in inferior. Use `overlay manual' mode.")); return 0; } @@ -3460,8 +3448,8 @@ simple_read_overlay_table (void) = (unsigned int (*)[4]) xmalloc (cache_novlys * sizeof (*cache_ovly_table)); cache_ovly_table_base = BMSYMBOL_VALUE_ADDRESS (ovly_table_msym); read_target_long_array (cache_ovly_table_base, - (unsigned int *) cache_ovly_table, - cache_novlys * 4, word_size, byte_order); + (unsigned int *) cache_ovly_table, + cache_novlys * 4, word_size, byte_order); return 1; /* SUCCESS */ } @@ -3561,23 +3549,11 @@ simple_overlay_update (struct obj_section *osect) } } -/* Set the output sections and output offsets for section SECTP in - ABFD. The relocation code in BFD will read these offsets, so we - need to be sure they're initialized. We map each section to itself, - with no offset; this means that SECTP->vma will be honored. */ - -static void -symfile_dummy_outputs (bfd *abfd, asection *sectp, void *dummy) -{ - sectp->output_section = sectp; - sectp->output_offset = 0; -} - /* Default implementation for sym_relocate. */ bfd_byte * default_symfile_relocate (struct objfile *objfile, asection *sectp, - bfd_byte *buf) + bfd_byte *buf) { /* Use sectp->owner instead of objfile->obfd. sectp may point to a DWO file. */ @@ -3590,7 +3566,11 @@ default_symfile_relocate (struct objfile *objfile, asection *sectp, /* We will handle section offsets properly elsewhere, so relocate as if all sections begin at 0. */ - bfd_map_over_sections (abfd, symfile_dummy_outputs, NULL); + for (asection *sect : gdb_bfd_sections (abfd)) + { + sect->output_section = sect; + sect->output_offset = 0; + } return bfd_simple_get_relocated_section_contents (abfd, sectp, buf, NULL); } @@ -3611,7 +3591,7 @@ default_symfile_relocate (struct objfile *objfile, asection *sectp, bfd_byte * symfile_relocate_debug_section (struct objfile *objfile, - asection *sectp, bfd_byte *buf) + asection *sectp, bfd_byte *buf) { gdb_assert (objfile->sf->sym_relocate); @@ -3670,14 +3650,14 @@ symfile_map_offsets_to_segments (bfd *abfd, gdb_assert (0 <= which && which <= data->segments.size ()); /* Don't bother computing offsets for sections that aren't - loaded as part of any segment. */ + loaded as part of any segment. */ if (! which) - continue; + continue; /* Use the last SEGMENT_BASES entry as the address of any extra - segments mentioned in DATA->segment_info. */ + segments mentioned in DATA->segment_info. */ if (which > num_segment_bases) - which = num_segment_bases; + which = num_segment_bases; offsets[i] = segment_bases[which - 1] - data->segments[which - 1].base; } @@ -3730,7 +3710,7 @@ symfile_free_objfile (struct objfile *objfile) { /* Remove the target sections owned by this objfile. */ if (objfile != NULL) - remove_target_sections ((void *) objfile); + current_program_space->remove_target_sections ((void *) objfile); } /* Wrapper around the quick_symbol_functions expand_symtabs_matching "method". @@ -3746,13 +3726,10 @@ expand_symtabs_matching enum search_domain kind) { for (objfile *objfile : current_program_space->objfiles ()) - { - if (objfile->sf) - objfile->sf->qf->expand_symtabs_matching (objfile, file_matcher, - &lookup_name, - symbol_matcher, - expansion_notify, kind); - } + objfile->expand_symtabs_matching (file_matcher, + &lookup_name, + symbol_matcher, + expansion_notify, kind); } /* Wrapper around the quick_symbol_functions map_symbol_filenames "method". @@ -3764,11 +3741,7 @@ map_symbol_filenames (symbol_filename_ftype *fun, void *data, int need_fullname) { for (objfile *objfile : current_program_space->objfiles ()) - { - if (objfile->sf) - objfile->sf->qf->map_symbol_filenames (objfile, fun, data, - need_fullname); - } + objfile->map_symbol_filenames (fun, data, need_fullname); } #if GDB_SELF_TEST @@ -3942,9 +3915,9 @@ Set printing of symbol loading messages."), _("\ Show printing of symbol loading messages."), _("\ off == turn all messages off\n\ brief == print messages for the executable,\n\ - and brief messages for shared libraries\n\ + and brief messages for shared libraries\n\ full == print messages for the executable,\n\ - and messages for each shared library."), + and messages for each shared library."), NULL, NULL, &setprintlist, &showprintlist);