aboutsummaryrefslogtreecommitdiff
path: root/gdb/remote.c
diff options
context:
space:
mode:
authorPedro Alves <palves@redhat.com>2010-05-26 18:19:28 +0000
committerPedro Alves <palves@redhat.com>2010-05-26 18:19:28 +0000
commitdde08ee10924b57d4e1c80e40a6a1fe14c93dcb5 (patch)
tree1d24a9d5f315737edcb115c43f6ae024437126ba /gdb/remote.c
parent0a5b531f15567f9b4d5b5ac6b6e89ee5e8e0e7f0 (diff)
downloadgdb-dde08ee10924b57d4e1c80e40a6a1fe14c93dcb5.zip
gdb-dde08ee10924b57d4e1c80e40a6a1fe14c93dcb5.tar.gz
gdb-dde08ee10924b57d4e1c80e40a6a1fe14c93dcb5.tar.bz2
gdb/
2010-05-26 Pedro Alves <pedro@codesourcery.com> * NEWS: Mention the `qRelocInsn' feature. * gdbarch.sh (relocate_instruction): New. * amd64-tdep.c (rip_relative_offset): New. (append_insns): New. (amd64_relocate_instruction): New. (amd64_init_abi): Install it. * i386-tdep.c (append_insns): New. (i386_relocate_instruction): New. (i386_gdbarch_init): Install it. * remote.c (remote_get_noisy_reply): Handle qRelocInsn requests. * gdbarch.h, gdbarch.c: Regenerate. gdb/doc/ 2010-05-26 Pedro Alves <pedro@codesourcery.com> * gdb.texinfo (General Query Packets) <qSupported>: Describe the `qRelocInsn' feature. (Relocate instruction reply packet): New subsection of `Tracepoint Packets'. (Tracepoint Packets): Mention that packets QTDP and QTStart support the qRelocInsn request, and add cross reference to new subsection.
Diffstat (limited to 'gdb/remote.c')
-rw-r--r--gdb/remote.c62
1 files changed, 55 insertions, 7 deletions
diff --git a/gdb/remote.c b/gdb/remote.c
index 9dc4d2d..16e577b 100644
--- a/gdb/remote.c
+++ b/gdb/remote.c
@@ -242,6 +242,8 @@ static void remote_terminal_ours (void);
static int remote_read_description_p (struct target_ops *target);
+char *unpack_varlen_hex (char *buff, ULONGEST *result);
+
/* The non-stop remote protocol provisions for one pending stop reply.
This is where we keep it until it is acknowledged. */
@@ -433,6 +435,55 @@ remote_get_noisy_reply (char **buf_p,
buf = *buf_p;
if (buf[0] == 'E')
trace_error (buf);
+ else if (strncmp (buf, "qRelocInsn:", strlen ("qRelocInsn:")) == 0)
+ {
+ ULONGEST ul;
+ CORE_ADDR from, to, org_to;
+ char *p, *pp;
+ int adjusted_size = 0;
+ volatile struct gdb_exception ex;
+
+ p = buf + strlen ("qRelocInsn:");
+ pp = unpack_varlen_hex (p, &ul);
+ if (*pp != ';')
+ error (_("invalid qRelocInsn packet: %s\n"), buf);
+ from = ul;
+
+ p = pp + 1;
+ pp = unpack_varlen_hex (p, &ul);
+ to = ul;
+
+ org_to = to;
+
+ TRY_CATCH (ex, RETURN_MASK_ALL)
+ {
+ gdbarch_relocate_instruction (target_gdbarch, &to, from);
+ }
+ if (ex.reason >= 0)
+ {
+ adjusted_size = to - org_to;
+
+ sprintf (buf, "qRelocInsn:%x", adjusted_size);
+ putpkt (buf);
+ }
+ else if (ex.reason < 0 && ex.error == MEMORY_ERROR)
+ {
+ /* Propagate memory errors silently back to the target.
+ The stub may have limited the range of addresses we
+ can write to, for example. */
+ putpkt ("E01");
+ }
+ else
+ {
+ /* Something unexpectedly bad happened. Be verbose so
+ we can tell what, and propagate the error back to the
+ stub, so it doesn't get stuck waiting for a
+ response. */
+ exception_fprintf (gdb_stderr, ex,
+ _("warning: relocating instruction: "));
+ putpkt ("E01");
+ }
+ }
else if (buf[0] == 'O' && buf[1] != 'K')
remote_console_output (buf + 1); /* 'O' message from stub */
else
@@ -3584,13 +3635,10 @@ remote_query_supported (void)
if (remote_support_xml)
q = remote_query_supported_append (q, remote_support_xml);
- if (q)
- {
- q = reconcat (q, "qSupported:", q, (char *) NULL);
- putpkt (q);
- }
- else
- putpkt ("qSupported");
+ q = remote_query_supported_append (q, "qRelocInsn+");
+
+ q = reconcat (q, "qSupported:", q, (char *) NULL);
+ putpkt (q);
do_cleanups (old_chain);