X-Git-Url: http://git.efficios.com/?a=blobdiff_plain;f=gdb%2Fsymmisc.c;h=f4c3fc51af0a9171ea2d788745b63977e2923d9d;hb=4ff70b847ca222dcd9e7fc33ef2be300f75be68a;hp=d3028e66ba82742ffafdd35897cb58ac5e5ce75a;hpb=27618ce42a9eaeb1c95bca6ed8f2a261df0e6981;p=deliverable%2Fbinutils-gdb.git diff --git a/gdb/symmisc.c b/gdb/symmisc.c index d3028e66ba..f4c3fc51af 100644 --- a/gdb/symmisc.c +++ b/gdb/symmisc.c @@ -1,7 +1,6 @@ /* Do various things to symbol tables (other than lookup), for GDB. - Copyright (C) 1986-2000, 2002-2004, 2007-2012 Free Software - Foundation, Inc. + Copyright (C) 1986-2013 Free Software Foundation, Inc. This file is part of GDB. @@ -35,8 +34,11 @@ #include "gdb_regex.h" #include "gdb_stat.h" #include "dictionary.h" +#include "typeprint.h" +#include "gdbcmd.h" +#include "source.h" -#include "gdb_string.h" +#include #include "readline/readline.h" #include "psymtab.h" @@ -57,13 +59,6 @@ FILE *std_err; /* Prototypes for local functions */ -static void dump_symtab (struct objfile *, struct symtab *, - struct ui_file *); - -static void dump_msymbols (struct objfile *, struct ui_file *); - -static void dump_objfile (struct objfile *); - static int block_depth (struct block *); void _initialize_symmisc (void); @@ -89,11 +84,14 @@ print_symbol_bcache_statistics (void) ALL_PSPACE_OBJFILES (pspace, objfile) { QUIT; - printf_filtered (_("Byte cache statistics for '%s':\n"), objfile->name); + printf_filtered (_("Byte cache statistics for '%s':\n"), + objfile_name (objfile)); print_bcache_statistics (psymbol_bcache_get_bcache (objfile->psymbol_cache), "partial symbol cache"); - print_bcache_statistics (objfile->macro_cache, "preprocessor macro cache"); - print_bcache_statistics (objfile->filename_cache, "file name cache"); + print_bcache_statistics (objfile->per_bfd->macro_cache, + "preprocessor macro cache"); + print_bcache_statistics (objfile->per_bfd->filename_cache, + "file name cache"); } } @@ -109,7 +107,7 @@ print_objfile_statistics (void) ALL_PSPACE_OBJFILES (pspace, objfile) { QUIT; - printf_filtered (_("Statistics for '%s':\n"), objfile->name); + printf_filtered (_("Statistics for '%s':\n"), objfile_name (objfile)); if (OBJSTAT (objfile, n_stabs) > 0) printf_filtered (_(" Number of \"stab\" symbols read: %d\n"), OBJSTAT (objfile, n_stabs)); @@ -147,13 +145,15 @@ print_objfile_statistics (void) OBJSTAT (objfile, sz_strtab)); printf_filtered (_(" Total memory used for objfile obstack: %d\n"), obstack_memory_used (&objfile->objfile_obstack)); + printf_filtered (_(" Total memory used for BFD obstack: %d\n"), + obstack_memory_used (&objfile->per_bfd->storage_obstack)); printf_filtered (_(" Total memory used for psymbol cache: %d\n"), bcache_memory_used (psymbol_bcache_get_bcache (objfile->psymbol_cache))); printf_filtered (_(" Total memory used for macro cache: %d\n"), - bcache_memory_used (objfile->macro_cache)); + bcache_memory_used (objfile->per_bfd->macro_cache)); printf_filtered (_(" Total memory used for file name cache: %d\n"), - bcache_memory_used (objfile->filename_cache)); + bcache_memory_used (objfile->per_bfd->filename_cache)); } } @@ -162,7 +162,7 @@ dump_objfile (struct objfile *objfile) { struct symtab *symtab; - printf_filtered ("\nObject file %s: ", objfile->name); + printf_filtered ("\nObject file %s: ", objfile_name (objfile)); printf_filtered ("Objfile at "); gdb_print_host_address (objfile, gdb_stdout); printf_filtered (", bfd at "); @@ -180,7 +180,7 @@ dump_objfile (struct objfile *objfile) symtab != NULL; symtab = symtab->next) { - printf_filtered ("%s at ", symtab->filename); + printf_filtered ("%s at ", symtab_to_filename_for_display (symtab)); gdb_print_host_address (symtab, gdb_stdout); printf_filtered (", "); if (symtab->objfile != objfile) @@ -203,7 +203,7 @@ dump_msymbols (struct objfile *objfile, struct ui_file *outfile) int index; char ms_type; - fprintf_filtered (outfile, "\nObject file %s:\n\n", objfile->name); + fprintf_filtered (outfile, "\nObject file %s:\n\n", objfile_name (objfile)); if (objfile->minimal_symbol_count == 0) { fprintf_filtered (outfile, "No minimal symbols found.\n"); @@ -212,7 +212,7 @@ dump_msymbols (struct objfile *objfile, struct ui_file *outfile) index = 0; ALL_OBJFILE_MSYMBOLS (objfile, msymbol) { - struct obj_section *section = SYMBOL_OBJ_SECTION (msymbol); + struct obj_section *section = SYMBOL_OBJ_SECTION (objfile, msymbol); switch (MSYMBOL_TYPE (msymbol)) { @@ -255,9 +255,15 @@ dump_msymbols (struct objfile *objfile, struct ui_file *outfile) outfile); fprintf_filtered (outfile, " %s", SYMBOL_LINKAGE_NAME (msymbol)); if (section) - fprintf_filtered (outfile, " section %s", - bfd_section_name (objfile->obfd, - section->the_bfd_section)); + { + if (section->the_bfd_section != NULL) + fprintf_filtered (outfile, " section %s", + bfd_section_name (objfile->obfd, + section->the_bfd_section)); + else + fprintf_filtered (outfile, " spurious section %ld", + (long) (section - objfile->sections)); + } if (SYMBOL_DEMANGLED_NAME (msymbol) != NULL) { fprintf_filtered (outfile, " %s", SYMBOL_DEMANGLED_NAME (msymbol)); @@ -289,11 +295,13 @@ dump_symtab_1 (struct objfile *objfile, struct symtab *symtab, struct block *b; int depth; - fprintf_filtered (outfile, "\nSymtab for file %s\n", symtab->filename); + fprintf_filtered (outfile, "\nSymtab for file %s\n", + symtab_to_filename_for_display (symtab)); if (symtab->dirname) fprintf_filtered (outfile, "Compilation directory is %s\n", symtab->dirname); - fprintf_filtered (outfile, "Read from object file %s (", objfile->name); + fprintf_filtered (outfile, "Read from object file %s (", + objfile_name (objfile)); gdb_print_host_address (objfile, outfile); fprintf_filtered (outfile, ")\n"); fprintf_filtered (outfile, "Language: %s\n", @@ -396,7 +404,7 @@ dump_symtab (struct objfile *objfile, struct symtab *symtab, dump_symtab_1 (objfile, symtab, outfile); } -void +static void maintenance_print_symbols (char *args, int from_tty) { char **argv; @@ -438,7 +446,8 @@ maintenance_print_symbols (char *args, int from_tty) ALL_SYMTABS (objfile, s) { QUIT; - if (symname == NULL || filename_cmp (symname, s->filename) == 0) + if (symname == NULL + || filename_cmp (symname, symtab_to_filename_for_display (s)) == 0) dump_symtab (objfile, s, outfile); } do_cleanups (cleanups); @@ -456,7 +465,8 @@ print_symbol (void *args) struct symbol *symbol = ((struct print_symbol_args *) args)->symbol; int depth = ((struct print_symbol_args *) args)->depth; struct ui_file *outfile = ((struct print_symbol_args *) args)->outfile; - struct obj_section *section = SYMBOL_OBJ_SECTION (symbol); + struct obj_section *section = SYMBOL_OBJ_SECTION (SYMBOL_OBJFILE (symbol), + symbol); print_spaces (depth, outfile); if (SYMBOL_DOMAIN (symbol) == LABEL_DOMAIN) @@ -476,7 +486,8 @@ print_symbol (void *args) { if (TYPE_TAG_NAME (SYMBOL_TYPE (symbol))) { - LA_PRINT_TYPE (SYMBOL_TYPE (symbol), "", outfile, 1, depth); + LA_PRINT_TYPE (SYMBOL_TYPE (symbol), "", outfile, 1, depth, + &type_print_raw_options); } else { @@ -486,7 +497,8 @@ print_symbol (void *args) : (TYPE_CODE (SYMBOL_TYPE (symbol)) == TYPE_CODE_STRUCT ? "struct" : "union")), SYMBOL_LINKAGE_NAME (symbol)); - LA_PRINT_TYPE (SYMBOL_TYPE (symbol), "", outfile, 1, depth); + LA_PRINT_TYPE (SYMBOL_TYPE (symbol), "", outfile, 1, depth, + &type_print_raw_options); } fprintf_filtered (outfile, ";\n"); } @@ -500,7 +512,8 @@ print_symbol (void *args) LA_PRINT_TYPE (SYMBOL_TYPE (symbol), SYMBOL_PRINT_NAME (symbol), outfile, TYPE_CODE (SYMBOL_TYPE (symbol)) != TYPE_CODE_ENUM, - depth); + depth, + &type_print_raw_options); fprintf_filtered (outfile, "; "); } else @@ -618,7 +631,7 @@ print_symbol (void *args) return 1; } -void +static void maintenance_print_msymbols (char *args, int from_tty) { char **argv; @@ -647,7 +660,7 @@ maintenance_print_msymbols (char *args, int from_tty) /* If a second arg is supplied, it is a source file name to match on. */ if (argv[1] != NULL) { - symname = xfullpath (argv[1]); + symname = gdb_realpath (argv[1]); make_cleanup (xfree, symname); if (symname && stat (symname, &sym_st)) perror_with_name (symname); @@ -666,7 +679,8 @@ maintenance_print_msymbols (char *args, int from_tty) ALL_PSPACE_OBJFILES (pspace, objfile) { QUIT; - if (symname == NULL || (!stat (objfile->name, &obj_st) + if (symname == NULL || (!stat (objfile_name (objfile), &obj_st) + && sym_st.st_dev == obj_st.st_dev && sym_st.st_ino == obj_st.st_ino)) dump_msymbols (objfile, outfile); } @@ -674,30 +688,37 @@ maintenance_print_msymbols (char *args, int from_tty) do_cleanups (cleanups); } -void -maintenance_print_objfiles (char *ignore, int from_tty) +static void +maintenance_print_objfiles (char *regexp, int from_tty) { struct program_space *pspace; struct objfile *objfile; dont_repeat (); + if (regexp) + re_comp (regexp); + ALL_PSPACES (pspace) ALL_PSPACE_OBJFILES (pspace, objfile) { QUIT; - dump_objfile (objfile); + if (! regexp + || re_exec (objfile_name (objfile))) + dump_objfile (objfile); } } - /* List all the symbol tables whose names match REGEXP (optional). */ -void + +static void maintenance_info_symtabs (char *regexp, int from_tty) { struct program_space *pspace; struct objfile *objfile; + dont_repeat (); + if (regexp) re_comp (regexp); @@ -715,18 +736,19 @@ maintenance_info_symtabs (char *regexp, int from_tty) QUIT; if (! regexp - || re_exec (symtab->filename)) + || re_exec (symtab_to_filename_for_display (symtab))) { if (! printed_objfile_start) { - printf_filtered ("{ objfile %s ", objfile->name); + printf_filtered ("{ objfile %s ", objfile_name (objfile)); wrap_here (" "); printf_filtered ("((struct objfile *) %s)\n", host_address_to_string (objfile)); printed_objfile_start = 1; } - printf_filtered (" { symtab %s ", symtab->filename); + printf_filtered (" { symtab %s ", + symtab_to_filename_for_display (symtab)); wrap_here (" "); printf_filtered ("((struct symtab *) %s)\n", host_address_to_string (symtab)); @@ -751,6 +773,136 @@ maintenance_info_symtabs (char *regexp, int from_tty) printf_filtered ("}\n"); } } + +/* Check consistency of symtabs. + An example of what this checks for is NULL blockvectors. + They can happen if there's a bug during debug info reading. + GDB assumes they are always non-NULL. + + Note: This does not check for psymtab vs symtab consistency. + Use "maint check-psymtabs" for that. */ + +static void +maintenance_check_symtabs (char *ignore, int from_tty) +{ + struct program_space *pspace; + struct objfile *objfile; + + ALL_PSPACES (pspace) + ALL_PSPACE_OBJFILES (pspace, objfile) + { + struct symtab *symtab; + + /* We don't want to print anything for this objfile until we + actually find something worth printing. */ + int printed_objfile_start = 0; + + ALL_OBJFILE_SYMTABS (objfile, symtab) + { + int found_something = 0; + + QUIT; + + if (symtab->blockvector == NULL) + found_something = 1; + /* Add more checks here. */ + + if (found_something) + { + if (! printed_objfile_start) + { + printf_filtered ("{ objfile %s ", objfile_name (objfile)); + wrap_here (" "); + printf_filtered ("((struct objfile *) %s)\n", + host_address_to_string (objfile)); + printed_objfile_start = 1; + } + printf_filtered (" { symtab %s\n", + symtab_to_filename_for_display (symtab)); + if (symtab->blockvector == NULL) + printf_filtered (" NULL blockvector\n"); + printf_filtered (" }\n"); + } + } + + if (printed_objfile_start) + printf_filtered ("}\n"); + } +} + +/* Helper function for maintenance_expand_symtabs. + This is the name_matcher function for expand_symtabs_matching. */ + +static int +maintenance_expand_name_matcher (const char *symname, void *data) +{ + /* Since we're not searching on symbols, just return TRUE. */ + return 1; +} + +/* Helper function for maintenance_expand_symtabs. + This is the file_matcher function for expand_symtabs_matching. */ + +static int +maintenance_expand_file_matcher (const char *filename, void *data, + int basenames) +{ + const char *regexp = data; + + QUIT; + + /* KISS: Only apply the regexp to the complete file name. */ + if (basenames) + return 0; + + if (regexp == NULL || re_exec (filename)) + return 1; + + return 0; +} + +/* Expand all symbol tables whose name matches an optional regexp. */ + +static void +maintenance_expand_symtabs (char *args, int from_tty) +{ + struct program_space *pspace; + struct objfile *objfile; + struct cleanup *cleanups; + char **argv; + char *regexp = NULL; + + /* We use buildargv here so that we handle spaces in the regexp + in a way that allows adding more arguments later. */ + argv = gdb_buildargv (args); + cleanups = make_cleanup_freeargv (argv); + + if (argv != NULL) + { + if (argv[0] != NULL) + { + regexp = argv[0]; + if (argv[1] != NULL) + error (_("Extra arguments after regexp.")); + } + } + + if (regexp) + re_comp (regexp); + + ALL_PSPACES (pspace) + ALL_PSPACE_OBJFILES (pspace, objfile) + { + if (objfile->sf) + { + objfile->sf->qf->expand_symtabs_matching + (objfile, maintenance_expand_file_matcher, + maintenance_expand_name_matcher, ALL_DOMAIN, regexp); + } + } + + do_cleanups (cleanups); +} /* Return the nexting depth of a block within other blocks in its symtab. */ @@ -769,10 +921,45 @@ block_depth (struct block *block) /* Do early runtime initializations. */ + void _initialize_symmisc (void) { std_in = stdin; std_out = stdout; std_err = stderr; + + add_cmd ("symbols", class_maintenance, maintenance_print_symbols, _("\ +Print dump of current symbol definitions.\n\ +Entries in the full symbol table are dumped to file OUTFILE.\n\ +If a SOURCE file is specified, dump only that file's symbols."), + &maintenanceprintlist); + + add_cmd ("msymbols", class_maintenance, maintenance_print_msymbols, _("\ +Print dump of current minimal symbol definitions.\n\ +Entries in the minimal symbol table are dumped to file OUTFILE.\n\ +If a SOURCE file is specified, dump only that file's minimal symbols."), + &maintenanceprintlist); + + add_cmd ("objfiles", class_maintenance, maintenance_print_objfiles, + _("Print dump of current object file definitions.\n\ +With an argument REGEXP, list the object files with matching names."), + &maintenanceprintlist); + + add_cmd ("symtabs", class_maintenance, maintenance_info_symtabs, _("\ +List the full symbol tables for all object files.\n\ +This does not include information about individual symbols, blocks, or\n\ +linetables --- just the symbol table structures themselves.\n\ +With an argument REGEXP, list the symbol tables with matching names."), + &maintenanceinfolist); + + add_cmd ("check-symtabs", class_maintenance, maintenance_check_symtabs, + _("\ +Check consistency of currently expanded symtabs."), + &maintenancelist); + + add_cmd ("expand-symtabs", class_maintenance, maintenance_expand_symtabs, + _("Expand symbol tables.\n\ +With an argument REGEXP, only expand the symbol tables with matching names."), + &maintenancelist); }