From 0f552c5fc6ed8ddf060a01c97cbef7c0c890ffe4 Mon Sep 17 00:00:00 2001 From: John Gilmore Date: Tue, 30 Jun 1992 08:53:28 +0000 Subject: [PATCH] * buildsym.c (scan_file_globals): Beware the null file. Fix from Jim Williams. * stack.c (return_command): Evaluate expression *before* popping off the stack frames! Fix inspired by Jim Williams. (up_silently_command, down_silently_command): No sel frame is error. * defs.h (memcpy, memset): Conditionalize decls on #ifndef MEM_FNS_DECLARED, since DECstation differs. (alloca): Break out the STDC and non-STDC alloca cases, to make it work on old preprocessors as well as "picky ANSI" ones. * xm-mips.h (memcpy, memset): Declare, and set MEM_FNS_DECLARED. * mips-tdep.c (heuristic_proc_start): Zero arg produces zero. * utils.c (fputs_demangled): Rename SLOP since DECstation system header files define it! --- gdb/ChangeLog | 17 ++++++++ gdb/buildsym.c | 3 ++ gdb/defs.h | 10 ++++- gdb/mips-tdep.c | 108 ++++++++++++++++++++++-------------------------- gdb/stack.c | 17 ++++++-- gdb/utils.c | 6 +-- gdb/xm-mips.h | 6 +++ 7 files changed, 102 insertions(+), 65 deletions(-) diff --git a/gdb/ChangeLog b/gdb/ChangeLog index 2fb16a7fe94..251f9b558db 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,5 +1,22 @@ Mon Jun 29 18:30:57 1992 John Gilmore (gnu at cygnus.com) + * buildsym.c (scan_file_globals): Beware the null file. + Fix from Jim Williams. + + * stack.c (return_command): Evaluate expression *before* popping + off the stack frames! Fix inspired by Jim Williams. + (up_silently_command, down_silently_command): No sel frame is error. + + * defs.h (memcpy, memset): Conditionalize decls on + #ifndef MEM_FNS_DECLARED, since DECstation differs. + (alloca): Break out the STDC and non-STDC alloca cases, to make + it work on old preprocessors as well as "picky ANSI" ones. + * xm-mips.h (memcpy, memset): Declare, and set MEM_FNS_DECLARED. + + * mips-tdep.c (heuristic_proc_start): Zero arg produces zero. + * utils.c (fputs_demangled): Rename SLOP since DECstation system + header files define it! + * tm-29k.h (BREAKPOINT): Allow it to be overridden with -D. Mon Jun 29 16:30:25 1992 Fred Fish (fnf@cygnus.com) diff --git a/gdb/buildsym.c b/gdb/buildsym.c index bf8cdda929e..e9ca175d3ab 100644 --- a/gdb/buildsym.c +++ b/gdb/buildsym.c @@ -985,6 +985,9 @@ scan_file_globals (objfile) struct minimal_symbol *msymbol; struct symbol *sym, *prev; + if (objfile->msymbols == 0) /* Beware the null file. */ + return; + for (msymbol = objfile -> msymbols; msymbol -> name != NULL; msymbol++) { QUIT; diff --git a/gdb/defs.h b/gdb/defs.h index a4b0a23f731..1190f058c59 100644 --- a/gdb/defs.h +++ b/gdb/defs.h @@ -664,8 +664,10 @@ qsort PARAMS ((void *base, size_t nmemb, /* 4.10.5.2 */ size_t size, int (*comp)(const void *, const void *))); +#ifndef MEM_FNS_DECLARED /* Some non-ANSI use void *, not char *. */ extern PTR memcpy PARAMS ((void *, const void *, size_t)); /* 4.11.2.1 */ +#endif extern int memcmp PARAMS ((const void *, const void *, size_t)); /* 4.11.4.1 */ @@ -682,8 +684,10 @@ strstr PARAMS ((const char *, const char *)); /* 4.11.5.7 */ extern char * strtok PARAMS ((char *, const char *)); /* 4.11.5.8 */ +#ifndef MEM_FNS_DECLARED /* Some non-ANSI use void *, not char *. */ extern PTR memset PARAMS ((void *, int, size_t)); /* 4.11.6.1 */ +#endif extern char * strerror PARAMS ((int)); /* 4.11.6.2 */ @@ -696,7 +700,11 @@ strerror PARAMS ((int)); /* 4.11.6.2 */ # ifdef sparc # include /* NOTE: Doesn't declare alloca() */ # endif - extern PTR alloca PARAMS ((size_t)); +# ifdef __STDC__ + extern void *alloca (size_t); +# else /* __STDC__ */ + extern char *alloca (); +# endif # endif #endif diff --git a/gdb/mips-tdep.c b/gdb/mips-tdep.c index ef221018a8a..c7e65475672 100644 --- a/gdb/mips-tdep.c +++ b/gdb/mips-tdep.c @@ -61,19 +61,19 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include -#define PROC_LOW_ADDR(proc) ((proc)->adr) /* least address */ -#define PROC_HIGH_ADDR(proc) ((proc)->pad2) /* upper address bound */ -#define PROC_FRAME_OFFSET(proc) ((proc)->framesize) -#define PROC_FRAME_REG(proc) ((proc)->framereg) -#define PROC_REG_MASK(proc) ((proc)->regmask) -#define PROC_FREG_MASK(proc) ((proc)->fregmask) -#define PROC_REG_OFFSET(proc) ((proc)->regoffset) -#define PROC_FREG_OFFSET(proc) ((proc)->fregoffset) -#define PROC_PC_REG(proc) ((proc)->pcreg) -#define PROC_SYMBOL(proc) (*(struct symbol**)&(proc)->isym) +#define PROC_LOW_ADDR(proc) ((proc)->pdr.adr) /* least address */ +#define PROC_HIGH_ADDR(proc) ((proc)->pdr.iline) /* upper address bound */ +#define PROC_FRAME_OFFSET(proc) ((proc)->pdr.frameoffset) +#define PROC_FRAME_REG(proc) ((proc)->pdr.framereg) +#define PROC_REG_MASK(proc) ((proc)->pdr.regmask) +#define PROC_FREG_MASK(proc) ((proc)->pdr.fregmask) +#define PROC_REG_OFFSET(proc) ((proc)->pdr.regoffset) +#define PROC_FREG_OFFSET(proc) ((proc)->pdr.fregoffset) +#define PROC_PC_REG(proc) ((proc)->pdr.pcreg) +#define PROC_SYMBOL(proc) (*(struct symbol**)&(proc)->pdr.isym) #define _PROC_MAGIC_ 0x0F0F0F0F -#define PROC_DESC_IS_DUMMY(proc) ((proc)->isym == _PROC_MAGIC_) -#define SET_PROC_DESC_IS_DUMMY(proc) ((proc)->isym = _PROC_MAGIC_) +#define PROC_DESC_IS_DUMMY(proc) ((proc)->pdr.isym == _PROC_MAGIC_) +#define SET_PROC_DESC_IS_DUMMY(proc) ((proc)->pdr.isym = _PROC_MAGIC_) struct linked_proc_info { @@ -84,7 +84,7 @@ struct linked_proc_info #define READ_FRAME_REG(fi, regno) read_next_frame_reg((fi)->next, regno) -int +static int read_next_frame_reg(fi, regno) FRAME fi; int regno; @@ -113,38 +113,28 @@ int mips_frame_saved_pc(frame) FRAME frame; { - mips_extra_func_info_t proc_desc = (mips_extra_func_info_t)frame->proc_desc; + mips_extra_func_info_t proc_desc = frame->proc_desc; int pcreg = proc_desc ? PROC_PC_REG(proc_desc) : RA_REGNUM; + if (proc_desc && PROC_DESC_IS_DUMMY(proc_desc)) return read_memory_integer(frame->frame - 4, 4); -#if 0 - /* If in the procedure prologue, RA_REGNUM might not have been saved yet. - * Assume non-leaf functions start with: - * addiu $sp,$sp,-frame_size - * sw $ra,ra_offset($sp) - * This if the pc is pointing at either of these instructions, - * then $ra hasn't been trashed. - * If the pc has advanced beyond these two instructions, - * then $ra has been saved. - * critical, and much more complex. Handling $ra is enough to get - * a stack trace, but some register values with be wrong. - */ - if (frame->proc_desc && frame->pc < PROC_LOW_ADDR(proc_desc) + 8) - return read_register(pcreg); -#endif + return read_next_frame_reg(frame, pcreg); } static struct mips_extra_func_info temp_proc_desc; static struct frame_saved_regs temp_saved_regs; -CORE_ADDR heuristic_proc_start(pc) +static CORE_ADDR +heuristic_proc_start(pc) CORE_ADDR pc; { - CORE_ADDR start_pc = pc; CORE_ADDR fence = start_pc - 200; + + if (start_pc == 0) return 0; if (fence < VM_MIN_ADDRESS) fence = VM_MIN_ADDRESS; + /* search back for previous return */ for (start_pc -= 4; ; start_pc -= 4) if (start_pc < fence) return 0; @@ -160,7 +150,7 @@ CORE_ADDR heuristic_proc_start(pc) return start_pc; } -mips_extra_func_info_t +static mips_extra_func_info_t heuristic_proc_desc(start_pc, limit_pc, next_frame) CORE_ADDR start_pc, limit_pc; FRAME next_frame; @@ -231,18 +221,17 @@ heuristic_proc_desc(start_pc, limit_pc, next_frame) return &temp_proc_desc; } -mips_extra_func_info_t +static mips_extra_func_info_t find_proc_desc(pc, next_frame) CORE_ADDR pc; FRAME next_frame; { mips_extra_func_info_t proc_desc; - extern struct block *block_for_pc(); - struct block *b = block_for_pc(pc); - + struct block *b = block_for_pc(pc); struct symbol *sym = b ? lookup_symbol(".gdbinfo.", b, LABEL_NAMESPACE, 0, NULL) : NULL; - if (sym != NULL) + + if (sym) { /* IF this is the topmost frame AND * (this proc does not have debugging information OR @@ -250,11 +239,12 @@ find_proc_desc(pc, next_frame) * THEN create a "heuristic" proc_desc (by analyzing * the actual code) to replace the "official" proc_desc. */ - proc_desc = (struct mips_extra_func_info *)sym->value.value; + proc_desc = (mips_extra_func_info_t)SYMBOL_VALUE(sym); if (next_frame == NULL) { struct symtab_and_line val; struct symbol *proc_symbol = PROC_DESC_IS_DUMMY(proc_desc) ? 0 : PROC_SYMBOL(proc_desc); + if (proc_symbol) { val = find_pc_line (BLOCK_START (SYMBOL_BLOCK_VALUE(proc_symbol)), @@ -271,6 +261,11 @@ find_proc_desc(pc, next_frame) } else { + /* Is linked_proc_desc_table really necessary? It only seems to be used + by procedure call dummys. However, the procedures being called ought + to have their own proc_descs, and even if they don't, + heuristic_proc_desc knows how to create them! */ + register struct linked_proc_info *link; for (link = linked_proc_desc_table; link; link = link->next) if (PROC_LOW_ADDR(&link->info) <= pc @@ -284,28 +279,23 @@ find_proc_desc(pc, next_frame) mips_extra_func_info_t cached_proc_desc; -FRAME_ADDR mips_frame_chain(frame) +FRAME_ADDR +mips_frame_chain(frame) FRAME frame; { mips_extra_func_info_t proc_desc; CORE_ADDR saved_pc = FRAME_SAVED_PC(frame); - if (symfile_objfile->ei.entry_file_lowpc) - { /* has at least the __start symbol */ - if (saved_pc == 0 || inside_entry_file (saved_pc)) return 0; - } - else - { /* This hack depends on the internals of __start. */ - /* We also assume the breakpoints are *not* inserted */ - if (saved_pc == 0 - || read_memory_integer (saved_pc + 8, 4) & 0xFC00003F == 0xD) - return 0; /* break */ - } + if (saved_pc == 0 || inside_entry_file (saved_pc)) + return 0; + proc_desc = find_proc_desc(saved_pc, frame); - if (!proc_desc) return 0; + if (!proc_desc) + return 0; + cached_proc_desc = proc_desc; return read_next_frame_reg(frame, PROC_FRAME_REG(proc_desc)) - + PROC_FRAME_OFFSET(proc_desc); + + PROC_FRAME_OFFSET(proc_desc); } void @@ -316,11 +306,12 @@ init_extra_frame_info(fci) /* Use proc_desc calculated in frame_chain */ mips_extra_func_info_t proc_desc = fci->next ? cached_proc_desc : find_proc_desc(fci->pc, fci->next); + fci->saved_regs = (struct frame_saved_regs*) obstack_alloc (&frame_cache_obstack, sizeof(struct frame_saved_regs)); bzero(fci->saved_regs, sizeof(struct frame_saved_regs)); fci->proc_desc = - proc_desc == &temp_proc_desc ? (char*)NULL : (char*)proc_desc; + proc_desc == &temp_proc_desc ? 0 : proc_desc; if (proc_desc) { int ireg; @@ -373,12 +364,11 @@ init_extra_frame_info(fci) fci->saved_regs->regs[PC_REGNUM] = fci->saved_regs->regs[RA_REGNUM]; } - if (fci->next == 0) - supply_register(FP_REGNUM, &fci->frame); } -CORE_ADDR mips_push_arguments(nargs, args, sp, struct_return, struct_addr) +CORE_ADDR +mips_push_arguments(nargs, args, sp, struct_return, struct_addr) int nargs; value *args; CORE_ADDR sp; @@ -538,7 +528,7 @@ mips_pop_frame() set_current_frame (create_new_frame (new_sp, read_pc ())); } -static +static void mips_print_register(regnum, all) int regnum, all; { @@ -592,6 +582,7 @@ mips_print_register(regnum, all) } /* Replacement for generic do_registers_info. */ +void mips_do_registers_info (regnum, fpregs) int regnum; int fpregs; @@ -618,6 +609,7 @@ mips_do_registers_info (regnum, fpregs) /* Return number of args passed to a frame. described by FIP. Can return -1, meaning no way to tell. */ +int mips_frame_num_args(fip) FRAME fip; { @@ -805,7 +797,7 @@ mips_skip_prologue(pc) Actually, it would not hurt to skip the storing of arguments on the stack as well. */ - if (((struct mips_extra_func_info *)f->value.value)->framesize) + if (((mips_extra_func_info_t)SYMBOL_VALUE(f))->pdr.frameoffset) return pc + 4; return pc; diff --git a/gdb/stack.c b/gdb/stack.c index 7857347adff..4aeb7c40f92 100644 --- a/gdb/stack.c +++ b/gdb/stack.c @@ -1066,7 +1066,7 @@ up_silently_command (count_exp, from_tty) count = parse_and_eval_address (count_exp); count1 = count; - if (!target_has_stack) + if (target_has_stack == 0 || selected_frame == 0) error ("No stack."); frame = find_relative_frame (selected_frame, &count1); @@ -1099,7 +1099,7 @@ down_silently_command (count_exp, from_tty) count = - parse_and_eval_address (count_exp); count1 = count; - if (!target_has_stack) + if (target_has_stack == 0 || selected_frame == 0) error ("No stack."); frame = find_relative_frame (selected_frame, &count1); @@ -1129,6 +1129,7 @@ return_command (retval_exp, from_tty) FRAME frame; char *funcname; struct cleanup *back_to; + value return_value; if (selected_frame == NULL) error ("No selected frame."); @@ -1136,6 +1137,16 @@ return_command (retval_exp, from_tty) selected_frame_addr = FRAME_FP (selected_frame); selected_frame_pc = (get_frame_info (selected_frame))->pc; + /* Compute the return value (if any -- possibly getting errors here). + Call VALUE_CONTENTS to make sure we have fully evaluated it, since + it might live in the stack frame we're about to pop. */ + + if (retval_exp) + { + return_value = parse_and_eval (retval_exp); + (void) (VALUE_CONTENTS (return_value)); + } + /* If interactive, require confirmation. */ if (from_tty) @@ -1173,7 +1184,7 @@ return_command (retval_exp, from_tty) for return values. */ if (retval_exp) - set_return_value (parse_and_eval (retval_exp)); + set_return_value (return_value); /* If interactive, print the frame that is now current. */ diff --git a/gdb/utils.c b/gdb/utils.c index 15efc730d34..a1c33edc234 100644 --- a/gdb/utils.c +++ b/gdb/utils.c @@ -1098,7 +1098,7 @@ fputs_demangled (linebuffer, stream, arg_mode) && (isalnum(c) || (c) == '_' || (c) == CPLUS_MARKER)) char buf[SYMBOL_MAX+1]; -# define SLOP 5 /* How much room to leave in buf */ +# define DMSLOP 5 /* How much room to leave in buf */ char *p; if (linebuffer == NULL) @@ -1116,7 +1116,7 @@ fputs_demangled (linebuffer, stream, arg_mode) int i = 0; /* collect non-interesting characters into buf */ - while ( *p != (char) 0 && !SYMBOL_CHAR(*p) && i < (int)sizeof(buf)-SLOP ) { + while (*p != (char) 0 && !SYMBOL_CHAR(*p) && i < (int)sizeof(buf)-DMSLOP ) { buf[i++] = *p; p++; } @@ -1131,7 +1131,7 @@ fputs_demangled (linebuffer, stream, arg_mode) while (i < SYMBOL_MAX && *p != (char) 0 && SYMBOL_CHAR(*p) - && i < (int)sizeof(buf) - SLOP) { + && i < (int)sizeof(buf) - DMSLOP) { buf[i++] = *p; p++; } diff --git a/gdb/xm-mips.h b/gdb/xm-mips.h index 42ea0554588..1318bba60b4 100644 --- a/gdb/xm-mips.h +++ b/gdb/xm-mips.h @@ -33,6 +33,12 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ extern char *strdup(); #endif +/* DECstation memcpy and memset return void *, not char *. */ + +extern void *memcpy(); +extern void *memset(); +#define MEM_FNS_DECLARED + /* Only used for core files on DECstations. */ #define REGISTER_U_ADDR(addr, blockend, regno) \ -- 2.30.2