* a29k-tdep.c (init_frame_info): Cast null arg to examine_tag.

(pop_frame):  Restore PC2 and LR0 from dummy frames.
(push_dummy_frame):  Save PC2 and LR0 into dummy frames.
(setup_arbitrary_frame):  Handle 3 args and set up real frames.
* config/a29k/tm-a29k.h (FRAME_NUM_ARGS):  Update comments.
(DUMMY_FRAME_RSIZE):  Add 2 longwords for PC2 and LR0.
(SETUP_ARBITRARY_FRAME):  Define.
This commit is contained in:
John Gilmore 1994-01-12 07:47:14 +00:00
parent a1c91916e8
commit eb5b74ca6c
3 changed files with 98 additions and 26 deletions

View File

@ -1,3 +1,13 @@
Tue Jan 11 00:53:46 1994 John Gilmore (gnu@cygnus.com)
* a29k-tdep.c (init_frame_info): Cast null arg to examine_tag.
(pop_frame): Restore PC2 and LR0 from dummy frames.
(push_dummy_frame): Save PC2 and LR0 into dummy frames.
(setup_arbitrary_frame): Handle 3 args and set up real frames.
* config/a29k/tm-a29k.h (FRAME_NUM_ARGS): Update comments.
(DUMMY_FRAME_RSIZE): Add 2 longwords for PC2 and LR0.
(SETUP_ARBITRARY_FRAME): Define.
Tue Jan 11 06:59:10 1994 Jim Kingdon (kingdon@deneb.cygnus.com) Tue Jan 11 06:59:10 1994 Jim Kingdon (kingdon@deneb.cygnus.com)
* infrun.c, config/mips/tm-irix5.h: Remove #if 0'd AT_FUNCTION_START. * infrun.c, config/mips/tm-irix5.h: Remove #if 0'd AT_FUNCTION_START.

View File

