Speed up GDB startup time by not demangling partial symbols.
* symfile.h (ADD_PSYMBOL_VT_TO_LIST), symfile.c (add_psymbol_to_list, add_psymbol_addr_to_list): No longer demangle partial symbols. * symtab.c (lookup_symbol, list_symbols): Handle mangled variables, e.g. C++ static members, via the minimal symbols. Handle reordered functions in an objfile, for Irix 5.2 shared libraries. * objfiles.h (OBJF_REORDERED): New bit in the objfile flags, set if the functions in an objfile are reordered. * mdebugread.c (parse_partial_symbols): Detect reordered functions in an objfile. * symtab.c (find_pc_psymtab, find_pc_symtab): Use expensive lookup algorithm if the functions in the objfile are reordered. * xcoffexec.c (exec_close): If the current target has a copy of the exec_ops sections, reflect the freeing of the sections in current_target. * valops.c (call_function_by_hand): Use `sizeof dummy1', not `sizeof dummy', for constructing the call dummy code. * config/sparc/tm-sparc.h: Add PARAMS declarations to all function declarations. * sparc-tdep.c (sparc_pop_frame): Cast result of read_memory_integer to CORE_ADDR when passing it to PC_ADJUST. * irix5-nat.c (enable_break): Set breakpoint at the entry point of the executable, to handle the case where main resides in a shared library. * irix5-nat.c (solib_create_inferior_hook): Reset stop_soon_quietly after shared library symbol reading, to get rid of a warning from heuristic_proc_start if the startup code has no symbolic debug info. * breakpoint.h (struct breakpoint): Add new fields language and input_radix, to enable breakpoint resetting with the proper language and radix. * breakpoint.c (set_raw_breakpoint): Initialize them. (breakpoint_re_set_one): Use them when resetting the breakpoint. (breakpoint_re_set): Preserve current language and input_radix across breakpoint_re_set_one calls. * symtab.c (decode_line_1): Do not build a canonical line specification for `*expr' line specifications. * breakpoint.h (bpstat_stop_status): Fix prototype declaration.
This commit is contained in:
parent
15a90f75cb
commit
7621229598
@ -1,3 +1,53 @@
|
|||||||
|
Sat Oct 8 04:27:21 1994 Peter Schauer (pes@regent.e-technik.tu-muenchen.de)
|
||||||
|
|
||||||
|
Speed up GDB startup time by not demangling partial symbols.
|
||||||
|
* symfile.h (ADD_PSYMBOL_VT_TO_LIST),
|
||||||
|
symfile.c (add_psymbol_to_list, add_psymbol_addr_to_list):
|
||||||
|
No longer demangle partial symbols.
|
||||||
|
* symtab.c (lookup_symbol, list_symbols): Handle mangled
|
||||||
|
variables, e.g. C++ static members, via the minimal symbols.
|
||||||
|
|
||||||
|
Handle reordered functions in an objfile, for Irix 5.2 shared
|
||||||
|
libraries.
|
||||||
|
* objfiles.h (OBJF_REORDERED): New bit in the objfile flags,
|
||||||
|
set if the functions in an objfile are reordered.
|
||||||
|
* mdebugread.c (parse_partial_symbols): Detect reordered
|
||||||
|
functions in an objfile.
|
||||||
|
* symtab.c (find_pc_psymtab, find_pc_symtab): Use expensive
|
||||||
|
lookup algorithm if the functions in the objfile are reordered.
|
||||||
|
|
||||||
|
* xcoffexec.c (exec_close): If the current target has a copy
|
||||||
|
of the exec_ops sections, reflect the freeing of the sections
|
||||||
|
in current_target.
|
||||||
|
|
||||||
|
* valops.c (call_function_by_hand): Use `sizeof dummy1', not
|
||||||
|
`sizeof dummy', for constructing the call dummy code.
|
||||||
|
|
||||||
|
* config/sparc/tm-sparc.h: Add PARAMS declarations to all
|
||||||
|
function declarations.
|
||||||
|
* sparc-tdep.c (sparc_pop_frame): Cast result of
|
||||||
|
read_memory_integer to CORE_ADDR when passing it to PC_ADJUST.
|
||||||
|
|
||||||
|
* irix5-nat.c (enable_break): Set breakpoint at the entry point
|
||||||
|
of the executable, to handle the case where main resides in a
|
||||||
|
shared library.
|
||||||
|
* irix5-nat.c (solib_create_inferior_hook): Reset stop_soon_quietly
|
||||||
|
after shared library symbol reading, to get rid of a warning from
|
||||||
|
heuristic_proc_start if the startup code has no symbolic debug info.
|
||||||
|
|
||||||
|
* breakpoint.h (struct breakpoint): Add new fields language
|
||||||
|
and input_radix, to enable breakpoint resetting with the
|
||||||
|
proper language and radix.
|
||||||
|
* breakpoint.c (set_raw_breakpoint): Initialize them.
|
||||||
|
(breakpoint_re_set_one): Use them when resetting the breakpoint.
|
||||||
|
(breakpoint_re_set): Preserve current language and input_radix
|
||||||
|
across breakpoint_re_set_one calls.
|
||||||
|
|
||||||
|
* symtab.c (decode_line_1): Do not build a canonical line
|
||||||
|
specification for `*expr' line specifications.
|
||||||
|
|
||||||
|
* breakpoint.h (bpstat_stop_status): Fix prototype declaration.
|
||||||
|
|
||||||
Fri Oct 7 08:48:18 1994 Jim Kingdon (kingdon@lioth.cygnus.com)
|
Fri Oct 7 08:48:18 1994 Jim Kingdon (kingdon@lioth.cygnus.com)
|
||||||
|
|
||||||
The point of these changes is to avoid reading the frame pointer
|
The point of these changes is to avoid reading the frame pointer
|
||||||
|
101
gdb/irix5-nat.c
101
gdb/irix5-nat.c
@ -194,21 +194,6 @@ fetch_core_registers (core_reg_sect, core_reg_size, which, reg_addr)
|
|||||||
#include "inferior.h"
|
#include "inferior.h"
|
||||||
#include "language.h"
|
#include "language.h"
|
||||||
|
|
||||||
/* We need to set a breakpoint at a point when we know that the
|
|
||||||
mapping of shared libraries is complete. dbx simply breaks at main
|
|
||||||
(or, for FORTRAN, MAIN__), so we do the same. We can not break at
|
|
||||||
the very beginning of main, because the startup code will jump into
|
|
||||||
main after the GP initialization instructions. SOLIB_BKPT_OFFSET
|
|
||||||
is used to skip those instructions. */
|
|
||||||
|
|
||||||
#define SOLIB_BKPT_OFFSET 12
|
|
||||||
|
|
||||||
static char *bkpt_names[] = {
|
|
||||||
"main",
|
|
||||||
"MAIN__",
|
|
||||||
NULL
|
|
||||||
};
|
|
||||||
|
|
||||||
/* The symbol which starts off the list of shared libraries. */
|
/* The symbol which starts off the list of shared libraries. */
|
||||||
#define DEBUG_BASE "__rld_obj_head"
|
#define DEBUG_BASE "__rld_obj_head"
|
||||||
|
|
||||||
@ -878,84 +863,22 @@ SYNOPSIS
|
|||||||
|
|
||||||
DESCRIPTION
|
DESCRIPTION
|
||||||
|
|
||||||
Both the SunOS and the SVR4 dynamic linkers have, as part of their
|
This functions inserts a breakpoint at the entry point of the
|
||||||
debugger interface, support for arranging for the inferior to hit
|
main executable, where all shared libraries are mapped in.
|
||||||
a breakpoint after mapping in the shared libraries. This function
|
|
||||||
enables that breakpoint.
|
|
||||||
|
|
||||||
For SunOS, there is a special flag location (in_debugger) which we
|
|
||||||
set to 1. When the dynamic linker sees this flag set, it will set
|
|
||||||
a breakpoint at a location known only to itself, after saving the
|
|
||||||
original contents of that place and the breakpoint address itself,
|
|
||||||
in it's own internal structures. When we resume the inferior, it
|
|
||||||
will eventually take a SIGTRAP when it runs into the breakpoint.
|
|
||||||
We handle this (in a different place) by restoring the contents of
|
|
||||||
the breakpointed location (which is only known after it stops),
|
|
||||||
chasing around to locate the shared libraries that have been
|
|
||||||
loaded, then resuming.
|
|
||||||
|
|
||||||
For SVR4, the debugger interface structure contains a member (r_brk)
|
|
||||||
which is statically initialized at the time the shared library is
|
|
||||||
built, to the offset of a function (_r_debug_state) which is guaran-
|
|
||||||
teed to be called once before mapping in a library, and again when
|
|
||||||
the mapping is complete. At the time we are examining this member,
|
|
||||||
it contains only the unrelocated offset of the function, so we have
|
|
||||||
to do our own relocation. Later, when the dynamic linker actually
|
|
||||||
runs, it relocates r_brk to be the actual address of _r_debug_state().
|
|
||||||
|
|
||||||
The debugger interface structure also contains an enumeration which
|
|
||||||
is set to either RT_ADD or RT_DELETE prior to changing the mapping,
|
|
||||||
depending upon whether or not the library is being mapped or unmapped,
|
|
||||||
and then set to RT_CONSISTENT after the library is mapped/unmapped.
|
|
||||||
|
|
||||||
Irix 5, on the other hand, has no such features. Instead, we
|
|
||||||
set a breakpoint at main.
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
static int
|
static int
|
||||||
enable_break ()
|
enable_break ()
|
||||||
{
|
{
|
||||||
int success = 0;
|
if (symfile_objfile != NULL
|
||||||
struct minimal_symbol *msymbol;
|
&& target_insert_breakpoint (symfile_objfile->ei.entry_point,
|
||||||
char **bkpt_namep;
|
shadow_contents) == 0)
|
||||||
CORE_ADDR bkpt_addr;
|
|
||||||
|
|
||||||
/* Scan through the list of symbols, trying to look up the symbol and
|
|
||||||
set a breakpoint there. Terminate loop when we/if we succeed. */
|
|
||||||
|
|
||||||
breakpoint_addr = 0;
|
|
||||||
for (bkpt_namep = bkpt_names; *bkpt_namep != NULL; bkpt_namep++)
|
|
||||||
{
|
{
|
||||||
msymbol = lookup_minimal_symbol (*bkpt_namep, symfile_objfile);
|
breakpoint_addr = symfile_objfile->ei.entry_point;
|
||||||
if ((msymbol != NULL) && (SYMBOL_VALUE_ADDRESS (msymbol) != 0))
|
return 1;
|
||||||
{
|
|
||||||
bkpt_addr = SYMBOL_VALUE_ADDRESS (msymbol);
|
|
||||||
#ifdef SOLIB_BKPT_OFFSET
|
|
||||||
/* We only want to skip if bkpt_addr is currently pointing
|
|
||||||
at a GP setting instruction. */
|
|
||||||
{
|
|
||||||
char buf[4];
|
|
||||||
|
|
||||||
if (target_read_memory (bkpt_addr, buf, 4) == 0)
|
|
||||||
{
|
|
||||||
unsigned long insn;
|
|
||||||
|
|
||||||
insn = extract_unsigned_integer (buf, 4);
|
|
||||||
if ((insn & 0xffff0000) == 0x3c1c0000) /* lui $gp,n */
|
|
||||||
bkpt_addr += SOLIB_BKPT_OFFSET;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
if (target_insert_breakpoint (bkpt_addr, shadow_contents) == 0)
|
|
||||||
{
|
|
||||||
breakpoint_addr = bkpt_addr;
|
|
||||||
success = 1;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return (success);
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -1033,7 +956,6 @@ solib_create_inferior_hook()
|
|||||||
wait_for_inferior ();
|
wait_for_inferior ();
|
||||||
}
|
}
|
||||||
while (stop_signal != SIGTRAP);
|
while (stop_signal != SIGTRAP);
|
||||||
stop_soon_quietly = 0;
|
|
||||||
|
|
||||||
/* We are now either at the "mapping complete" breakpoint (or somewhere
|
/* We are now either at the "mapping complete" breakpoint (or somewhere
|
||||||
else, a condition we aren't prepared to deal with anyway), so adjust
|
else, a condition we aren't prepared to deal with anyway), so adjust
|
||||||
@ -1051,7 +973,14 @@ solib_create_inferior_hook()
|
|||||||
warning ("shared library handler failed to disable breakpoint");
|
warning ("shared library handler failed to disable breakpoint");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* solib_add will call reinit_frame_cache.
|
||||||
|
But we are stopped in the startup code and we might not have symbols
|
||||||
|
for the startup code, so heuristic_proc_start could be called
|
||||||
|
and will put out an annoying warning.
|
||||||
|
Delaying the resetting of stop_soon_quietly until after symbol loading
|
||||||
|
suppresses the warning. */
|
||||||
solib_add ((char *) 0, 0, (struct target_ops *) 0);
|
solib_add ((char *) 0, 0, (struct target_ops *) 0);
|
||||||
|
stop_soon_quietly = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -2793,6 +2793,35 @@ parse_partial_symbols (objfile, section_offsets)
|
|||||||
objfile->ei.entry_file_lowpc = save_pst->textlow;
|
objfile->ei.entry_file_lowpc = save_pst->textlow;
|
||||||
objfile->ei.entry_file_highpc = save_pst->texthigh;
|
objfile->ei.entry_file_highpc = save_pst->texthigh;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* The objfile has its functions reordered if this partial symbol
|
||||||
|
table overlaps any other partial symbol table.
|
||||||
|
We cannot assume a reordered objfile if a partial symbol table
|
||||||
|
is contained within another partial symbol table, as partial symbol
|
||||||
|
tables for include files with executable code are contained
|
||||||
|
within the partial symbol table for the including source file,
|
||||||
|
and we do not want to flag the objfile reordered for these cases.
|
||||||
|
|
||||||
|
This strategy works well for Irix-5.2 shared libraries, but we
|
||||||
|
might have to use a more elaborate (and slower) algorithm for
|
||||||
|
other cases. */
|
||||||
|
save_pst = fdr_to_pst[f_idx].pst;
|
||||||
|
if (save_pst != NULL
|
||||||
|
&& save_pst->textlow != 0
|
||||||
|
&& !(objfile->flags & OBJF_REORDERED))
|
||||||
|
{
|
||||||
|
ALL_OBJFILE_PSYMTABS (objfile, pst)
|
||||||
|
{
|
||||||
|
if (save_pst != pst
|
||||||
|
&& save_pst->textlow >= pst->textlow
|
||||||
|
&& save_pst->textlow < pst->texthigh
|
||||||
|
&& save_pst->texthigh > pst->texthigh)
|
||||||
|
{
|
||||||
|
objfile->flags |= OBJF_REORDERED;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Now scan the FDRs for dependencies */
|
/* Now scan the FDRs for dependencies */
|
||||||
|
@ -343,6 +343,14 @@ struct objfile
|
|||||||
|
|
||||||
#define OBJF_SYMS (1 << 1) /* Have tried to read symbols */
|
#define OBJF_SYMS (1 << 1) /* Have tried to read symbols */
|
||||||
|
|
||||||
|
/* When an object file has its functions reordered (currently Irix-5.2
|
||||||
|
shared libraries exhibit this behaviour), we will need an expensive
|
||||||
|
algorithm to locate a partial symtab or symtab via an address.
|
||||||
|
To avoid this penalty for normal object files, we use this flag,
|
||||||
|
whose setting is determined upon symbol table read in. */
|
||||||
|
|
||||||
|
#define OBJF_REORDERED (2 << 1) /* Functions are reordered */
|
||||||
|
|
||||||
/* The object file that the main symbol table was loaded from (e.g. the
|
/* The object file that the main symbol table was loaded from (e.g. the
|
||||||
argument to the "symbol-file" or "file" command). */
|
argument to the "symbol-file" or "file" command). */
|
||||||
|
|
||||||
|
@ -572,7 +572,7 @@ sparc_pop_frame ()
|
|||||||
else if (fsr.regs[I7_REGNUM])
|
else if (fsr.regs[I7_REGNUM])
|
||||||
{
|
{
|
||||||
/* Return address in %i7 -- adjust it, then restore PC and NPC from it */
|
/* Return address in %i7 -- adjust it, then restore PC and NPC from it */
|
||||||
pc = PC_ADJUST (read_memory_integer (fsr.regs[I7_REGNUM], 4));
|
pc = PC_ADJUST ((CORE_ADDR) read_memory_integer (fsr.regs[I7_REGNUM], 4));
|
||||||
write_register (PC_REGNUM, pc);
|
write_register (PC_REGNUM, pc);
|
||||||
write_register (NPC_REGNUM, pc + 4);
|
write_register (NPC_REGNUM, pc + 4);
|
||||||
}
|
}
|
||||||
|
@ -620,11 +620,6 @@ symbol_file_add (name, from_tty, addr, mainline, mapped, readnow)
|
|||||||
}
|
}
|
||||||
|
|
||||||
new_symfile_objfile (objfile, mainline, from_tty);
|
new_symfile_objfile (objfile, mainline, from_tty);
|
||||||
|
|
||||||
/* Getting new symbols may change our opinion about what is
|
|
||||||
frameless. */
|
|
||||||
|
|
||||||
reinit_frame_cache ();
|
|
||||||
|
|
||||||
return (objfile);
|
return (objfile);
|
||||||
}
|
}
|
||||||
@ -710,6 +705,11 @@ symbol_file_command (args, from_tty)
|
|||||||
else
|
else
|
||||||
symbol_file_add (name, from_tty, (CORE_ADDR)text_relocation,
|
symbol_file_add (name, from_tty, (CORE_ADDR)text_relocation,
|
||||||
0, mapped, readnow);
|
0, mapped, readnow);
|
||||||
|
|
||||||
|
/* Getting new symbols may change our opinion about what is
|
||||||
|
frameless. */
|
||||||
|
reinit_frame_cache ();
|
||||||
|
|
||||||
set_initial_language ();
|
set_initial_language ();
|
||||||
}
|
}
|
||||||
argv++;
|
argv++;
|
||||||
@ -1025,6 +1025,10 @@ add_symbol_file_command (args, from_tty)
|
|||||||
error ("Not confirmed.");
|
error ("Not confirmed.");
|
||||||
|
|
||||||
symbol_file_add (name, 0, text_addr, 0, mapped, readnow);
|
symbol_file_add (name, 0, text_addr, 0, mapped, readnow);
|
||||||
|
|
||||||
|
/* Getting new symbols may change our opinion about what is
|
||||||
|
frameless. */
|
||||||
|
reinit_frame_cache ();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@ -1079,6 +1083,7 @@ reread_symbols ()
|
|||||||
struct section_offsets *offsets;
|
struct section_offsets *offsets;
|
||||||
int num_offsets;
|
int num_offsets;
|
||||||
int section_offsets_size;
|
int section_offsets_size;
|
||||||
|
char *obfd_filename;
|
||||||
|
|
||||||
printf_filtered ("`%s' has changed; re-reading symbols.\n",
|
printf_filtered ("`%s' has changed; re-reading symbols.\n",
|
||||||
objfile->name);
|
objfile->name);
|
||||||
@ -1100,9 +1105,10 @@ reread_symbols ()
|
|||||||
/* Clean up any state BFD has sitting around. We don't need
|
/* Clean up any state BFD has sitting around. We don't need
|
||||||
to close the descriptor but BFD lacks a way of closing the
|
to close the descriptor but BFD lacks a way of closing the
|
||||||
BFD without closing the descriptor. */
|
BFD without closing the descriptor. */
|
||||||
|
obfd_filename = bfd_get_filename (objfile->obfd);
|
||||||
if (!bfd_close (objfile->obfd))
|
if (!bfd_close (objfile->obfd))
|
||||||
error ("Can't close BFD for %s.", objfile->name);
|
error ("Can't close BFD for %s.", objfile->name);
|
||||||
objfile->obfd = bfd_openr (objfile->name, gnutarget);
|
objfile->obfd = bfd_openr (obfd_filename, gnutarget);
|
||||||
if (objfile->obfd == NULL)
|
if (objfile->obfd == NULL)
|
||||||
error ("Can't open %s to read symbols.", objfile->name);
|
error ("Can't open %s to read symbols.", objfile->name);
|
||||||
/* bfd_openr sets cacheable to true, which is what we want. */
|
/* bfd_openr sets cacheable to true, which is what we want. */
|
||||||
@ -1237,6 +1243,8 @@ deduce_language_from_filename (filename)
|
|||||||
return language_cplus;
|
return language_cplus;
|
||||||
else if (STREQ (c, ".ch") || STREQ (c, ".c186") || STREQ (c, ".c286"))
|
else if (STREQ (c, ".ch") || STREQ (c, ".c186") || STREQ (c, ".c286"))
|
||||||
return language_chill;
|
return language_chill;
|
||||||
|
else if (STREQ (c, ".f") || STREQ (c, ".F"))
|
||||||
|
return language_fortran;
|
||||||
else if (STREQ (c, ".mod"))
|
else if (STREQ (c, ".mod"))
|
||||||
return language_m2;
|
return language_m2;
|
||||||
else if (STREQ (c, ".s") || STREQ (c, ".S"))
|
else if (STREQ (c, ".s") || STREQ (c, ".S"))
|
||||||
@ -1603,7 +1611,7 @@ add_psymbol_to_list (name, namelength, namespace, class, list, val, language,
|
|||||||
SYMBOL_LANGUAGE (psym) = language;
|
SYMBOL_LANGUAGE (psym) = language;
|
||||||
PSYMBOL_NAMESPACE (psym) = namespace;
|
PSYMBOL_NAMESPACE (psym) = namespace;
|
||||||
PSYMBOL_CLASS (psym) = class;
|
PSYMBOL_CLASS (psym) = class;
|
||||||
SYMBOL_INIT_DEMANGLED_NAME (psym, &objfile->psymbol_obstack);
|
SYMBOL_INIT_LANGUAGE_SPECIFIC (psym, language);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Add a symbol with a CORE_ADDR value to a psymtab. */
|
/* Add a symbol with a CORE_ADDR value to a psymtab. */
|
||||||
@ -1637,7 +1645,7 @@ add_psymbol_addr_to_list (name, namelength, namespace, class, list, val,
|
|||||||
SYMBOL_LANGUAGE (psym) = language;
|
SYMBOL_LANGUAGE (psym) = language;
|
||||||
PSYMBOL_NAMESPACE (psym) = namespace;
|
PSYMBOL_NAMESPACE (psym) = namespace;
|
||||||
PSYMBOL_CLASS (psym) = class;
|
PSYMBOL_CLASS (psym) = class;
|
||||||
SYMBOL_INIT_DEMANGLED_NAME (psym, &objfile->psymbol_obstack);
|
SYMBOL_INIT_LANGUAGE_SPECIFIC (psym, language);
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif /* !INLINE_ADD_PSYMBOL */
|
#endif /* !INLINE_ADD_PSYMBOL */
|
||||||
|
324
gdb/symtab.c
324
gdb/symtab.c
@ -35,7 +35,6 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
|
|||||||
#include "demangle.h"
|
#include "demangle.h"
|
||||||
|
|
||||||
#include <obstack.h>
|
#include <obstack.h>
|
||||||
#include <assert.h>
|
|
||||||
|
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
@ -291,7 +290,6 @@ gdb_mangle_name (type, i, j)
|
|||||||
if (!is_destructor)
|
if (!is_destructor)
|
||||||
is_destructor = (strncmp(physname, "__dt", 4) == 0);
|
is_destructor = (strncmp(physname, "__dt", 4) == 0);
|
||||||
|
|
||||||
#ifndef GCC_MANGLE_BUG
|
|
||||||
if (is_destructor || is_full_physname_constructor)
|
if (is_destructor || is_full_physname_constructor)
|
||||||
{
|
{
|
||||||
mangled_name = (char*) xmalloc(strlen(physname)+1);
|
mangled_name = (char*) xmalloc(strlen(physname)+1);
|
||||||
@ -305,6 +303,13 @@ gdb_mangle_name (type, i, j)
|
|||||||
if (strcmp(buf, "__") == 0)
|
if (strcmp(buf, "__") == 0)
|
||||||
buf[0] = '\0';
|
buf[0] = '\0';
|
||||||
}
|
}
|
||||||
|
else if (newname != NULL && strchr (newname, '<') != NULL)
|
||||||
|
{
|
||||||
|
/* Template methods are fully mangled. */
|
||||||
|
sprintf (buf, "__%s%s", const_prefix, volatile_prefix);
|
||||||
|
newname = NULL;
|
||||||
|
len = 0;
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
sprintf (buf, "__%s%s%d", const_prefix, volatile_prefix, len);
|
sprintf (buf, "__%s%s%d", const_prefix, volatile_prefix, len);
|
||||||
@ -343,51 +348,6 @@ gdb_mangle_name (type, i, j)
|
|||||||
if (newname != NULL)
|
if (newname != NULL)
|
||||||
strcat (mangled_name, newname);
|
strcat (mangled_name, newname);
|
||||||
|
|
||||||
#else
|
|
||||||
|
|
||||||
if (is_constructor)
|
|
||||||
{
|
|
||||||
buf[0] = '\0';
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
sprintf (buf, "__%s%s", const_prefix, volatile_prefix);
|
|
||||||
}
|
|
||||||
|
|
||||||
mangled_name_len = ((is_constructor ? 0 : strlen (field_name))
|
|
||||||
+ strlen (buf) + strlen (physname) + 1);
|
|
||||||
|
|
||||||
/* Only needed for GNU-mangled names. ANSI-mangled names
|
|
||||||
work with the normal mechanisms. */
|
|
||||||
if (OPNAME_PREFIX_P (field_name))
|
|
||||||
{
|
|
||||||
char *opname;
|
|
||||||
opname = cplus_mangle_opname (field_name + 3, 0);
|
|
||||||
if (opname == NULL)
|
|
||||||
{
|
|
||||||
error ("No mangling for \"%s\"", field_name);
|
|
||||||
}
|
|
||||||
mangled_name_len += strlen (opname);
|
|
||||||
mangled_name = (char *) xmalloc (mangled_name_len);
|
|
||||||
|
|
||||||
strncpy (mangled_name, field_name, 3);
|
|
||||||
strcpy (mangled_name + 3, opname);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
mangled_name = (char *) xmalloc (mangled_name_len);
|
|
||||||
if (is_constructor)
|
|
||||||
{
|
|
||||||
mangled_name[0] = '\0';
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
strcpy (mangled_name, field_name);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
strcat (mangled_name, buf);
|
|
||||||
|
|
||||||
#endif
|
|
||||||
strcat (mangled_name, physname);
|
strcat (mangled_name, physname);
|
||||||
return (mangled_name);
|
return (mangled_name);
|
||||||
}
|
}
|
||||||
@ -405,7 +365,36 @@ find_pc_psymtab (pc)
|
|||||||
ALL_PSYMTABS (objfile, pst)
|
ALL_PSYMTABS (objfile, pst)
|
||||||
{
|
{
|
||||||
if (pc >= pst->textlow && pc < pst->texthigh)
|
if (pc >= pst->textlow && pc < pst->texthigh)
|
||||||
return (pst);
|
{
|
||||||
|
struct minimal_symbol *msymbol;
|
||||||
|
struct partial_symtab *tpst;
|
||||||
|
|
||||||
|
/* An objfile that has its functions reordered might have
|
||||||
|
many partial symbol tables containing the PC, but
|
||||||
|
we want the partial symbol table that contains the
|
||||||
|
function containing the PC. */
|
||||||
|
if (!(objfile->flags & OBJF_REORDERED))
|
||||||
|
return (pst);
|
||||||
|
|
||||||
|
msymbol = lookup_minimal_symbol_by_pc (pc);
|
||||||
|
if (msymbol == NULL)
|
||||||
|
return (pst);
|
||||||
|
|
||||||
|
for (tpst = pst; tpst != NULL; tpst = tpst->next)
|
||||||
|
{
|
||||||
|
if (pc >= tpst->textlow && pc < tpst->texthigh)
|
||||||
|
{
|
||||||
|
struct partial_symbol *p;
|
||||||
|
|
||||||
|
p = find_pc_psymbol (tpst, pc);
|
||||||
|
if (p != NULL
|
||||||
|
&& SYMBOL_VALUE_ADDRESS(p)
|
||||||
|
== SYMBOL_VALUE_ADDRESS (msymbol))
|
||||||
|
return (tpst);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (pst);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return (NULL);
|
return (NULL);
|
||||||
}
|
}
|
||||||
@ -590,9 +579,9 @@ found:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Check for the possibility of the symbol being a global function
|
/* Check for the possibility of the symbol being a function or
|
||||||
that is stored in one of the minimal symbol tables. Eventually, all
|
a mangled variable that is stored in one of the minimal symbol tables.
|
||||||
global symbols might be resolved in this way. */
|
Eventually, all global symbols might be resolved in this way. */
|
||||||
|
|
||||||
if (namespace == VAR_NAMESPACE)
|
if (namespace == VAR_NAMESPACE)
|
||||||
{
|
{
|
||||||
@ -600,10 +589,9 @@ found:
|
|||||||
if (msymbol != NULL)
|
if (msymbol != NULL)
|
||||||
{
|
{
|
||||||
s = find_pc_symtab (SYMBOL_VALUE_ADDRESS (msymbol));
|
s = find_pc_symtab (SYMBOL_VALUE_ADDRESS (msymbol));
|
||||||
/* If S is NULL, there are no debug symbols for this file.
|
|
||||||
Skip this stuff and check for matching static symbols below. */
|
|
||||||
if (s != NULL)
|
if (s != NULL)
|
||||||
{
|
{
|
||||||
|
/* This is a function which has a symtab for its address. */
|
||||||
bv = BLOCKVECTOR (s);
|
bv = BLOCKVECTOR (s);
|
||||||
block = BLOCKVECTOR_BLOCK (bv, GLOBAL_BLOCK);
|
block = BLOCKVECTOR_BLOCK (bv, GLOBAL_BLOCK);
|
||||||
sym = lookup_block_symbol (block, SYMBOL_NAME (msymbol),
|
sym = lookup_block_symbol (block, SYMBOL_NAME (msymbol),
|
||||||
@ -633,6 +621,18 @@ found:
|
|||||||
*symtab = s;
|
*symtab = s;
|
||||||
return sym;
|
return sym;
|
||||||
}
|
}
|
||||||
|
else if (MSYMBOL_TYPE (msymbol) != mst_text
|
||||||
|
&& MSYMBOL_TYPE (msymbol) != mst_file_text
|
||||||
|
&& !STREQ (name, SYMBOL_NAME (msymbol)))
|
||||||
|
{
|
||||||
|
/* This is a mangled variable, look it up by its
|
||||||
|
mangled name. */
|
||||||
|
return lookup_symbol (SYMBOL_NAME (msymbol), block,
|
||||||
|
namespace, is_a_field_of_this, symtab);
|
||||||
|
}
|
||||||
|
/* There are no debug symbols for this file, or we are looking
|
||||||
|
for an unmangled variable.
|
||||||
|
Try to find a matching static symbol below. */
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -765,7 +765,8 @@ lookup_partial_symbol (pst, name, global, namespace)
|
|||||||
while (top > bottom)
|
while (top > bottom)
|
||||||
{
|
{
|
||||||
center = bottom + (top - bottom) / 2;
|
center = bottom + (top - bottom) / 2;
|
||||||
assert (center < top);
|
if (!(center < top))
|
||||||
|
abort ();
|
||||||
if (!do_linear_search && SYMBOL_LANGUAGE (center) == language_cplus)
|
if (!do_linear_search && SYMBOL_LANGUAGE (center) == language_cplus)
|
||||||
{
|
{
|
||||||
do_linear_search = 1;
|
do_linear_search = 1;
|
||||||
@ -779,7 +780,8 @@ lookup_partial_symbol (pst, name, global, namespace)
|
|||||||
bottom = center + 1;
|
bottom = center + 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
assert (top == bottom);
|
if (!(top == bottom))
|
||||||
|
abort ();
|
||||||
while (STREQ (SYMBOL_NAME (top), name))
|
while (STREQ (SYMBOL_NAME (top), name))
|
||||||
{
|
{
|
||||||
if (SYMBOL_NAMESPACE (top) == namespace)
|
if (SYMBOL_NAMESPACE (top) == namespace)
|
||||||
@ -1003,8 +1005,15 @@ find_pc_symtab (pc)
|
|||||||
to deal with a case like symtab a is at 0x1000-0x2000 and 0x3000-0x4000
|
to deal with a case like symtab a is at 0x1000-0x2000 and 0x3000-0x4000
|
||||||
and symtab b is at 0x2000-0x3000. So the GLOBAL_BLOCK for a is from
|
and symtab b is at 0x2000-0x3000. So the GLOBAL_BLOCK for a is from
|
||||||
0x1000-0x4000, but for address 0x2345 we want to return symtab b.
|
0x1000-0x4000, but for address 0x2345 we want to return symtab b.
|
||||||
This is said to happen for the mips; it might be swifter to create
|
|
||||||
several symtabs with the same name like xcoff does (I'm not sure). */
|
This happens for native ecoff format, where code from included files
|
||||||
|
gets its own symtab. The symtab for the included file should have
|
||||||
|
been read in already via the dependency mechanism.
|
||||||
|
It might be swifter to create several symtabs with the same name
|
||||||
|
like xcoff does (I'm not sure).
|
||||||
|
|
||||||
|
It also happens for objfiles that have their functions reordered.
|
||||||
|
For these, the symtab we are looking for is not necessarily read in. */
|
||||||
|
|
||||||
ALL_SYMTABS (objfile, s)
|
ALL_SYMTABS (objfile, s)
|
||||||
{
|
{
|
||||||
@ -1015,6 +1024,18 @@ find_pc_symtab (pc)
|
|||||||
&& (distance == 0
|
&& (distance == 0
|
||||||
|| BLOCK_END (b) - BLOCK_START (b) < distance))
|
|| BLOCK_END (b) - BLOCK_START (b) < distance))
|
||||||
{
|
{
|
||||||
|
/* For an objfile that has its functions reordered,
|
||||||
|
find_pc_psymtab will find the proper partial symbol table
|
||||||
|
and we simply return its corresponding symtab. */
|
||||||
|
if (objfile->flags & OBJF_REORDERED)
|
||||||
|
{
|
||||||
|
ps = find_pc_psymtab (pc);
|
||||||
|
if (ps)
|
||||||
|
s = PSYMTAB_TO_SYMTAB (ps);
|
||||||
|
else
|
||||||
|
s = NULL;
|
||||||
|
return (s);
|
||||||
|
}
|
||||||
distance = BLOCK_END (b) - BLOCK_START (b);
|
distance = BLOCK_END (b) - BLOCK_START (b);
|
||||||
best_s = s;
|
best_s = s;
|
||||||
}
|
}
|
||||||
@ -1500,6 +1521,51 @@ find_pc_line_pc_range (pc, startptr, endptr)
|
|||||||
*endptr = sal.end;
|
*endptr = sal.end;
|
||||||
return sal.symtab != 0;
|
return sal.symtab != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Given a function symbol SYM, find the symtab and line for the start
|
||||||
|
of the function.
|
||||||
|
If the argument FUNFIRSTLINE is nonzero, we want the first line
|
||||||
|
of real code inside the function. */
|
||||||
|
|
||||||
|
static struct symtab_and_line
|
||||||
|
find_function_start_sal PARAMS ((struct symbol *sym, int));
|
||||||
|
|
||||||
|
static struct symtab_and_line
|
||||||
|
find_function_start_sal (sym, funfirstline)
|
||||||
|
struct symbol *sym;
|
||||||
|
int funfirstline;
|
||||||
|
{
|
||||||
|
CORE_ADDR pc;
|
||||||
|
struct symtab_and_line sal;
|
||||||
|
|
||||||
|
pc = BLOCK_START (SYMBOL_BLOCK_VALUE (sym));
|
||||||
|
if (funfirstline)
|
||||||
|
{
|
||||||
|
pc += FUNCTION_START_OFFSET;
|
||||||
|
SKIP_PROLOGUE (pc);
|
||||||
|
}
|
||||||
|
sal = find_pc_line (pc, 0);
|
||||||
|
|
||||||
|
#ifdef PROLOGUE_FIRSTLINE_OVERLAP
|
||||||
|
/* Convex: no need to suppress code on first line, if any */
|
||||||
|
sal.pc = pc;
|
||||||
|
#else
|
||||||
|
/* Check if SKIP_PROLOGUE left us in mid-line, and the next
|
||||||
|
line is still part of the same function. */
|
||||||
|
if (sal.pc != pc
|
||||||
|
&& BLOCK_START (SYMBOL_BLOCK_VALUE (sym)) <= sal.end
|
||||||
|
&& sal.end < BLOCK_END (SYMBOL_BLOCK_VALUE (sym)))
|
||||||
|
{
|
||||||
|
/* First pc of next line */
|
||||||
|
pc = sal.end;
|
||||||
|
/* Recalculate the line number (might not be N+1). */
|
||||||
|
sal = find_pc_line (pc, 0);
|
||||||
|
}
|
||||||
|
sal.pc = pc;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return sal;
|
||||||
|
}
|
||||||
|
|
||||||
/* If P is of the form "operator[ \t]+..." where `...' is
|
/* If P is of the form "operator[ \t]+..." where `...' is
|
||||||
some legitimate operator text, return a pointer to the
|
some legitimate operator text, return a pointer to the
|
||||||
@ -1752,7 +1818,8 @@ build_canonical_line_spec (sal, symname, canonical)
|
|||||||
FUNCTION may be an undebuggable function found in minimal symbol table.
|
FUNCTION may be an undebuggable function found in minimal symbol table.
|
||||||
|
|
||||||
If the argument FUNFIRSTLINE is nonzero, we want the first line
|
If the argument FUNFIRSTLINE is nonzero, we want the first line
|
||||||
of real code inside a function when a function is specified.
|
of real code inside a function when a function is specified, and it is
|
||||||
|
not OK to specify a variable or type to get its line number.
|
||||||
|
|
||||||
DEFAULT_SYMTAB specifies the file to use if none is specified.
|
DEFAULT_SYMTAB specifies the file to use if none is specified.
|
||||||
It defaults to current_source_symtab.
|
It defaults to current_source_symtab.
|
||||||
@ -1846,17 +1913,13 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line, canonical)
|
|||||||
|
|
||||||
if (**argptr == '*')
|
if (**argptr == '*')
|
||||||
{
|
{
|
||||||
if (**argptr == '*')
|
(*argptr)++;
|
||||||
{
|
|
||||||
(*argptr)++;
|
|
||||||
}
|
|
||||||
pc = parse_and_eval_address_1 (argptr);
|
pc = parse_and_eval_address_1 (argptr);
|
||||||
values.sals = (struct symtab_and_line *)
|
values.sals = (struct symtab_and_line *)
|
||||||
xmalloc (sizeof (struct symtab_and_line));
|
xmalloc (sizeof (struct symtab_and_line));
|
||||||
values.nelts = 1;
|
values.nelts = 1;
|
||||||
values.sals[0] = find_pc_line (pc, 0);
|
values.sals[0] = find_pc_line (pc, 0);
|
||||||
values.sals[0].pc = pc;
|
values.sals[0].pc = pc;
|
||||||
build_canonical_line_spec (values.sals, NULL, canonical);
|
|
||||||
return values;
|
return values;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1871,7 +1934,7 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line, canonical)
|
|||||||
{
|
{
|
||||||
if (p[0] == '<')
|
if (p[0] == '<')
|
||||||
{
|
{
|
||||||
while(!++p && *p != '>');
|
while(++p && *p != '>');
|
||||||
if (!p)
|
if (!p)
|
||||||
{
|
{
|
||||||
error ("non-matching '<' and '>' in command");
|
error ("non-matching '<' and '>' in command");
|
||||||
@ -1988,17 +2051,10 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line, canonical)
|
|||||||
|
|
||||||
if (sym && SYMBOL_CLASS (sym) == LOC_BLOCK)
|
if (sym && SYMBOL_CLASS (sym) == LOC_BLOCK)
|
||||||
{
|
{
|
||||||
/* Arg is the name of a function */
|
|
||||||
pc = BLOCK_START (SYMBOL_BLOCK_VALUE (sym));
|
|
||||||
if (funfirstline)
|
|
||||||
{
|
|
||||||
pc += FUNCTION_START_OFFSET;
|
|
||||||
SKIP_PROLOGUE (pc);
|
|
||||||
}
|
|
||||||
values.sals = (struct symtab_and_line *)xmalloc (sizeof (struct symtab_and_line));
|
values.sals = (struct symtab_and_line *)xmalloc (sizeof (struct symtab_and_line));
|
||||||
values.nelts = 1;
|
values.nelts = 1;
|
||||||
values.sals[0] = find_pc_line (pc, 0);
|
values.sals[0] = find_function_start_sal (sym,
|
||||||
values.sals[0].pc = (values.sals[0].end && values.sals[0].pc != pc) ? values.sals[0].end : pc;
|
funfirstline);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -2185,32 +2241,8 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line, canonical)
|
|||||||
if (SYMBOL_CLASS (sym) == LOC_BLOCK)
|
if (SYMBOL_CLASS (sym) == LOC_BLOCK)
|
||||||
{
|
{
|
||||||
/* Arg is the name of a function */
|
/* Arg is the name of a function */
|
||||||
pc = BLOCK_START (SYMBOL_BLOCK_VALUE (sym));
|
|
||||||
if (funfirstline)
|
|
||||||
{
|
|
||||||
pc += FUNCTION_START_OFFSET;
|
|
||||||
SKIP_PROLOGUE (pc);
|
|
||||||
}
|
|
||||||
val = find_pc_line (pc, 0);
|
|
||||||
#ifdef PROLOGUE_FIRSTLINE_OVERLAP
|
|
||||||
/* Convex: no need to suppress code on first line, if any */
|
|
||||||
val.pc = pc;
|
|
||||||
#else
|
|
||||||
/* Check if SKIP_PROLOGUE left us in mid-line, and the next
|
|
||||||
line is still part of the same function. */
|
|
||||||
if (val.pc != pc
|
|
||||||
&& BLOCK_START (SYMBOL_BLOCK_VALUE (sym)) <= val.end
|
|
||||||
&& val.end < BLOCK_END (SYMBOL_BLOCK_VALUE (sym)))
|
|
||||||
{
|
|
||||||
/* First pc of next line */
|
|
||||||
pc = val.end;
|
|
||||||
/* Recalculate the line number (might not be N+1). */
|
|
||||||
val = find_pc_line (pc, 0);
|
|
||||||
}
|
|
||||||
val.pc = pc;
|
|
||||||
#endif
|
|
||||||
values.sals = (struct symtab_and_line *)xmalloc (sizeof (struct symtab_and_line));
|
values.sals = (struct symtab_and_line *)xmalloc (sizeof (struct symtab_and_line));
|
||||||
values.sals[0] = val;
|
values.sals[0] = find_function_start_sal (sym, funfirstline);
|
||||||
values.nelts = 1;
|
values.nelts = 1;
|
||||||
|
|
||||||
/* Don't use the SYMBOL_LINE; if used at all it points to
|
/* Don't use the SYMBOL_LINE; if used at all it points to
|
||||||
@ -2228,23 +2260,29 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line, canonical)
|
|||||||
}
|
}
|
||||||
return values;
|
return values;
|
||||||
}
|
}
|
||||||
else if (SYMBOL_LINE (sym) != 0)
|
|
||||||
{
|
|
||||||
/* We know its line number. */
|
|
||||||
values.sals = (struct symtab_and_line *)
|
|
||||||
xmalloc (sizeof (struct symtab_and_line));
|
|
||||||
values.nelts = 1;
|
|
||||||
memset (&values.sals[0], 0, sizeof (values.sals[0]));
|
|
||||||
values.sals[0].symtab = sym_symtab;
|
|
||||||
values.sals[0].line = SYMBOL_LINE (sym);
|
|
||||||
return values;
|
|
||||||
}
|
|
||||||
else
|
else
|
||||||
/* This can happen if it is compiled with a compiler which doesn't
|
{
|
||||||
put out line numbers for variables. */
|
if (funfirstline)
|
||||||
/* FIXME: Shouldn't we just set .line and .symtab to zero and
|
error ("\"%s\" is not a function", copy);
|
||||||
return? For example, "info line foo" could print the address. */
|
else if (SYMBOL_LINE (sym) != 0)
|
||||||
error ("Line number not known for symbol \"%s\"", copy);
|
{
|
||||||
|
/* We know its line number. */
|
||||||
|
values.sals = (struct symtab_and_line *)
|
||||||
|
xmalloc (sizeof (struct symtab_and_line));
|
||||||
|
values.nelts = 1;
|
||||||
|
memset (&values.sals[0], 0, sizeof (values.sals[0]));
|
||||||
|
values.sals[0].symtab = sym_symtab;
|
||||||
|
values.sals[0].line = SYMBOL_LINE (sym);
|
||||||
|
return values;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
/* This can happen if it is compiled with a compiler which doesn't
|
||||||
|
put out line numbers for variables. */
|
||||||
|
/* FIXME: Shouldn't we just set .line and .symtab to zero
|
||||||
|
and return? For example, "info line foo" could print
|
||||||
|
the address. */
|
||||||
|
error ("Line number not known for symbol \"%s\"", copy);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
msymbol = lookup_minimal_symbol (copy, (struct objfile *) NULL);
|
msymbol = lookup_minimal_symbol (copy, (struct objfile *) NULL);
|
||||||
@ -2301,7 +2339,6 @@ decode_line_2 (sym_arr, nelts, funfirstline, canonical)
|
|||||||
char ***canonical;
|
char ***canonical;
|
||||||
{
|
{
|
||||||
struct symtabs_and_lines values, return_values;
|
struct symtabs_and_lines values, return_values;
|
||||||
register CORE_ADDR pc;
|
|
||||||
char *args, *arg1;
|
char *args, *arg1;
|
||||||
int i;
|
int i;
|
||||||
char *prompt;
|
char *prompt;
|
||||||
@ -2327,20 +2364,15 @@ decode_line_2 (sym_arr, nelts, funfirstline, canonical)
|
|||||||
{
|
{
|
||||||
if (sym_arr[i] && SYMBOL_CLASS (sym_arr[i]) == LOC_BLOCK)
|
if (sym_arr[i] && SYMBOL_CLASS (sym_arr[i]) == LOC_BLOCK)
|
||||||
{
|
{
|
||||||
/* Arg is the name of a function */
|
values.sals[i] = find_function_start_sal (sym_arr[i], funfirstline);
|
||||||
pc = BLOCK_START (SYMBOL_BLOCK_VALUE (sym_arr[i]));
|
printf_unfiltered ("[%d] %s at %s:%d\n",
|
||||||
if (funfirstline)
|
(i+2),
|
||||||
{
|
SYMBOL_SOURCE_NAME (sym_arr[i]),
|
||||||
pc += FUNCTION_START_OFFSET;
|
values.sals[i].symtab->filename,
|
||||||
SKIP_PROLOGUE (pc);
|
values.sals[i].line);
|
||||||
}
|
|
||||||
values.sals[i] = find_pc_line (pc, 0);
|
|
||||||
values.sals[i].pc = (values.sals[i].end && values.sals[i].pc != pc) ?
|
|
||||||
values.sals[i].end : pc;
|
|
||||||
printf_unfiltered("[%d] %s at %s:%d\n", (i+2), SYMBOL_SOURCE_NAME (sym_arr[i]),
|
|
||||||
values.sals[i].symtab->filename, values.sals[i].line);
|
|
||||||
}
|
}
|
||||||
else printf_unfiltered ("?HERE\n");
|
else
|
||||||
|
printf_unfiltered ("?HERE\n");
|
||||||
i++;
|
i++;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2652,13 +2684,20 @@ list_symbols (regexp, class, bpt, from_tty)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Here, we search through the minimal symbol tables for functions that
|
/* Here, we search through the minimal symbol tables for functions
|
||||||
match, and call find_pc_symtab on them to force their symbols to
|
and variables that match, and force their symbols to be read.
|
||||||
be read. The symbol will then be found during the scan of symtabs
|
This is in particular necessary for demangled variable names,
|
||||||
below. If find_pc_symtab fails, set found_misc so that we will
|
which are no longer put into the partial symbol tables.
|
||||||
rescan to print any matching symbols without debug info. */
|
The symbol will then be found during the scan of symtabs below.
|
||||||
|
|
||||||
if (class == 1)
|
For functions, find_pc_symtab should succeed if we have debug info
|
||||||
|
for the function, for variables we have to call lookup_symbol
|
||||||
|
to determine if the variable has debug info.
|
||||||
|
If the lookup fails, set found_misc so that we will rescan to print
|
||||||
|
any matching symbols without debug info.
|
||||||
|
*/
|
||||||
|
|
||||||
|
if (class == 0 || class == 1)
|
||||||
{
|
{
|
||||||
ALL_MSYMBOLS (objfile, msymbol)
|
ALL_MSYMBOLS (objfile, msymbol)
|
||||||
{
|
{
|
||||||
@ -2671,7 +2710,12 @@ list_symbols (regexp, class, bpt, from_tty)
|
|||||||
{
|
{
|
||||||
if (0 == find_pc_symtab (SYMBOL_VALUE_ADDRESS (msymbol)))
|
if (0 == find_pc_symtab (SYMBOL_VALUE_ADDRESS (msymbol)))
|
||||||
{
|
{
|
||||||
found_misc = 1;
|
if (class == 1
|
||||||
|
|| lookup_symbol (SYMBOL_NAME (msymbol),
|
||||||
|
(struct block *) NULL,
|
||||||
|
VAR_NAMESPACE,
|
||||||
|
0, (struct symtab **) NULL) == NULL)
|
||||||
|
found_misc = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -2724,14 +2768,18 @@ list_symbols (regexp, class, bpt, from_tty)
|
|||||||
same name but in different files. In order to
|
same name but in different files. In order to
|
||||||
set breakpoints on all of them, we must give
|
set breakpoints on all of them, we must give
|
||||||
both the file name and the function name to
|
both the file name and the function name to
|
||||||
break_command. */
|
break_command.
|
||||||
|
Quoting the symbol name gets rid of problems
|
||||||
|
with mangled symbol names that contain
|
||||||
|
CPLUS_MARKER characters. */
|
||||||
char *string =
|
char *string =
|
||||||
(char *) alloca (strlen (s->filename)
|
(char *) alloca (strlen (s->filename)
|
||||||
+ strlen (SYMBOL_NAME(sym))
|
+ strlen (SYMBOL_NAME(sym))
|
||||||
+ 2);
|
+ 4);
|
||||||
strcpy (string, s->filename);
|
strcpy (string, s->filename);
|
||||||
strcat (string, ":");
|
strcat (string, ":'");
|
||||||
strcat (string, SYMBOL_NAME(sym));
|
strcat (string, SYMBOL_NAME(sym));
|
||||||
|
strcat (string, "'");
|
||||||
break_command (string, from_tty);
|
break_command (string, from_tty);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -111,6 +111,16 @@ exec_close (quitting)
|
|||||||
|
|
||||||
if (exec_ops.to_sections)
|
if (exec_ops.to_sections)
|
||||||
{
|
{
|
||||||
|
/* Reflect to_sections freeing in current_target if it is
|
||||||
|
the exec target. Otherwise target_xfer_memory (eventually
|
||||||
|
called from clear_symtab_users) might access the freed
|
||||||
|
exec_ops.to_sections via the copy in current_target. */
|
||||||
|
if (current_target.to_sections == exec_ops.to_sections)
|
||||||
|
{
|
||||||
|
current_target.to_sections = NULL;
|
||||||
|
current_target.to_sections_end = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
free (exec_ops.to_sections);
|
free (exec_ops.to_sections);
|
||||||
exec_ops.to_sections = NULL;
|
exec_ops.to_sections = NULL;
|
||||||
exec_ops.to_sections_end = NULL;
|
exec_ops.to_sections_end = NULL;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user