diff options
author | Daniel Jacobowitz <dan@debian.org> | 2004-11-07 21:16:11 +0000 |
---|---|---|
committer | Daniel Jacobowitz <dan@debian.org> | 2004-11-07 21:16:11 +0000 |
commit | 81ae55503b371625eccd79f65dfd978e354de963 (patch) | |
tree | be8e0b1872a1450721ac63c731c3f6e662b0367c /gdb | |
parent | c634af77cd554f7f3d1c705a71025a4fa8f75196 (diff) | |
download | gdb-81ae55503b371625eccd79f65dfd978e354de963.tar.gz |
* dwarf2-frame.c (struct dwarf2_frame_ops): Add signal_frame_p.
(dwarf2_frame_set_signal_frame_p, dwarf2_frame_signal_frame_p)
(dwarf2_signal_frame_unwind): New.
(dwarf2_frame_sniffer): Use dwarf2_frame_signal_frame_p.
* dwarf2-frame.h (dwarf2_frame_set_signal_frame_p): New prototype.
Diffstat (limited to 'gdb')
-rw-r--r-- | gdb/ChangeLog | 8 | ||||
-rw-r--r-- | gdb/dwarf2-frame.c | 52 | ||||
-rw-r--r-- | gdb/dwarf2-frame.h | 8 |
3 files changed, 65 insertions, 3 deletions
diff --git a/gdb/ChangeLog b/gdb/ChangeLog index 4a9b4e39134..2b171379c83 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,3 +1,11 @@ +2004-11-07 Daniel Jacobowitz <dan@debian.org> + + * dwarf2-frame.c (struct dwarf2_frame_ops): Add signal_frame_p. + (dwarf2_frame_set_signal_frame_p, dwarf2_frame_signal_frame_p) + (dwarf2_signal_frame_unwind): New. + (dwarf2_frame_sniffer): Use dwarf2_frame_signal_frame_p. + * dwarf2-frame.h (dwarf2_frame_set_signal_frame_p): New prototype. + 2004-11-07 Mark Kettenis <kettenis@gnu.org> * Makefile.in (mips64obsd-tdep.o): Fix typo. diff --git a/gdb/dwarf2-frame.c b/gdb/dwarf2-frame.c index 4bad147ffd1..6a37e5df7df 100644 --- a/gdb/dwarf2-frame.c +++ b/gdb/dwarf2-frame.c @@ -471,6 +471,10 @@ struct dwarf2_frame_ops { /* Pre-initialize the register state REG for register REGNUM. */ void (*init_reg) (struct gdbarch *, int, struct dwarf2_frame_state_reg *); + + /* Check whether the frame preceding NEXT_FRAME will be a signal + trampoline. */ + int (*signal_frame_p) (struct gdbarch *, struct frame_info *); }; /* Default architecture-specific register state initialization @@ -547,6 +551,33 @@ dwarf2_frame_init_reg (struct gdbarch *gdbarch, int regnum, ops->init_reg (gdbarch, regnum, reg); } + +/* Set the architecture-specific signal trampoline recognition + function for GDBARCH to SIGNAL_FRAME_P. */ + +void +dwarf2_frame_set_signal_frame_p (struct gdbarch *gdbarch, + int (*signal_frame_p) (struct gdbarch *, + struct frame_info *)) +{ + struct dwarf2_frame_ops *ops = gdbarch_data (gdbarch, dwarf2_frame_data); + + ops->signal_frame_p = signal_frame_p; +} + +/* Query the architecture-specific signal frame recognizer for + NEXT_FRAME. */ + +static int +dwarf2_frame_signal_frame_p (struct gdbarch *gdbarch, + struct frame_info *next_frame) +{ + struct dwarf2_frame_ops *ops = gdbarch_data (gdbarch, dwarf2_frame_data); + + if (ops->signal_frame_p == NULL) + return 0; + return ops->signal_frame_p (gdbarch, next_frame); +} struct dwarf2_frame_cache @@ -845,6 +876,13 @@ static const struct frame_unwind dwarf2_frame_unwind = dwarf2_frame_prev_register }; +static const struct frame_unwind dwarf2_signal_frame_unwind = +{ + SIGTRAMP_FRAME, + dwarf2_frame_this_id, + dwarf2_frame_prev_register +}; + const struct frame_unwind * dwarf2_frame_sniffer (struct frame_info *next_frame) { @@ -852,10 +890,18 @@ dwarf2_frame_sniffer (struct frame_info *next_frame) function. frame_pc_unwind(), for a no-return next function, can end up returning something past the end of this function's body. */ CORE_ADDR block_addr = frame_unwind_address_in_block (next_frame); - if (dwarf2_frame_find_fde (&block_addr)) - return &dwarf2_frame_unwind; + if (!dwarf2_frame_find_fde (&block_addr)) + return NULL; - return NULL; + /* On some targets, signal trampolines may have unwind information. + We need to recognize them so that we set the frame type + correctly. */ + + if (dwarf2_frame_signal_frame_p (get_frame_arch (next_frame), + next_frame)) + return &dwarf2_signal_frame_unwind; + + return &dwarf2_frame_unwind; } diff --git a/gdb/dwarf2-frame.h b/gdb/dwarf2-frame.h index 1ae44b5064c..5191c0e8d49 100644 --- a/gdb/dwarf2-frame.h +++ b/gdb/dwarf2-frame.h @@ -79,6 +79,14 @@ extern void dwarf2_frame_set_init_reg (struct gdbarch *gdbarch, void (*init_reg) (struct gdbarch *, int, struct dwarf2_frame_state_reg *)); +/* Set the architecture-specific signal trampoline recognition + function for GDBARCH to SIGNAL_FRAME_P. */ + +extern void + dwarf2_frame_set_signal_frame_p (struct gdbarch *gdbarch, + int (*signal_frame_p) (struct gdbarch *, + struct frame_info *)); + /* Return the frame unwind methods for the function that contains PC, or NULL if it can't be handled by DWARF CFI frame unwinder. */ |