diff options
author | Pedro Alves <pedro@codesourcery.com> | 2008-05-02 16:49:54 +0000 |
---|---|---|
committer | Pedro Alves <pedro@codesourcery.com> | 2008-05-02 16:49:54 +0000 |
commit | 3402a51fc3c25dee0015983f5d0f2d248cda1176 (patch) | |
tree | 8f0482f389b011c1ce5a952513085d1c2dec191e /gdb/gdbarch.sh | |
parent | a0c7b9bc39e3afa372f954898f296b693ff05933 (diff) | |
download | gdb-3402a51fc3c25dee0015983f5d0f2d248cda1176.tar.gz |
Implement displaced stepping.
gdb/
* gdbarch.sh (max_insn_length): New 'variable'.
(displaced_step_copy, displaced_step_fixup)
(displaced_step_free_closure, displaced_step_location): New
functions.
(struct displaced_step_closure): Add forward declaration.
* gdbarch.c, gdbarch.h: Regenerated.
* arch-utils.c: #include "objfiles.h".
(simple_displaced_step_copy_insn)
(simple_displaced_step_free_closure)
(displaced_step_at_entry_point): New functions.
* arch-utils.h (simple_displaced_step_copy_insn)
(simple_displaced_step_free_closure)
(displaced_step_at_entry_point): New prototypes.
* i386-tdep.c (I386_MAX_INSN_LEN): Rename to...
(I386_MAX_MATCHED_INSN_LEN): ... this.
(i386_absolute_jmp_p, i386_absolute_call_p)
(i386_ret_p, i386_call_p, i386_breakpoint_p, i386_syscall_p)
(i386_displaced_step_fixup): New functions.
(struct i386_insn, i386_match_insn): Update.
(i386_gdbarch_init): Set gdbarch_max_insn_length.
* i386-tdep.h (I386_MAX_INSN_LEN): New.
(i386_displaced_step_fixup): New prototype.
* i386-linux-tdep.c (i386_linux_init_abi): Include "arch-utils.h".
Register gdbarch_displaced_step_copy,
gdbarch_displaced_step_fixup, gdbarch_displaced_step_free_closure,
and gdbarch_displaced_step_location functions.
* infrun.c (debug_displaced): New variable.
(show_debug_displaced): New function.
(struct displaced_step_request): New struct.
(displaced_step_request_queue, displaced_step_ptid)
(displaced_step_gdbarch, displaced_step_closure)
(displaced_step_original, displaced_step_copy)
(displaced_step_saved_copy, can_use_displaced_stepping): New
variables.
(show_can_use_displaced_stepping, use_displaced_stepping)
(displaced_step_clear, cleanup_displaced_step_closure)
(displaced_step_dump_bytes, displaced_step_prepare)
(displaced_step_clear_cleanup, write_memory_ptid)
(displaced_step_fixup): New functions.
(resume): Call displaced_step_prepare.
(proceed): Call read_pc once, and remember the value. If using
displaced stepping, don't remove breakpoints.
(handle_inferior_event): Call displaced_step_fixup. Add some
debugging output. When we try to step over a breakpoint, but get
a signal to deliver to the thread instead, ensure the step-resume
breakpoint is actually inserted. If a thread hop is needed, and
displaced stepping is enabled, don't remove breakpoints.
(init_wait_for_inferior): Call displaced_step_clear.
(_initialize_infrun): Add "set debug displaced" command. Add
"maint set can-use-displaced-stepping" command. Clear
displaced_step_ptid.
* inferior.h (debug_displaced): Declare variable.
(displaced_step_dump_bytes): Declare function.
* Makefile.in (arch-utils.o, i386-linux-tdep.o): Update
dependencies.
gdb/testsuite/
* gdb.asm/asmsrc1.s: Add scratch space.
gdb/doc/
* gdb.texinfo (Debugging Output): Document "set/show debug
displaced".
(Maintenance Commands): Document "maint set/show
can-use-displaced-stepping".
Diffstat (limited to 'gdb/gdbarch.sh')
-rwxr-xr-x | gdb/gdbarch.sh | 70 |
1 files changed, 70 insertions, 0 deletions
diff --git a/gdb/gdbarch.sh b/gdb/gdbarch.sh index 9f04f089d8f..08e37418a9a 100755 --- a/gdb/gdbarch.sh +++ b/gdb/gdbarch.sh @@ -616,6 +616,75 @@ v:int:vbit_in_delta:::0:0::0 # Advance PC to next instruction in order to skip a permanent breakpoint. F:void:skip_permanent_breakpoint:struct regcache *regcache:regcache +# The maximum length of an instruction on this architecture. +V:ULONGEST:max_insn_length:::0:0 + +# Copy the instruction at FROM to TO, and make any adjustments +# necessary to single-step it at that address. +# +# REGS holds the state the thread's registers will have before +# executing the copied instruction; the PC in REGS will refer to FROM, +# not the copy at TO. The caller should update it to point at TO later. +# +# Return a pointer to data of the architecture's choice to be passed +# to gdbarch_displaced_step_fixup. Or, return NULL to indicate that +# the instruction's effects have been completely simulated, with the +# resulting state written back to REGS. +# +# For a general explanation of displaced stepping and how GDB uses it, +# see the comments in infrun.c. +# +# The TO area is only guaranteed to have space for +# gdbarch_max_insn_length (arch) bytes, so this function must not +# write more bytes than that to that area. +# +# If you do not provide this function, GDB assumes that the +# architecture does not support displaced stepping. +# +# If your architecture doesn't need to adjust instructions before +# single-stepping them, consider using simple_displaced_step_copy_insn +# here. +M:struct displaced_step_closure *:displaced_step_copy_insn:CORE_ADDR from, CORE_ADDR to, struct regcache *regs:from, to, regs + +# Fix up the state resulting from successfully single-stepping a +# displaced instruction, to give the result we would have gotten from +# stepping the instruction in its original location. +# +# REGS is the register state resulting from single-stepping the +# displaced instruction. +# +# CLOSURE is the result from the matching call to +# gdbarch_displaced_step_copy_insn. +# +# If you provide gdbarch_displaced_step_copy_insn.but not this +# function, then GDB assumes that no fixup is needed after +# single-stepping the instruction. +# +# For a general explanation of displaced stepping and how GDB uses it, +# see the comments in infrun.c. +M:void:displaced_step_fixup:struct displaced_step_closure *closure, CORE_ADDR from, CORE_ADDR to, struct regcache *regs:closure, from, to, regs::NULL + +# Free a closure returned by gdbarch_displaced_step_copy_insn. +# +# If you provide gdbarch_displaced_step_copy_insn, you must provide +# this function as well. +# +# If your architecture uses closures that don't need to be freed, then +# you can use simple_displaced_step_free_closure here. +# +# For a general explanation of displaced stepping and how GDB uses it, +# see the comments in infrun.c. +m:void:displaced_step_free_closure:struct displaced_step_closure *closure:closure::NULL::(! gdbarch->displaced_step_free_closure) != (! gdbarch->displaced_step_copy_insn) + +# Return the address of an appropriate place to put displaced +# instructions while we step over them. There need only be one such +# place, since we're only stepping one thread over a breakpoint at a +# time. +# +# For a general explanation of displaced stepping and how GDB uses it, +# see the comments in infrun.c. +m:CORE_ADDR:displaced_step_location:void:::NULL::(! gdbarch->displaced_step_location) != (! gdbarch->displaced_step_copy_insn) + # Refresh overlay mapped state for section OSECT. F:void:overlay_update:struct obj_section *osect:osect @@ -742,6 +811,7 @@ struct target_ops; struct obstack; struct bp_target_info; struct target_desc; +struct displaced_step_closure; extern struct gdbarch *current_gdbarch; EOF |