+Sun Nov 6 12:54:54 1994 Jeff Law (law@snake.cs.utah.edu)
+
+ * hppa-tdep.c (frame_saved_pc): Mask off low two bits when
+ retrieving the PC from a signal handler caller. Fix thinko
+ in Stan's last change ("frame", should have been "frame->next").
+ If the next frame is a signal handler caller and it's a system
+ call which has entered the kernel ((PSW & 0x2) != 0), then the
+ saved pc is in %r2 instead of %r31.
+
Fri Nov 4 23:47:07 1994 Jeff Law (law@snake.cs.utah.edu)
* hppa-tdep.c (hppa_frame_find_saved_regs): Change "frame" to
{
CORE_ADDR rp;
FRAME_SAVED_PC_IN_SIGTRAMP (frame, &rp);
- return rp;
+ return rp & ~0x3;
}
if (frameless_function_invocation (frame))
{
struct frame_saved_regs saved_regs;
- get_frame_saved_regs (frame, &saved_regs);
+ get_frame_saved_regs (frame->next, &saved_regs);
if (read_memory_integer (saved_regs.regs[FLAGS_REGNUM], 4) & 0x2)
- pc = read_memory_integer (saved_regs.regs[31], 4) & ~0x3;
+ {
+ pc = read_memory_integer (saved_regs.regs[31], 4) & ~0x3;
+
+ /* Syscalls are really two frames. The syscall stub itself
+ with a return pointer in %rp and the kernel call with
+ a return pointer in %r31. We return the %rp variant
+ if %r31 is the same as frame->pc. */
+ if (pc == frame->pc)
+ pc = read_memory_integer (saved_regs.regs[RP_REGNUM], 4) & ~0x3;
+ }
else
pc = read_memory_integer (saved_regs.regs[RP_REGNUM], 4) & ~0x3;
}
get_frame_saved_regs (frame->next, &saved_regs);
if (read_memory_integer (saved_regs.regs[FLAGS_REGNUM], 4) & 0x2)
- pc = read_memory_integer (saved_regs.regs[31], 4) & ~0x3;
+ {
+ pc = read_memory_integer (saved_regs.regs[31], 4) & ~0x3;
+
+ /* Syscalls are really two frames. The syscall stub itself
+ with a return pointer in %rp and the kernel call with
+ a return pointer in %r31. We return the %rp variant
+ if %r31 is the same as frame->pc. */
+ if (pc == frame->pc)
+ pc = read_memory_integer (saved_regs.regs[RP_REGNUM], 4) & ~0x3;
+ }
else
pc = read_memory_integer (saved_regs.regs[RP_REGNUM], 4) & ~0x3;
}