Make tracepoint operations go through target vector.
* target.h (enum trace_find_type): New enum. (struct target_ops): New fields to_trace_init, to_download_tracepoint, to_download_trace_state_variable, to_trace_set_readonly_regions, to_trace_start, to_get_trace_status, to_trace_stop, to_trace_find, to_get_trace_state_variable_value, to_set_disconnected_tracing. (target_trace_init): New macro. (target_download_tracepoint): New macro. (target_download_trace_state_variable): New macro. (target_trace_start): New macro. (target_trace_set_readonly_regions): New macro. (target_get_trace_status): New macro. (target_trace_stop): New macro. (target_trace_find): New macro. (target_get_trace_state_variable_value): New macro. (target_set_disconnected_tracing): New macro. * target.c (update_current_target): Inherit and set defaults for tracepoint operations. * tracepoint.c (default_collect): Make globally visible. (target_is_remote): Remove, along with all calls. (tvariables_info): Call target_get_trace_state_variable_value. (remote_set_transparent_ranges): Remove. (trace_start_command): Call target_trace_init, target_download_tracepoint, etc. (download_tracepoint): Remove. (trace_stop_command): Simplify. (stop_tracing): Call target_trace_stop. (get_trace_status): Call target_get_trace_status. (trace_status_command): Add case for targets that cannot trace. (finish_tfind_command): Change to take numerical arguments, call target_trace_find. (trace_find_command): Update call to finish_tfind_command. (trace_find_pc_command): Ditto. (trace_find_tracepoint_command): Ditto. (trace_find_line_command): Ditto. (trace_find_range_command): Ditto. (trace_find_outside_command): Ditto. (set_disconnected_tracing_value): Call target_set_disconnected_tracing. * remote.c: Add protocol encoding bits from tracepoint.c. (trace_error): Move from tracepoint.c. (remote_get_noisy_reply): Ditto. (free_actions_list_cleanup_wrapper): Ditto. (free_actions_list): Ditto. (remote_trace_init): New function. (remote_download_tracepoint): New function. (remote_download_trace_state_variable): New function. (remote_trace_set_readonly_regions): New function. (remote_trace_start): New function. (remote_get_trace_status): New function. (remote_trace_stop): New function. (remote_trace_find): New function. (remote_download_trace_state_variable): New function. (remote_set_disconnected_tracing): New function. (init_remote_ops): Add tracepoint operations.
This commit is contained in:
parent
3f08eb3589
commit
35b1e5cca0
@ -1,5 +1,62 @@
|
|||||||
2010-01-07 Stan Shebs <stan@codesourcery.com>
|
2010-01-07 Stan Shebs <stan@codesourcery.com>
|
||||||
|
|
||||||
|
Make tracepoint operations go through target vector.
|
||||||
|
* target.h (enum trace_find_type): New enum.
|
||||||
|
(struct target_ops): New fields to_trace_init,
|
||||||
|
to_download_tracepoint, to_download_trace_state_variable,
|
||||||
|
to_trace_set_readonly_regions, to_trace_start, to_get_trace_status,
|
||||||
|
to_trace_stop, to_trace_find, to_get_trace_state_variable_value,
|
||||||
|
to_set_disconnected_tracing.
|
||||||
|
(target_trace_init): New macro.
|
||||||
|
(target_download_tracepoint): New macro.
|
||||||
|
(target_download_trace_state_variable): New macro.
|
||||||
|
(target_trace_start): New macro.
|
||||||
|
(target_trace_set_readonly_regions): New macro.
|
||||||
|
(target_get_trace_status): New macro.
|
||||||
|
(target_trace_stop): New macro.
|
||||||
|
(target_trace_find): New macro.
|
||||||
|
(target_get_trace_state_variable_value): New macro.
|
||||||
|
(target_set_disconnected_tracing): New macro.
|
||||||
|
* target.c (update_current_target): Inherit and set defaults for
|
||||||
|
tracepoint operations.
|
||||||
|
* tracepoint.c (default_collect): Make globally visible.
|
||||||
|
(target_is_remote): Remove, along with all calls.
|
||||||
|
(tvariables_info): Call target_get_trace_state_variable_value.
|
||||||
|
(remote_set_transparent_ranges): Remove.
|
||||||
|
(trace_start_command): Call target_trace_init,
|
||||||
|
target_download_tracepoint, etc.
|
||||||
|
(download_tracepoint): Remove.
|
||||||
|
(trace_stop_command): Simplify.
|
||||||
|
(stop_tracing): Call target_trace_stop.
|
||||||
|
(get_trace_status): Call target_get_trace_status.
|
||||||
|
(trace_status_command): Add case for targets that cannot trace.
|
||||||
|
(finish_tfind_command): Change to take numerical arguments, call
|
||||||
|
target_trace_find.
|
||||||
|
(trace_find_command): Update call to finish_tfind_command.
|
||||||
|
(trace_find_pc_command): Ditto.
|
||||||
|
(trace_find_tracepoint_command): Ditto.
|
||||||
|
(trace_find_line_command): Ditto.
|
||||||
|
(trace_find_range_command): Ditto.
|
||||||
|
(trace_find_outside_command): Ditto.
|
||||||
|
(set_disconnected_tracing_value): Call
|
||||||
|
target_set_disconnected_tracing.
|
||||||
|
* remote.c: Add protocol encoding bits from tracepoint.c.
|
||||||
|
(trace_error): Move from tracepoint.c.
|
||||||
|
(remote_get_noisy_reply): Ditto.
|
||||||
|
(free_actions_list_cleanup_wrapper): Ditto.
|
||||||
|
(free_actions_list): Ditto.
|
||||||
|
(remote_trace_init): New function.
|
||||||
|
(remote_download_tracepoint): New function.
|
||||||
|
(remote_download_trace_state_variable): New function.
|
||||||
|
(remote_trace_set_readonly_regions): New function.
|
||||||
|
(remote_trace_start): New function.
|
||||||
|
(remote_get_trace_status): New function.
|
||||||
|
(remote_trace_stop): New function.
|
||||||
|
(remote_trace_find): New function.
|
||||||
|
(remote_download_trace_state_variable): New function.
|
||||||
|
(remote_set_disconnected_tracing): New function.
|
||||||
|
(init_remote_ops): Add tracepoint operations.
|
||||||
|
|
||||||
* tracepoint.c (trace_dump_command): Don't decr_pc_after_break.
|
* tracepoint.c (trace_dump_command): Don't decr_pc_after_break.
|
||||||
|
|
||||||
2010-01-07 Tristan Gingold <gingold@adacore.com>
|
2010-01-07 Tristan Gingold <gingold@adacore.com>
|
||||||
|
396
gdb/remote.c
396
gdb/remote.c
@ -63,6 +63,17 @@
|
|||||||
|
|
||||||
#include "memory-map.h"
|
#include "memory-map.h"
|
||||||
|
|
||||||
|
#include "tracepoint.h"
|
||||||
|
#include "ax.h"
|
||||||
|
#include "ax-gdb.h"
|
||||||
|
|
||||||
|
/* temp hacks for tracepoint encoding migration */
|
||||||
|
static char *target_buf;
|
||||||
|
static long target_buf_size;
|
||||||
|
/*static*/ void
|
||||||
|
encode_actions (struct breakpoint *t, char ***tdp_actions,
|
||||||
|
char ***stepping_actions);
|
||||||
|
|
||||||
/* The size to align memory write packets, when practical. The protocol
|
/* The size to align memory write packets, when practical. The protocol
|
||||||
does not guarantee any alignment, and gdb will generate short
|
does not guarantee any alignment, and gdb will generate short
|
||||||
writes and unaligned writes, but even as a best-effort attempt this
|
writes and unaligned writes, but even as a best-effort attempt this
|
||||||
@ -368,6 +379,52 @@ struct remote_arch_state
|
|||||||
long remote_packet_size;
|
long remote_packet_size;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
long sizeof_pkt = 2000;
|
||||||
|
|
||||||
|
/* Utility: generate error from an incoming stub packet. */
|
||||||
|
static void
|
||||||
|
trace_error (char *buf)
|
||||||
|
{
|
||||||
|
if (*buf++ != 'E')
|
||||||
|
return; /* not an error msg */
|
||||||
|
switch (*buf)
|
||||||
|
{
|
||||||
|
case '1': /* malformed packet error */
|
||||||
|
if (*++buf == '0') /* general case: */
|
||||||
|
error (_("remote.c: error in outgoing packet."));
|
||||||
|
else
|
||||||
|
error (_("remote.c: error in outgoing packet at field #%ld."),
|
||||||
|
strtol (buf, NULL, 16));
|
||||||
|
case '2':
|
||||||
|
error (_("trace API error 0x%s."), ++buf);
|
||||||
|
default:
|
||||||
|
error (_("Target returns error code '%s'."), buf);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Utility: wait for reply from stub, while accepting "O" packets. */
|
||||||
|
static char *
|
||||||
|
remote_get_noisy_reply (char **buf_p,
|
||||||
|
long *sizeof_buf)
|
||||||
|
{
|
||||||
|
do /* Loop on reply from remote stub. */
|
||||||
|
{
|
||||||
|
char *buf;
|
||||||
|
QUIT; /* allow user to bail out with ^C */
|
||||||
|
getpkt (buf_p, sizeof_buf, 0);
|
||||||
|
buf = *buf_p;
|
||||||
|
if (buf[0] == 0)
|
||||||
|
error (_("Target does not support this command."));
|
||||||
|
else if (buf[0] == 'E')
|
||||||
|
trace_error (buf);
|
||||||
|
else if (buf[0] == 'O' &&
|
||||||
|
buf[1] != 'K')
|
||||||
|
remote_console_output (buf + 1); /* 'O' message from stub */
|
||||||
|
else
|
||||||
|
return buf; /* here's the actual reply */
|
||||||
|
}
|
||||||
|
while (1);
|
||||||
|
}
|
||||||
|
|
||||||
/* Handle for retreving the remote protocol data from gdbarch. */
|
/* Handle for retreving the remote protocol data from gdbarch. */
|
||||||
static struct gdbarch_data *remote_gdbarch_data_handle;
|
static struct gdbarch_data *remote_gdbarch_data_handle;
|
||||||
@ -8942,6 +8999,331 @@ remote_supports_fast_tracepoints (void)
|
|||||||
return rs->fast_tracepoints;
|
return rs->fast_tracepoints;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
remote_trace_init ()
|
||||||
|
{
|
||||||
|
putpkt ("QTinit");
|
||||||
|
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
||||||
|
if (strcmp (target_buf, "OK"))
|
||||||
|
error (_("Target does not support this command."));
|
||||||
|
}
|
||||||
|
|
||||||
|
static void free_actions_list (char **actions_list);
|
||||||
|
static void free_actions_list_cleanup_wrapper (void *);
|
||||||
|
static void
|
||||||
|
free_actions_list_cleanup_wrapper (void *al)
|
||||||
|
{
|
||||||
|
free_actions_list (al);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
free_actions_list (char **actions_list)
|
||||||
|
{
|
||||||
|
int ndx;
|
||||||
|
|
||||||
|
if (actions_list == 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
for (ndx = 0; actions_list[ndx]; ndx++)
|
||||||
|
xfree (actions_list[ndx]);
|
||||||
|
|
||||||
|
xfree (actions_list);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
remote_download_tracepoint (struct breakpoint *t)
|
||||||
|
{
|
||||||
|
CORE_ADDR tpaddr;
|
||||||
|
char tmp[40];
|
||||||
|
char buf[2048];
|
||||||
|
char **tdp_actions;
|
||||||
|
char **stepping_actions;
|
||||||
|
int ndx;
|
||||||
|
struct cleanup *old_chain = NULL;
|
||||||
|
struct agent_expr *aexpr;
|
||||||
|
struct cleanup *aexpr_chain = NULL;
|
||||||
|
char *pkt;
|
||||||
|
|
||||||
|
encode_actions (t, &tdp_actions, &stepping_actions);
|
||||||
|
old_chain = make_cleanup (free_actions_list_cleanup_wrapper,
|
||||||
|
tdp_actions);
|
||||||
|
(void) make_cleanup (free_actions_list_cleanup_wrapper, stepping_actions);
|
||||||
|
|
||||||
|
tpaddr = t->loc->address;
|
||||||
|
sprintf_vma (tmp, (t->loc ? tpaddr : 0));
|
||||||
|
sprintf (buf, "QTDP:%x:%s:%c:%lx:%x", t->number,
|
||||||
|
tmp, /* address */
|
||||||
|
(t->enable_state == bp_enabled ? 'E' : 'D'),
|
||||||
|
t->step_count, t->pass_count);
|
||||||
|
/* Fast tracepoints are mostly handled by the target, but we can
|
||||||
|
tell the target how big of an instruction block should be moved
|
||||||
|
around. */
|
||||||
|
if (t->type == bp_fast_tracepoint)
|
||||||
|
{
|
||||||
|
/* Only test for support at download time; we may not know
|
||||||
|
target capabilities at definition time. */
|
||||||
|
if (remote_supports_fast_tracepoints ())
|
||||||
|
{
|
||||||
|
int isize;
|
||||||
|
|
||||||
|
if (gdbarch_fast_tracepoint_valid_at (target_gdbarch,
|
||||||
|
tpaddr, &isize, NULL))
|
||||||
|
sprintf (buf + strlen (buf), ":F%x", isize);
|
||||||
|
else
|
||||||
|
/* If it passed validation at definition but fails now,
|
||||||
|
something is very wrong. */
|
||||||
|
internal_error (__FILE__, __LINE__,
|
||||||
|
"Fast tracepoint not valid during download");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
/* Fast tracepoints are functionally identical to regular
|
||||||
|
tracepoints, so don't take lack of support as a reason to
|
||||||
|
give up on the trace run. */
|
||||||
|
warning (_("Target does not support fast tracepoints, downloading %d as regular tracepoint"), t->number);
|
||||||
|
}
|
||||||
|
/* If the tracepoint has a conditional, make it into an agent
|
||||||
|
expression and append to the definition. */
|
||||||
|
if (t->loc->cond)
|
||||||
|
{
|
||||||
|
/* Only test support at download time, we may not know target
|
||||||
|
capabilities at definition time. */
|
||||||
|
if (remote_supports_cond_tracepoints ())
|
||||||
|
{
|
||||||
|
aexpr = gen_eval_for_expr (t->loc->address, t->loc->cond);
|
||||||
|
aexpr_chain = make_cleanup_free_agent_expr (aexpr);
|
||||||
|
sprintf (buf + strlen (buf), ":X%x,", aexpr->len);
|
||||||
|
pkt = buf + strlen (buf);
|
||||||
|
for (ndx = 0; ndx < aexpr->len; ++ndx)
|
||||||
|
pkt = pack_hex_byte (pkt, aexpr->buf[ndx]);
|
||||||
|
*pkt = '\0';
|
||||||
|
do_cleanups (aexpr_chain);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
warning (_("Target does not support conditional tracepoints, ignoring tp %d cond"), t->number);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (t->actions || *default_collect)
|
||||||
|
strcat (buf, "-");
|
||||||
|
putpkt (buf);
|
||||||
|
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
||||||
|
if (strcmp (target_buf, "OK"))
|
||||||
|
error (_("Target does not support tracepoints."));
|
||||||
|
|
||||||
|
if (!t->actions && !*default_collect)
|
||||||
|
return;
|
||||||
|
|
||||||
|
/* do_single_steps (t); */
|
||||||
|
if (tdp_actions)
|
||||||
|
{
|
||||||
|
for (ndx = 0; tdp_actions[ndx]; ndx++)
|
||||||
|
{
|
||||||
|
QUIT; /* allow user to bail out with ^C */
|
||||||
|
sprintf (buf, "QTDP:-%x:%s:%s%c",
|
||||||
|
t->number, tmp, /* address */
|
||||||
|
tdp_actions[ndx],
|
||||||
|
((tdp_actions[ndx + 1] || stepping_actions)
|
||||||
|
? '-' : 0));
|
||||||
|
putpkt (buf);
|
||||||
|
remote_get_noisy_reply (&target_buf,
|
||||||
|
&target_buf_size);
|
||||||
|
if (strcmp (target_buf, "OK"))
|
||||||
|
error (_("Error on target while setting tracepoints."));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (stepping_actions)
|
||||||
|
{
|
||||||
|
for (ndx = 0; stepping_actions[ndx]; ndx++)
|
||||||
|
{
|
||||||
|
QUIT; /* allow user to bail out with ^C */
|
||||||
|
sprintf (buf, "QTDP:-%x:%s:%s%s%s",
|
||||||
|
t->number, tmp, /* address */
|
||||||
|
((ndx == 0) ? "S" : ""),
|
||||||
|
stepping_actions[ndx],
|
||||||
|
(stepping_actions[ndx + 1] ? "-" : ""));
|
||||||
|
putpkt (buf);
|
||||||
|
remote_get_noisy_reply (&target_buf,
|
||||||
|
&target_buf_size);
|
||||||
|
if (strcmp (target_buf, "OK"))
|
||||||
|
error (_("Error on target while setting tracepoints."));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
do_cleanups (old_chain);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
remote_download_trace_state_variable (struct trace_state_variable *tsv)
|
||||||
|
{
|
||||||
|
struct remote_state *rs = get_remote_state ();
|
||||||
|
|
||||||
|
sprintf (rs->buf, "QTDV:%x:%s",
|
||||||
|
tsv->number, phex ((ULONGEST) tsv->initial_value, 8));
|
||||||
|
putpkt (rs->buf);
|
||||||
|
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
remote_trace_set_readonly_regions ()
|
||||||
|
{
|
||||||
|
asection *s;
|
||||||
|
bfd_size_type size;
|
||||||
|
bfd_vma lma;
|
||||||
|
int anysecs = 0;
|
||||||
|
|
||||||
|
if (!exec_bfd)
|
||||||
|
return; /* No information to give. */
|
||||||
|
|
||||||
|
strcpy (target_buf, "QTro");
|
||||||
|
for (s = exec_bfd->sections; s; s = s->next)
|
||||||
|
{
|
||||||
|
char tmp1[40], tmp2[40];
|
||||||
|
|
||||||
|
if ((s->flags & SEC_LOAD) == 0 ||
|
||||||
|
/* (s->flags & SEC_CODE) == 0 || */
|
||||||
|
(s->flags & SEC_READONLY) == 0)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
anysecs = 1;
|
||||||
|
lma = s->lma;
|
||||||
|
size = bfd_get_section_size (s);
|
||||||
|
sprintf_vma (tmp1, lma);
|
||||||
|
sprintf_vma (tmp2, lma + size);
|
||||||
|
sprintf (target_buf + strlen (target_buf),
|
||||||
|
":%s,%s", tmp1, tmp2);
|
||||||
|
}
|
||||||
|
if (anysecs)
|
||||||
|
{
|
||||||
|
putpkt (target_buf);
|
||||||
|
getpkt (&target_buf, &target_buf_size, 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
remote_trace_start ()
|
||||||
|
{
|
||||||
|
putpkt ("QTStart");
|
||||||
|
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
||||||
|
if (strcmp (target_buf, "OK"))
|
||||||
|
error (_("Bogus reply from target: %s"), target_buf);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
remote_get_trace_status (int *stop_reason)
|
||||||
|
{
|
||||||
|
putpkt ("qTStatus");
|
||||||
|
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
||||||
|
|
||||||
|
if (target_buf[0] != 'T' ||
|
||||||
|
(target_buf[1] != '0' && target_buf[1] != '1'))
|
||||||
|
error (_("Bogus trace status reply from target: %s"), target_buf);
|
||||||
|
|
||||||
|
return (target_buf[1] == '1');
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
remote_trace_stop ()
|
||||||
|
{
|
||||||
|
putpkt ("QTStop");
|
||||||
|
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
||||||
|
if (strcmp (target_buf, "OK"))
|
||||||
|
error (_("Bogus reply from target: %s"), target_buf);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
remote_trace_find (enum trace_find_type type, int num,
|
||||||
|
ULONGEST addr1, ULONGEST addr2,
|
||||||
|
int *tpp)
|
||||||
|
{
|
||||||
|
struct remote_state *rs = get_remote_state ();
|
||||||
|
char *p, *reply;
|
||||||
|
int target_frameno = -1, target_tracept = -1;
|
||||||
|
|
||||||
|
p = rs->buf;
|
||||||
|
strcpy (p, "QTFrame:");
|
||||||
|
p = strchr (p, '\0');
|
||||||
|
switch (type)
|
||||||
|
{
|
||||||
|
case tfind_number:
|
||||||
|
sprintf (p, "%x", num);
|
||||||
|
break;
|
||||||
|
case tfind_pc:
|
||||||
|
sprintf (p, "pc:%s", paddress (target_gdbarch, addr1));
|
||||||
|
break;
|
||||||
|
case tfind_tp:
|
||||||
|
sprintf (p, "tdp:%x", num);
|
||||||
|
break;
|
||||||
|
case tfind_range:
|
||||||
|
sprintf (p, "range:%s:%s", paddress (target_gdbarch, addr1), paddress (target_gdbarch, addr2));
|
||||||
|
break;
|
||||||
|
case tfind_outside:
|
||||||
|
sprintf (p, "outside:%s:%s", paddress (target_gdbarch, addr1), paddress (target_gdbarch, addr2));
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
error ("Unknown trace find type %d", type);
|
||||||
|
}
|
||||||
|
|
||||||
|
putpkt (rs->buf);
|
||||||
|
reply = remote_get_noisy_reply (&(rs->buf), &sizeof_pkt);
|
||||||
|
|
||||||
|
while (reply && *reply)
|
||||||
|
switch (*reply)
|
||||||
|
{
|
||||||
|
case 'F':
|
||||||
|
if ((target_frameno = (int) strtol (++reply, &reply, 16)) == -1)
|
||||||
|
error (_("Target failed to find requested trace frame."));
|
||||||
|
break;
|
||||||
|
case 'T':
|
||||||
|
if ((target_tracept = (int) strtol (++reply, &reply, 16)) == -1)
|
||||||
|
error (_("Target failed to find requested trace frame."));
|
||||||
|
break;
|
||||||
|
case 'O': /* "OK"? */
|
||||||
|
if (reply[1] == 'K' && reply[2] == '\0')
|
||||||
|
reply += 2;
|
||||||
|
else
|
||||||
|
error (_("Bogus reply from target: %s"), reply);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
error (_("Bogus reply from target: %s"), reply);
|
||||||
|
}
|
||||||
|
if (tpp)
|
||||||
|
*tpp = target_tracept;
|
||||||
|
return target_frameno;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
remote_get_trace_state_variable_value (int tsvnum, LONGEST *val)
|
||||||
|
{
|
||||||
|
struct remote_state *rs = get_remote_state ();
|
||||||
|
char *reply;
|
||||||
|
ULONGEST uval;
|
||||||
|
|
||||||
|
sprintf (rs->buf, "qTV:%x", tsvnum);
|
||||||
|
putpkt (rs->buf);
|
||||||
|
reply = remote_get_noisy_reply (&target_buf, &target_buf_size);
|
||||||
|
if (reply && *reply)
|
||||||
|
{
|
||||||
|
if (*reply == 'V')
|
||||||
|
{
|
||||||
|
unpack_varlen_hex (reply + 1, &uval);
|
||||||
|
*val = (LONGEST) uval;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
remote_set_disconnected_tracing (int val)
|
||||||
|
{
|
||||||
|
struct remote_state *rs = get_remote_state ();
|
||||||
|
|
||||||
|
sprintf (rs->buf, "QTDisconnected:%x", val);
|
||||||
|
putpkt (rs->buf);
|
||||||
|
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
||||||
|
if (strcmp (target_buf, "OK"))
|
||||||
|
error (_("Target does not support this command."));
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
init_remote_ops (void)
|
init_remote_ops (void)
|
||||||
{
|
{
|
||||||
@ -9005,6 +9387,16 @@ Specify the serial device it is connected to\n\
|
|||||||
remote_ops.to_terminal_ours = remote_terminal_ours;
|
remote_ops.to_terminal_ours = remote_terminal_ours;
|
||||||
remote_ops.to_supports_non_stop = remote_supports_non_stop;
|
remote_ops.to_supports_non_stop = remote_supports_non_stop;
|
||||||
remote_ops.to_supports_multi_process = remote_supports_multi_process;
|
remote_ops.to_supports_multi_process = remote_supports_multi_process;
|
||||||
|
remote_ops.to_trace_init = remote_trace_init;
|
||||||
|
remote_ops.to_download_tracepoint = remote_download_tracepoint;
|
||||||
|
remote_ops.to_download_trace_state_variable = remote_download_trace_state_variable;
|
||||||
|
remote_ops.to_trace_set_readonly_regions = remote_trace_set_readonly_regions;
|
||||||
|
remote_ops.to_trace_start = remote_trace_start;
|
||||||
|
remote_ops.to_get_trace_status = remote_get_trace_status;
|
||||||
|
remote_ops.to_trace_stop = remote_trace_stop;
|
||||||
|
remote_ops.to_trace_find = remote_trace_find;
|
||||||
|
remote_ops.to_get_trace_state_variable_value = remote_get_trace_state_variable_value;
|
||||||
|
remote_ops.to_set_disconnected_tracing = remote_set_disconnected_tracing;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Set up the extended remote vector by making a copy of the standard
|
/* Set up the extended remote vector by making a copy of the standard
|
||||||
@ -9227,7 +9619,6 @@ remote_get_tracing_state (struct remote_state *rs)
|
|||||||
struct uploaded_tp *utp;
|
struct uploaded_tp *utp;
|
||||||
struct breakpoint *t;
|
struct breakpoint *t;
|
||||||
extern void get_trace_status ();
|
extern void get_trace_status ();
|
||||||
extern unsigned long trace_running_p;
|
|
||||||
|
|
||||||
get_trace_status ();
|
get_trace_status ();
|
||||||
if (trace_running_p)
|
if (trace_running_p)
|
||||||
@ -9646,4 +10037,7 @@ Show the remote pathname for \"run\""), NULL, NULL, NULL,
|
|||||||
magic_null_ptid = ptid_build (42000, 1, -1);
|
magic_null_ptid = ptid_build (42000, 1, -1);
|
||||||
not_sent_ptid = ptid_build (42000, 1, -2);
|
not_sent_ptid = ptid_build (42000, 1, -2);
|
||||||
any_thread_ptid = ptid_build (42000, 1, 0);
|
any_thread_ptid = ptid_build (42000, 1, 0);
|
||||||
|
|
||||||
|
target_buf_size = 2048;
|
||||||
|
target_buf = xmalloc (target_buf_size);
|
||||||
}
|
}
|
||||||
|
40
gdb/target.c
40
gdb/target.c
@ -685,6 +685,16 @@ update_current_target (void)
|
|||||||
INHERIT (to_get_ada_task_ptid, t);
|
INHERIT (to_get_ada_task_ptid, t);
|
||||||
/* Do not inherit to_search_memory. */
|
/* Do not inherit to_search_memory. */
|
||||||
INHERIT (to_supports_multi_process, t);
|
INHERIT (to_supports_multi_process, t);
|
||||||
|
INHERIT (to_trace_init, t);
|
||||||
|
INHERIT (to_download_tracepoint, t);
|
||||||
|
INHERIT (to_download_trace_state_variable, t);
|
||||||
|
INHERIT (to_trace_set_readonly_regions, t);
|
||||||
|
INHERIT (to_trace_start, t);
|
||||||
|
INHERIT (to_get_trace_status, t);
|
||||||
|
INHERIT (to_trace_stop, t);
|
||||||
|
INHERIT (to_trace_find, t);
|
||||||
|
INHERIT (to_get_trace_state_variable_value, t);
|
||||||
|
INHERIT (to_set_disconnected_tracing, t);
|
||||||
INHERIT (to_magic, t);
|
INHERIT (to_magic, t);
|
||||||
/* Do not inherit to_memory_map. */
|
/* Do not inherit to_memory_map. */
|
||||||
/* Do not inherit to_flash_erase. */
|
/* Do not inherit to_flash_erase. */
|
||||||
@ -833,6 +843,36 @@ update_current_target (void)
|
|||||||
de_fault (to_supports_multi_process,
|
de_fault (to_supports_multi_process,
|
||||||
(int (*) (void))
|
(int (*) (void))
|
||||||
return_zero);
|
return_zero);
|
||||||
|
de_fault (to_trace_init,
|
||||||
|
(void (*) (void))
|
||||||
|
tcomplain);
|
||||||
|
de_fault (to_download_tracepoint,
|
||||||
|
(void (*) (struct breakpoint *))
|
||||||
|
tcomplain);
|
||||||
|
de_fault (to_download_trace_state_variable,
|
||||||
|
(void (*) (struct trace_state_variable *))
|
||||||
|
tcomplain);
|
||||||
|
de_fault (to_trace_set_readonly_regions,
|
||||||
|
(void (*) (void))
|
||||||
|
tcomplain);
|
||||||
|
de_fault (to_trace_start,
|
||||||
|
(void (*) (void))
|
||||||
|
tcomplain);
|
||||||
|
de_fault (to_get_trace_status,
|
||||||
|
(int (*) (int *))
|
||||||
|
return_minus_one);
|
||||||
|
de_fault (to_trace_stop,
|
||||||
|
(void (*) (void))
|
||||||
|
tcomplain);
|
||||||
|
de_fault (to_trace_find,
|
||||||
|
(int (*) (enum trace_find_type, int, ULONGEST, ULONGEST, int *))
|
||||||
|
return_zero);
|
||||||
|
de_fault (to_get_trace_state_variable_value,
|
||||||
|
(int (*) (int, LONGEST *))
|
||||||
|
return_zero);
|
||||||
|
de_fault (to_set_disconnected_tracing,
|
||||||
|
(void (*) (int))
|
||||||
|
tcomplain);
|
||||||
#undef de_fault
|
#undef de_fault
|
||||||
|
|
||||||
/* Finally, position the target-stack beneath the squashed
|
/* Finally, position the target-stack beneath the squashed
|
||||||
|
86
gdb/target.h
86
gdb/target.h
@ -31,6 +31,7 @@ struct target_ops;
|
|||||||
struct bp_target_info;
|
struct bp_target_info;
|
||||||
struct regcache;
|
struct regcache;
|
||||||
struct target_section_table;
|
struct target_section_table;
|
||||||
|
struct trace_state_variable;
|
||||||
|
|
||||||
/* This include file defines the interface between the main part
|
/* This include file defines the interface between the main part
|
||||||
of the debugger, and the part which is target-specific, or
|
of the debugger, and the part which is target-specific, or
|
||||||
@ -258,6 +259,18 @@ enum target_object
|
|||||||
/* Possible future objects: TARGET_OBJECT_FILE, ... */
|
/* Possible future objects: TARGET_OBJECT_FILE, ... */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/* Enumeration of the kinds of traceframe searches that a target may
|
||||||
|
be able to perform. */
|
||||||
|
|
||||||
|
enum trace_find_type
|
||||||
|
{
|
||||||
|
tfind_number,
|
||||||
|
tfind_pc,
|
||||||
|
tfind_tp,
|
||||||
|
tfind_range,
|
||||||
|
tfind_outside,
|
||||||
|
};
|
||||||
|
|
||||||
/* Request that OPS transfer up to LEN 8-bit bytes of the target's
|
/* Request that OPS transfer up to LEN 8-bit bytes of the target's
|
||||||
OBJECT. The OFFSET, for a seekable object, specifies the
|
OBJECT. The OFFSET, for a seekable object, specifies the
|
||||||
starting point. The ANNEX can be used to provide additional
|
starting point. The ANNEX can be used to provide additional
|
||||||
@ -597,6 +610,47 @@ struct target_ops
|
|||||||
struct address_space *(*to_thread_address_space) (struct target_ops *,
|
struct address_space *(*to_thread_address_space) (struct target_ops *,
|
||||||
ptid_t);
|
ptid_t);
|
||||||
|
|
||||||
|
/* Tracepoint-related operations. */
|
||||||
|
|
||||||
|
/* Prepare the target for a tracing run. */
|
||||||
|
void (*to_trace_init) (void);
|
||||||
|
|
||||||
|
/* Send full details of a tracepoint to the target. */
|
||||||
|
void (*to_download_tracepoint) (struct breakpoint *t);
|
||||||
|
|
||||||
|
/* Send full details of a trace state variable to the target. */
|
||||||
|
void (*to_download_trace_state_variable) (struct trace_state_variable *tsv);
|
||||||
|
|
||||||
|
/* Inform the target info of memory regions that are readonly
|
||||||
|
(such as text sections), and so it should return data from
|
||||||
|
those rather than look in the trace buffer. */
|
||||||
|
void (*to_trace_set_readonly_regions) (void);
|
||||||
|
|
||||||
|
/* Start a trace run. */
|
||||||
|
void (*to_trace_start) (void);
|
||||||
|
|
||||||
|
/* Get the current status of a tracing run. */
|
||||||
|
int (*to_get_trace_status) (int *stop_reason);
|
||||||
|
|
||||||
|
/* Stop a trace run. */
|
||||||
|
void (*to_trace_stop) (void);
|
||||||
|
|
||||||
|
/* Ask the target to find a trace frame of the given type TYPE,
|
||||||
|
using NUM, ADDR1, and ADDR2 as search parameters. Returns the
|
||||||
|
number of the trace frame, and also the tracepoint number at
|
||||||
|
TPP. */
|
||||||
|
int (*to_trace_find) (enum trace_find_type type, int num,
|
||||||
|
ULONGEST addr1, ULONGEST addr2, int *tpp);
|
||||||
|
|
||||||
|
/* Get the value of the trace state variable number TSV, returning
|
||||||
|
1 if the value is known and writing the value itself into the
|
||||||
|
location pointed to by VAL, else returning 0. */
|
||||||
|
int (*to_get_trace_state_variable_value) (int tsv, LONGEST *val);
|
||||||
|
|
||||||
|
/* Set the target's tracing behavior in response to unexpected
|
||||||
|
disconnection - set VAL to 1 to keep tracing, 0 to stop. */
|
||||||
|
void (*to_set_disconnected_tracing) (int val);
|
||||||
|
|
||||||
int to_magic;
|
int to_magic;
|
||||||
/* Need sub-structure for target machine related rather than comm related?
|
/* Need sub-structure for target machine related rather than comm related?
|
||||||
*/
|
*/
|
||||||
@ -1238,6 +1292,38 @@ extern int target_search_memory (CORE_ADDR start_addr,
|
|||||||
ULONGEST pattern_len,
|
ULONGEST pattern_len,
|
||||||
CORE_ADDR *found_addrp);
|
CORE_ADDR *found_addrp);
|
||||||
|
|
||||||
|
/* Tracepoint-related operations. */
|
||||||
|
|
||||||
|
#define target_trace_init() \
|
||||||
|
(*current_target.to_trace_init) ()
|
||||||
|
|
||||||
|
#define target_download_tracepoint(t) \
|
||||||
|
(*current_target.to_download_tracepoint) (t)
|
||||||
|
|
||||||
|
#define target_download_trace_state_variable(tsv) \
|
||||||
|
(*current_target.to_download_trace_state_variable) (tsv)
|
||||||
|
|
||||||
|
#define target_trace_start() \
|
||||||
|
(*current_target.to_trace_start) ()
|
||||||
|
|
||||||
|
#define target_trace_set_readonly_regions() \
|
||||||
|
(*current_target.to_trace_set_readonly_regions) ()
|
||||||
|
|
||||||
|
#define target_get_trace_status(stop_reason) \
|
||||||
|
(*current_target.to_get_trace_status) (stop_reason)
|
||||||
|
|
||||||
|
#define target_trace_stop() \
|
||||||
|
(*current_target.to_trace_stop) ()
|
||||||
|
|
||||||
|
#define target_trace_find(type,num,addr1,addr2,tpp) \
|
||||||
|
(*current_target.to_trace_find) ((type), (num), (addr1), (addr2), (tpp))
|
||||||
|
|
||||||
|
#define target_get_trace_state_variable_value(tsv,val) \
|
||||||
|
(*current_target.to_get_trace_state_variable_value) ((tsv), (val))
|
||||||
|
|
||||||
|
#define target_set_disconnected_tracing(val) \
|
||||||
|
(*current_target.to_set_disconnected_tracing) (val)
|
||||||
|
|
||||||
/* Command logging facility. */
|
/* Command logging facility. */
|
||||||
|
|
||||||
#define target_log_command(p) \
|
#define target_log_command(p) \
|
||||||
|
498
gdb/tracepoint.c
498
gdb/tracepoint.c
@ -32,10 +32,6 @@
|
|||||||
#include "inferior.h"
|
#include "inferior.h"
|
||||||
#include "breakpoint.h"
|
#include "breakpoint.h"
|
||||||
#include "tracepoint.h"
|
#include "tracepoint.h"
|
||||||
#include "remote.h"
|
|
||||||
extern int remote_supports_cond_tracepoints (void);
|
|
||||||
extern int remote_supports_fast_tracepoints (void);
|
|
||||||
extern char *unpack_varlen_hex (char *buff, ULONGEST *result);
|
|
||||||
#include "linespec.h"
|
#include "linespec.h"
|
||||||
#include "regcache.h"
|
#include "regcache.h"
|
||||||
#include "completer.h"
|
#include "completer.h"
|
||||||
@ -46,6 +42,7 @@ extern char *unpack_varlen_hex (char *buff, ULONGEST *result);
|
|||||||
#include "valprint.h"
|
#include "valprint.h"
|
||||||
#include "gdbcore.h"
|
#include "gdbcore.h"
|
||||||
#include "objfiles.h"
|
#include "objfiles.h"
|
||||||
|
#include "filenames.h"
|
||||||
|
|
||||||
#include "ax.h"
|
#include "ax.h"
|
||||||
#include "ax-gdb.h"
|
#include "ax-gdb.h"
|
||||||
@ -144,13 +141,10 @@ static struct symtab_and_line traceframe_sal;
|
|||||||
static struct cmd_list_element *tfindlist;
|
static struct cmd_list_element *tfindlist;
|
||||||
|
|
||||||
/* List of expressions to collect by default at each tracepoint hit. */
|
/* List of expressions to collect by default at each tracepoint hit. */
|
||||||
static char *default_collect = "";
|
char *default_collect = "";
|
||||||
|
|
||||||
static int disconnected_tracing;
|
static int disconnected_tracing;
|
||||||
|
|
||||||
static char *target_buf;
|
|
||||||
static long target_buf_size;
|
|
||||||
|
|
||||||
/* ======= Important command functions: ======= */
|
/* ======= Important command functions: ======= */
|
||||||
static void trace_actions_command (char *, int);
|
static void trace_actions_command (char *, int);
|
||||||
static void trace_start_command (char *, int);
|
static void trace_start_command (char *, int);
|
||||||
@ -173,70 +167,11 @@ static char *mem2hex (gdb_byte *, char *, int);
|
|||||||
static void add_register (struct collection_list *collection,
|
static void add_register (struct collection_list *collection,
|
||||||
unsigned int regno);
|
unsigned int regno);
|
||||||
static struct cleanup *make_cleanup_free_actions (struct breakpoint *t);
|
static struct cleanup *make_cleanup_free_actions (struct breakpoint *t);
|
||||||
static void free_actions_list (char **actions_list);
|
|
||||||
static void free_actions_list_cleanup_wrapper (void *);
|
|
||||||
|
|
||||||
extern void send_disconnected_tracing_value (int value);
|
extern void send_disconnected_tracing_value (int value);
|
||||||
|
|
||||||
extern void _initialize_tracepoint (void);
|
extern void _initialize_tracepoint (void);
|
||||||
|
|
||||||
/* Utility: returns true if "target remote" */
|
|
||||||
static int
|
|
||||||
target_is_remote (void)
|
|
||||||
{
|
|
||||||
if (current_target.to_shortname &&
|
|
||||||
(strcmp (current_target.to_shortname, "remote") == 0
|
|
||||||
|| strcmp (current_target.to_shortname, "extended-remote") == 0))
|
|
||||||
return 1;
|
|
||||||
else
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Utility: generate error from an incoming stub packet. */
|
|
||||||
static void
|
|
||||||
trace_error (char *buf)
|
|
||||||
{
|
|
||||||
if (*buf++ != 'E')
|
|
||||||
return; /* not an error msg */
|
|
||||||
switch (*buf)
|
|
||||||
{
|
|
||||||
case '1': /* malformed packet error */
|
|
||||||
if (*++buf == '0') /* general case: */
|
|
||||||
error (_("tracepoint.c: error in outgoing packet."));
|
|
||||||
else
|
|
||||||
error (_("tracepoint.c: error in outgoing packet at field #%ld."),
|
|
||||||
strtol (buf, NULL, 16));
|
|
||||||
case '2':
|
|
||||||
error (_("trace API error 0x%s."), ++buf);
|
|
||||||
default:
|
|
||||||
error (_("Target returns error code '%s'."), buf);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Utility: wait for reply from stub, while accepting "O" packets. */
|
|
||||||
static char *
|
|
||||||
remote_get_noisy_reply (char **buf_p,
|
|
||||||
long *sizeof_buf)
|
|
||||||
{
|
|
||||||
do /* Loop on reply from remote stub. */
|
|
||||||
{
|
|
||||||
char *buf;
|
|
||||||
QUIT; /* allow user to bail out with ^C */
|
|
||||||
getpkt (buf_p, sizeof_buf, 0);
|
|
||||||
buf = *buf_p;
|
|
||||||
if (buf[0] == 0)
|
|
||||||
error (_("Target does not support this command."));
|
|
||||||
else if (buf[0] == 'E')
|
|
||||||
trace_error (buf);
|
|
||||||
else if (buf[0] == 'O' &&
|
|
||||||
buf[1] != 'K')
|
|
||||||
remote_console_output (buf + 1); /* 'O' message from stub */
|
|
||||||
else
|
|
||||||
return buf; /* here's the actual reply */
|
|
||||||
}
|
|
||||||
while (1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Set traceframe number to NUM. */
|
/* Set traceframe number to NUM. */
|
||||||
static void
|
static void
|
||||||
set_traceframe_num (int num)
|
set_traceframe_num (int num)
|
||||||
@ -449,37 +384,17 @@ tvariables_info (char *args, int from_tty)
|
|||||||
char *reply;
|
char *reply;
|
||||||
ULONGEST tval;
|
ULONGEST tval;
|
||||||
|
|
||||||
if (target_is_remote ())
|
|
||||||
{
|
|
||||||
char buf[20];
|
|
||||||
|
|
||||||
for (ix = 0; VEC_iterate (tsv_s, tvariables, ix, tsv); ++ix)
|
|
||||||
{
|
|
||||||
/* We don't know anything about the value until we get a
|
|
||||||
valid packet. */
|
|
||||||
tsv->value_known = 0;
|
|
||||||
sprintf (buf, "qTV:%x", tsv->number);
|
|
||||||
putpkt (buf);
|
|
||||||
reply = remote_get_noisy_reply (&target_buf, &target_buf_size);
|
|
||||||
if (reply && *reply)
|
|
||||||
{
|
|
||||||
if (*reply == 'V')
|
|
||||||
{
|
|
||||||
unpack_varlen_hex (reply + 1, &tval);
|
|
||||||
tsv->value = (LONGEST) tval;
|
|
||||||
tsv->value_known = 1;
|
|
||||||
}
|
|
||||||
/* FIXME say anything about oddball replies? */
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (VEC_length (tsv_s, tvariables) == 0)
|
if (VEC_length (tsv_s, tvariables) == 0)
|
||||||
{
|
{
|
||||||
printf_filtered (_("No trace state variables.\n"));
|
printf_filtered (_("No trace state variables.\n"));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Try to acquire values from the target. */
|
||||||
|
for (ix = 0; VEC_iterate (tsv_s, tvariables, ix, tsv); ++ix)
|
||||||
|
tsv->value_known = target_get_trace_state_variable_value (tsv->number,
|
||||||
|
&(tsv->value));
|
||||||
|
|
||||||
printf_filtered (_("Name\t\t Initial\tCurrent\n"));
|
printf_filtered (_("Name\t\t Initial\tCurrent\n"));
|
||||||
|
|
||||||
for (ix = 0; VEC_iterate (tsv_s, tvariables, ix, tsv); ++ix)
|
for (ix = 0; VEC_iterate (tsv_s, tvariables, ix, tsv); ++ix)
|
||||||
@ -1293,28 +1208,8 @@ stringify_collection_list (struct collection_list *list, char *string)
|
|||||||
return *str_list;
|
return *str_list;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
|
||||||
free_actions_list_cleanup_wrapper (void *al)
|
|
||||||
{
|
|
||||||
free_actions_list (al);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
free_actions_list (char **actions_list)
|
|
||||||
{
|
|
||||||
int ndx;
|
|
||||||
|
|
||||||
if (actions_list == 0)
|
|
||||||
return;
|
|
||||||
|
|
||||||
for (ndx = 0; actions_list[ndx]; ndx++)
|
|
||||||
xfree (actions_list[ndx]);
|
|
||||||
|
|
||||||
xfree (actions_list);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Render all actions into gdb protocol. */
|
/* Render all actions into gdb protocol. */
|
||||||
static void
|
/*static*/ void
|
||||||
encode_actions (struct breakpoint *t, char ***tdp_actions,
|
encode_actions (struct breakpoint *t, char ***tdp_actions,
|
||||||
char ***stepping_actions)
|
char ***stepping_actions)
|
||||||
{
|
{
|
||||||
@ -1583,49 +1478,6 @@ add_aexpr (struct collection_list *collect, struct agent_expr *aexpr)
|
|||||||
collect->next_aexpr_elt++;
|
collect->next_aexpr_elt++;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Set "transparent" memory ranges
|
|
||||||
|
|
||||||
Allow trace mechanism to treat text-like sections
|
|
||||||
(and perhaps all read-only sections) transparently,
|
|
||||||
i.e. don't reject memory requests from these address ranges
|
|
||||||
just because they haven't been collected. */
|
|
||||||
|
|
||||||
static void
|
|
||||||
remote_set_transparent_ranges (void)
|
|
||||||
{
|
|
||||||
asection *s;
|
|
||||||
bfd_size_type size;
|
|
||||||
bfd_vma lma;
|
|
||||||
int anysecs = 0;
|
|
||||||
|
|
||||||
if (!exec_bfd)
|
|
||||||
return; /* No information to give. */
|
|
||||||
|
|
||||||
strcpy (target_buf, "QTro");
|
|
||||||
for (s = exec_bfd->sections; s; s = s->next)
|
|
||||||
{
|
|
||||||
char tmp1[40], tmp2[40];
|
|
||||||
|
|
||||||
if ((s->flags & SEC_LOAD) == 0 ||
|
|
||||||
/* (s->flags & SEC_CODE) == 0 || */
|
|
||||||
(s->flags & SEC_READONLY) == 0)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
anysecs = 1;
|
|
||||||
lma = s->lma;
|
|
||||||
size = bfd_get_section_size (s);
|
|
||||||
sprintf_vma (tmp1, lma);
|
|
||||||
sprintf_vma (tmp2, lma + size);
|
|
||||||
sprintf (target_buf + strlen (target_buf),
|
|
||||||
":%s,%s", tmp1, tmp2);
|
|
||||||
}
|
|
||||||
if (anysecs)
|
|
||||||
{
|
|
||||||
putpkt (target_buf);
|
|
||||||
getpkt (&target_buf, &target_buf_size, 0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* tstart command:
|
/* tstart command:
|
||||||
|
|
||||||
Tell target to clear any previous trace experiment.
|
Tell target to clear any previous trace experiment.
|
||||||
@ -1633,8 +1485,6 @@ remote_set_transparent_ranges (void)
|
|||||||
to the target. If no errors,
|
to the target. If no errors,
|
||||||
Tell target to start a new trace experiment. */
|
Tell target to start a new trace experiment. */
|
||||||
|
|
||||||
int download_tracepoint (struct breakpoint *t);
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
trace_start_command (char *args, int from_tty)
|
trace_start_command (char *args, int from_tty)
|
||||||
{
|
{
|
||||||
@ -1647,23 +1497,16 @@ trace_start_command (char *args, int from_tty)
|
|||||||
|
|
||||||
dont_repeat (); /* Like "run", dangerous to repeat accidentally. */
|
dont_repeat (); /* Like "run", dangerous to repeat accidentally. */
|
||||||
|
|
||||||
if (target_is_remote ())
|
target_trace_init ();
|
||||||
{
|
|
||||||
putpkt ("QTinit");
|
|
||||||
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
|
||||||
if (strcmp (target_buf, "OK"))
|
|
||||||
error (_("Target does not support this command."));
|
|
||||||
|
|
||||||
tp_vec = all_tracepoints ();
|
tp_vec = all_tracepoints ();
|
||||||
for (ix = 0; VEC_iterate (breakpoint_p, tp_vec, ix, t); ix++)
|
for (ix = 0; VEC_iterate (breakpoint_p, tp_vec, ix, t); ix++)
|
||||||
{
|
{
|
||||||
t->number_on_target = 0;
|
t->number_on_target = 0;
|
||||||
if (download_tracepoint (t))
|
target_download_tracepoint (t);
|
||||||
{
|
|
||||||
t->number_on_target = t->number;
|
t->number_on_target = t->number;
|
||||||
any_downloaded = 1;
|
any_downloaded = 1;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
VEC_free (breakpoint_p, tp_vec);
|
VEC_free (breakpoint_p, tp_vec);
|
||||||
|
|
||||||
/* No point in tracing without any tracepoints... */
|
/* No point in tracing without any tracepoints... */
|
||||||
@ -1671,206 +1514,61 @@ trace_start_command (char *args, int from_tty)
|
|||||||
error ("No tracepoints downloaded, not starting trace");
|
error ("No tracepoints downloaded, not starting trace");
|
||||||
|
|
||||||
/* Init any trace state variables that start with nonzero values. */
|
/* Init any trace state variables that start with nonzero values. */
|
||||||
|
|
||||||
for (ix = 0; VEC_iterate (tsv_s, tvariables, ix, tsv); ++ix)
|
for (ix = 0; VEC_iterate (tsv_s, tvariables, ix, tsv); ++ix)
|
||||||
{
|
{
|
||||||
if (tsv->initial_value != 0)
|
if (tsv->initial_value != 0)
|
||||||
{
|
target_download_trace_state_variable (tsv);
|
||||||
sprintf (buf, "QTDV:%x:%s",
|
|
||||||
tsv->number, phex ((ULONGEST) tsv->initial_value, 8));
|
|
||||||
putpkt (buf);
|
|
||||||
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Tell target to treat text-like sections as transparent. */
|
/* Tell target to treat text-like sections as transparent. */
|
||||||
remote_set_transparent_ranges ();
|
target_trace_set_readonly_regions ();
|
||||||
|
|
||||||
/* Now insert traps and begin collecting data. */
|
/* Now insert traps and begin collecting data. */
|
||||||
putpkt ("QTStart");
|
target_trace_start ();
|
||||||
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
|
||||||
if (strcmp (target_buf, "OK"))
|
/* Reset our local state. */
|
||||||
error (_("Bogus reply from target: %s"), target_buf);
|
set_traceframe_num (-1);
|
||||||
set_traceframe_num (-1); /* All old traceframes invalidated. */
|
|
||||||
set_tracepoint_num (-1);
|
set_tracepoint_num (-1);
|
||||||
set_traceframe_context (NULL);
|
set_traceframe_context (NULL);
|
||||||
trace_running_p = 1;
|
trace_running_p = 1;
|
||||||
if (deprecated_trace_start_stop_hook)
|
|
||||||
deprecated_trace_start_stop_hook (1, from_tty);
|
|
||||||
|
|
||||||
}
|
|
||||||
else
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Send the definition of a single tracepoint to the target. Return 1
|
|
||||||
if successful, 0 if not. */
|
|
||||||
|
|
||||||
int
|
|
||||||
download_tracepoint (struct breakpoint *t)
|
|
||||||
{
|
|
||||||
CORE_ADDR tpaddr;
|
|
||||||
char tmp[40];
|
|
||||||
char buf[2048];
|
|
||||||
char **tdp_actions;
|
|
||||||
char **stepping_actions;
|
|
||||||
int ndx;
|
|
||||||
struct cleanup *old_chain = NULL;
|
|
||||||
struct agent_expr *aexpr;
|
|
||||||
struct cleanup *aexpr_chain = NULL;
|
|
||||||
|
|
||||||
tpaddr = t->loc->address;
|
|
||||||
sprintf_vma (tmp, (t->loc ? tpaddr : 0));
|
|
||||||
sprintf (buf, "QTDP:%x:%s:%c:%lx:%x", t->number,
|
|
||||||
tmp, /* address */
|
|
||||||
(t->enable_state == bp_enabled ? 'E' : 'D'),
|
|
||||||
t->step_count, t->pass_count);
|
|
||||||
/* Fast tracepoints are mostly handled by the target, but we can
|
|
||||||
tell the target how big of an instruction block should be moved
|
|
||||||
around. */
|
|
||||||
if (t->type == bp_fast_tracepoint)
|
|
||||||
{
|
|
||||||
/* Only test for support at download time; we may not know
|
|
||||||
target capabilities at definition time. */
|
|
||||||
if (remote_supports_fast_tracepoints ())
|
|
||||||
{
|
|
||||||
int isize;
|
|
||||||
|
|
||||||
if (gdbarch_fast_tracepoint_valid_at (get_current_arch (),
|
|
||||||
tpaddr, &isize, NULL))
|
|
||||||
sprintf (buf + strlen (buf), ":F%x", isize);
|
|
||||||
else
|
|
||||||
/* If it passed validation at definition but fails now,
|
|
||||||
something is very wrong. */
|
|
||||||
internal_error (__FILE__, __LINE__,
|
|
||||||
"Fast tracepoint not valid during download");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
/* Fast tracepoints are functionally identical to regular
|
|
||||||
tracepoints, so don't take lack of support as a reason to
|
|
||||||
give up on the trace run. */
|
|
||||||
warning (_("Target does not support fast tracepoints, downloading %d as regular tracepoint"), t->number);
|
|
||||||
}
|
|
||||||
/* If the tracepoint has a conditional, make it into an agent
|
|
||||||
expression and append to the definition. */
|
|
||||||
if (t->loc->cond)
|
|
||||||
{
|
|
||||||
/* Only test support at download time, we may not know target
|
|
||||||
capabilities at definition time. */
|
|
||||||
if (remote_supports_cond_tracepoints ())
|
|
||||||
{
|
|
||||||
aexpr = gen_eval_for_expr (t->loc->address, t->loc->cond);
|
|
||||||
aexpr_chain = make_cleanup_free_agent_expr (aexpr);
|
|
||||||
sprintf (buf + strlen (buf), ":X%x,", aexpr->len);
|
|
||||||
mem2hex (aexpr->buf, buf + strlen (buf), aexpr->len);
|
|
||||||
do_cleanups (aexpr_chain);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
warning (_("Target does not support conditional tracepoints, ignoring tp %d cond"), t->number);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (t->actions || *default_collect)
|
|
||||||
strcat (buf, "-");
|
|
||||||
putpkt (buf);
|
|
||||||
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
|
||||||
if (strcmp (target_buf, "OK"))
|
|
||||||
error (_("Target does not support tracepoints."));
|
|
||||||
|
|
||||||
if (!t->actions && !*default_collect)
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
encode_actions (t, &tdp_actions, &stepping_actions);
|
|
||||||
old_chain = make_cleanup (free_actions_list_cleanup_wrapper,
|
|
||||||
tdp_actions);
|
|
||||||
(void) make_cleanup (free_actions_list_cleanup_wrapper, stepping_actions);
|
|
||||||
|
|
||||||
/* do_single_steps (t); */
|
|
||||||
if (tdp_actions)
|
|
||||||
{
|
|
||||||
for (ndx = 0; tdp_actions[ndx]; ndx++)
|
|
||||||
{
|
|
||||||
QUIT; /* allow user to bail out with ^C */
|
|
||||||
sprintf (buf, "QTDP:-%x:%s:%s%c",
|
|
||||||
t->number, tmp, /* address */
|
|
||||||
tdp_actions[ndx],
|
|
||||||
((tdp_actions[ndx + 1] || stepping_actions)
|
|
||||||
? '-' : 0));
|
|
||||||
putpkt (buf);
|
|
||||||
remote_get_noisy_reply (&target_buf,
|
|
||||||
&target_buf_size);
|
|
||||||
if (strcmp (target_buf, "OK"))
|
|
||||||
error (_("Error on target while setting tracepoints."));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (stepping_actions)
|
|
||||||
{
|
|
||||||
for (ndx = 0; stepping_actions[ndx]; ndx++)
|
|
||||||
{
|
|
||||||
QUIT; /* allow user to bail out with ^C */
|
|
||||||
sprintf (buf, "QTDP:-%x:%s:%s%s%s",
|
|
||||||
t->number, tmp, /* address */
|
|
||||||
((ndx == 0) ? "S" : ""),
|
|
||||||
stepping_actions[ndx],
|
|
||||||
(stepping_actions[ndx + 1] ? "-" : ""));
|
|
||||||
putpkt (buf);
|
|
||||||
remote_get_noisy_reply (&target_buf,
|
|
||||||
&target_buf_size);
|
|
||||||
if (strcmp (target_buf, "OK"))
|
|
||||||
error (_("Error on target while setting tracepoints."));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
do_cleanups (old_chain);
|
|
||||||
return 1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* tstop command */
|
/* tstop command */
|
||||||
static void
|
static void
|
||||||
trace_stop_command (char *args, int from_tty)
|
trace_stop_command (char *args, int from_tty)
|
||||||
{
|
{
|
||||||
if (target_is_remote ())
|
|
||||||
{
|
|
||||||
stop_tracing ();
|
stop_tracing ();
|
||||||
if (deprecated_trace_start_stop_hook)
|
|
||||||
deprecated_trace_start_stop_hook (0, from_tty);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
stop_tracing ()
|
stop_tracing ()
|
||||||
{
|
{
|
||||||
putpkt ("QTStop");
|
target_trace_stop ();
|
||||||
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
|
||||||
if (strcmp (target_buf, "OK"))
|
|
||||||
error (_("Bogus reply from target: %s"), target_buf);
|
|
||||||
trace_running_p = 0;
|
trace_running_p = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned long trace_running_p;
|
unsigned long trace_running_p;
|
||||||
|
|
||||||
void
|
int
|
||||||
get_trace_status ()
|
get_trace_status ()
|
||||||
{
|
{
|
||||||
putpkt ("qTStatus");
|
int status = target_get_trace_status (NULL);
|
||||||
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
|
||||||
|
|
||||||
if (target_buf[0] != 'T' ||
|
|
||||||
(target_buf[1] != '0' && target_buf[1] != '1'))
|
|
||||||
error (_("Bogus trace status reply from target: %s"), target_buf);
|
|
||||||
|
|
||||||
/* exported for use by the GUI */
|
/* exported for use by the GUI */
|
||||||
trace_running_p = (target_buf[1] == '1');
|
trace_running_p = (status > 0);
|
||||||
|
|
||||||
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* tstatus command */
|
/* tstatus command */
|
||||||
static void
|
static void
|
||||||
trace_status_command (char *args, int from_tty)
|
trace_status_command (char *args, int from_tty)
|
||||||
{
|
{
|
||||||
if (target_is_remote ())
|
int status = get_trace_status ();
|
||||||
{
|
|
||||||
get_trace_status ();
|
|
||||||
|
|
||||||
if (trace_running_p)
|
if (status < 0)
|
||||||
|
printf_filtered (_("Trace can not be run on the target.\n"));
|
||||||
|
else if (trace_running_p)
|
||||||
{
|
{
|
||||||
printf_filtered (_("Trace is running on the target.\n"));
|
printf_filtered (_("Trace is running on the target.\n"));
|
||||||
if (disconnected_tracing)
|
if (disconnected_tracing)
|
||||||
@ -1886,10 +1584,6 @@ trace_status_command (char *args, int from_tty)
|
|||||||
traceframe_number, tracepoint_number);
|
traceframe_number, tracepoint_number);
|
||||||
else
|
else
|
||||||
printf_filtered (_("Not looking at any trace frame.\n"));
|
printf_filtered (_("Not looking at any trace frame.\n"));
|
||||||
|
|
||||||
}
|
|
||||||
else
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -1912,8 +1606,8 @@ disconnect_or_stop_tracing (int from_tty)
|
|||||||
|
|
||||||
/* Worker function for the various flavors of the tfind command. */
|
/* Worker function for the various flavors of the tfind command. */
|
||||||
static void
|
static void
|
||||||
finish_tfind_command (char **msg,
|
finish_tfind_command (enum trace_find_type type, int num,
|
||||||
long *sizeof_msg,
|
ULONGEST addr1, ULONGEST addr2,
|
||||||
int from_tty)
|
int from_tty)
|
||||||
{
|
{
|
||||||
int target_frameno = -1, target_tracept = -1;
|
int target_frameno = -1, target_tracept = -1;
|
||||||
@ -1923,14 +1617,16 @@ finish_tfind_command (char **msg,
|
|||||||
|
|
||||||
old_frame_id = get_frame_id (get_current_frame ());
|
old_frame_id = get_frame_id (get_current_frame ());
|
||||||
|
|
||||||
putpkt (*msg);
|
target_frameno = target_trace_find (type, num, addr1, addr2,
|
||||||
reply = remote_get_noisy_reply (msg, sizeof_msg);
|
&target_tracept);
|
||||||
|
|
||||||
while (reply && *reply)
|
if (type == tfind_number
|
||||||
switch (*reply)
|
&& num == -1
|
||||||
|
&& target_frameno == -1)
|
||||||
{
|
{
|
||||||
case 'F':
|
/* We told the target to get out of tfind mode, and it did. */
|
||||||
if ((target_frameno = (int) strtol (++reply, &reply, 16)) == -1)
|
}
|
||||||
|
else if (target_frameno == -1)
|
||||||
{
|
{
|
||||||
/* A request for a non-existant trace frame has failed.
|
/* A request for a non-existant trace frame has failed.
|
||||||
Our response will be different, depending on FROM_TTY:
|
Our response will be different, depending on FROM_TTY:
|
||||||
@ -1959,27 +1655,13 @@ finish_tfind_command (char **msg,
|
|||||||
{
|
{
|
||||||
if (info_verbose)
|
if (info_verbose)
|
||||||
printf_filtered ("End of trace buffer.\n");
|
printf_filtered ("End of trace buffer.\n");
|
||||||
|
#if 0 /* dubious now? */
|
||||||
/* The following will not recurse, since it's
|
/* The following will not recurse, since it's
|
||||||
special-cased. */
|
special-cased. */
|
||||||
trace_find_command ("-1", from_tty);
|
trace_find_command ("-1", from_tty);
|
||||||
reply = NULL; /* Break out of loop
|
#endif
|
||||||
(avoid recursive nonsense). */
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
case 'T':
|
|
||||||
if ((target_tracept = (int) strtol (++reply, &reply, 16)) == -1)
|
|
||||||
error (_("Target failed to find requested trace frame."));
|
|
||||||
break;
|
|
||||||
case 'O': /* "OK"? */
|
|
||||||
if (reply[1] == 'K' && reply[2] == '\0')
|
|
||||||
reply += 2;
|
|
||||||
else
|
|
||||||
error (_("Bogus reply from target: %s"), reply);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
error (_("Bogus reply from target: %s"), reply);
|
|
||||||
}
|
|
||||||
|
|
||||||
tp = get_tracepoint_by_number_on_target (target_tracept);
|
tp = get_tracepoint_by_number_on_target (target_tracept);
|
||||||
|
|
||||||
@ -2033,14 +1715,9 @@ trace_find_command (char *args, int from_tty)
|
|||||||
{ /* this should only be called with a numeric argument */
|
{ /* this should only be called with a numeric argument */
|
||||||
int frameno = -1;
|
int frameno = -1;
|
||||||
|
|
||||||
if (target_is_remote ())
|
|
||||||
{
|
|
||||||
if (trace_running_p)
|
if (trace_running_p)
|
||||||
error ("May not look at trace frames while trace is running.");
|
error ("May not look at trace frames while trace is running.");
|
||||||
|
|
||||||
if (deprecated_trace_find_hook)
|
|
||||||
deprecated_trace_find_hook (args, from_tty);
|
|
||||||
|
|
||||||
if (args == 0 || *args == 0)
|
if (args == 0 || *args == 0)
|
||||||
{ /* TFIND with no args means find NEXT trace frame. */
|
{ /* TFIND with no args means find NEXT trace frame. */
|
||||||
if (traceframe_number == -1)
|
if (traceframe_number == -1)
|
||||||
@ -2057,17 +1734,16 @@ trace_find_command (char *args, int from_tty)
|
|||||||
|
|
||||||
frameno = traceframe_number - 1;
|
frameno = traceframe_number - 1;
|
||||||
}
|
}
|
||||||
|
/* A hack to work around eval's need for fp to have been collected. */
|
||||||
|
else if (0 == strcmp (args, "-1"))
|
||||||
|
frameno = -1;
|
||||||
else
|
else
|
||||||
frameno = parse_and_eval_long (args);
|
frameno = parse_and_eval_long (args);
|
||||||
|
|
||||||
if (frameno < -1)
|
if (frameno < -1)
|
||||||
error (_("invalid input (%d is less than zero)"), frameno);
|
error (_("invalid input (%d is less than zero)"), frameno);
|
||||||
|
|
||||||
sprintf (target_buf, "QTFrame:%x", frameno);
|
finish_tfind_command (tfind_number, frameno, 0, 0, from_tty);
|
||||||
finish_tfind_command (&target_buf, &target_buf_size, from_tty);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* tfind end */
|
/* tfind end */
|
||||||
@ -2098,8 +1774,6 @@ trace_find_pc_command (char *args, int from_tty)
|
|||||||
CORE_ADDR pc;
|
CORE_ADDR pc;
|
||||||
char tmp[40];
|
char tmp[40];
|
||||||
|
|
||||||
if (target_is_remote ())
|
|
||||||
{
|
|
||||||
if (trace_running_p)
|
if (trace_running_p)
|
||||||
error ("May not look at trace frames while trace is running.");
|
error ("May not look at trace frames while trace is running.");
|
||||||
|
|
||||||
@ -2108,12 +1782,7 @@ trace_find_pc_command (char *args, int from_tty)
|
|||||||
else
|
else
|
||||||
pc = parse_and_eval_address (args);
|
pc = parse_and_eval_address (args);
|
||||||
|
|
||||||
sprintf_vma (tmp, pc);
|
finish_tfind_command (tfind_pc, 0, pc, 0, from_tty);
|
||||||
sprintf (target_buf, "QTFrame:pc:%s", tmp);
|
|
||||||
finish_tfind_command (&target_buf, &target_buf_size, from_tty);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* tfind tracepoint command */
|
/* tfind tracepoint command */
|
||||||
@ -2123,8 +1792,6 @@ trace_find_tracepoint_command (char *args, int from_tty)
|
|||||||
int tdp;
|
int tdp;
|
||||||
struct breakpoint *tp;
|
struct breakpoint *tp;
|
||||||
|
|
||||||
if (target_is_remote ())
|
|
||||||
{
|
|
||||||
if (trace_running_p)
|
if (trace_running_p)
|
||||||
error ("May not look at trace frames while trace is running.");
|
error ("May not look at trace frames while trace is running.");
|
||||||
|
|
||||||
@ -2145,11 +1812,7 @@ trace_find_tracepoint_command (char *args, int from_tty)
|
|||||||
if (tp)
|
if (tp)
|
||||||
tdp = tp->number_on_target;
|
tdp = tp->number_on_target;
|
||||||
|
|
||||||
sprintf (target_buf, "QTFrame:tdp:%x", tdp);
|
finish_tfind_command (tfind_tp, tdp, 0, 0, from_tty);
|
||||||
finish_tfind_command (&target_buf, &target_buf_size, from_tty);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* TFIND LINE command:
|
/* TFIND LINE command:
|
||||||
@ -2169,8 +1832,6 @@ trace_find_line_command (char *args, int from_tty)
|
|||||||
struct cleanup *old_chain;
|
struct cleanup *old_chain;
|
||||||
char startpc_str[40], endpc_str[40];
|
char startpc_str[40], endpc_str[40];
|
||||||
|
|
||||||
if (target_is_remote ())
|
|
||||||
{
|
|
||||||
if (trace_running_p)
|
if (trace_running_p)
|
||||||
error ("May not look at trace frames while trace is running.");
|
error ("May not look at trace frames while trace is running.");
|
||||||
|
|
||||||
@ -2191,8 +1852,6 @@ trace_find_line_command (char *args, int from_tty)
|
|||||||
old_chain = make_cleanup (xfree, sals.sals);
|
old_chain = make_cleanup (xfree, sals.sals);
|
||||||
if (sal.symtab == 0)
|
if (sal.symtab == 0)
|
||||||
{
|
{
|
||||||
struct gdbarch *gdbarch = get_current_arch ();
|
|
||||||
|
|
||||||
printf_filtered ("TFIND: No line number information available");
|
printf_filtered ("TFIND: No line number information available");
|
||||||
if (sal.pc != 0)
|
if (sal.pc != 0)
|
||||||
{
|
{
|
||||||
@ -2201,7 +1860,7 @@ trace_find_line_command (char *args, int from_tty)
|
|||||||
have the symbolic address. */
|
have the symbolic address. */
|
||||||
printf_filtered (" for address ");
|
printf_filtered (" for address ");
|
||||||
wrap_here (" ");
|
wrap_here (" ");
|
||||||
print_address (gdbarch, sal.pc, gdb_stdout);
|
print_address (get_current_arch (), sal.pc, gdb_stdout);
|
||||||
printf_filtered (";\n -- will attempt to find by PC. \n");
|
printf_filtered (";\n -- will attempt to find by PC. \n");
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -2213,21 +1872,19 @@ trace_find_line_command (char *args, int from_tty)
|
|||||||
else if (sal.line > 0
|
else if (sal.line > 0
|
||||||
&& find_line_pc_range (sal, &start_pc, &end_pc))
|
&& find_line_pc_range (sal, &start_pc, &end_pc))
|
||||||
{
|
{
|
||||||
struct gdbarch *gdbarch = get_objfile_arch (sal.symtab->objfile);
|
|
||||||
|
|
||||||
if (start_pc == end_pc)
|
if (start_pc == end_pc)
|
||||||
{
|
{
|
||||||
printf_filtered ("Line %d of \"%s\"",
|
printf_filtered ("Line %d of \"%s\"",
|
||||||
sal.line, sal.symtab->filename);
|
sal.line, sal.symtab->filename);
|
||||||
wrap_here (" ");
|
wrap_here (" ");
|
||||||
printf_filtered (" is at address ");
|
printf_filtered (" is at address ");
|
||||||
print_address (gdbarch, start_pc, gdb_stdout);
|
print_address (get_current_arch (), start_pc, gdb_stdout);
|
||||||
wrap_here (" ");
|
wrap_here (" ");
|
||||||
printf_filtered (" but contains no code.\n");
|
printf_filtered (" but contains no code.\n");
|
||||||
sal = find_pc_line (start_pc, 0);
|
sal = find_pc_line (start_pc, 0);
|
||||||
if (sal.line > 0 &&
|
if (sal.line > 0
|
||||||
find_line_pc_range (sal, &start_pc, &end_pc) &&
|
&& find_line_pc_range (sal, &start_pc, &end_pc)
|
||||||
start_pc != end_pc)
|
&& start_pc != end_pc)
|
||||||
printf_filtered ("Attempting to find line %d instead.\n",
|
printf_filtered ("Attempting to find line %d instead.\n",
|
||||||
sal.line);
|
sal.line);
|
||||||
else
|
else
|
||||||
@ -2241,22 +1898,12 @@ trace_find_line_command (char *args, int from_tty)
|
|||||||
error (_("Line number %d is out of range for \"%s\"."),
|
error (_("Line number %d is out of range for \"%s\"."),
|
||||||
sal.line, sal.symtab->filename);
|
sal.line, sal.symtab->filename);
|
||||||
|
|
||||||
sprintf_vma (startpc_str, start_pc);
|
|
||||||
sprintf_vma (endpc_str, end_pc - 1);
|
|
||||||
/* Find within range of stated line. */
|
/* Find within range of stated line. */
|
||||||
if (args && *args)
|
if (args && *args)
|
||||||
sprintf (target_buf, "QTFrame:range:%s:%s",
|
finish_tfind_command (tfind_range, 0, start_pc, end_pc - 1, from_tty);
|
||||||
startpc_str, endpc_str);
|
|
||||||
/* Find OUTSIDE OF range of CURRENT line. */
|
|
||||||
else
|
else
|
||||||
sprintf (target_buf, "QTFrame:outside:%s:%s",
|
finish_tfind_command (tfind_outside, 0, start_pc, end_pc - 1, from_tty);
|
||||||
startpc_str, endpc_str);
|
|
||||||
finish_tfind_command (&target_buf, &target_buf_size,
|
|
||||||
from_tty);
|
|
||||||
do_cleanups (old_chain);
|
do_cleanups (old_chain);
|
||||||
}
|
|
||||||
else
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* tfind range command */
|
/* tfind range command */
|
||||||
@ -2267,8 +1914,6 @@ trace_find_range_command (char *args, int from_tty)
|
|||||||
char start_str[40], stop_str[40];
|
char start_str[40], stop_str[40];
|
||||||
char *tmp;
|
char *tmp;
|
||||||
|
|
||||||
if (target_is_remote ())
|
|
||||||
{
|
|
||||||
if (trace_running_p)
|
if (trace_running_p)
|
||||||
error ("May not look at trace frames while trace is running.");
|
error ("May not look at trace frames while trace is running.");
|
||||||
|
|
||||||
@ -2292,13 +1937,7 @@ trace_find_range_command (char *args, int from_tty)
|
|||||||
stop = start + 1; /* ??? */
|
stop = start + 1; /* ??? */
|
||||||
}
|
}
|
||||||
|
|
||||||
sprintf_vma (start_str, start);
|
finish_tfind_command (tfind_range, 0, start, stop, from_tty);
|
||||||
sprintf_vma (stop_str, stop);
|
|
||||||
sprintf (target_buf, "QTFrame:range:%s:%s", start_str, stop_str);
|
|
||||||
finish_tfind_command (&target_buf, &target_buf_size, from_tty);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* tfind outside command */
|
/* tfind outside command */
|
||||||
@ -2309,8 +1948,6 @@ trace_find_outside_command (char *args, int from_tty)
|
|||||||
char start_str[40], stop_str[40];
|
char start_str[40], stop_str[40];
|
||||||
char *tmp;
|
char *tmp;
|
||||||
|
|
||||||
if (target_is_remote ())
|
|
||||||
{
|
|
||||||
if (trace_running_p)
|
if (trace_running_p)
|
||||||
error ("May not look at trace frames while trace is running.");
|
error ("May not look at trace frames while trace is running.");
|
||||||
|
|
||||||
@ -2334,13 +1971,7 @@ trace_find_outside_command (char *args, int from_tty)
|
|||||||
stop = start + 1; /* ??? */
|
stop = start + 1; /* ??? */
|
||||||
}
|
}
|
||||||
|
|
||||||
sprintf_vma (start_str, start);
|
finish_tfind_command (tfind_outside, 0, start, stop, from_tty);
|
||||||
sprintf_vma (stop_str, stop);
|
|
||||||
sprintf (target_buf, "QTFrame:outside:%s:%s", start_str, stop_str);
|
|
||||||
finish_tfind_command (&target_buf, &target_buf_size, from_tty);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* info scope command: list the locals for a scope. */
|
/* info scope command: list the locals for a scope. */
|
||||||
@ -2511,12 +2142,6 @@ trace_dump_command (char *args, int from_tty)
|
|||||||
int stepping_actions = 0;
|
int stepping_actions = 0;
|
||||||
int stepping_frame = 0;
|
int stepping_frame = 0;
|
||||||
|
|
||||||
if (!target_is_remote ())
|
|
||||||
{
|
|
||||||
error (_("Trace can only be run on remote targets."));
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (tracepoint_number == -1)
|
if (tracepoint_number == -1)
|
||||||
{
|
{
|
||||||
warning (_("No current trace frame."));
|
warning (_("No current trace frame."));
|
||||||
@ -2620,17 +2245,7 @@ trace_dump_command (char *args, int from_tty)
|
|||||||
void
|
void
|
||||||
send_disconnected_tracing_value (int value)
|
send_disconnected_tracing_value (int value)
|
||||||
{
|
{
|
||||||
char buf[30];
|
target_set_disconnected_tracing (value);
|
||||||
|
|
||||||
/* No need to do anything special if target not active. */
|
|
||||||
if (!target_is_remote ())
|
|
||||||
return;
|
|
||||||
|
|
||||||
sprintf (buf, "QTDisconnected:%x", value);
|
|
||||||
putpkt (buf);
|
|
||||||
remote_get_noisy_reply (&target_buf, &target_buf_size);
|
|
||||||
if (strcmp (target_buf, "OK"))
|
|
||||||
error (_("Target does not support this command."));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@ -2847,7 +2462,4 @@ trace data collected in the meantime."),
|
|||||||
NULL,
|
NULL,
|
||||||
&setlist,
|
&setlist,
|
||||||
&showlist);
|
&showlist);
|
||||||
|
|
||||||
target_buf_size = 2048;
|
|
||||||
target_buf = xmalloc (target_buf_size);
|
|
||||||
}
|
}
|
||||||
|
@ -65,6 +65,8 @@ struct trace_state_variable
|
|||||||
|
|
||||||
extern unsigned long trace_running_p;
|
extern unsigned long trace_running_p;
|
||||||
|
|
||||||
|
extern char *default_collect;
|
||||||
|
|
||||||
/* A hook used to notify the UI of tracepoint operations. */
|
/* A hook used to notify the UI of tracepoint operations. */
|
||||||
|
|
||||||
extern void (*deprecated_trace_find_hook) (char *arg, int from_tty);
|
extern void (*deprecated_trace_find_hook) (char *arg, int from_tty);
|
||||||
|
Loading…
Reference in New Issue
Block a user