@ -437,14 +437,14 @@ init_frame_info (innermost_frame, fci)
after the trace-back tag. */ after the trace-back tag. */
p += 4; p += 4;
} }
/* We've found the start of the function. /* We've found the start of the function.
* Try looking for a tag word that indicates whether there is a Try looking for a tag word that indicates whether there is a
* memory frame pointer and what the memory stack allocation is. memory frame pointer and what the memory stack allocation is.
* If one doesn't exist, try using a more exhaustive search of If one doesn't exist, try using a more exhaustive search of
* the prologue. For now we don't care about the argcount or the prologue. */
* whether or not the routine is transparent.
*/ if (examine_tag(p-4,&trans,(int *)NULL,&msize,&mfp_used)) /* Found good tag */
if (examine_tag(p-4,&trans,NULL,&msize,&mfp_used)) /* Found a good tag */
examine_prologue (p, &rsize, 0, 0); examine_prologue (p, &rsize, 0, 0);
else /* No tag try prologue */ else /* No tag try prologue */
examine_prologue (p, &rsize, &msize, &mfp_used); examine_prologue (p, &rsize, &msize, &mfp_used);
@ -730,6 +730,8 @@ pop_frame ()
CORE_ADDR rfb = read_register (RFB_REGNUM); CORE_ADDR rfb = read_register (RFB_REGNUM);
CORE_ADDR gr1 = fi->frame + fi->rsize; CORE_ADDR gr1 = fi->frame + fi->rsize;
CORE_ADDR lr1; CORE_ADDR lr1;
CORE_ADDR original_lr0;
int must_fix_lr0 = 0;
int i; int i;
/* If popping a dummy frame, need to restore registers. */ /* If popping a dummy frame, need to restore registers. */
@ -744,15 +746,23 @@ pop_frame ()
write_register (SR_REGNUM(i+160), read_register (lrnum++)); write_register (SR_REGNUM(i+160), read_register (lrnum++));
for (i = 0; i < DUMMY_SAVE_GREGS; ++i) for (i = 0; i < DUMMY_SAVE_GREGS; ++i)
write_register (RETURN_REGNUM + i, read_register (lrnum++)); write_register (RETURN_REGNUM + i, read_register (lrnum++));
/* Restore the PCs. */ /* Restore the PCs and prepare to restore LR0. */
write_register(PC_REGNUM, read_register (lrnum++)); write_register(PC_REGNUM, read_register (lrnum++));
write_register(NPC_REGNUM, read_register (lrnum)); write_register(NPC_REGNUM, read_register (lrnum++));
write_register(PC2_REGNUM, read_register (lrnum++));
original_lr0 = read_register (lrnum++);
must_fix_lr0 = 1;
} }
/* Restore the memory stack pointer. */ /* Restore the memory stack pointer. */
write_register (MSP_REGNUM, fi->saved_msp); write_register (MSP_REGNUM, fi->saved_msp);
/* Restore the register stack pointer. */ /* Restore the register stack pointer. */
write_register (GR1_REGNUM, gr1); write_register (GR1_REGNUM, gr1);
/* If we popped a dummy frame, restore lr0 now that gr1 has been restored. */
if (must_fix_lr0)
write_register (LR0_REGNUM, original_lr0);
/* Check whether we need to fill registers. */ /* Check whether we need to fill registers. */
lr1 = read_register (LR0_REGNUM + 1); lr1 = read_register (LR0_REGNUM + 1);
if (lr1 > rfb) if (lr1 > rfb)
@ -782,8 +792,13 @@ push_dummy_frame ()
long w; long w;
CORE_ADDR rab, gr1; CORE_ADDR rab, gr1;
CORE_ADDR msp = read_register (MSP_REGNUM); CORE_ADDR msp = read_register (MSP_REGNUM);
int lrnum, i, saved_lr0; int lrnum, i;
CORE_ADDR original_lr0;
/* Read original lr0 before changing gr1. This order isn't really needed
since GDB happens to have a snapshot of all the regs and doesn't toss
it when gr1 is changed. But it's The Right Thing To Do. */
original_lr0 = read_register (LR0_REGNUM);
/* Allocate the new frame. */ /* Allocate the new frame. */
gr1 = read_register (GR1_REGNUM) - DUMMY_FRAME_RSIZE; gr1 = read_register (GR1_REGNUM) - DUMMY_FRAME_RSIZE;
@ -826,11 +841,54 @@ push_dummy_frame ()
write_register (lrnum++, read_register (SR_REGNUM (i + 160))); write_register (lrnum++, read_register (SR_REGNUM (i + 160)));
for (i = 0; i < DUMMY_SAVE_GREGS; ++i) for (i = 0; i < DUMMY_SAVE_GREGS; ++i)
write_register (lrnum++, read_register (RETURN_REGNUM + i)); write_register (lrnum++, read_register (RETURN_REGNUM + i));
/* Save the PCs. */ /* Save the PCs and LR0. */
write_register (lrnum++, read_register (PC_REGNUM)); write_register (lrnum++, read_register (PC_REGNUM));
write_register (lrnum, read_register (NPC_REGNUM)); write_register (lrnum++, read_register (NPC_REGNUM));
write_register (lrnum++, read_register (PC2_REGNUM));
write_register (lrnum++, original_lr0);
} }
/*
This routine takes three arguments and makes the cached frames look
as if these arguments defined a frame on the cache. This allows the
rest of `info frame' to extract the important arguments without much
difficulty. Since an individual frame on the 29K is determined by
three values (FP, PC, and MSP), we really need all three to do a
good job. */
FRAME
setup_arbitrary_frame (argc, argv)
int argc;
FRAME_ADDR *argv;
{
FRAME fid;
if (argc != 3)
error ("AMD 29k frame specifications require three arguments: rsp pc msp");
fid = create_new_frame (argv[0], argv[1]);
if (!fid)
fatal ("internal: create_new_frame returned invalid frame id");
/* Creating a new frame munges the `frame' value from the current
GR1, so we restore it again here. FIXME, untangle all this
29K frame stuff... */
fid->frame = argv[0];
/* Our MSP is in argv[2]. It'd be intelligent if we could just
save this value in the FRAME. But the way it's set up (FIXME),
we must save our caller's MSP. We compute that by adding our
memory stack frame size to our MSP. */
fid->saved_msp = argv[2] + fid->msize;
return fid;
}
enum a29k_processor_types processor_type = a29k_unknown; enum a29k_processor_types processor_type = a29k_unknown;
void void

