aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMark Kettenis <kettenis@gnu.org>2005-12-22 14:09:17 +0000
committerMark Kettenis <kettenis@gnu.org>2005-12-22 14:09:17 +0000
commit7238f00288e6636f71fd6eede5cd929683861be1 (patch)
tree1d8600f99ffae06020b315519ee907591ee04f51
parentf6acec6208a44cd7da34bb2d19ddde2fd3a51d91 (diff)
downloadgdb-7238f00288e6636f71fd6eede5cd929683861be1.zip
gdb-7238f00288e6636f71fd6eede5cd929683861be1.tar.gz
gdb-7238f00288e6636f71fd6eede5cd929683861be1.tar.bz2
* amd64obsd-tdep.c (amd64obsd_trapframe_cache): Fix detection of
interrupts from user space. * i386obsd-tdep.c (i386obsd_trapframe_cache): Handle interrupt frames too. (i386obsd_trapframe_sniffer): Turn into a proper unwinder sniffer. (i386obsd_trapframe_unwind): Add sniffer. (i386obsd_init_abi): Prepend i386obsd_trapframe_unwind instead of appending i386obsd_trapframe_sniffer.
-rw-r--r--gdb/ChangeLog9
-rw-r--r--gdb/amd64obsd-tdep.c2
-rw-r--r--gdb/i386obsd-tdep.c48
3 files changed, 39 insertions, 20 deletions
diff --git a/gdb/ChangeLog b/gdb/ChangeLog
index a98c1d8..aa4ce94 100644
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,5 +1,14 @@
2005-12-22 Mark Kettenis <kettenis@gnu.org>
+ * amd64obsd-tdep.c (amd64obsd_trapframe_cache): Fix detection of
+ interrupts from user space.
+ * i386obsd-tdep.c (i386obsd_trapframe_cache): Handle interrupt
+ frames too.
+ (i386obsd_trapframe_sniffer): Turn into a proper unwinder sniffer.
+ (i386obsd_trapframe_unwind): Add sniffer.
+ (i386obsd_init_abi): Prepend i386obsd_trapframe_unwind instead of
+ appending i386obsd_trapframe_sniffer.
+
* amd64obsd-tdep.c: Include "frame-unwind.h" and "trad-frame.h".
(amd64obsd_tf_reg_offset): New define.
(amd64obsd_trapframe_cache, amd64obsd_trapframe_this_id)
diff --git a/gdb/amd64obsd-tdep.c b/gdb/amd64obsd-tdep.c
index 30e8fc1..a0611c0 100644
--- a/gdb/amd64obsd-tdep.c
+++ b/gdb/amd64obsd-tdep.c
@@ -370,7 +370,7 @@ amd64obsd_trapframe_cache(struct frame_info *next_frame, void **this_cache)
trad_frame_set_reg_addr (cache, i, addr + amd64obsd_tf_reg_offset[i]);
/* Read %cs from trap frame. */
- addr = sp + amd64obsd_tf_reg_offset[AMD64_CS_REGNUM];
+ addr += amd64obsd_tf_reg_offset[AMD64_CS_REGNUM];
cs = read_memory_unsigned_integer (addr, 8);
if ((cs & I386_SEL_RPL) == I386_SEL_UPL)
{
diff --git a/gdb/i386obsd-tdep.c b/gdb/i386obsd-tdep.c
index ab38269..dafb657 100644
--- a/gdb/i386obsd-tdep.c
+++ b/gdb/i386obsd-tdep.c
@@ -345,6 +345,7 @@ i386obsd_trapframe_cache(struct frame_info *next_frame, void **this_cache)
struct trad_frame_cache *cache;
CORE_ADDR func, sp, addr;
ULONGEST cs;
+ char *name;
int i;
if (*this_cache)
@@ -355,12 +356,19 @@ i386obsd_trapframe_cache(struct frame_info *next_frame, void **this_cache)
func = frame_func_unwind (next_frame);
sp = frame_unwind_register_unsigned (next_frame, I386_ESP_REGNUM);
+
+ find_pc_partial_function (func, &name, NULL, NULL);
+ if (name && strncmp(name, "Xintr", 5) == 0)
+ addr = sp + 8; /* It's an interrupt frame. */
+ else
+ addr = sp;
+
for (i = 0; i < ARRAY_SIZE (i386obsd_tf_reg_offset); i++)
if (i386obsd_tf_reg_offset[i] != -1)
- trad_frame_set_reg_addr (cache, i, sp + i386obsd_tf_reg_offset[i]);
+ trad_frame_set_reg_addr (cache, i, addr + i386obsd_tf_reg_offset[i]);
/* Read %cs from trap frame. */
- addr = sp + i386obsd_tf_reg_offset[I386_CS_REGNUM];
+ addr += i386obsd_tf_reg_offset[I386_CS_REGNUM];
cs = read_memory_unsigned_integer (addr, 4);
if ((cs & I386_SEL_RPL) == I386_SEL_UPL)
{
@@ -400,17 +408,10 @@ i386obsd_trapframe_prev_register (struct frame_info *next_frame,
optimizedp, lvalp, addrp, realnump, valuep);
}
-static const struct frame_unwind i386obsd_trapframe_unwind = {
- /* FIXME: kettenis/20051219: This really is more like an interrupt
- frame, but SIGTRAMP_FRAME would print <signal handler called>,
- which really is not what we want here. */
- NORMAL_FRAME,
- i386obsd_trapframe_this_id,
- i386obsd_trapframe_prev_register
-};
-
-static const struct frame_unwind *
-i386obsd_trapframe_sniffer (struct frame_info *next_frame)
+static int
+i386obsd_trapframe_sniffer (const struct frame_unwind *self,
+ struct frame_info *next_frame,
+ void **this_prologue_cache)
{
ULONGEST cs;
char *name;
@@ -420,12 +421,21 @@ i386obsd_trapframe_sniffer (struct frame_info *next_frame)
return NULL;
find_pc_partial_function (frame_pc_unwind (next_frame), &name, NULL, NULL);
- if (name && ((strcmp ("calltrap", name) == 0)
- || (strcmp ("syscall1", name) == 0)))
- return &i386obsd_trapframe_unwind;
-
- return NULL;
+ return (name && ((strcmp (name, "calltrap") == 0)
+ || (strcmp (name, "syscall1") == 0)
+ || (strncmp (name, "Xintr", 5) == 0)));
}
+
+static const struct frame_unwind i386obsd_trapframe_unwind = {
+ /* FIXME: kettenis/20051219: This really is more like an interrupt
+ frame, but SIGTRAMP_FRAME would print <signal handler called>,
+ which really is not what we want here. */
+ NORMAL_FRAME,
+ i386obsd_trapframe_this_id,
+ i386obsd_trapframe_prev_register,
+ NULL,
+ i386obsd_trapframe_sniffer
+};
static void
@@ -459,7 +469,7 @@ i386obsd_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch)
bsd_uthread_set_collect_uthread (gdbarch, i386obsd_collect_uthread);
/* Unwind kernel trap frames correctly. */
- frame_unwind_append_sniffer (gdbarch, i386obsd_trapframe_sniffer);
+ frame_unwind_prepend_unwinder (gdbarch, &i386obsd_trapframe_unwind);
}
/* OpenBSD a.out. */