diff options
author | Stu Grossman <grossman@cygnus> | 1993-04-23 18:01:02 +0000 |
---|---|---|
committer | Stu Grossman <grossman@cygnus> | 1993-04-23 18:01:02 +0000 |
commit | b5728692b43217ea2babbe08a94552cb4b2ffeff (patch) | |
tree | c8d9bdff58794e4ef37a05faa4111665f7626829 /gdb/hppah-tdep.c | |
parent | c156f3c1c9395bcb721678e07a5cf10b7c0d7b18 (diff) | |
download | gdb-b5728692b43217ea2babbe08a94552cb4b2ffeff.zip gdb-b5728692b43217ea2babbe08a94552cb4b2ffeff.tar.gz gdb-b5728692b43217ea2babbe08a94552cb4b2ffeff.tar.bz2 |
* Fix two bugs found by deja-gnu. One is the incorrect reporting
of the PC being in a stack dummy when looking at a core file
without symbols. The other is the incorrect passing of char
arguments during expression evaluation (ie: p foo('a','b') would
mess up the passing of it's args because it wasn't coercing the
char's to ints).
* hppah-tdep.c: Rename global functions to have consistent hppa_
prefix. Make more functions static. Drop hp_ prefix from static
functions. (hppa_push_arguments): Call value_arg_coerce to cast
char to int args if necessary. (hppa_fix_call_dummy): Create
this routine from FIX_CALL_DUMMY macro in tm-hppa.h.
* inferior.h (PC_IN_CALL_DUMMY): Check for frame_address being
valid (ie: != 0) before doing comparison against PC.
* valops.c (call_function_by_hand): Adjust call to FIX_CALL_DUMMY
to reflect new arguments.
* config/pa/tm-hppa.h (POP_FRAME, PUSH_ARGUMENTS): Use new hppa_
prefix for func name. (FIX_CALL_DUMMY): Move code into
hppah-tdep.c.
* testsuite/gdb.t16/gdbme.c, testsuite/gdb.t17/gdbme.c: Add calls
to malloc() so that we can test GDB eval of dynamically created
arrays (like char strings in `print "foo"').
Diffstat (limited to 'gdb/hppah-tdep.c')
-rw-r--r-- | gdb/hppah-tdep.c | 71 |
1 files changed, 61 insertions, 10 deletions
diff --git a/gdb/hppah-tdep.c b/gdb/hppah-tdep.c index 5a1227a..cd0d157 100644 --- a/gdb/hppah-tdep.c +++ b/gdb/hppah-tdep.c @@ -59,6 +59,9 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "symfile.h" #include "objfiles.h" +static int restore_pc_queue PARAMS ((struct frame_saved_regs *fsr)); +static int hppa_alignof PARAMS ((struct type *arg)); + /* Routines to extract various sized constants out of hppa instructions. */ @@ -534,7 +537,7 @@ find_dummy_frame_regs (frame, frame_saved_regs) } int -hp_pop_frame () +hppa_pop_frame () { register FRAME frame = get_current_frame (); register CORE_ADDR fp; @@ -548,7 +551,7 @@ hp_pop_frame () get_frame_saved_regs (fi, &fsr); if (fsr.regs[IPSW_REGNUM]) /* Restoring a call dummy frame */ - hp_restore_pc_queue (&fsr); + restore_pc_queue (&fsr); for (regnum = 31; regnum > 0; regnum--) if (fsr.regs[regnum]) @@ -589,8 +592,8 @@ hp_pop_frame () * After returning to a dummy on the stack, restore the instruction * queue space registers. */ -int -hp_restore_pc_queue (fsr) +static int +restore_pc_queue (fsr) struct frame_saved_regs *fsr; { CORE_ADDR pc = read_pc (); @@ -638,7 +641,7 @@ hp_restore_pc_queue (fsr) } CORE_ADDR -hp_push_arguments (nargs, args, sp, struct_return, struct_addr) +hppa_push_arguments (nargs, args, sp, struct_return, struct_addr) int nargs; value *args; CORE_ADDR sp; @@ -652,11 +655,14 @@ hp_push_arguments (nargs, args, sp, struct_return, struct_addr) for (i = 0; i < nargs; i++) { + /* Coerce chars to int & float to double if necessary */ + args[i] = value_arg_coerce (args[i]); + cum += TYPE_LENGTH (VALUE_TYPE (args[i])); /* value must go at proper alignment. Assume alignment is a power of two.*/ - alignment = hp_alignof (VALUE_TYPE (args[i])); + alignment = hppa_alignof (VALUE_TYPE (args[i])); if (cum % alignment) cum = (cum + alignment) & -alignment; offset[i] = -cum; @@ -672,11 +678,56 @@ hp_push_arguments (nargs, args, sp, struct_return, struct_addr) return sp + 32; } +/* + * Insert the specified number of args and function address + * into a call sequence of the above form stored at DUMMYNAME. + * + * On the hppa we need to call the stack dummy through $$dyncall. + * Therefore our version of FIX_CALL_DUMMY takes an extra argument, + * real_pc, which is the location where gdb should start up the + * inferior to do the function call. + */ + +CORE_ADDR +hppa_fix_call_dummy (dummy, pc, fun, nargs, args, type, gcc_p) + REGISTER_TYPE *dummy; + CORE_ADDR pc; + CORE_ADDR fun; + int nargs; + value *args; + struct type *type; + int gcc_p; +{ + CORE_ADDR dyncall_addr, sr4export_addr; + struct minimal_symbol *msymbol; + + msymbol = lookup_minimal_symbol ("$$dyncall", (struct objfile *) NULL); + if (msymbol == NULL) + error ("Can't find an address for $$dyncall trampoline"); + + dyncall_addr = SYMBOL_VALUE_ADDRESS (msymbol); + + msymbol = lookup_minimal_symbol ("_sr4export", (struct objfile *) NULL); + if (msymbol == NULL) + error ("Can't find an address for _sr4export trampoline"); + + sr4export_addr = SYMBOL_VALUE_ADDRESS (msymbol); + + dummy[9] = deposit_21 (fun >> 11, dummy[9]); + dummy[10] = deposit_14 (fun & MASK_11, dummy[10]); + dummy[12] = deposit_21 (sr4export_addr >> 11, dummy[12]); + dummy[13] = deposit_14 (sr4export_addr & MASK_11, dummy[13]); + + write_register (22, pc); + + return dyncall_addr; +} + /* return the alignment of a type in bytes. Structures have the maximum alignment required by their fields. */ -int -hp_alignof (arg) +static int +hppa_alignof (arg) struct type *arg; { int max_align, align, i; @@ -687,7 +738,7 @@ hp_alignof (arg) case TYPE_CODE_FLT: return TYPE_LENGTH (arg); case TYPE_CODE_ARRAY: - return hp_alignof (TYPE_FIELD_TYPE (arg, 0)); + return hppa_alignof (TYPE_FIELD_TYPE (arg, 0)); case TYPE_CODE_STRUCT: case TYPE_CODE_UNION: max_align = 2; @@ -696,7 +747,7 @@ hp_alignof (arg) /* Bit fields have no real alignment. */ if (!TYPE_FIELD_BITPOS (arg, i)) { - align = hp_alignof (TYPE_FIELD_TYPE (arg, i)); + align = hppa_alignof (TYPE_FIELD_TYPE (arg, i)); max_align = max (max_align, align); } } |