aboutsummaryrefslogtreecommitdiff
path: root/gdb/gdbserver/target.h
diff options
context:
space:
mode:
authorAntoine Tremblay <antoine.tremblay@ericsson.com>2015-11-30 15:08:04 -0500
committerAntoine Tremblay <antoine.tremblay@ericsson.com>2015-11-30 15:08:04 -0500
commit769ef81fec526f3c7513c88e82f98045f8971d14 (patch)
tree3c540206c97b423611558c38efbae5e4dcd35278 /gdb/gdbserver/target.h
parentfddedbe665db9cb9824150e454c89abdc750957a (diff)
downloadgdb-769ef81fec526f3c7513c88e82f98045f8971d14.zip
gdb-769ef81fec526f3c7513c88e82f98045f8971d14.tar.gz
gdb-769ef81fec526f3c7513c88e82f98045f8971d14.tar.bz2
Fix breakpoint size when stepping over a permanent breakpoint in GDBServer.
When manually stepping over a permanent breakpoint on ARM we need to fetch the right breakpoint size based on the current instruction set used. Since this is not encoded in the stop_pc, the instruction mode needs to be fetched from the CPSR register. This is done by introducing a new target operation called : breakpoint_kind_from_current_state. For other targets that do not need this, breakpoint_kind_from_pc is used. No regressions, tested on ubuntu 14.04 ARMv7 and x86. With gdbserver-{native,extended} / { -marm -mthumb } gdb/gdbserver/ChangeLog: * linux-arm-low.c (arm_is_thumb_mode): New function. (arm_breakpoint_at): Use arm_is_thumb_mode. (arm_breakpoint_kind_from_current_state): New function. (struct linux_target_ops) <breakpoint_kind_from_current_state>: Initialize. * linux-low.c (linux_wait_1): Call breakpoint_kind_from_current_state. (linux_breakpoint_kind_from_current_state): New function. (struct target_ops <breakpoint_kind_from_current_state>: Initialize. * linux-low.h (struct linux_target_ops) <breakpoint_kind_from_current_state>: New field. * target.h (struct target_ops): Likewise. (target_breakpoint_kind_from_current_state): New macro.
Diffstat (limited to 'gdb/gdbserver/target.h')
-rw-r--r--gdb/gdbserver/target.h11
1 files changed, 11 insertions, 0 deletions
diff --git a/gdb/gdbserver/target.h b/gdb/gdbserver/target.h
index a09ba2f..d3fcb36 100644
--- a/gdb/gdbserver/target.h
+++ b/gdb/gdbserver/target.h
@@ -457,6 +457,12 @@ struct target_ops
/* Return the thread's name, or NULL if the target is unable to determine it.
The returned value must not be freed by the caller. */
const char *(*thread_name) (ptid_t thread);
+
+ /* Return the breakpoint kind for this target based on the current
+ processor state (e.g. the current instruction mode on ARM) and the
+ PC. The PCPTR is adjusted to the real memory location in case a flag
+ (e.g., the Thumb bit on ARM) is present in the PC. */
+ int (*breakpoint_kind_from_current_state) (CORE_ADDR *pcptr);
};
extern struct target_ops *the_target;
@@ -644,6 +650,11 @@ int kill_inferior (int);
? (*the_target->breakpoint_kind_from_pc) (pcptr) \
: default_breakpoint_kind_from_pc (pcptr))
+#define target_breakpoint_kind_from_current_state(pcptr) \
+ (the_target->breakpoint_kind_from_current_state \
+ ? (*the_target->breakpoint_kind_from_current_state) (pcptr) \
+ : target_breakpoint_kind_from_pc (pcptr))
+
/* Start non-stop mode, returns 0 on success, -1 on failure. */
int start_non_stop (int nonstop);