COFF changes for dealing better with EPI 29K C compiler output.

* coffread.c (record_minimal_symbol):  Pass the minsym type to it.
Callers changed.
(coff_end_symtab):  Sort blocks if needed.  Complain if misordered.
(read_coff_symtab):  Move patch_opaque_types call from
coff_symfile_read.  Restrict it to symtabs from this objfile.
(process_coff_symbol: C_TPDEF):  Don't put ordinary foward
references on opaque type chain; just let coff_lookup_type handle 'em.
(decode_type):  Complain about tagndx values on
non-struct/union/enum types, which the EPI compiler tends to produce.

* symtab.c (list_symbols):  Make minimal symbol variable-finding work.

* tm-68k.h (FIX_CALL_DUMMY): Avoid alignment and byte order
dependency.

* elfread.c (elf_symfile_read):  Update bfd_elf_find_section
usage to match new prototype.  Include libbfd.h to get prototype.
This commit is contained in:
John Gilmore 1992-06-21 02:20:30 +00:00
parent 0cc37e2948
commit f70be3e45a
5 changed files with 493 additions and 181 deletions

View File

@ -1,3 +1,25 @@
Sat Jun 20 19:19:52 1992 John Gilmore (gnu at cygnus.com)
COFF changes for dealing better with EPI 29K C compiler output.
* coffread.c (record_minimal_symbol): Pass the minsym type to it.
Callers changed.
(coff_end_symtab): Sort blocks if needed. Complain if misordered.
(read_coff_symtab): Move patch_opaque_types call from
coff_symfile_read. Restrict it to symtabs from this objfile.
(process_coff_symbol: C_TPDEF): Don't put ordinary foward
references on opaque type chain; just let coff_lookup_type handle 'em.
(decode_type): Complain about tagndx values on
non-struct/union/enum types, which the EPI compiler tends to produce.
* symtab.c (list_symbols): Make minimal symbol variable-finding work.
* tm-68k.h (FIX_CALL_DUMMY): Avoid alignment and byte order
dependency.
* elfread.c (elf_symfile_read): Update bfd_elf_find_section
usage to match new prototype. Include libbfd.h to get prototype.
Sat Jun 20 16:28:39 1992 Fred Fish (fnf@cygnus.com)
* infcmd.c (jump_command): Use cleanups to avoid memory leaks.
@ -10,9 +32,6 @@ Fri Jun 19 19:06:41 1992 John Gilmore (gnu at cygnus.com)
* tm-29k.h (SDB_REG_TO_REGNUM): Add for EPI 29K C compiler.
* elfread.c (elf_symfile_read): Update bfd_elf_find_section
usage to match new prototype. Include libbfd.h to get prototype.
Fri Jun 19 15:30:15 1992 Stu Grossman (grossman at cygnus.com)
* configure.in, dbxread.c, hppa-coredep.c, hppa-pinsn.c,

View File

