diff options
author | Mark Kettenis <kettenis@gnu.org> | 2005-12-22 14:09:17 +0000 |
---|---|---|
committer | Mark Kettenis <kettenis@gnu.org> | 2005-12-22 14:09:17 +0000 |
commit | 7238f00288e6636f71fd6eede5cd929683861be1 (patch) | |
tree | 1d8600f99ffae06020b315519ee907591ee04f51 | |
parent | f6acec6208a44cd7da34bb2d19ddde2fd3a51d91 (diff) | |
download | gdb-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/ChangeLog | 9 | ||||
-rw-r--r-- | gdb/amd64obsd-tdep.c | 2 | ||||
-rw-r--r-- | gdb/i386obsd-tdep.c | 48 |
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. */ |