mirror of
https://github.com/espressif/binutils-gdb.git
synced 2025-06-24 12:23:31 +08:00
* hppa-tdep.c (pc_in_linker_stub): New function.
(find_proc_framesize): Return 0 for linker stubs. (rp_saved): Tell the caller where rp is saved. (frame_chain_valid): Return 1 for linker stubs. (frame_saved_pc): Use return value from rp_saved.
This commit is contained in:
@ -1,5 +1,11 @@
|
|||||||
Thu Jul 15 08:34:49 1993 Jim Kingdon (kingdon@lioth.cygnus.com)
|
Thu Jul 15 08:34:49 1993 Jim Kingdon (kingdon@lioth.cygnus.com)
|
||||||
|
|
||||||
|
* hppa-tdep.c (pc_in_linker_stub): New function.
|
||||||
|
(find_proc_framesize): Return 0 for linker stubs.
|
||||||
|
(rp_saved): Tell the caller where rp is saved.
|
||||||
|
(frame_chain_valid): Return 1 for linker stubs.
|
||||||
|
(frame_saved_pc): Use return value from rp_saved.
|
||||||
|
|
||||||
* stack.c (print_frame_info): When checking PC_IN_CALL_DUMMY,
|
* stack.c (print_frame_info): When checking PC_IN_CALL_DUMMY,
|
||||||
pass the sp relative to the frame in question, not the sp in the
|
pass the sp relative to the frame in question, not the sp in the
|
||||||
innermost frame.
|
innermost frame.
|
||||||
|
101
gdb/hppa-tdep.c
101
gdb/hppa-tdep.c
@ -296,6 +296,62 @@ find_unwind_entry(pc)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Called when no unwind descriptor was found for PC. Returns 1 if it
|
||||||
|
appears that PC is in a linker stub. */
|
||||||
|
static int pc_in_linker_stub PARAMS ((CORE_ADDR));
|
||||||
|
|
||||||
|
static int
|
||||||
|
pc_in_linker_stub (pc)
|
||||||
|
CORE_ADDR pc;
|
||||||
|
{
|
||||||
|
|
||||||
|
int found_magic_instruction = 0;
|
||||||
|
int i;
|
||||||
|
|
||||||
|
/* Maximum known linker stub size is 4 instructions. Search forward
|
||||||
|
from the given PC, then backward. */
|
||||||
|
for (i = 0; i < 4; i++)
|
||||||
|
{
|
||||||
|
/* If we hit something with an unwind, stop searching this direction.
|
||||||
|
|
||||||
|
if (find_unwind_entry (pc + i * 4) != 0)
|
||||||
|
break;
|
||||||
|
|
||||||
|
/* Check for ldsid (rp),r1 which is the magic instruction for a
|
||||||
|
return from a cross-space function call. */
|
||||||
|
if (read_memory_integer (pc + i * 4, 4) == 0x004010a1)
|
||||||
|
{
|
||||||
|
found_magic_instruction = 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
/* Add code to handle long call/branch and argument relocation stubs
|
||||||
|
here. */
|
||||||
|
}
|
||||||
|
|
||||||
|
if (found_magic_instruction != 0)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
/* Now look backward. */
|
||||||
|
for (i = 0; i < 4; i++)
|
||||||
|
{
|
||||||
|
/* If we hit something with an unwind, stop searching this direction.
|
||||||
|
|
||||||
|
if (find_unwind_entry (pc - i * 4) != 0)
|
||||||
|
break;
|
||||||
|
|
||||||
|
/* Check for ldsid (rp),r1 which is the magic instruction for a
|
||||||
|
return from a cross-space function call. */
|
||||||
|
if (read_memory_integer (pc - i * 4, 4) == 0x004010a1)
|
||||||
|
{
|
||||||
|
found_magic_instruction = 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
/* Add code to handle long call/branch and argument relocation stubs
|
||||||
|
here. */
|
||||||
|
}
|
||||||
|
return found_magic_instruction;
|
||||||
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
find_return_regnum(pc)
|
find_return_regnum(pc)
|
||||||
CORE_ADDR pc;
|
CORE_ADDR pc;
|
||||||
@ -313,6 +369,7 @@ find_return_regnum(pc)
|
|||||||
return RP_REGNUM;
|
return RP_REGNUM;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Return size of frame, or -1 if we should use a frame pointer. */
|
||||||
int
|
int
|
||||||
find_proc_framesize(pc)
|
find_proc_framesize(pc)
|
||||||
CORE_ADDR pc;
|
CORE_ADDR pc;
|
||||||
@ -325,7 +382,13 @@ find_proc_framesize(pc)
|
|||||||
u = find_unwind_entry (pc);
|
u = find_unwind_entry (pc);
|
||||||
|
|
||||||
if (!u)
|
if (!u)
|
||||||
|
{
|
||||||
|
if (pc_in_linker_stub (pc))
|
||||||
|
/* Linker stubs have a zero size frame. */
|
||||||
|
return 0;
|
||||||
|
else
|
||||||
return -1;
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
if (u->Save_SP)
|
if (u->Save_SP)
|
||||||
/* If this bit is set, it means there is a frame pointer and we should
|
/* If this bit is set, it means there is a frame pointer and we should
|
||||||
@ -335,18 +398,28 @@ find_proc_framesize(pc)
|
|||||||
return u->Total_frame_size << 3;
|
return u->Total_frame_size << 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
/* Return offset from sp at which rp is saved, or 0 if not saved. */
|
||||||
rp_saved(pc)
|
static int rp_saved PARAMS ((CORE_ADDR));
|
||||||
|
|
||||||
|
static int
|
||||||
|
rp_saved (pc)
|
||||||
|
CORE_ADDR pc;
|
||||||
{
|
{
|
||||||
struct unwind_table_entry *u;
|
struct unwind_table_entry *u;
|
||||||
|
|
||||||
u = find_unwind_entry (pc);
|
u = find_unwind_entry (pc);
|
||||||
|
|
||||||
if (!u)
|
if (!u)
|
||||||
|
{
|
||||||
|
if (pc_in_linker_stub (pc))
|
||||||
|
/* This is the so-called RP'. */
|
||||||
|
return -24;
|
||||||
|
else
|
||||||
return 0;
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (u->Save_RP)
|
if (u->Save_RP)
|
||||||
return 1;
|
return -20;
|
||||||
else
|
else
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -396,10 +469,15 @@ frame_saved_pc (frame)
|
|||||||
|
|
||||||
return read_register (ret_regnum) & ~0x3;
|
return read_register (ret_regnum) & ~0x3;
|
||||||
}
|
}
|
||||||
else if (rp_saved (pc))
|
|
||||||
return read_memory_integer (frame->frame - 20, 4) & ~0x3;
|
|
||||||
else
|
else
|
||||||
|
{
|
||||||
|
int rp_offset = rp_saved (pc);
|
||||||
|
|
||||||
|
if (rp_offset == 0)
|
||||||
return read_register (RP_REGNUM) & ~0x3;
|
return read_register (RP_REGNUM) & ~0x3;
|
||||||
|
else
|
||||||
|
return read_memory_integer (frame->frame - rp_offset, 4) & ~0x3;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* We need to correct the PC and the FP for the outermost frame when we are
|
/* We need to correct the PC and the FP for the outermost frame when we are
|
||||||
@ -470,9 +548,18 @@ frame_chain_valid (chain, thisframe)
|
|||||||
|
|
||||||
u = find_unwind_entry (thisframe->pc);
|
u = find_unwind_entry (thisframe->pc);
|
||||||
|
|
||||||
if (u && (u->Save_SP || u->Total_frame_size))
|
if (u == NULL)
|
||||||
|
/* FIXME, we should probably fall back to some other technique,
|
||||||
|
if we want to deal gracefully with stripped executables or others
|
||||||
|
without unwind info. */
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
if (u->Save_SP || u->Total_frame_size)
|
||||||
return 1;
|
return 1;
|
||||||
else
|
|
||||||
|
if (pc_in_linker_stub (thisframe->pc))
|
||||||
|
return 1;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
Reference in New Issue
Block a user