@ -183,6 +183,12 @@ struct complaint unexpected_type_complaint =
struct complaint bad_sclass_complaint =
{"Bad n_sclass for symbol %s", 0, 0};
struct complaint misordered_blocks_complaint =
{"Blocks out of order at address %x", 0, 0};
struct complaint tagndx_bad_complaint =
{"Symbol table entry for %s has bad tagndx value", 0, 0};
/* Simplified internal version of coff symbol table information */
struct coff_symbol {
@ -220,8 +226,8 @@ static struct symbol *
process_coff_symbol PARAMS ((struct coff_symbol *, union internal_auxent *,
struct objfile *));
static PTR
patch_opaque_types PARAMS ((struct objfile *, struct symtab *, PTR, PTR, PTR));
static void
patch_opaque_types PARAMS ((struct symtab *));
static void
patch_type PARAMS ((struct type *, struct type *));
@ -249,7 +255,7 @@ read_one_sym PARAMS ((struct coff_symbol *, struct internal_syment *,
union internal_auxent *));
static void
read_coff_symtab PARAMS ((int, int, struct objfile *));
read_coff_symtab PARAMS ((long, int, struct objfile *));
static void
find_linenos PARAMS ((bfd *, sec_ptr, PTR));
@ -267,7 +273,7 @@ static void
coff_symfile_finish PARAMS ((struct objfile *));
static void
record_minimal_symbol PARAMS ((char *, CORE_ADDR));
record_minimal_symbol PARAMS ((char *, CORE_ADDR, enum minimal_symbol_type));
static void
coff_end_symtab PARAMS ((struct objfile *));
@ -411,7 +417,7 @@ coff_finish_block (symbol, listhead, old_blocks, start, end, objfile)
for (next = *listhead; next; next = next1)
{
next1 = next->next;
free (next);
free ((PTR)next);
}
*listhead = 0;
@ -475,7 +481,7 @@ make_blockvector (objfile)
for (next = pending_blocks; next; next = next1)
{
next1 = next->next;
free (next);
free ((PTR)next);
}
pending_blocks = 0;
@ -521,7 +527,7 @@ coff_start_symtab ()
/* Initialize the source file line number information for this file. */
if (line_vector) /* Unlikely, but maybe possible? */
free (line_vector);
free ((PTR)line_vector);
line_vector_index = 0;
line_vector_length = 1000;
prev_line_number = -2; /* Force first line number to be explicit */
@ -576,19 +582,49 @@ coff_end_symtab (objfile)
/* Make a block for the local symbols within. */
coff_finish_block (cstk->name, &coff_local_symbols, cstk->old_blocks,
cstk->start_addr, cur_src_end_addr, objfile);
free (cstk);
free ((PTR)cstk);
}
/* Ignore a file that has no functions with real debugging info. */
if (pending_blocks == 0 && coff_file_symbols == 0 && coff_global_symbols == 0)
{
free (line_vector);
free ((PTR)line_vector);
line_vector = 0;
line_vector_length = -1;
last_source_file = 0;
return;
}
/* It is unfortunate that in amdcoff, pending blocks might not be ordered
in this stage. Especially, blocks for static functions will show up at
the end. We need to sort them, so tools like `find_pc_function' and
`find_pc_block' can work reliably. */
if (pending_blocks) {
/* FIXME! Remove this horrid bubble sort and use qsort!!! */
int swapped;
do {
struct pending_block *pb, *pbnext;
pb = pending_blocks, pbnext = pb->next;
swapped = 0;
while ( pbnext ) {
/* swap blocks if unordered! */
if (BLOCK_START(pb->block) < BLOCK_START(pbnext->block)) {
struct block *tmp = pb->block;
complain (&misordered_blocks_complaint, BLOCK_START (pb->block));
pb->block = pbnext->block;
pbnext->block = tmp;
swapped = 1;
}
pb = pbnext;
pbnext = pbnext->next;
}
} while (swapped);
}
/* Create the two top-level blocks for this file (STATIC_BLOCK and
GLOBAL_BLOCK). */
coff_finish_block (0, &coff_file_symbols, 0, cur_src_start_addr, cur_src_end_addr, objfile);
@ -621,9 +657,10 @@ coff_end_symtab (objfile)
}
static void
record_minimal_symbol (name, address)
record_minimal_symbol (name, address, type)
char *name;
CORE_ADDR address;
enum minimal_symbol_type type;
{
/* We don't want TDESC entry points in the minimal symbol table */
if (name[0] == '@') return;
@ -632,7 +669,7 @@ record_minimal_symbol (name, address)
is, so this guess is more useful than mst_unknown. */
prim_record_minimal_symbol (savestring (name, strlen (name)),
address,
(int)mst_text);
type);
}
/* coff_symfile_init ()
@ -669,7 +706,8 @@ coff_symfile_init (objfile)
init_entry_point_info (objfile);
/* Save the section number for the text section */
if (section = bfd_get_section_by_name(abfd,".text"))
section = bfd_get_section_by_name(abfd,".text");
if (section)
text_bfd_scnum = section->index;
else
text_bfd_scnum = -1;
@ -737,6 +775,7 @@ coff_symfile_read (objfile, addr, mainline)
int num_symbols;
int symtab_offset;
int stringtab_offset;
struct symtab *s;
info = (struct coff_symfile_info *) objfile -> sym_private;
symfile_bfd = abfd; /* Kludge for swap routines */
@ -770,7 +809,7 @@ coff_symfile_read (objfile, addr, mainline)
/* Read the line number table, all at once. */
info->min_lineno_offset = 0;
info->max_lineno_offset = 0;
bfd_map_over_sections (abfd, find_linenos, info);
bfd_map_over_sections (abfd, find_linenos, (PTR)info);
val = init_lineno (desc, info->min_lineno_offset,
info->max_lineno_offset - info->min_lineno_offset);
@ -784,21 +823,13 @@ coff_symfile_read (objfile, addr, mainline)
error ("\"%s\": can't get string table", name);
make_cleanup (free_stringtab, 0);
/* Position to read the symbol table. Do not read it all at once. */
val = lseek (desc, (long)symtab_offset, 0);
if (val < 0)
perror_with_name (name);
init_minimal_symbol_collection ();
make_cleanup (discard_minimal_symbols, 0);
/* Now that the executable file is positioned at symbol table,
process it and define symbols accordingly. */
read_coff_symtab (desc, num_symbols, objfile);
iterate_over_symtabs (patch_opaque_types, (PTR) NULL, (PTR) NULL,
(PTR) NULL);
read_coff_symtab ((long)symtab_offset, num_symbols, objfile);
/* Sort symbols alphabetically within each block. */
@ -811,8 +842,8 @@ coff_symfile_read (objfile, addr, mainline)
}
static void
coff_new_init (objfile)
struct objfile *objfile;
coff_new_init (ignore)
struct objfile *ignore;
{
/* Nothin' to do */
}
@ -839,12 +870,11 @@ coff_symfile_finish (objfile)
We read them one at a time using read_one_sym (). */
static void
read_coff_symtab (desc, nsyms, objfile)
int desc;
read_coff_symtab (symtab_offset, nsyms, objfile)
long symtab_offset;
int nsyms;
struct objfile *objfile;
{
int newfd; /* Avoid multiple closes on same desc */
FILE *stream;
register struct coff_context_stack *new;
struct coff_symbol coff_symbol;
@ -854,7 +884,8 @@ read_coff_symtab (desc, nsyms, objfile)
struct coff_symbol fcn_cs_saved;
static struct internal_syment fcn_sym_saved;
static union internal_auxent fcn_aux_saved;
struct symtab *s;
/* A .file is open. */
int in_source_file = 0;
int num_object_files = 0;
@ -862,18 +893,22 @@ read_coff_symtab (desc, nsyms, objfile)
/* Name of the current file. */
char *filestring = "";
int depth;
int fcn_first_line;
int fcn_last_line;
int fcn_start_addr;
long fcn_line_ptr;
int depth = 0;
int fcn_first_line = 0;
int fcn_last_line = 0;
int fcn_start_addr = 0;
long fcn_line_ptr = 0;
struct cleanup *old_chain;
int val;
stream = fopen (objfile->name, FOPEN_RB);
if (!stream)
perror_with_name(objfile->name);
newfd = dup (desc);
if (newfd == -1)
fatal ("Too many open files");
stream = fdopen (newfd, "r");
/* Position to read the symbol table. */
val = fseek (stream, (long)symtab_offset, 0);
if (val < 0)
perror_with_name (objfile->name);
/* These cleanups will be discarded below if we succeed. */
old_chain = make_cleanup (free_objfile, objfile);
@ -886,7 +921,7 @@ read_coff_symtab (desc, nsyms, objfile)
bzero (opaque_type_chain, sizeof opaque_type_chain);
if (type_vector) /* Get rid of previous one */
free (type_vector);
free ((PTR)type_vector);
type_vector_length = 160;
type_vector = (struct type **)
xmalloc (type_vector_length * sizeof (struct type *));
@ -928,7 +963,7 @@ read_coff_symtab (desc, nsyms, objfile)
/* record as a minimal symbol. if we get '.bf' next,
* then we undo this step
*/
record_minimal_symbol (cs->c_name, cs->c_value);
record_minimal_symbol (cs->c_name, cs->c_value, mst_text);
fcn_line_ptr = main_aux.x_sym.x_fcnary.x_fcn.x_lnnoptr;
fcn_start_addr = cs->c_value;
@ -1013,10 +1048,13 @@ read_coff_symtab (desc, nsyms, objfile)
record this symbol as a function in the minimal symbol table.
But why are absolute syms recorded as functions, anyway? */
if (cs->c_secnum <= text_bfd_scnum+1) {/* text or abs */
record_minimal_symbol (cs->c_name, cs->c_value);
record_minimal_symbol (cs->c_name, cs->c_value,
mst_text);
break;
} else {
cs->c_type = T_INT;
record_minimal_symbol (cs->c_name, cs->c_value,
mst_data);
break;
}
}
(void) process_coff_symbol (cs, &main_aux, objfile);
@ -1087,7 +1125,7 @@ read_coff_symtab (desc, nsyms, objfile)
);
coff_context_stack = 0;
within_function = 0;
free (new);
free ((PTR)new);
}
break;
@ -1121,7 +1159,7 @@ read_coff_symtab (desc, nsyms, objfile)
depth--;
coff_local_symbols = new->locals;
coff_context_stack = new->next;
free (new);
free ((PTR)new);
}
break;
@ -1134,6 +1172,12 @@ read_coff_symtab (desc, nsyms, objfile)
if (last_source_file)
coff_end_symtab (objfile);
fclose (stream);
/* Patch up any opaque types (references to types that are not defined
in the file where they are referenced, e.g. "struct foo *bar"). */
ALL_OBJFILE_SYMTABS (objfile, s)
patch_opaque_types (s);
discard_cleanups (old_chain);
current_objfile = NULL;
}
@ -1451,20 +1495,11 @@ patch_type (type, real_type)
}
/* Patch up all appropriate typedef symbols in the opaque_type_chains
so that they can be used to print out opaque data structures properly.
so that they can be used to print out opaque data structures properly. */
This is called via iterate_over_symtabs, and thus simply returns NULL
for each time it is called, to indicate that the iteration should
continue. */
/* ARGSUSED */
static PTR
patch_opaque_types (objfile, s, arg1, arg2, arg3)
struct objfile *objfile;
static void
patch_opaque_types (s)
struct symtab *s;
PTR arg1;
PTR arg2;
PTR arg3;
{
register struct block *b;
register int i;
@ -1522,7 +1557,6 @@ patch_opaque_types (objfile, s, arg1, arg2, arg3)
}
}
}
return (NULL);
}
static struct symbol *
@ -1670,9 +1704,14 @@ process_coff_symbol (cs, aux, objfile)
TYPE_NAME (SYMBOL_TYPE (sym)) = concat (SYMBOL_NAME (sym), NULL);
/* Keep track of any type which points to empty structured type,
so it can be filled from a definition from another file */
so it can be filled from a definition from another file. A
simple forward reference (TYPE_CODE_UNDEF) is not an
empty structured type, though; the forward references
work themselves out via the magic of coff_lookup_type. */
if (TYPE_CODE (SYMBOL_TYPE (sym)) == TYPE_CODE_PTR &&
TYPE_LENGTH (TYPE_TARGET_TYPE (SYMBOL_TYPE (sym))) == 0)
TYPE_LENGTH (TYPE_TARGET_TYPE (SYMBOL_TYPE (sym))) == 0 &&
TYPE_CODE (TYPE_TARGET_TYPE (SYMBOL_TYPE (sym))) !=
TYPE_CODE_UNDEF)
{
register int i = hashname (SYMBOL_NAME (sym));
@ -1765,11 +1804,23 @@ decode_type (cs, c_type, aux)
return type;
}
/* Reference to existing type */
/* Reference to existing type. This only occurs with the
struct, union, and enum types. EPI a29k coff
fakes us out by producing aux entries with a nonzero
x_tagndx for definitions of structs, unions, and enums, so we
have to check the c_sclass field. */
if (cs->c_naux > 0 && aux->x_sym.x_tagndx.l != 0)
{
type = coff_alloc_type (aux->x_sym.x_tagndx.l);
return type;
if (cs->c_sclass != C_STRTAG
&& cs->c_sclass != C_UNTAG
&& cs->c_sclass != C_ENTAG)
{
type = coff_alloc_type (aux->x_sym.x_tagndx.l);
return type;
} else {
complain (&tagndx_bad_complaint, cs->c_name);
/* And fall through to decode_base_type... */
}
}
return decode_base_type (cs, BTYPE (c_type), aux);