View File

@ -1,5 +1,5 @@
/* Parameters for target machine of AMD 29000, for GDB, the GNU debugger. /* Parameters for target machine AMD 29000, for GDB, the GNU debugger.
Copyright 1990, 1991, 1993 Free Software Foundation, Inc. Copyright 1990, 1991, 1993, 1994 Free Software Foundation, Inc.
Contributed by Cygnus Support. Written by Jim Kingdon. Contributed by Cygnus Support. Written by Jim Kingdon.
This file is part of GDB. This file is part of GDB.
@ -504,16 +504,11 @@ extern CORE_ADDR frame_locals_address ();
/* Return number of args passed to a frame. /* Return number of args passed to a frame.
Can return -1, meaning no way to tell. */ Can return -1, meaning no way to tell. */
/* While we could go the effort of finding the tags word and getting /* We tried going to the effort of finding the tags word and getting
the argcount field from it, the argcount field from it, to support debugging assembler code.
(1) It only counts arguments in registers, i.e. the first 16 words Problem was, the "argcount" field never did hold the argument
of arguments count. */
(2) It gives the number of arguments the function was declared with #define FRAME_NUM_ARGS(numargs, fi) ((numargs) = -1)
not how many it was called with (or some variation, like all 16
words for varadic functions). This makes argcount pretty much
redundant with -g info, even for varadic functions.
So don't bother. */
#define FRAME_NUM_ARGS(numargs, fi) ((numargs) = -1)
#define FRAME_ARGS_ADDRESS(fi) FRAME_LOCALS_ADDRESS (fi) #define FRAME_ARGS_ADDRESS(fi) FRAME_LOCALS_ADDRESS (fi)
@ -544,6 +539,7 @@ extern CORE_ADDR frame_locals_address ();
|____________|<-msp 0 <-----------mfp_dummy_____| | |____________|<-msp 0 <-----------mfp_dummy_____| |
| | (at start) | save regs | | | | (at start) | save regs | |
| arg_slop | | pc0,pc1 | | | arg_slop | | pc0,pc1 | |
| | | pc2,lr0 sproc | |
| (16 words) | | gr96-gr124 | | | (16 words) | | gr96-gr124 | |
|____________|<-msp 1--after | sr160-sr162 | | |____________|<-msp 1--after | sr160-sr162 | |
| | PUSH_DUMMY_FRAME| sr128-sr135 | | | | PUSH_DUMMY_FRAME| sr128-sr135 | |
@ -591,7 +587,7 @@ extern CORE_ADDR frame_locals_address ();
#define DUMMY_FRAME_RSIZE \ #define DUMMY_FRAME_RSIZE \
(4 /* mfp_dummy */ \ (4 /* mfp_dummy */ \
+ 2 * 4 /* pc0, pc1 */ \ + 4 * 4 /* pc0, pc1, pc2, lr0 */ \
+ DUMMY_SAVE_GREGS * 4 \ + DUMMY_SAVE_GREGS * 4 \
+ DUMMY_SAVE_SR160 * 4 \ + DUMMY_SAVE_SR160 * 4 \
+ DUMMY_SAVE_SR128 * 4 \ + DUMMY_SAVE_SR128 * 4 \
@ -716,3 +712,11 @@ extern enum a29k_processor_types {
/* Bit 0x400 of the CPS does identify freeze mode, i.e. 29050. */ /* Bit 0x400 of the CPS does identify freeze mode, i.e. 29050. */
a29k_freeze_mode a29k_freeze_mode
} processor_type; } processor_type;
/* We need three arguments for a general frame specification for the
"frame" or "info frame" command. */
#define SETUP_ARBITRARY_FRAME(argc, argv) setup_arbitrary_frame (argc, argv)
/* FIXME: Depends on equivalence between FRAME and "struct frame_info *",
and equivalence between CORE_ADDR and FRAME_ADDR. */
extern struct frame_info *setup_arbitrary_frame PARAMS ((int, CORE_ADDR *));