View File

@ -37,6 +37,7 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "elf/external.h"
#include "elf/internal.h"
#include "bfd.h"
#include "libbfd.h" /* For bfd_elf_find_section */
#include "symtab.h"
#include "symfile.h"
#include "objfiles.h"
@ -354,8 +355,9 @@ elf_symfile_read (objfile, addr, mainline)
sections visible to the caller. So we have to search the
ELF section table, not the BFD section table, for the string
table. */
Elf_Internal_Shdr *elf_sect = bfd_elf_find_section (abfd, ".stabstr");
struct elf_internal_shdr *elf_sect;
elf_sect = bfd_elf_find_section (abfd, ".stabstr");
if (elf_sect)
elfstab_build_psymtabs (objfile,
addr, /* We really pass the text seg addr, not the offset, here. */

View File

@ -32,6 +32,7 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "regex.h"
#include "expression.h"
#include "language.h"
#include "demangle.h"
#include <obstack.h>
#include <assert.h>
@ -44,11 +45,14 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
/* Prototypes for local functions */
static char *
expensive_mangler PARAMS ((const char *));
extern int
find_methods PARAMS ((struct type *, char *, char **, struct symbol **));
static void
completion_list_add_symbol PARAMS ((char *));
completion_list_add_symbol PARAMS ((char *, char *, int));
static struct symtabs_and_lines
decode_line_2 PARAMS ((struct symbol *[], int, int));
@ -107,6 +111,18 @@ const struct block *block_found;
char no_symtab_msg[] = "No symbol table is loaded. Use the \"file\" command.";
/* While the C++ support is still in flux, issue a possibly helpful hint on
using the new command completion feature on single quoted demangled C++
symbols. Remove when loose ends are cleaned up. FIXME -fnf */
void
cplusplus_hint (name)
char *name;
{
printf ("Hint: try '%s<TAB> or '%s<ESC-?>\n", name, name);
printf ("(Note leading single quote.)\n");
}
/* Check for a symtab of a specific name; first in symtabs, then in
psymtabs. *If* there is no '/' in the name, a match after a '/'
in the symtab filename will also work. */
@ -359,6 +375,20 @@ lookup_symbol (name, block, namespace, is_a_field_of_this, symtab)
register struct objfile *objfile;
register struct block *b;
register struct minimal_symbol *msymbol;
char *temp;
extern char *gdb_completer_word_break_characters;
/* If NAME contains any characters from gdb_completer_word_break_characters
then it is probably from a quoted name string. So check to see if it
has a C++ mangled equivalent, and if so, use the mangled equivalent. */
if (strpbrk (name, gdb_completer_word_break_characters) != NULL)
{
if ((temp = expensive_mangler (name)) != NULL)
{
name = temp;
}
}
/* Search specified block and its superiors. */
@ -466,29 +496,22 @@ found:
/* Test each minimal symbol to see if the minimal symbol's name
is a C++ mangled name that matches a user visible name. */
int matchcount = strlen (name);
char *demangled;
ALL_MSYMBOLS (objfile, msymbol)
{
if (strncmp (msymbol -> name, name, matchcount) == 0)
demangled = demangle_and_match (msymbol -> name, name, 0);
if (demangled != NULL)
{
demangled = cplus_demangle (msymbol -> name, -1);
if (demangled != NULL)
{
if (strcmp (demangled, name) == 0)
{
free (demangled);
goto found_msym;
}
free (demangled);
}
free (demangled);
goto found_msym;
}
}
msymbol = NULL; /* Not found */
}
found_msym:
if (msymbol != NULL && msymbol -> name != NULL)
if (msymbol != NULL)
{
s = find_pc_symtab (msymbol -> address);
/* If S is NULL, there are no debug symbols for this file.
@ -624,32 +647,29 @@ lookup_demangled_block_symbol (block, name)
register const struct block *block;
const char *name;
{
register int bot, top, inc;
register int bot, top;
register struct symbol *sym;
char *demangled;
bot = 0;
top = BLOCK_NSYMS (block);
inc = name[0];
while (bot < top)
{
sym = BLOCK_SYM (block, bot);
if (SYMBOL_NAME (sym)[0] == inc
&& SYMBOL_NAMESPACE (sym) == VAR_NAMESPACE)
if (SYMBOL_NAMESPACE (sym) == VAR_NAMESPACE)
{
char *demangled = cplus_demangle(SYMBOL_NAME (sym), -1);
demangled = demangle_and_match (SYMBOL_NAME (sym), name, 0);
if (demangled != NULL)
{
int cond = strcmp (demangled, name);
free (demangled);
if (!cond)
return sym;
return (sym);
}
}
bot++;
}
return 0;
return (NULL);
}
/* Look, in partial_symtab PST, for static mangled symbol NAME. */
@ -661,7 +681,7 @@ lookup_demangled_partial_symbol (pst, name)
{
struct partial_symbol *start, *psym;
int length = pst->n_static_syms;
register int inc = name[0];
char *demangled;
if (!length)
return (struct partial_symbol *) 0;
@ -669,21 +689,18 @@ lookup_demangled_partial_symbol (pst, name)
start = pst->objfile->static_psymbols.list + pst->statics_offset;
for (psym = start; psym < start + length; psym++)
{
if (SYMBOL_NAME (psym)[0] == inc
&& SYMBOL_NAMESPACE (psym) == VAR_NAMESPACE)
if (SYMBOL_NAMESPACE (psym) == VAR_NAMESPACE)
{
char *demangled = cplus_demangle(SYMBOL_NAME (psym), -1);
demangled = demangle_and_match (SYMBOL_NAME (psym), name, 0);
if (demangled != NULL)
{
int cond = strcmp (demangled, name);
free (demangled);
if (!cond)
return psym;
return (psym);
}
}
}
return (struct partial_symbol *) 0;
return (NULL);
}
/* Look, in partial_symtab PST, for symbol NAME. Check the global
@ -1344,7 +1361,7 @@ find_methods (t, name, physnames, sym_arr)
else
{
fputs_filtered("(Cannot find method ", stdout);
fputs_demangled(phys_name, stdout, 0);
fputs_demangled(phys_name, stdout, DMGL_PARAMS);
fputs_filtered(" - possibly inlined.)\n", stdout);
}
}
@ -1415,6 +1432,8 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line)
struct symbol **sym_arr;
struct type *t;
char **physnames;
char *saved_arg = *argptr;
extern char *gdb_completer_quote_characters;
/* Defaults have defaults. */
@ -1424,11 +1443,27 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line)
default_line = current_source_line;
}
/* See if arg is *PC */
if (**argptr == '*')
/* Check to see if *ARGPTR points to a string that has been quoted with
gdb_completer_quote_characters. If so, P will be left pointing at
someplace other than *ARGPTR */
if (((p = skip_quoted (*argptr)) != *argptr) &&
((*(p - 1) != **argptr) ||
(strchr (gdb_completer_quote_characters, **argptr) == NULL)))
{
(*argptr)++;
/* Not quoted symbol string specification, reset P */
p = *argptr;
}
/* See if arg is *PC or '<some symbol specifier string>' */
if ((**argptr == '*') || (p != *argptr))
{
if (**argptr == '*')
{
(*argptr)++;
}
pc = parse_and_eval_address_1 (argptr);
values.sals = (struct symtab_and_line *)
xmalloc (sizeof (struct symtab_and_line));
@ -1488,7 +1523,11 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line)
tmp[q1 - q] = '\0';
opname = cplus_mangle_opname (tmp, 1);
if (opname == NULL)
error ("No mangling for \"%s\"", tmp);
{
warning ("no mangling for \"%s\"", tmp);
cplusplus_hint (saved_arg);
return_to_top_level ();
}
copy = (char*) alloca (3 + strlen(opname));
sprintf (copy, "__%s", opname);
p = q1;
@ -1566,16 +1605,23 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line)
else
tmp = copy;
if (tmp[0] == '~')
error ("The class `%s' does not have destructor defined",
sym_class->name);
warning ("the class `%s' does not have destructor defined",
sym_class->name);
else
error ("The class %s does not have any method named %s",
sym_class->name, tmp);
warning ("the class %s does not have any method named %s",
sym_class->name, tmp);
cplusplus_hint (saved_arg);
return_to_top_level ();
}
}
else
/* The quotes are important if copy is empty. */
error("No class, struct, or union named \"%s\"", copy );
{
/* The quotes are important if copy is empty. */
warning ("can't find class, struct, or union named \"%s\"",
copy);
cplusplus_hint (saved_arg);
return_to_top_level ();
}
}
/* end of C++ */
@ -1669,11 +1715,21 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line)
/* Arg token is not digits => try it as a variable name
Find the next token (everything up to end or next whitespace). */
p = *argptr;
while (*p && *p != ' ' && *p != '\t' && *p != ',') p++;
p = skip_quoted (*argptr);
copy = (char *) alloca (p - *argptr + 1);
bcopy (*argptr, copy, p - *argptr);
copy[p - *argptr] = 0;
copy[p - *argptr] = '\0';
if ((copy[0] == copy [p - *argptr - 1])
&& strchr (gdb_completer_quote_characters, copy[0]) != NULL)
{
char *temp;
copy [p - *argptr - 1] = '\0';
copy++;
if ((temp = expensive_mangler (copy)) != NULL)
{
copy = temp;
}
}
while (*p == ' ' || *p == '\t') p++;
*argptr = p;
@ -1757,7 +1813,7 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line)
!have_partial_symbols () && !have_minimal_symbols ())
error (no_symtab_msg);
error ("Function %s not defined.", copy);
error ("Function \"%s\" not defined.", copy);
return values; /* for lint */
}
@ -1882,7 +1938,6 @@ output_source_filename (name, first)
char *name;
int *first;
{
static unsigned int column;
/* Table of files printed so far. Since a single source file can
result in several partial symbol tables, we need to avoid printing
it more than once. Note: if some of the psymtabs are read in and
@ -1923,27 +1978,15 @@ output_source_filename (name, first)
if (*first)
{
column = 0;
*first = 0;
}
else
{
printf_filtered (",");
column++;
printf_filtered (", ");
}
if (column != 0 && column + strlen (name) >= 70)
{
printf_filtered ("\n");
column = 0;
}
else if (column != 0)
{
printf_filtered (" ");
column++;
}
wrap_here ("");
fputs_filtered (name, stdout);
column += strlen (name);
}
static void
@ -1984,17 +2027,17 @@ sources_info (ignore, from_tty)
}
static int
name_match(name)
name_match (name)
char *name;
{
char *demangled = cplus_demangle(name, -1);
char *demangled = cplus_demangle (name, 0);
if (demangled != NULL)
{
int cond = re_exec (demangled);
free (demangled);
return cond;
return (cond);
}
return re_exec(name);
return (re_exec (name));
}
#define NAME_MATCH(NAME) name_match(NAME)
@ -2245,8 +2288,8 @@ list_symbols (regexp, class, bpt)
if (regexp == 0 || NAME_MATCH (msymbol -> name))
{
/* Functions: Look up by address. */
if (class != 1 &&
(find_pc_symtab (msymbol -> address) != NULL))
if (class != 1 ||
(0 == find_pc_symtab (msymbol -> address)))
{
/* Variables/Absolutes: Look up by name */
if (lookup_symbol (msymbol -> name,
@ -2329,51 +2372,79 @@ contained_in (a, b)
/* Helper routine for make_symbol_completion_list. */
int return_val_size, return_val_index;
char **return_val;
static int return_val_size;
static int return_val_index;
static char **return_val;
/* Test to see if the symbol specified by SYMNAME (or it's demangled
equivalent) matches TEXT in the first TEXT_LEN characters. If so,
add it to the current completion list. */
static void
completion_list_add_symbol (symname)
completion_list_add_symbol (symname, text, text_len)
char *symname;
char *text;
int text_len;
{
if (return_val_index + 3 > return_val_size)
return_val = (char **) xrealloc ((char *) return_val,
(return_val_size *= 2) * sizeof (char *));
return_val[return_val_index] =
(char *)xmalloc (1 + strlen (symname));
strcpy (return_val[return_val_index], symname);
return_val[++return_val_index] = (char *)NULL;
char *demangled;
int newsize;
/* First see if SYMNAME is a C++ mangled name, and if so, use the
demangled name instead, including any parameters. */
if ((demangled = cplus_demangle (symname, DMGL_PARAMS | DMGL_ANSI)) != NULL)
{
symname = demangled;
}
/* If we have a match for a completion, then add SYMNAME to the current
list of matches. Note that we always make a copy of the string, even
if it is one that was returned from cplus_demangle and is already
in malloc'd memory. */
if (strncmp (symname, text, text_len) == 0)
{
if (return_val_index + 3 > return_val_size)
{
newsize = (return_val_size *= 2) * sizeof (char *);
return_val = (char **) xrealloc ((char *) return_val, newsize);
}
return_val[return_val_index++] = savestring (symname, strlen (symname));
return_val[return_val_index] = NULL;
}
if (demangled != NULL)
{
free (demangled);
}
}
/* Return a NULL terminated array of all symbols (regardless of class) which
begin by matching TEXT. If the answer is no symbols, then the return value
is an array which contains only a NULL pointer.
Problem: All of the symbols have to be copied because readline
frees them. I'm not going to worry about this; hopefully there
won't be that many. */
Problem: All of the symbols have to be copied because readline frees them.
I'm not going to worry about this; hopefully there won't be that many. */
char **
make_symbol_completion_list (text)
char *text;
{
register struct symbol *sym;
register struct symtab *s;
register struct partial_symtab *ps;
register struct minimal_symbol *msymbol;
register struct objfile *objfile;
register struct block *b, *surrounding_static_block = 0;
register int i, j;
int text_len;
struct partial_symbol *psym;
int text_len = strlen (text);
text_len = strlen (text);
return_val_size = 100;
return_val_index = 0;
return_val =
(char **)xmalloc ((1 + return_val_size) *sizeof (char *));
return_val[0] = (char *)NULL;
return_val = (char **) xmalloc ((return_val_size + 1) * sizeof (char *));
return_val[0] = NULL;
/* Look through the partial symtabs for all symbols which begin
by matching TEXT. Add each one that you find to the list. */
@ -2389,9 +2460,9 @@ make_symbol_completion_list (text)
+ ps->n_global_syms);
psym++)
{
QUIT; /* If interrupted, then quit. */
if ((strncmp (SYMBOL_NAME (psym), text, text_len) == 0))
completion_list_add_symbol (SYMBOL_NAME (psym));
/* If interrupted, then quit. */
QUIT;
completion_list_add_symbol (SYMBOL_NAME (psym), text, text_len);
}
for (psym = objfile->static_psymbols.list + ps->statics_offset;
@ -2400,8 +2471,7 @@ make_symbol_completion_list (text)
psym++)
{
QUIT;
if ((strncmp (SYMBOL_NAME (psym), text, text_len) == 0))
completion_list_add_symbol (SYMBOL_NAME (psym));
completion_list_add_symbol (SYMBOL_NAME (psym), text, text_len);
}
}
@ -2412,14 +2482,151 @@ make_symbol_completion_list (text)
ALL_MSYMBOLS (objfile, msymbol)
{
if (strncmp (text, msymbol -> name, text_len) == 0)
{
completion_list_add_symbol (msymbol -> name);
}
QUIT;
completion_list_add_symbol (msymbol -> name, text, text_len);
}
/* Search upwards from currently selected frame (so that we can
complete on local vars. */
for (b = get_selected_block (); b != NULL; b = BLOCK_SUPERBLOCK (b))
{
if (!BLOCK_SUPERBLOCK (b))
{
surrounding_static_block = b; /* For elmin of dups */
}
/* Also catch fields of types defined in this places which match our
text string. Only complete on types visible from current context. */
for (i = 0; i < BLOCK_NSYMS (b); i++)
{
sym = BLOCK_SYM (b, i);
completion_list_add_symbol (SYMBOL_NAME (sym), text, text_len);
if (SYMBOL_CLASS (sym) == LOC_TYPEDEF)
{
struct type *t = SYMBOL_TYPE (sym);
enum type_code c = TYPE_CODE (t);
if (c == TYPE_CODE_UNION || c == TYPE_CODE_STRUCT)
{
for (j = TYPE_N_BASECLASSES (t); j < TYPE_NFIELDS (t); j++)
{
if (TYPE_FIELD_NAME (t, j))
{
completion_list_add_symbol (TYPE_FIELD_NAME (t, j),
text, text_len);
}
}
}
}
}
}
/* Go through the symtabs and check the externs and statics for
symbols which match. */
ALL_SYMTABS (objfile, s)
{
QUIT;
b = BLOCKVECTOR_BLOCK (BLOCKVECTOR (s), GLOBAL_BLOCK);
for (i = 0; i < BLOCK_NSYMS (b); i++)
{
sym = BLOCK_SYM (b, i);
completion_list_add_symbol (SYMBOL_NAME (sym), text, text_len);
}
}
ALL_SYMTABS (objfile, s)
{
QUIT;
b = BLOCKVECTOR_BLOCK (BLOCKVECTOR (s), STATIC_BLOCK);
/* Don't do this block twice. */
if (b == surrounding_static_block) continue;
for (i = 0; i < BLOCK_NSYMS (b); i++)
{
sym = BLOCK_SYM (b, i);
completion_list_add_symbol (SYMBOL_NAME (sym), text, text_len);
}
}
return (return_val);
}
/* Find a mangled symbol that corresponds to LOOKFOR using brute force.
Basically we go munging through available symbols, demangling each one,
looking for a match on the demangled result. */
static char *
expensive_mangler (lookfor)
const char *lookfor;
{
register struct symbol *sym;
register struct symtab *s;
register struct partial_symtab *ps;
register struct minimal_symbol *msymbol;
register struct objfile *objfile;
register struct block *b, *surrounding_static_block = 0;
register int i, j;
struct partial_symbol *psym;
char *demangled;
/* Look through the partial symtabs for a symbol that matches */
ALL_PSYMTABS (objfile, ps)
{
/* If the psymtab's been read in we'll get it when we search
through the blockvector. */
if (ps->readin) continue;
for (psym = objfile->global_psymbols.list + ps->globals_offset;
psym < (objfile->global_psymbols.list + ps->globals_offset
+ ps->n_global_syms);
psym++)
{
QUIT; /* If interrupted, then quit. */
demangled = demangle_and_match (SYMBOL_NAME (psym), lookfor,
DMGL_PARAMS | DMGL_ANSI);
if (demangled != NULL)
{
free (demangled);
return (SYMBOL_NAME (psym));
}
}
for (psym = objfile->static_psymbols.list + ps->statics_offset;
psym < (objfile->static_psymbols.list + ps->statics_offset
+ ps->n_static_syms);
psym++)
{
QUIT;
demangled = demangle_and_match (SYMBOL_NAME (psym), lookfor,
DMGL_PARAMS | DMGL_ANSI);
if (demangled != NULL)
{
free (demangled);
return (SYMBOL_NAME (psym));
}
}
}
/* Scan through the misc symbol vectors looking for a match. */
ALL_MSYMBOLS (objfile, msymbol)
{
QUIT;
demangled = demangle_and_match (msymbol -> name, lookfor,
DMGL_PARAMS | DMGL_ANSI);
if (demangled != NULL)
{
free (demangled);
return (msymbol -> name);
}
}
/* Search upwards from currently selected frame looking for a match */
for (b = get_selected_block (); b; b = BLOCK_SUPERBLOCK (b))
{
if (!BLOCK_SUPERBLOCK (b))
@ -2430,21 +2637,37 @@ make_symbol_completion_list (text)
from current context. */
for (i = 0; i < BLOCK_NSYMS (b); i++)
{
register struct symbol *sym = BLOCK_SYM (b, i);
if (!strncmp (SYMBOL_NAME (sym), text, text_len))
completion_list_add_symbol (SYMBOL_NAME (sym));
sym = BLOCK_SYM (b, i);
demangled = demangle_and_match (SYMBOL_NAME (sym), lookfor,
DMGL_PARAMS | DMGL_ANSI);
if (demangled != NULL)
{
free (demangled);
return (SYMBOL_NAME (sym));
}
if (SYMBOL_CLASS (sym) == LOC_TYPEDEF)
{
struct type *t = SYMBOL_TYPE (sym);
enum type_code c = TYPE_CODE (t);
if (c == TYPE_CODE_UNION || c == TYPE_CODE_STRUCT)
for (j = TYPE_N_BASECLASSES (t); j < TYPE_NFIELDS (t); j++)
if (TYPE_FIELD_NAME (t, j) &&
!strncmp (TYPE_FIELD_NAME (t, j), text, text_len))
completion_list_add_symbol (TYPE_FIELD_NAME (t, j));
{
for (j = TYPE_N_BASECLASSES (t); j < TYPE_NFIELDS (t); j++)
{
if (TYPE_FIELD_NAME (t, j))
{
demangled =
demangle_and_match (TYPE_FIELD_NAME (t, j),
lookfor,
DMGL_PARAMS | DMGL_ANSI);
if (demangled != NULL)
{
free (demangled);
return (TYPE_FIELD_NAME (t, j));
}
}
}
}
}
}
}
@ -2454,27 +2677,43 @@ make_symbol_completion_list (text)
ALL_SYMTABS (objfile, s)
{
QUIT;
b = BLOCKVECTOR_BLOCK (BLOCKVECTOR (s), GLOBAL_BLOCK);
for (i = 0; i < BLOCK_NSYMS (b); i++)
if (!strncmp (SYMBOL_NAME (BLOCK_SYM (b, i)), text, text_len))
completion_list_add_symbol (SYMBOL_NAME (BLOCK_SYM (b, i)));
{
sym = BLOCK_SYM (b, i);
demangled = demangle_and_match (SYMBOL_NAME (sym), lookfor,
DMGL_PARAMS | DMGL_ANSI);
if (demangled != NULL)
{
free (demangled);
return (SYMBOL_NAME (sym));
}
}
}
ALL_SYMTABS (objfile, s)
{
QUIT;
b = BLOCKVECTOR_BLOCK (BLOCKVECTOR (s), STATIC_BLOCK);
/* Don't do this block twice. */
if (b == surrounding_static_block) continue;
for (i = 0; i < BLOCK_NSYMS (b); i++)
if (!strncmp (SYMBOL_NAME (BLOCK_SYM (b, i)), text, text_len))
completion_list_add_symbol (SYMBOL_NAME (BLOCK_SYM (b, i)));
{
sym = BLOCK_SYM (b, i);
demangled = demangle_and_match (SYMBOL_NAME (sym), lookfor,
DMGL_PARAMS | DMGL_ANSI);
if (demangled != NULL)
{
free (demangled);
return (SYMBOL_NAME (sym));
}
}
}
return (return_val);
return (NULL);
}
#if 0
/* Add the type of the symbol sym to the type of the current

View File

@ -501,11 +501,12 @@ extern const struct ext_format ext_format_68881;
#endif /* HAVE_68881 */
/* Insert the specified number of args and function address
into a call sequence of the above form stored at DUMMYNAME. */
into a call sequence of the above form stored at DUMMYNAME.
We use the BFD routines to store a big-endian value of known size. */
#define FIX_CALL_DUMMY(dummyname, pc, fun, nargs, args, type, gcc_p) \
{ *(int *)((char *) dummyname + CALL_DUMMY_START_OFFSET + 2) = fun; \
*(int *)((char *) dummyname + CALL_DUMMY_START_OFFSET + 8) = nargs * 4; }
{ _do_putb32 (fun, (char *) dummyname + CALL_DUMMY_START_OFFSET + 2); \
_do_putb32 (nargs*4, (char *) dummyname + CALL_DUMMY_START_OFFSET + 8); }
/* Push an empty stack frame, to record the current PC, etc. */