/* Tracing functionality for remote targets in custom GDB protocol

   Copyright (C) 1997-2020 Free Software Foundation, Inc.

   This file is part of GDB.

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */

#include "defs.h"
#include "arch-utils.h"
#include "symtab.h"
#include "frame.h"
#include "gdbtypes.h"
#include "expression.h"
#include "gdbcmd.h"
#include "value.h"
#include "target.h"
#include "target-dcache.h"
#include "language.h"
#include "inferior.h"
#include "breakpoint.h"
#include "tracepoint.h"
#include "linespec.h"
#include "regcache.h"
#include "completer.h"
#include "block.h"
#include "dictionary.h"
#include "observable.h"
#include "user-regs.h"
#include "valprint.h"
#include "gdbcore.h"
#include "objfiles.h"
#include "filenames.h"
#include "gdbthread.h"
#include "stack.h"
#include "remote.h"
#include "source.h"
#include "ax.h"
#include "ax-gdb.h"
#include "memrange.h"
#include "cli/cli-utils.h"
#include "probe.h"
#include "gdbsupport/filestuff.h"
#include "gdbsupport/rsp-low.h"
#include "tracefile.h"
#include "location.h"
#include <algorithm>
#include "cli/cli-style.h"

#include <unistd.h>

/* Maximum length of an agent aexpression.
   This accounts for the fact that packets are limited to 400 bytes
   (which includes everything -- including the checksum), and assumes
   the worst case of maximum length for each of the pieces of a
   continuation packet.

   NOTE: expressions get mem2hex'ed otherwise this would be twice as
   large.  (400 - 31)/2 == 184 */
#define MAX_AGENT_EXPR_LEN	184

/* A hook used to notify the UI of tracepoint operations.  */

void (*deprecated_trace_find_hook) (char *arg, int from_tty);
void (*deprecated_trace_start_stop_hook) (int start, int from_tty);

/* 
   Tracepoint.c:

   This module defines the following debugger commands:
   trace            : set a tracepoint on a function, line, or address.
   info trace       : list all debugger-defined tracepoints.
   delete trace     : delete one or more tracepoints.
   enable trace     : enable one or more tracepoints.
   disable trace    : disable one or more tracepoints.
   actions          : specify actions to be taken at a tracepoint.
   passcount        : specify a pass count for a tracepoint.
   tstart           : start a trace experiment.
   tstop            : stop a trace experiment.
   tstatus          : query the status of a trace experiment.
   tfind            : find a trace frame in the trace buffer.
   tdump            : print everything collected at the current tracepoint.
   save-tracepoints : write tracepoint setup into a file.

   This module defines the following user-visible debugger variables:
   $trace_frame : sequence number of trace frame currently being debugged.
   $trace_line  : source line of trace frame currently being debugged.
   $trace_file  : source file of trace frame currently being debugged.
   $tracepoint  : tracepoint number of trace frame currently being debugged.
 */


/* ======= Important global variables: ======= */

/* The list of all trace state variables.  We don't retain pointers to
   any of these for any reason - API is by name or number only - so it
   works to have a vector of objects.  */

static std::vector<trace_state_variable> tvariables;

/* The next integer to assign to a variable.  */

static int next_tsv_number = 1;

/* Number of last traceframe collected.  */
static int traceframe_number;

/* Tracepoint for last traceframe collected.  */
static int tracepoint_number;

/* The traceframe info of the current traceframe.  NULL if we haven't
   yet attempted to fetch it, or if the target does not support
   fetching this object, or if we're not inspecting a traceframe
   presently.  */
static traceframe_info_up current_traceframe_info;

/* Tracing command lists.  */
static struct cmd_list_element *tfindlist;

/* List of expressions to collect by default at each tracepoint hit.  */
char *default_collect;

static bool disconnected_tracing;

/* This variable controls whether we ask the target for a linear or
   circular trace buffer.  */

static bool circular_trace_buffer;

/* This variable is the requested trace buffer size, or -1 to indicate
   that we don't care and leave it up to the target to set a size.  */

static int trace_buffer_size = -1;

/* Textual notes applying to the current and/or future trace runs.  */

char *trace_user = NULL;

/* Textual notes applying to the current and/or future trace runs.  */

char *trace_notes = NULL;

/* Textual notes applying to the stopping of a trace.  */

char *trace_stop_notes = NULL;

/* support routines */

struct collection_list;
static char *mem2hex (gdb_byte *, char *, int);

static counted_command_line all_tracepoint_actions (struct breakpoint *);

static struct trace_status trace_status;

const char *stop_reason_names[] = {
  "tunknown",
  "tnotrun",
  "tstop",
  "tfull",
  "tdisconnected",
  "tpasscount",
  "terror"
};

struct trace_status *
current_trace_status (void)
{
  return &trace_status;
}

/* Free and clear the traceframe info cache of the current
   traceframe.  */

static void
clear_traceframe_info (void)
{
  current_traceframe_info = NULL;
}

/* Set traceframe number to NUM.  */
static void
set_traceframe_num (int num)
{
  traceframe_number = num;
  set_internalvar_integer (lookup_internalvar ("trace_frame"), num);
}

/* Set tracepoint number to NUM.  */
static void
set_tracepoint_num (int num)
{
  tracepoint_number = num;
  set_internalvar_integer (lookup_internalvar ("tracepoint"), num);
}

/* Set externally visible debug variables for querying/printing
   the traceframe context (line, function, file).  */

static void
set_traceframe_context (struct frame_info *trace_frame)
{
  CORE_ADDR trace_pc;
  struct symbol *traceframe_fun;
  symtab_and_line traceframe_sal;

  /* Save as globals for internal use.  */
  if (trace_frame != NULL
      && get_frame_pc_if_available (trace_frame, &trace_pc))
    {
      traceframe_sal = find_pc_line (trace_pc, 0);
      traceframe_fun = find_pc_function (trace_pc);

      /* Save linenumber as "$trace_line", a debugger variable visible to
	 users.  */
      set_internalvar_integer (lookup_internalvar ("trace_line"),
			       traceframe_sal.line);
    }
  else
    {
      traceframe_fun = NULL;
      set_internalvar_integer (lookup_internalvar ("trace_line"), -1);
    }

  /* Save func name as "$trace_func", a debugger variable visible to
     users.  */
  if (traceframe_fun == NULL
      || traceframe_fun->linkage_name () == NULL)
    clear_internalvar (lookup_internalvar ("trace_func"));
  else
    set_internalvar_string (lookup_internalvar ("trace_func"),
			    traceframe_fun->linkage_name ());

  /* Save file name as "$trace_file", a debugger variable visible to
     users.  */
  if (traceframe_sal.symtab == NULL)
    clear_internalvar (lookup_internalvar ("trace_file"));
  else
    set_internalvar_string (lookup_internalvar ("trace_file"),
			symtab_to_filename_for_display (traceframe_sal.symtab));
}

/* Create a new trace state variable with the given name.  */

struct trace_state_variable *
create_trace_state_variable (const char *name)
{
  tvariables.emplace_back (name, next_tsv_number++);
  return &tvariables.back ();
}

/* Look for a trace state variable of the given name.  */

struct trace_state_variable *
find_trace_state_variable (const char *name)
{
  for (trace_state_variable &tsv : tvariables)
    if (tsv.name == name)
      return &tsv;

  return NULL;
}

/* Look for a trace state variable of the given number.  Return NULL if
   not found.  */

struct trace_state_variable *
find_trace_state_variable_by_number (int number)
{
  for (trace_state_variable &tsv : tvariables)
    if (tsv.number == number)
      return &tsv;

  return NULL;
}

static void
delete_trace_state_variable (const char *name)
{
  for (auto it = tvariables.begin (); it != tvariables.end (); it++)
    if (it->name == name)
      {
	gdb::observers::tsv_deleted.notify (&*it);
	tvariables.erase (it);
	return;
      }

  warning (_("No trace variable named \"$%s\", not deleting"), name);
}

/* Throws an error if NAME is not valid syntax for a trace state
   variable's name.  */

void
validate_trace_state_variable_name (const char *name)
{
  const char *p;

  if (*name == '\0')
    error (_("Must supply a non-empty variable name"));

  /* All digits in the name is reserved for value history
     references.  */
  for (p = name; isdigit (*p); p++)
    ;
  if (*p == '\0')
    error (_("$%s is not a valid trace state variable name"), name);

  for (p = name; isalnum (*p) || *p == '_'; p++)
    ;
  if (*p != '\0')
    error (_("$%s is not a valid trace state variable name"), name);
}

/* The 'tvariable' command collects a name and optional expression to
   evaluate into an initial value.  */

static void
trace_variable_command (const char *args, int from_tty)
{
  LONGEST initval = 0;
  struct trace_state_variable *tsv;
  const char *name_start, *p;

  if (!args || !*args)
    error_no_arg (_("Syntax is $NAME [ = EXPR ]"));

  /* Only allow two syntaxes; "$name" and "$name=value".  */
  p = skip_spaces (args);

  if (*p++ != '$')
    error (_("Name of trace variable should start with '$'"));

  name_start = p;
  while (isalnum (*p) || *p == '_')
    p++;
  std::string name (name_start, p - name_start);

  p = skip_spaces (p);
  if (*p != '=' && *p != '\0')
    error (_("Syntax must be $NAME [ = EXPR ]"));

  validate_trace_state_variable_name (name.c_str ());

  if (*p == '=')
    initval = value_as_long (parse_and_eval (++p));

  /* If the variable already exists, just change its initial value.  */
  tsv = find_trace_state_variable (name.c_str ());
  if (tsv)
    {
      if (tsv->initial_value != initval)
	{
	  tsv->initial_value = initval;
	  gdb::observers::tsv_modified.notify (tsv);
	}
      printf_filtered (_("Trace state variable $%s "
			 "now has initial value %s.\n"),
		       tsv->name.c_str (), plongest (tsv->initial_value));
      return;
    }

  /* Create a new variable.  */
  tsv = create_trace_state_variable (name.c_str ());
  tsv->initial_value = initval;

  gdb::observers::tsv_created.notify (tsv);

  printf_filtered (_("Trace state variable $%s "
		     "created, with initial value %s.\n"),
		   tsv->name.c_str (), plongest (tsv->initial_value));
}

static void
delete_trace_variable_command (const char *args, int from_tty)
{
  if (args == NULL)
    {
      if (query (_("Delete all trace state variables? ")))
	tvariables.clear ();
      dont_repeat ();
      gdb::observers::tsv_deleted.notify (NULL);
      return;
    }

  gdb_argv argv (args);

  for (char *arg : argv)
    {
      if (*arg == '$')
	delete_trace_state_variable (arg + 1);
      else
	warning (_("Name \"%s\" not prefixed with '$', ignoring"), arg);
    }

  dont_repeat ();
}

void
tvariables_info_1 (void)
{
  struct ui_out *uiout = current_uiout;

  /* Try to acquire values from the target.  */
  for (trace_state_variable &tsv : tvariables)
    tsv.value_known
      = target_get_trace_state_variable_value (tsv.number, &tsv.value);

  {
    ui_out_emit_table table_emitter (uiout, 3, tvariables.size (),
				     "trace-variables");
    uiout->table_header (15, ui_left, "name", "Name");
    uiout->table_header (11, ui_left, "initial", "Initial");
    uiout->table_header (11, ui_left, "current", "Current");

    uiout->table_body ();

    for (const trace_state_variable &tsv : tvariables)
      {
	const char *c;

	ui_out_emit_tuple tuple_emitter (uiout, "variable");

	uiout->field_string ("name", std::string ("$") + tsv.name);
	uiout->field_string ("initial", plongest (tsv.initial_value));

	ui_file_style style;
	if (tsv.value_known)
	  c = plongest (tsv.value);
	else if (uiout->is_mi_like_p ())
	  /* For MI, we prefer not to use magic string constants, but rather
	     omit the field completely.  The difference between unknown and
	     undefined does not seem important enough to represent.  */
	  c = NULL;
	else if (current_trace_status ()->running || traceframe_number >= 0)
	  {
	    /* The value is/was defined, but we don't have it.  */
	    c = "<unknown>";
	    style = metadata_style.style ();
	  }
	else
	  {
	    /* It is not meaningful to ask about the value.  */
	    c = "<undefined>";
	    style = metadata_style.style ();
	  }
	if (c)
	  uiout->field_string ("current", c, style);
	uiout->text ("\n");
      }
  }

  if (tvariables.empty ())
    uiout->text (_("No trace state variables.\n"));
}

/* List all the trace state variables.  */

static void
info_tvariables_command (const char *args, int from_tty)
{
  tvariables_info_1 ();
}

/* Stash definitions of tsvs into the given file.  */

void
save_trace_state_variables (struct ui_file *fp)
{
  for (const trace_state_variable &tsv : tvariables)
    {
      fprintf_unfiltered (fp, "tvariable $%s", tsv.name.c_str ());
      if (tsv.initial_value)
	fprintf_unfiltered (fp, " = %s", plongest (tsv.initial_value));
      fprintf_unfiltered (fp, "\n");
    }
}

/* ACTIONS functions: */

/* The three functions:
   collect_pseudocommand, 
   while_stepping_pseudocommand, and 
   end_actions_pseudocommand
   are placeholders for "commands" that are actually ONLY to be used
   within a tracepoint action list.  If the actual function is ever called,
   it means that somebody issued the "command" at the top level,
   which is always an error.  */

static void
end_actions_pseudocommand (const char *args, int from_tty)
{
  error (_("This command cannot be used at the top level."));
}

static void
while_stepping_pseudocommand (const char *args, int from_tty)
{
  error (_("This command can only be used in a tracepoint actions list."));
}

static void
collect_pseudocommand (const char *args, int from_tty)
{
  error (_("This command can only be used in a tracepoint actions list."));
}

static void
teval_pseudocommand (const char *args, int from_tty)
{
  error (_("This command can only be used in a tracepoint actions list."));
}

/* Parse any collection options, such as /s for strings.  */

const char *
decode_agent_options (const char *exp, int *trace_string)
{
  struct value_print_options opts;

  *trace_string = 0;

  if (*exp != '/')
    return exp;

  /* Call this to borrow the print elements default for collection
     size.  */
  get_user_print_options (&opts);

  exp++;
  if (*exp == 's')
    {
      if (target_supports_string_tracing ())
	{
	  /* Allow an optional decimal number giving an explicit maximum
	     string length, defaulting it to the "print elements" value;
	     so "collect/s80 mystr" gets at most 80 bytes of string.  */
	  *trace_string = opts.print_max;
	  exp++;
	  if (*exp >= '0' && *exp <= '9')
	    *trace_string = atoi (exp);
	  while (*exp >= '0' && *exp <= '9')
	    exp++;
	}
      else
	error (_("Target does not support \"/s\" option for string tracing."));
    }
  else
    error (_("Undefined collection format \"%c\"."), *exp);

  exp = skip_spaces (exp);

  return exp;
}

/* Enter a list of actions for a tracepoint.  */
static void
actions_command (const char *args, int from_tty)
{
  struct tracepoint *t;

  t = get_tracepoint_by_number (&args, NULL);
  if (t)
    {
      std::string tmpbuf =
	string_printf ("Enter actions for tracepoint %d, one per line.",
		       t->number);

      counted_command_line l = read_command_lines (tmpbuf.c_str (),
						   from_tty, 1,
						   [=] (const char *line)
						     {
						       validate_actionline (line, t);
						     });
      breakpoint_set_commands (t, std::move (l));
    }
  /* else just return */
}

/* Report the results of checking the agent expression, as errors or
   internal errors.  */

static void
report_agent_reqs_errors (struct agent_expr *aexpr)
{
  /* All of the "flaws" are serious bytecode generation issues that
     should never occur.  */
  if (aexpr->flaw != agent_flaw_none)
    internal_error (__FILE__, __LINE__, _("expression is malformed"));

  /* If analysis shows a stack underflow, GDB must have done something
     badly wrong in its bytecode generation.  */
  if (aexpr->min_height < 0)
    internal_error (__FILE__, __LINE__,
		    _("expression has min height < 0"));

  /* Issue this error if the stack is predicted to get too deep.  The
     limit is rather arbitrary; a better scheme might be for the
     target to report how much stack it will have available.  The
     depth roughly corresponds to parenthesization, so a limit of 20
     amounts to 20 levels of expression nesting, which is actually
     a pretty big hairy expression.  */
  if (aexpr->max_height > 20)
    error (_("Expression is too complicated."));
}

/* Call ax_reqs on AEXPR and raise an error if something is wrong.  */

static void
finalize_tracepoint_aexpr (struct agent_expr *aexpr)
{
  ax_reqs (aexpr);

  if (aexpr->len > MAX_AGENT_EXPR_LEN)
    error (_("Expression is too complicated."));

  report_agent_reqs_errors (aexpr);
}

/* worker function */
void
validate_actionline (const char *line, struct breakpoint *b)
{
  struct cmd_list_element *c;
  const char *tmp_p;
  const char *p;
  struct bp_location *loc;
  struct tracepoint *t = (struct tracepoint *) b;

  /* If EOF is typed, *line is NULL.  */
  if (line == NULL)
    return;

  p = skip_spaces (line);

  /* Symbol lookup etc.  */
  if (*p == '\0')	/* empty line: just prompt for another line.  */
    return;

  if (*p == '#')		/* comment line */
    return;

  c = lookup_cmd (&p, cmdlist, "", NULL, -1, 1);
  if (c == 0)
    error (_("`%s' is not a tracepoint action, or is ambiguous."), p);

  if (cmd_cfunc_eq (c, collect_pseudocommand))
    {
      int trace_string = 0;

      if (*p == '/')
	p = decode_agent_options (p, &trace_string);

      do
	{			/* Repeat over a comma-separated list.  */
	  QUIT;			/* Allow user to bail out with ^C.  */
	  p = skip_spaces (p);

	  if (*p == '$')	/* Look for special pseudo-symbols.  */
	    {
	      if (0 == strncasecmp ("reg", p + 1, 3)
		  || 0 == strncasecmp ("arg", p + 1, 3)
		  || 0 == strncasecmp ("loc", p + 1, 3)
		  || 0 == strncasecmp ("_ret", p + 1, 4)
		  || 0 == strncasecmp ("_sdata", p + 1, 6))
		{
		  p = strchr (p, ',');
		  continue;
		}
	      /* else fall thru, treat p as an expression and parse it!  */
	    }
	  tmp_p = p;
	  for (loc = t->loc; loc; loc = loc->next)
	    {
	      p = tmp_p;
	      expression_up exp = parse_exp_1 (&p, loc->address,
					       block_for_pc (loc->address), 1);

	      if (exp->elts[0].opcode == OP_VAR_VALUE)
		{
		  if (SYMBOL_CLASS (exp->elts[2].symbol) == LOC_CONST)
		    {
		      error (_("constant `%s' (value %s) "
			       "will not be collected."),
			     exp->elts[2].symbol->print_name (),
			     plongest (SYMBOL_VALUE (exp->elts[2].symbol)));
		    }
		  else if (SYMBOL_CLASS (exp->elts[2].symbol)
			   == LOC_OPTIMIZED_OUT)
		    {
		      error (_("`%s' is optimized away "
			       "and cannot be collected."),
			     exp->elts[2].symbol->print_name ());
		    }
		}

	      /* We have something to collect, make sure that the expr to
		 bytecode translator can handle it and that it's not too
		 long.  */
	      agent_expr_up aexpr = gen_trace_for_expr (loc->address,
							exp.get (),
							trace_string);

	      finalize_tracepoint_aexpr (aexpr.get ());
	    }
	}
      while (p && *p++ == ',');
    }

  else if (cmd_cfunc_eq (c, teval_pseudocommand))
    {
      do
	{			/* Repeat over a comma-separated list.  */
	  QUIT;			/* Allow user to bail out with ^C.  */
	  p = skip_spaces (p);

	  tmp_p = p;
	  for (loc = t->loc; loc; loc = loc->next)
	    {
	      p = tmp_p;

	      /* Only expressions are allowed for this action.  */
	      expression_up exp = parse_exp_1 (&p, loc->address,
					       block_for_pc (loc->address), 1);

	      /* We have something to evaluate, make sure that the expr to
		 bytecode translator can handle it and that it's not too
		 long.  */
	      agent_expr_up aexpr = gen_eval_for_expr (loc->address, exp.get ());

	      finalize_tracepoint_aexpr (aexpr.get ());
	    }
	}
      while (p && *p++ == ',');
    }

  else if (cmd_cfunc_eq (c, while_stepping_pseudocommand))
    {
      char *endp;

      p = skip_spaces (p);
      t->step_count = strtol (p, &endp, 0);
      if (endp == p || t->step_count == 0)
	error (_("while-stepping step count `%s' is malformed."), line);
      p = endp;
    }

  else if (cmd_cfunc_eq (c, end_actions_pseudocommand))
    ;

  else
    error (_("`%s' is not a supported tracepoint action."), line);
}

enum {
  memrange_absolute = -1
};

/* MEMRANGE functions: */

/* Compare memranges for std::sort.  */

static bool
memrange_comp (const memrange &a, const memrange &b)
{
  if (a.type == b.type)
    {
      if (a.type == memrange_absolute)
	return (bfd_vma) a.start < (bfd_vma) b.start;
      else
	return a.start < b.start;
    }

  return a.type < b.type;
}

/* Sort the memrange list using std::sort, and merge adjacent memranges.  */

static void
memrange_sortmerge (std::vector<memrange> &memranges)
{
  if (!memranges.empty ())
    {
      int a, b;

      std::sort (memranges.begin (), memranges.end (), memrange_comp);

      for (a = 0, b = 1; b < memranges.size (); b++)
	{
	  /* If memrange b overlaps or is adjacent to memrange a,
	     merge them.  */
	  if (memranges[a].type == memranges[b].type
	      && memranges[b].start <= memranges[a].end)
	    {
	      if (memranges[b].end > memranges[a].end)
		memranges[a].end = memranges[b].end;
	      continue;		/* next b, same a */
	    }
	  a++;			/* next a */
	  if (a != b)
	    memranges[a] = memranges[b];
	}
      memranges.resize (a + 1);
    }
}

/* Add remote register number REGNO to the collection list mask.  */

void
collection_list::add_remote_register (unsigned int regno)
{
  if (info_verbose)
    printf_filtered ("collect register %d\n", regno);

  m_regs_mask.at (regno / 8) |= 1 << (regno % 8);
}

/* Add all the registers from the mask in AEXPR to the mask in the
   collection list.  Registers in the AEXPR mask are already remote
   register numbers.  */

void
collection_list::add_ax_registers (struct agent_expr *aexpr)
{
  if (aexpr->reg_mask_len > 0)
    {
      for (int ndx1 = 0; ndx1 < aexpr->reg_mask_len; ndx1++)
	{
	  QUIT;	/* Allow user to bail out with ^C.  */
	  if (aexpr->reg_mask[ndx1] != 0)
	    {
	      /* Assume chars have 8 bits.  */
	      for (int ndx2 = 0; ndx2 < 8; ndx2++)
		if (aexpr->reg_mask[ndx1] & (1 << ndx2))
		  /* It's used -- record it.  */
		  add_remote_register (ndx1 * 8 + ndx2);
	    }
	}
    }
}

/* If REGNO is raw, add its corresponding remote register number to
   the mask.  If REGNO is a pseudo-register, figure out the necessary
   registers using a temporary agent expression, and add it to the
   list if it needs more than just a mask.  */

void
collection_list::add_local_register (struct gdbarch *gdbarch,
				     unsigned int regno,
				     CORE_ADDR scope)
{
  if (regno < gdbarch_num_regs (gdbarch))
    {
      int remote_regno = gdbarch_remote_register_number (gdbarch, regno);

      if (remote_regno < 0)
	error (_("Can't collect register %d"), regno);

      add_remote_register (remote_regno);
    }
  else
    {
      agent_expr_up aexpr (new agent_expr (gdbarch, scope));

      ax_reg_mask (aexpr.get (), regno);

      finalize_tracepoint_aexpr (aexpr.get ());

      add_ax_registers (aexpr.get ());

      /* Usually ax_reg_mask for a pseudo-regiser only sets the
	 corresponding raw registers in the ax mask, but if this isn't
	 the case add the expression that is generated to the
	 collection list.  */
      if (aexpr->len > 0)
	add_aexpr (std::move (aexpr));
    }
}

/* Add a memrange to a collection list.  */

void
collection_list::add_memrange (struct gdbarch *gdbarch,
			       int type, bfd_signed_vma base,
			       unsigned long len, CORE_ADDR scope)
{
  if (info_verbose)
    printf_filtered ("(%d,%s,%ld)\n", type, paddress (gdbarch, base), len);

  /* type: memrange_absolute == memory, other n == basereg */
  /* base: addr if memory, offset if reg relative.  */
  /* len: we actually save end (base + len) for convenience */
  m_memranges.emplace_back (type, base, base + len);

  if (type != memrange_absolute)    /* Better collect the base register!  */
    add_local_register (gdbarch, type, scope);
}

/* Add a symbol to a collection list.  */

void
collection_list::collect_symbol (struct symbol *sym,
				 struct gdbarch *gdbarch,
				 long frame_regno, long frame_offset,
				 CORE_ADDR scope,
				 int trace_string)
{
  unsigned long len;
  unsigned int reg;
  bfd_signed_vma offset;
  int treat_as_expr = 0;

  len = TYPE_LENGTH (check_typedef (SYMBOL_TYPE (sym)));
  switch (SYMBOL_CLASS (sym))
    {
    default:
      printf_filtered ("%s: don't know symbol class %d\n",
		       sym->print_name (), SYMBOL_CLASS (sym));
      break;
    case LOC_CONST:
      printf_filtered ("constant %s (value %s) will not be collected.\n",
		       sym->print_name (), plongest (SYMBOL_VALUE (sym)));
      break;
    case LOC_STATIC:
      offset = SYMBOL_VALUE_ADDRESS (sym);
      if (info_verbose)
	{
	  printf_filtered ("LOC_STATIC %s: collect %ld bytes at %s.\n",
			   sym->print_name (), len,
			   paddress (gdbarch, offset));
	}
      /* A struct may be a C++ class with static fields, go to general
	 expression handling.  */
      if (SYMBOL_TYPE (sym)->code () == TYPE_CODE_STRUCT)
	treat_as_expr = 1;
      else
	add_memrange (gdbarch, memrange_absolute, offset, len, scope);
      break;
    case LOC_REGISTER:
      reg = SYMBOL_REGISTER_OPS (sym)->register_number (sym, gdbarch);
      if (info_verbose)
	printf_filtered ("LOC_REG[parm] %s: ", sym->print_name ());
      add_local_register (gdbarch, reg, scope);
      /* Check for doubles stored in two registers.  */
      /* FIXME: how about larger types stored in 3 or more regs?  */
      if (SYMBOL_TYPE (sym)->code () == TYPE_CODE_FLT &&
	  len > register_size (gdbarch, reg))
	add_local_register (gdbarch, reg + 1, scope);
      break;
    case LOC_REF_ARG:
      printf_filtered ("Sorry, don't know how to do LOC_REF_ARG yet.\n");
      printf_filtered ("       (will not collect %s)\n", sym->print_name ());
      break;
    case LOC_ARG:
      reg = frame_regno;
      offset = frame_offset + SYMBOL_VALUE (sym);
      if (info_verbose)
	{
	  printf_filtered ("LOC_LOCAL %s: Collect %ld bytes at offset %s"
			   " from frame ptr reg %d\n", sym->print_name (), len,
			   paddress (gdbarch, offset), reg);
	}
      add_memrange (gdbarch, reg, offset, len, scope);
      break;
    case LOC_REGPARM_ADDR:
      reg = SYMBOL_VALUE (sym);
      offset = 0;
      if (info_verbose)
	{
	  printf_filtered ("LOC_REGPARM_ADDR %s: Collect %ld bytes at offset %s"
			   " from reg %d\n", sym->print_name (), len,
			   paddress (gdbarch, offset), reg);
	}
      add_memrange (gdbarch, reg, offset, len, scope);
      break;
    case LOC_LOCAL:
      reg = frame_regno;
      offset = frame_offset + SYMBOL_VALUE (sym);
      if (info_verbose)
	{
	  printf_filtered ("LOC_LOCAL %s: Collect %ld bytes at offset %s"
			   " from frame ptr reg %d\n", sym->print_name (), len,
			   paddress (gdbarch, offset), reg);
	}
      add_memrange (gdbarch, reg, offset, len, scope);
      break;

    case LOC_UNRESOLVED:
      treat_as_expr = 1;
      break;

    case LOC_OPTIMIZED_OUT:
      printf_filtered ("%s has been optimized out of existence.\n",
		       sym->print_name ());
      break;

    case LOC_COMPUTED:
      treat_as_expr = 1;
      break;
    }

  /* Expressions are the most general case.  */
  if (treat_as_expr)
    {
      agent_expr_up aexpr = gen_trace_for_var (scope, gdbarch,
					       sym, trace_string);

      /* It can happen that the symbol is recorded as a computed
	 location, but it's been optimized away and doesn't actually
	 have a location expression.  */
      if (!aexpr)
	{
	  printf_filtered ("%s has been optimized out of existence.\n",
			   sym->print_name ());
	  return;
	}

      finalize_tracepoint_aexpr (aexpr.get ());

      /* Take care of the registers.  */
      add_ax_registers (aexpr.get ());

      add_aexpr (std::move (aexpr));
    }
}

/* Data to be passed around in the calls to the locals and args
   iterators.  */

struct add_local_symbols_data
{
  struct collection_list *collect;
  struct gdbarch *gdbarch;
  CORE_ADDR pc;
  long frame_regno;
  long frame_offset;
  int count;
  int trace_string;
};

/* The callback for the locals and args iterators.  */

static void
do_collect_symbol (const char *print_name,
		   struct symbol *sym,
		   void *cb_data)
{
  struct add_local_symbols_data *p = (struct add_local_symbols_data *) cb_data;

  p->collect->collect_symbol (sym, p->gdbarch, p->frame_regno,
			      p->frame_offset, p->pc, p->trace_string);
  p->count++;

  p->collect->add_wholly_collected (print_name);
}

void
collection_list::add_wholly_collected (const char *print_name)
{
  m_wholly_collected.push_back (print_name);
}

/* Add all locals (or args) symbols to collection list.  */

void
collection_list::add_local_symbols (struct gdbarch *gdbarch, CORE_ADDR pc,
				    long frame_regno, long frame_offset, int type,
				    int trace_string)
{
  const struct block *block;
  struct add_local_symbols_data cb_data;

  cb_data.collect = this;
  cb_data.gdbarch = gdbarch;
  cb_data.pc = pc;
  cb_data.frame_regno = frame_regno;
  cb_data.frame_offset = frame_offset;
  cb_data.count = 0;
  cb_data.trace_string = trace_string;

  if (type == 'L')
    {
      block = block_for_pc (pc);
      if (block == NULL)
	{
	  warning (_("Can't collect locals; "
		     "no symbol table info available.\n"));
	  return;
	}

      iterate_over_block_local_vars (block, do_collect_symbol, &cb_data);
      if (cb_data.count == 0)
	warning (_("No locals found in scope."));
    }
  else
    {
      pc = get_pc_function_start (pc);
      block = block_for_pc (pc);
      if (block == NULL)
	{
	  warning (_("Can't collect args; no symbol table info available."));
	  return;
	}

      iterate_over_block_arg_vars (block, do_collect_symbol, &cb_data);
      if (cb_data.count == 0)
	warning (_("No args found in scope."));
    }
}

void
collection_list::add_static_trace_data ()
{
  if (info_verbose)
    printf_filtered ("collect static trace data\n");
  m_strace_data = true;
}

collection_list::collection_list ()
  : m_strace_data (false)
{
  int max_remote_regno = 0;
  for (int i = 0; i < gdbarch_num_regs (target_gdbarch ()); i++)
    {
      int remote_regno = (gdbarch_remote_register_number
			  (target_gdbarch (), i));

      if (remote_regno >= 0 && remote_regno > max_remote_regno)
	max_remote_regno = remote_regno;
    }

  m_regs_mask.resize ((max_remote_regno / 8) + 1);

  m_memranges.reserve (128);
  m_aexprs.reserve (128);
}

/* Reduce a collection list to string form (for gdb protocol).  */

std::vector<std::string>
collection_list::stringify ()
{
  gdb::char_vector temp_buf (2048);

  int count;
  char *end;
  long i;
  std::vector<std::string> str_list;

  if (m_strace_data)
    {
      if (info_verbose)
	printf_filtered ("\nCollecting static trace data\n");
      end = temp_buf.data ();
      *end++ = 'L';
      str_list.emplace_back (temp_buf.data (), end - temp_buf.data ());
    }

  for (i = m_regs_mask.size () - 1; i > 0; i--)
    if (m_regs_mask[i] != 0)    /* Skip leading zeroes in regs_mask.  */
      break;
  if (m_regs_mask[i] != 0)	/* Prepare to send regs_mask to the stub.  */
    {
      if (info_verbose)
	printf_filtered ("\nCollecting registers (mask): 0x");

      /* One char for 'R', one for the null terminator and two per
	 mask byte.  */
      std::size_t new_size = (i + 1) * 2 + 2;
      if (new_size > temp_buf.size ())
	temp_buf.resize (new_size);

      end = temp_buf.data ();
      *end++ = 'R';
      for (; i >= 0; i--)
	{
	  QUIT;			/* Allow user to bail out with ^C.  */
	  if (info_verbose)
	    printf_filtered ("%02X", m_regs_mask[i]);

	  end = pack_hex_byte (end, m_regs_mask[i]);
	}
      *end = '\0';

      str_list.emplace_back (temp_buf.data ());
    }
  if (info_verbose)
    printf_filtered ("\n");
  if (!m_memranges.empty () && info_verbose)
    printf_filtered ("Collecting memranges: \n");
  for (i = 0, count = 0, end = temp_buf.data ();
       i < m_memranges.size (); i++)
    {
      QUIT;			/* Allow user to bail out with ^C.  */
      if (info_verbose)
	{
	  printf_filtered ("(%d, %s, %ld)\n", 
			   m_memranges[i].type,
			   paddress (target_gdbarch (),
				     m_memranges[i].start),
			   (long) (m_memranges[i].end
				   - m_memranges[i].start));
	}
      if (count + 27 > MAX_AGENT_EXPR_LEN)
	{
	  str_list.emplace_back (temp_buf.data (), count);
	  count = 0;
	  end = temp_buf.data ();
	}

      {
	bfd_signed_vma length
	  = m_memranges[i].end - m_memranges[i].start;

	/* The "%X" conversion specifier expects an unsigned argument,
	   so passing -1 (memrange_absolute) to it directly gives you
	   "FFFFFFFF" (or more, depending on sizeof (unsigned)).
	   Special-case it.  */
	if (m_memranges[i].type == memrange_absolute)
	  sprintf (end, "M-1,%s,%lX", phex_nz (m_memranges[i].start, 0),
		   (long) length);
	else
	  sprintf (end, "M%X,%s,%lX", m_memranges[i].type,
		   phex_nz (m_memranges[i].start, 0), (long) length);
      }

      count += strlen (end);
      end = temp_buf.data () + count;
    }

  for (i = 0; i < m_aexprs.size (); i++)
    {
      QUIT;			/* Allow user to bail out with ^C.  */
      if ((count + 10 + 2 * m_aexprs[i]->len) > MAX_AGENT_EXPR_LEN)
	{
	  str_list.emplace_back (temp_buf.data (), count);
	  count = 0;
	  end = temp_buf.data ();
	}
      sprintf (end, "X%08X,", m_aexprs[i]->len);
      end += 10;		/* 'X' + 8 hex digits + ',' */
      count += 10;

      end = mem2hex (m_aexprs[i]->buf, end, m_aexprs[i]->len);
      count += 2 * m_aexprs[i]->len;
    }

  if (count != 0)
    {
      str_list.emplace_back (temp_buf.data (), count);
      count = 0;
      end = temp_buf.data ();
    }

  return str_list;
}

/* Add the printed expression EXP to *LIST.  */

void
collection_list::append_exp (struct expression *exp)
{
  string_file tmp_stream;

  print_expression (exp, &tmp_stream);

  m_computed.push_back (std::move (tmp_stream.string ()));
}

void
collection_list::finish ()
{
  memrange_sortmerge (m_memranges);
}

static void
encode_actions_1 (struct command_line *action,
		  struct bp_location *tloc,
		  int frame_reg,
		  LONGEST frame_offset,
		  struct collection_list *collect,
		  struct collection_list *stepping_list)
{
  const char *action_exp;
  int i;
  struct value *tempval;
  struct cmd_list_element *cmd;

  for (; action; action = action->next)
    {
      QUIT;			/* Allow user to bail out with ^C.  */
      action_exp = action->line;
      action_exp = skip_spaces (action_exp);

      cmd = lookup_cmd (&action_exp, cmdlist, "", NULL, -1, 1);
      if (cmd == 0)
	error (_("Bad action list item: %s"), action_exp);

      if (cmd_cfunc_eq (cmd, collect_pseudocommand))
	{
	  int trace_string = 0;

	  if (*action_exp == '/')
	    action_exp = decode_agent_options (action_exp, &trace_string);

	  do
	    {			/* Repeat over a comma-separated list.  */
	      QUIT;		/* Allow user to bail out with ^C.  */
	      action_exp = skip_spaces (action_exp);

	      if (0 == strncasecmp ("$reg", action_exp, 4))
		{
		  for (i = 0; i < gdbarch_num_regs (target_gdbarch ());
		       i++)
		    {
		      int remote_regno = (gdbarch_remote_register_number
					  (target_gdbarch (), i));

		      /* Ignore arch regnos without a corresponding
			 remote regno.  This can happen for regnos not
			 in the tdesc.  */
		      if (remote_regno >= 0)
			collect->add_remote_register (remote_regno);
		    }
		  action_exp = strchr (action_exp, ',');	/* more? */
		}
	      else if (0 == strncasecmp ("$arg", action_exp, 4))
		{
		  collect->add_local_symbols (target_gdbarch (),
					      tloc->address,
					      frame_reg,
					      frame_offset,
					      'A',
					      trace_string);
		  action_exp = strchr (action_exp, ',');	/* more? */
		}
	      else if (0 == strncasecmp ("$loc", action_exp, 4))
		{
		  collect->add_local_symbols (target_gdbarch (),
					      tloc->address,
					      frame_reg,
					      frame_offset,
					      'L',
					      trace_string);
		  action_exp = strchr (action_exp, ',');	/* more? */
		}
	      else if (0 == strncasecmp ("$_ret", action_exp, 5))
		{
		  agent_expr_up aexpr
		    = gen_trace_for_return_address (tloc->address,
						    target_gdbarch (),
						    trace_string);

		  finalize_tracepoint_aexpr (aexpr.get ());

		  /* take care of the registers */
		  collect->add_ax_registers (aexpr.get ());

		  collect->add_aexpr (std::move (aexpr));
		  action_exp = strchr (action_exp, ',');	/* more? */
		}
	      else if (0 == strncasecmp ("$_sdata", action_exp, 7))
		{
		  collect->add_static_trace_data ();
		  action_exp = strchr (action_exp, ',');	/* more? */
		}
	      else
		{
		  unsigned long addr;

		  expression_up exp = parse_exp_1 (&action_exp, tloc->address,
						   block_for_pc (tloc->address),
						   1);

		  switch (exp->elts[0].opcode)
		    {
		    case OP_REGISTER:
		      {
			const char *name = &exp->elts[2].string;

			i = user_reg_map_name_to_regnum (target_gdbarch (),
							 name, strlen (name));
			if (i == -1)
			  internal_error (__FILE__, __LINE__,
					  _("Register $%s not available"),
					  name);
			if (info_verbose)
			  printf_filtered ("OP_REGISTER: ");
			collect->add_local_register (target_gdbarch (),
						     i, tloc->address);
			break;
		      }

		    case UNOP_MEMVAL:
		      /* Safe because we know it's a simple expression.  */
		      tempval = evaluate_expression (exp.get ());
		      addr = value_address (tempval);
		      /* Initialize the TYPE_LENGTH if it is a typedef.  */
		      check_typedef (exp->elts[1].type);
		      collect->add_memrange (target_gdbarch (),
					     memrange_absolute, addr,
					     TYPE_LENGTH (exp->elts[1].type),
					     tloc->address);
		      collect->append_exp (exp.get ());
		      break;

		    case OP_VAR_VALUE:
		      {
			struct symbol *sym = exp->elts[2].symbol;
			const char *name = sym->natural_name ();

			collect->collect_symbol (exp->elts[2].symbol,
						 target_gdbarch (),
						 frame_reg,
						 frame_offset,
						 tloc->address,
						 trace_string);
			collect->add_wholly_collected (name);
		      }
		      break;

		    default:	/* Full-fledged expression.  */
		      agent_expr_up aexpr = gen_trace_for_expr (tloc->address,
								exp.get (),
								trace_string);

		      finalize_tracepoint_aexpr (aexpr.get ());

		      /* Take care of the registers.  */
		      collect->add_ax_registers (aexpr.get ());

		      collect->add_aexpr (std::move (aexpr));
		      collect->append_exp (exp.get ());
		      break;
		    }		/* switch */
		}		/* do */
	    }
	  while (action_exp && *action_exp++ == ',');
	}			/* if */
      else if (cmd_cfunc_eq (cmd, teval_pseudocommand))
	{
	  do
	    {			/* Repeat over a comma-separated list.  */
	      QUIT;		/* Allow user to bail out with ^C.  */
	      action_exp = skip_spaces (action_exp);

		{
		  expression_up exp = parse_exp_1 (&action_exp, tloc->address,
						   block_for_pc (tloc->address),
						   1);

		  agent_expr_up aexpr = gen_eval_for_expr (tloc->address,
							   exp.get ());

		  finalize_tracepoint_aexpr (aexpr.get ());

		  /* Even though we're not officially collecting, add
		     to the collect list anyway.  */
		  collect->add_aexpr (std::move (aexpr));
		}		/* do */
	    }
	  while (action_exp && *action_exp++ == ',');
	}			/* if */
      else if (cmd_cfunc_eq (cmd, while_stepping_pseudocommand))
	{
	  /* We check against nested while-stepping when setting
	     breakpoint action, so no way to run into nested
	     here.  */
	  gdb_assert (stepping_list);

	  encode_actions_1 (action->body_list_0.get (), tloc, frame_reg,
			    frame_offset, stepping_list, NULL);
	}
      else
	error (_("Invalid tracepoint command '%s'"), action->line);
    }				/* for */
}

/* Encode actions of tracepoint TLOC->owner and fill TRACEPOINT_LIST
   and STEPPING_LIST.  */

void
encode_actions (struct bp_location *tloc,
		struct collection_list *tracepoint_list,
		struct collection_list *stepping_list)
{
  int frame_reg;
  LONGEST frame_offset;

  gdbarch_virtual_frame_pointer (tloc->gdbarch,
				 tloc->address, &frame_reg, &frame_offset);

  counted_command_line actions = all_tracepoint_actions (tloc->owner);
  encode_actions_1 (actions.get (), tloc, frame_reg, frame_offset,
		    tracepoint_list, stepping_list);
  encode_actions_1 (breakpoint_commands (tloc->owner), tloc,
		    frame_reg, frame_offset, tracepoint_list, stepping_list);

  tracepoint_list->finish ();
  stepping_list->finish ();
}

/* Render all actions into gdb protocol.  */

void
encode_actions_rsp (struct bp_location *tloc,
		    std::vector<std::string> *tdp_actions,
		    std::vector<std::string> *stepping_actions)
{
  struct collection_list tracepoint_list, stepping_list;

  encode_actions (tloc, &tracepoint_list, &stepping_list);

  *tdp_actions = tracepoint_list.stringify ();
  *stepping_actions = stepping_list.stringify ();
}

void
collection_list::add_aexpr (agent_expr_up aexpr)
{
  m_aexprs.push_back (std::move (aexpr));
}

static void
process_tracepoint_on_disconnect (void)
{
  int has_pending_p = 0;

  /* Check whether we still have pending tracepoint.  If we have, warn the
     user that pending tracepoint will no longer work.  */
  for (breakpoint *b : all_tracepoints ())
    {
      if (b->loc == NULL)
	{
	  has_pending_p = 1;
	  break;
	}
      else
	{
	  struct bp_location *loc1;

	  for (loc1 = b->loc; loc1; loc1 = loc1->next)
	    {
	      if (loc1->shlib_disabled)
		{
		  has_pending_p = 1;
		  break;
		}
	    }

	  if (has_pending_p)
	    break;
	}
    }

  if (has_pending_p)
    warning (_("Pending tracepoints will not be resolved while"
	       " GDB is disconnected\n"));
}

/* Reset local state of tracing.  */

void
trace_reset_local_state (void)
{
  set_traceframe_num (-1);
  set_tracepoint_num (-1);
  set_traceframe_context (NULL);
  clear_traceframe_info ();
}

void
start_tracing (const char *notes)
{
  int any_enabled = 0, num_to_download = 0;
  int ret;

  std::vector<breakpoint *> tp_vec = all_tracepoints ();

  /* No point in tracing without any tracepoints...  */
  if (tp_vec.empty ())
    error (_("No tracepoints defined, not starting trace"));

  for (breakpoint *b : tp_vec)
    {
      if (b->enable_state == bp_enabled)
	any_enabled = 1;

      if ((b->type == bp_fast_tracepoint
	   ? may_insert_fast_tracepoints
	   : may_insert_tracepoints))
	++num_to_download;
      else
	warning (_("May not insert %stracepoints, skipping tracepoint %d"),
		 (b->type == bp_fast_tracepoint ? "fast " : ""), b->number);
    }

  if (!any_enabled)
    {
      if (target_supports_enable_disable_tracepoint ())
	warning (_("No tracepoints enabled"));
      else
	{
	  /* No point in tracing with only disabled tracepoints that
	     cannot be re-enabled.  */
	  error (_("No tracepoints enabled, not starting trace"));
	}
    }

  if (num_to_download <= 0)
    error (_("No tracepoints that may be downloaded, not starting trace"));

  target_trace_init ();

  for (breakpoint *b : tp_vec)
    {
      struct tracepoint *t = (struct tracepoint *) b;
      struct bp_location *loc;
      int bp_location_downloaded = 0;

      /* Clear `inserted' flag.  */
      for (loc = b->loc; loc; loc = loc->next)
	loc->inserted = 0;

      if ((b->type == bp_fast_tracepoint
	   ? !may_insert_fast_tracepoints
	   : !may_insert_tracepoints))
	continue;

      t->number_on_target = 0;

      for (loc = b->loc; loc; loc = loc->next)
	{
	  /* Since tracepoint locations are never duplicated, `inserted'
	     flag should be zero.  */
	  gdb_assert (!loc->inserted);

	  target_download_tracepoint (loc);

	  loc->inserted = 1;
	  bp_location_downloaded = 1;
	}

      t->number_on_target = b->number;

      for (loc = b->loc; loc; loc = loc->next)
	if (loc->probe.prob != NULL)
	  loc->probe.prob->set_semaphore (loc->probe.objfile,
					  loc->gdbarch);

      if (bp_location_downloaded)
	gdb::observers::breakpoint_modified.notify (b);
    }

  /* Send down all the trace state variables too.  */
  for (const trace_state_variable &tsv : tvariables)
    target_download_trace_state_variable (tsv);
  
  /* Tell target to treat text-like sections as transparent.  */
  target_trace_set_readonly_regions ();
  /* Set some mode flags.  */
  target_set_disconnected_tracing (disconnected_tracing);
  target_set_circular_trace_buffer (circular_trace_buffer);
  target_set_trace_buffer_size (trace_buffer_size);

  if (!notes)
    notes = trace_notes;
  ret = target_set_trace_notes (trace_user, notes, NULL);

  if (!ret && (trace_user || notes))
    warning (_("Target does not support trace user/notes, info ignored"));

  /* Now insert traps and begin collecting data.  */
  target_trace_start ();

  /* Reset our local state.  */
  trace_reset_local_state ();
  current_trace_status()->running = 1;
}

/* The tstart command requests the target to start a new trace run.
   The command passes any arguments it has to the target verbatim, as
   an optional "trace note".  This is useful as for instance a warning
   to other users if the trace runs disconnected, and you don't want
   anybody else messing with the target.  */

static void
tstart_command (const char *args, int from_tty)
{
  dont_repeat ();	/* Like "run", dangerous to repeat accidentally.  */

  if (current_trace_status ()->running)
    {
      if (from_tty
	  && !query (_("A trace is running already.  Start a new run? ")))
	error (_("New trace run not started."));
    }

  start_tracing (args);
}

/* The tstop command stops the tracing run.  The command passes any
   supplied arguments to the target verbatim as a "stop note"; if the
   target supports trace notes, then it will be reported back as part
   of the trace run's status.  */

static void
tstop_command (const char *args, int from_tty)
{
  if (!current_trace_status ()->running)
    error (_("Trace is not running."));

  stop_tracing (args);
}

void
stop_tracing (const char *note)
{
  int ret;

  target_trace_stop ();

  for (breakpoint *t : all_tracepoints ())
    {
      struct bp_location *loc;

      if ((t->type == bp_fast_tracepoint
	   ? !may_insert_fast_tracepoints
	   : !may_insert_tracepoints))
	continue;

      for (loc = t->loc; loc; loc = loc->next)
	{
	  /* GDB can be totally absent in some disconnected trace scenarios,
	     but we don't really care if this semaphore goes out of sync.
	     That's why we are decrementing it here, but not taking care
	     in other places.  */
	  if (loc->probe.prob != NULL)
	    loc->probe.prob->clear_semaphore (loc->probe.objfile,
					      loc->gdbarch);
	}
    }

  if (!note)
    note = trace_stop_notes;
  ret = target_set_trace_notes (NULL, NULL, note);

  if (!ret && note)
    warning (_("Target does not support trace notes, note ignored"));

  /* Should change in response to reply?  */
  current_trace_status ()->running = 0;
}

/* tstatus command */
static void
tstatus_command (const char *args, int from_tty)
{
  struct trace_status *ts = current_trace_status ();
  int status;
  
  status = target_get_trace_status (ts);

  if (status == -1)
    {
      if (ts->filename != NULL)
	printf_filtered (_("Using a trace file.\n"));
      else
	{
	  printf_filtered (_("Trace can not be run on this target.\n"));
	  return;
	}
    }

  if (!ts->running_known)
    {
      printf_filtered (_("Run/stop status is unknown.\n"));
    }
  else if (ts->running)
    {
      printf_filtered (_("Trace is running on the target.\n"));
    }
  else
    {
      switch (ts->stop_reason)
	{
	case trace_never_run:
	  printf_filtered (_("No trace has been run on the target.\n"));
	  break;
	case trace_stop_command:
	  if (ts->stop_desc)
	    printf_filtered (_("Trace stopped by a tstop command (%s).\n"),
			     ts->stop_desc);
	  else
	    printf_filtered (_("Trace stopped by a tstop command.\n"));
	  break;
	case trace_buffer_full:
	  printf_filtered (_("Trace stopped because the buffer was full.\n"));
	  break;
	case trace_disconnected:
	  printf_filtered (_("Trace stopped because of disconnection.\n"));
	  break;
	case tracepoint_passcount:
	  printf_filtered (_("Trace stopped by tracepoint %d.\n"),
			   ts->stopping_tracepoint);
	  break;
	case tracepoint_error:
	  if (ts->stopping_tracepoint)
	    printf_filtered (_("Trace stopped by an "
			       "error (%s, tracepoint %d).\n"),
			     ts->stop_desc, ts->stopping_tracepoint);
	  else
	    printf_filtered (_("Trace stopped by an error (%s).\n"),
			     ts->stop_desc);
	  break;
	case trace_stop_reason_unknown:
	  printf_filtered (_("Trace stopped for an unknown reason.\n"));
	  break;
	default:
	  printf_filtered (_("Trace stopped for some other reason (%d).\n"),
			   ts->stop_reason);
	  break;
	}
    }

  if (ts->traceframes_created >= 0
      && ts->traceframe_count != ts->traceframes_created)
    {
      printf_filtered (_("Buffer contains %d trace "
			 "frames (of %d created total).\n"),
		       ts->traceframe_count, ts->traceframes_created);
    }
  else if (ts->traceframe_count >= 0)
    {
      printf_filtered (_("Collected %d trace frames.\n"),
		       ts->traceframe_count);
    }

  if (ts->buffer_free >= 0)
    {
      if (ts->buffer_size >= 0)
	{
	  printf_filtered (_("Trace buffer has %d bytes of %d bytes free"),
			   ts->buffer_free, ts->buffer_size);
	  if (ts->buffer_size > 0)
	    printf_filtered (_(" (%d%% full)"),
			     ((int) ((((long long) (ts->buffer_size
						    - ts->buffer_free)) * 100)
				     / ts->buffer_size)));
	  printf_filtered (_(".\n"));
	}
      else
	printf_filtered (_("Trace buffer has %d bytes free.\n"),
			 ts->buffer_free);
    }

  if (ts->disconnected_tracing)
    printf_filtered (_("Trace will continue if GDB disconnects.\n"));
  else
    printf_filtered (_("Trace will stop if GDB disconnects.\n"));

  if (ts->circular_buffer)
    printf_filtered (_("Trace buffer is circular.\n"));

  if (ts->user_name && strlen (ts->user_name) > 0)
    printf_filtered (_("Trace user is %s.\n"), ts->user_name);

  if (ts->notes && strlen (ts->notes) > 0)
    printf_filtered (_("Trace notes: %s.\n"), ts->notes);

  /* Now report on what we're doing with tfind.  */
  if (traceframe_number >= 0)
    printf_filtered (_("Looking at trace frame %d, tracepoint %d.\n"),
		     traceframe_number, tracepoint_number);
  else
    printf_filtered (_("Not looking at any trace frame.\n"));

  /* Report start/stop times if supplied.  */
  if (ts->start_time)
    {
      if (ts->stop_time)
	{
	  LONGEST run_time = ts->stop_time - ts->start_time;

	  /* Reporting a run time is more readable than two long numbers.  */
	  printf_filtered (_("Trace started at %ld.%06ld secs, stopped %ld.%06ld secs later.\n"),
			   (long int) (ts->start_time / 1000000),
			   (long int) (ts->start_time % 1000000),
			   (long int) (run_time / 1000000),
			   (long int) (run_time % 1000000));
	}
      else
	printf_filtered (_("Trace started at %ld.%06ld secs.\n"),
			 (long int) (ts->start_time / 1000000),
			 (long int) (ts->start_time % 1000000));
    }
  else if (ts->stop_time)
    printf_filtered (_("Trace stopped at %ld.%06ld secs.\n"),
		     (long int) (ts->stop_time / 1000000),
		     (long int) (ts->stop_time % 1000000));

  /* Now report any per-tracepoint status available.  */
  for (breakpoint *t : all_tracepoints ())
    target_get_tracepoint_status (t, NULL);
}

/* Report the trace status to uiout, in a way suitable for MI, and not
   suitable for CLI.  If ON_STOP is true, suppress a few fields that
   are not meaningful in the -trace-stop response.

   The implementation is essentially parallel to trace_status_command, but
   merging them will result in unreadable code.  */
void
trace_status_mi (int on_stop)
{
  struct ui_out *uiout = current_uiout;
  struct trace_status *ts = current_trace_status ();
  int status;

  status = target_get_trace_status (ts);

  if (status == -1 && ts->filename == NULL)
    {
      uiout->field_string ("supported", "0");
      return;
    }

  if (ts->filename != NULL)
    uiout->field_string ("supported", "file");
  else if (!on_stop)
    uiout->field_string ("supported", "1");

  if (ts->filename != NULL)
    uiout->field_string ("trace-file", ts->filename);

  gdb_assert (ts->running_known);

  if (ts->running)
    {
      uiout->field_string ("running", "1");

      /* Unlike CLI, do not show the state of 'disconnected-tracing' variable.
	 Given that the frontend gets the status either on -trace-stop, or from
	 -trace-status after re-connection, it does not seem like this
	 information is necessary for anything.  It is not necessary for either
	 figuring the vital state of the target nor for navigation of trace
	 frames.  If the frontend wants to show the current state is some
	 configure dialog, it can request the value when such dialog is
	 invoked by the user.  */
    }
  else
    {
      const char *stop_reason = NULL;
      int stopping_tracepoint = -1;

      if (!on_stop)
	uiout->field_string ("running", "0");

      if (ts->stop_reason != trace_stop_reason_unknown)
	{
	  switch (ts->stop_reason)
	    {
	    case trace_stop_command:
	      stop_reason = "request";
	      break;
	    case trace_buffer_full:
	      stop_reason = "overflow";
	      break;
	    case trace_disconnected:
	      stop_reason = "disconnection";
	      break;
	    case tracepoint_passcount:
	      stop_reason = "passcount";
	      stopping_tracepoint = ts->stopping_tracepoint;
	      break;
	    case tracepoint_error:
	      stop_reason = "error";
	      stopping_tracepoint = ts->stopping_tracepoint;
	      break;
	    }
	  
	  if (stop_reason)
	    {
	      uiout->field_string ("stop-reason", stop_reason);
	      if (stopping_tracepoint != -1)
		uiout->field_signed ("stopping-tracepoint",
				     stopping_tracepoint);
	      if (ts->stop_reason == tracepoint_error)
		uiout->field_string ("error-description",
				     ts->stop_desc);
	    }
	}
    }

  if (ts->traceframe_count != -1)
    uiout->field_signed ("frames", ts->traceframe_count);
  if (ts->traceframes_created != -1)
    uiout->field_signed ("frames-created", ts->traceframes_created);
  if (ts->buffer_size != -1)
    uiout->field_signed ("buffer-size", ts->buffer_size);
  if (ts->buffer_free != -1)
    uiout->field_signed ("buffer-free", ts->buffer_free);

  uiout->field_signed ("disconnected",  ts->disconnected_tracing);
  uiout->field_signed ("circular",  ts->circular_buffer);

  uiout->field_string ("user-name", ts->user_name);
  uiout->field_string ("notes", ts->notes);

  {
    char buf[100];

    xsnprintf (buf, sizeof buf, "%ld.%06ld",
	       (long int) (ts->start_time / 1000000),
	       (long int) (ts->start_time % 1000000));
    uiout->field_string ("start-time", buf);
    xsnprintf (buf, sizeof buf, "%ld.%06ld",
	       (long int) (ts->stop_time / 1000000),
	       (long int) (ts->stop_time % 1000000));
    uiout->field_string ("stop-time", buf);
  }
}

/* Check if a trace run is ongoing.  If so, and FROM_TTY, query the
   user if she really wants to detach.  */

void
query_if_trace_running (int from_tty)
{
  if (!from_tty)
    return;

  /* It can happen that the target that was tracing went away on its
     own, and we didn't notice.  Get a status update, and if the
     current target doesn't even do tracing, then assume it's not
     running anymore.  */
  if (target_get_trace_status (current_trace_status ()) < 0)
    current_trace_status ()->running = 0;

  /* If running interactively, give the user the option to cancel and
     then decide what to do differently with the run.  Scripts are
     just going to disconnect and let the target deal with it,
     according to how it's been instructed previously via
     disconnected-tracing.  */
  if (current_trace_status ()->running)
    {
      process_tracepoint_on_disconnect ();

      if (current_trace_status ()->disconnected_tracing)
	{
	  if (!query (_("Trace is running and will "
			"continue after detach; detach anyway? ")))
	    error (_("Not confirmed."));
	}
      else
	{
	  if (!query (_("Trace is running but will "
			"stop on detach; detach anyway? ")))
	    error (_("Not confirmed."));
	}
    }
}

/* This function handles the details of what to do about an ongoing
   tracing run if the user has asked to detach or otherwise disconnect
   from the target.  */

void
disconnect_tracing (void)
{
  /* Also we want to be out of tfind mode, otherwise things can get
     confusing upon reconnection.  Just use these calls instead of
     full tfind_1 behavior because we're in the middle of detaching,
     and there's no point to updating current stack frame etc.  */
  trace_reset_local_state ();
}

/* Worker function for the various flavors of the tfind command.  */
void
tfind_1 (enum trace_find_type type, int num,
	 CORE_ADDR addr1, CORE_ADDR addr2,
	 int from_tty)
{
  int target_frameno = -1, target_tracept = -1;
  struct frame_id old_frame_id = null_frame_id;
  struct tracepoint *tp;
  struct ui_out *uiout = current_uiout;

  /* Only try to get the current stack frame if we have a chance of
     succeeding.  In particular, if we're trying to get a first trace
     frame while all threads are running, it's not going to succeed,
     so leave it with a default value and let the frame comparison
     below (correctly) decide to print out the source location of the
     trace frame.  */
  if (!(type == tfind_number && num == -1)
      && (has_stack_frames () || traceframe_number >= 0))
    old_frame_id = get_frame_id (get_current_frame ());

  target_frameno = target_trace_find (type, num, addr1, addr2,
				      &target_tracept);
  
  if (type == tfind_number
      && num == -1
      && target_frameno == -1)
    {
      /* We told the target to get out of tfind mode, and it did.  */
    }
  else if (target_frameno == -1)
    {
      /* A request for a non-existent trace frame has failed.
	 Our response will be different, depending on FROM_TTY:

	 If FROM_TTY is true, meaning that this command was 
	 typed interactively by the user, then give an error
	 and DO NOT change the state of traceframe_number etc.

	 However if FROM_TTY is false, meaning that we're either
	 in a script, a loop, or a user-defined command, then 
	 DON'T give an error, but DO change the state of
	 traceframe_number etc. to invalid.

	 The rationale is that if you typed the command, you
	 might just have committed a typo or something, and you'd
	 like to NOT lose your current debugging state.  However
	 if you're in a user-defined command or especially in a
	 loop, then you need a way to detect that the command
	 failed WITHOUT aborting.  This allows you to write
	 scripts that search thru the trace buffer until the end,
	 and then continue on to do something else.  */
  
      if (from_tty)
	error (_("Target failed to find requested trace frame."));
      else
	{
	  if (info_verbose)
	    printf_filtered ("End of trace buffer.\n");
#if 0 /* dubious now?  */
	  /* The following will not recurse, since it's
	     special-cased.  */
	  tfind_command ("-1", from_tty);
#endif
	}
    }
  
  tp = get_tracepoint_by_number_on_target (target_tracept);

  reinit_frame_cache ();
  target_dcache_invalidate ();

  set_tracepoint_num (tp ? tp->number : target_tracept);

  if (target_frameno != get_traceframe_number ())
    gdb::observers::traceframe_changed.notify (target_frameno, tracepoint_number);

  set_current_traceframe (target_frameno);

  if (target_frameno == -1)
    set_traceframe_context (NULL);
  else
    set_traceframe_context (get_current_frame ());

  if (traceframe_number >= 0)
    {
      /* Use different branches for MI and CLI to make CLI messages
	 i18n-eable.  */
      if (uiout->is_mi_like_p ())
	{
	  uiout->field_string ("found", "1");
	  uiout->field_signed ("tracepoint", tracepoint_number);
	  uiout->field_signed ("traceframe", traceframe_number);
	}
      else
	{
	  printf_unfiltered (_("Found trace frame %d, tracepoint %d\n"),
			     traceframe_number, tracepoint_number);
	}
    }
  else
    {
      if (uiout->is_mi_like_p ())
	uiout->field_string ("found", "0");
      else if (type == tfind_number && num == -1)
	printf_unfiltered (_("No longer looking at any trace frame\n"));
      else /* This case may never occur, check.  */
	printf_unfiltered (_("No trace frame found\n"));
    }

  /* If we're in nonstop mode and getting out of looking at trace
     frames, there won't be any current frame to go back to and
     display.  */
  if (from_tty
      && (has_stack_frames () || traceframe_number >= 0))
    {
      enum print_what print_what;

      /* NOTE: in imitation of the step command, try to determine
	 whether we have made a transition from one function to
	 another.  If so, we'll print the "stack frame" (ie. the new
	 function and it's arguments) -- otherwise we'll just show the
	 new source line.  */

      if (frame_id_eq (old_frame_id,
		       get_frame_id (get_current_frame ())))
	print_what = SRC_LINE;
      else
	print_what = SRC_AND_LOC;

      print_stack_frame (get_selected_frame (NULL), 1, print_what, 1);
      do_displays ();
    }
}

/* Error on looking at traceframes while trace is running.  */

void
check_trace_running (struct trace_status *status)
{
  if (status->running && status->filename == NULL)
    error (_("May not look at trace frames while trace is running."));
}

/* trace_find_command takes a trace frame number n, 
   sends "QTFrame:<n>" to the target, 
   and accepts a reply that may contain several optional pieces
   of information: a frame number, a tracepoint number, and an
   indication of whether this is a trap frame or a stepping frame.

   The minimal response is just "OK" (which indicates that the 
   target does not give us a frame number or a tracepoint number).
   Instead of that, the target may send us a string containing
   any combination of:
   F<hexnum>    (gives the selected frame number)
   T<hexnum>    (gives the selected tracepoint number)
 */

/* tfind command */
static void
tfind_command_1 (const char *args, int from_tty)
{ /* This should only be called with a numeric argument.  */
  int frameno = -1;

  check_trace_running (current_trace_status ());
  
  if (args == 0 || *args == 0)
    { /* TFIND with no args means find NEXT trace frame.  */
      if (traceframe_number == -1)
	frameno = 0;	/* "next" is first one.  */
	else
	frameno = traceframe_number + 1;
    }
  else if (0 == strcmp (args, "-"))
    {
      if (traceframe_number == -1)
	error (_("not debugging trace buffer"));
      else if (from_tty && traceframe_number == 0)
	error (_("already at start of trace buffer"));
      
      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
    frameno = parse_and_eval_long (args);

  if (frameno < -1)
    error (_("invalid input (%d is less than zero)"), frameno);

  tfind_1 (tfind_number, frameno, 0, 0, from_tty);
}

static void
tfind_command (const char *args, int from_tty)
{
  tfind_command_1 (args, from_tty);
}

/* tfind end */
static void
tfind_end_command (const char *args, int from_tty)
{
  tfind_command_1 ("-1", from_tty);
}

/* tfind start */
static void
tfind_start_command (const char *args, int from_tty)
{
  tfind_command_1 ("0", from_tty);
}

/* tfind pc command */
static void
tfind_pc_command (const char *args, int from_tty)
{
  CORE_ADDR pc;

  check_trace_running (current_trace_status ());

  if (args == 0 || *args == 0)
    pc = regcache_read_pc (get_current_regcache ());
  else
    pc = parse_and_eval_address (args);

  tfind_1 (tfind_pc, 0, pc, 0, from_tty);
}

/* tfind tracepoint command */
static void
tfind_tracepoint_command (const char *args, int from_tty)
{
  int tdp;
  struct tracepoint *tp;

  check_trace_running (current_trace_status ());

  if (args == 0 || *args == 0)
    {
      if (tracepoint_number == -1)
	error (_("No current tracepoint -- please supply an argument."));
      else
	tdp = tracepoint_number;	/* Default is current TDP.  */
    }
  else
    tdp = parse_and_eval_long (args);

  /* If we have the tracepoint on hand, use the number that the
     target knows about (which may be different if we disconnected
     and reconnected).  */
  tp = get_tracepoint (tdp);
  if (tp)
    tdp = tp->number_on_target;

  tfind_1 (tfind_tp, tdp, 0, 0, from_tty);
}

/* TFIND LINE command:

   This command will take a sourceline for argument, just like BREAK
   or TRACE (ie. anything that "decode_line_1" can handle).

   With no argument, this command will find the next trace frame 
   corresponding to a source line OTHER THAN THE CURRENT ONE.  */

static void
tfind_line_command (const char *args, int from_tty)
{
  check_trace_running (current_trace_status ());

  symtab_and_line sal;
  if (args == 0 || *args == 0)
    {
      sal = find_pc_line (get_frame_pc (get_current_frame ()), 0);
    }
  else
    {
      std::vector<symtab_and_line> sals
	= decode_line_with_current_source (args, DECODE_LINE_FUNFIRSTLINE);
      sal = sals[0];
    }

  if (sal.symtab == 0)
    error (_("No line number information available."));

  CORE_ADDR start_pc, end_pc;
  if (sal.line > 0 && find_line_pc_range (sal, &start_pc, &end_pc))
    {
      if (start_pc == end_pc)
  	{
	  printf_filtered ("Line %d of \"%s\"",
			   sal.line,
			   symtab_to_filename_for_display (sal.symtab));
	  wrap_here ("  ");
	  printf_filtered (" is at address ");
	  print_address (get_current_arch (), start_pc, gdb_stdout);
	  wrap_here ("  ");
	  printf_filtered (" but contains no code.\n");
	  sal = find_pc_line (start_pc, 0);
	  if (sal.line > 0
	      && find_line_pc_range (sal, &start_pc, &end_pc)
	      && start_pc != end_pc)
	    printf_filtered ("Attempting to find line %d instead.\n",
			     sal.line);
  	  else
	    error (_("Cannot find a good line."));
  	}
      }
    else
    /* Is there any case in which we get here, and have an address
       which the user would want to see?  If we have debugging
       symbols and no line numbers?  */
    error (_("Line number %d is out of range for \"%s\"."),
	   sal.line, symtab_to_filename_for_display (sal.symtab));

  /* Find within range of stated line.  */
  if (args && *args)
    tfind_1 (tfind_range, 0, start_pc, end_pc - 1, from_tty);
  else
    tfind_1 (tfind_outside, 0, start_pc, end_pc - 1, from_tty);
}

/* tfind range command */
static void
tfind_range_command (const char *args, int from_tty)
{
  static CORE_ADDR start, stop;
  const char *tmp;

  check_trace_running (current_trace_status ());

  if (args == 0 || *args == 0)
    { /* XXX FIXME: what should default behavior be?  */
      printf_filtered ("Usage: tfind range STARTADDR, ENDADDR\n");
      return;
    }

  if (0 != (tmp = strchr (args, ',')))
    {
      std::string start_addr (args, tmp);
      ++tmp;
      tmp = skip_spaces (tmp);
      start = parse_and_eval_address (start_addr.c_str ());
      stop = parse_and_eval_address (tmp);
    }
  else
    {			/* No explicit end address?  */
      start = parse_and_eval_address (args);
      stop = start + 1;	/* ??? */
    }

  tfind_1 (tfind_range, 0, start, stop, from_tty);
}

/* tfind outside command */
static void
tfind_outside_command (const char *args, int from_tty)
{
  CORE_ADDR start, stop;
  const char *tmp;

  if (current_trace_status ()->running
      && current_trace_status ()->filename == NULL)
    error (_("May not look at trace frames while trace is running."));

  if (args == 0 || *args == 0)
    { /* XXX FIXME: what should default behavior be?  */
      printf_filtered ("Usage: tfind outside STARTADDR, ENDADDR\n");
      return;
    }

  if (0 != (tmp = strchr (args, ',')))
    {
      std::string start_addr (args, tmp);
      ++tmp;
      tmp = skip_spaces (tmp);
      start = parse_and_eval_address (start_addr.c_str ());
      stop = parse_and_eval_address (tmp);
    }
  else
    {			/* No explicit end address?  */
      start = parse_and_eval_address (args);
      stop = start + 1;	/* ??? */
    }

  tfind_1 (tfind_outside, 0, start, stop, from_tty);
}

/* info scope command: list the locals for a scope.  */
static void
info_scope_command (const char *args_in, int from_tty)
{
  struct symbol *sym;
  struct bound_minimal_symbol msym;
  const struct block *block;
  const char *symname;
  const char *save_args = args_in;
  struct block_iterator iter;
  int j, count = 0;
  struct gdbarch *gdbarch;
  int regno;
  const char *args = args_in;

  if (args == 0 || *args == 0)
    error (_("requires an argument (function, "
	     "line or *addr) to define a scope"));

  event_location_up location = string_to_event_location (&args,
							 current_language);
  std::vector<symtab_and_line> sals
    = decode_line_1 (location.get (), DECODE_LINE_FUNFIRSTLINE,
		     NULL, NULL, 0);
  if (sals.empty ())
    {
      /* Presumably decode_line_1 has already warned.  */
      return;
    }

  /* Resolve line numbers to PC.  */
  resolve_sal_pc (&sals[0]);
  block = block_for_pc (sals[0].pc);

  while (block != 0)
    {
      QUIT;			/* Allow user to bail out with ^C.  */
      ALL_BLOCK_SYMBOLS (block, iter, sym)
	{
	  QUIT;			/* Allow user to bail out with ^C.  */
	  if (count == 0)
	    printf_filtered ("Scope for %s:\n", save_args);
	  count++;

	  symname = sym->print_name ();
	  if (symname == NULL || *symname == '\0')
	    continue;		/* Probably botched, certainly useless.  */

	  gdbarch = symbol_arch (sym);

	  printf_filtered ("Symbol %s is ", symname);

	  if (SYMBOL_COMPUTED_OPS (sym) != NULL)
	    SYMBOL_COMPUTED_OPS (sym)->describe_location (sym,
							  BLOCK_ENTRY_PC (block),
							  gdb_stdout);
	  else
	    {
	      switch (SYMBOL_CLASS (sym))
		{
		default:
		case LOC_UNDEF:	/* Messed up symbol?  */
		  printf_filtered ("a bogus symbol, class %d.\n",
				   SYMBOL_CLASS (sym));
		  count--;		/* Don't count this one.  */
		  continue;
		case LOC_CONST:
		  printf_filtered ("a constant with value %s (%s)",
				   plongest (SYMBOL_VALUE (sym)),
				   hex_string (SYMBOL_VALUE (sym)));
		  break;
		case LOC_CONST_BYTES:
		  printf_filtered ("constant bytes: ");
		  if (SYMBOL_TYPE (sym))
		    for (j = 0; j < TYPE_LENGTH (SYMBOL_TYPE (sym)); j++)
		      fprintf_filtered (gdb_stdout, " %02x",
					(unsigned) SYMBOL_VALUE_BYTES (sym)[j]);
		  break;
		case LOC_STATIC:
		  printf_filtered ("in static storage at address ");
		  printf_filtered ("%s", paddress (gdbarch,
						   SYMBOL_VALUE_ADDRESS (sym)));
		  break;
		case LOC_REGISTER:
		  /* GDBARCH is the architecture associated with the objfile
		     the symbol is defined in; the target architecture may be
		     different, and may provide additional registers.  However,
		     we do not know the target architecture at this point.
		     We assume the objfile architecture will contain all the
		     standard registers that occur in debug info in that
		     objfile.  */
		  regno = SYMBOL_REGISTER_OPS (sym)->register_number (sym,
								      gdbarch);

		  if (SYMBOL_IS_ARGUMENT (sym))
		    printf_filtered ("an argument in register $%s",
				     gdbarch_register_name (gdbarch, regno));
		  else
		    printf_filtered ("a local variable in register $%s",
				     gdbarch_register_name (gdbarch, regno));
		  break;
		case LOC_ARG:
		  printf_filtered ("an argument at stack/frame offset %s",
				   plongest (SYMBOL_VALUE (sym)));
		  break;
		case LOC_LOCAL:
		  printf_filtered ("a local variable at frame offset %s",
				   plongest (SYMBOL_VALUE (sym)));
		  break;
		case LOC_REF_ARG:
		  printf_filtered ("a reference argument at offset %s",
				   plongest (SYMBOL_VALUE (sym)));
		  break;
		case LOC_REGPARM_ADDR:
		  /* Note comment at LOC_REGISTER.  */
		  regno = SYMBOL_REGISTER_OPS (sym)->register_number (sym,
								      gdbarch);
		  printf_filtered ("the address of an argument, in register $%s",
				   gdbarch_register_name (gdbarch, regno));
		  break;
		case LOC_TYPEDEF:
		  printf_filtered ("a typedef.\n");
		  continue;
		case LOC_LABEL:
		  printf_filtered ("a label at address ");
		  printf_filtered ("%s", paddress (gdbarch,
						   SYMBOL_VALUE_ADDRESS (sym)));
		  break;
		case LOC_BLOCK:
		  printf_filtered ("a function at address ");
		  printf_filtered ("%s",
				   paddress (gdbarch, BLOCK_ENTRY_PC (SYMBOL_BLOCK_VALUE (sym))));
		  break;
		case LOC_UNRESOLVED:
		  msym = lookup_minimal_symbol (sym->linkage_name (),
						NULL, NULL);
		  if (msym.minsym == NULL)
		    printf_filtered ("Unresolved Static");
		  else
		    {
		      printf_filtered ("static storage at address ");
		      printf_filtered ("%s",
				       paddress (gdbarch,
						 BMSYMBOL_VALUE_ADDRESS (msym)));
		    }
		  break;
		case LOC_OPTIMIZED_OUT:
		  printf_filtered ("optimized out.\n");
		  continue;
		case LOC_COMPUTED:
		  gdb_assert_not_reached (_("LOC_COMPUTED variable missing a method"));
		}
	    }
	  if (SYMBOL_TYPE (sym))
	    {
	      struct type *t = check_typedef (SYMBOL_TYPE (sym));

	      printf_filtered (", length %s.\n", pulongest (TYPE_LENGTH (t)));
	    }
	}
      if (BLOCK_FUNCTION (block))
	break;
      else
	block = BLOCK_SUPERBLOCK (block);
    }
  if (count <= 0)
    printf_filtered ("Scope for %s contains no locals or arguments.\n",
		     save_args);
}

/* Helper for trace_dump_command.  Dump the action list starting at
   ACTION.  STEPPING_ACTIONS is true if we're iterating over the
   actions of the body of a while-stepping action.  STEPPING_FRAME is
   set if the current traceframe was determined to be a while-stepping
   traceframe.  */

static void
trace_dump_actions (struct command_line *action,
		    int stepping_actions, int stepping_frame,
		    int from_tty)
{
  const char *action_exp, *next_comma;

  for (; action != NULL; action = action->next)
    {
      struct cmd_list_element *cmd;

      QUIT;			/* Allow user to bail out with ^C.  */
      action_exp = action->line;
      action_exp = skip_spaces (action_exp);

      /* The collection actions to be done while stepping are
	 bracketed by the commands "while-stepping" and "end".  */

      if (*action_exp == '#')	/* comment line */
	continue;

      cmd = lookup_cmd (&action_exp, cmdlist, "", NULL, -1, 1);
      if (cmd == 0)
	error (_("Bad action list item: %s"), action_exp);

      if (cmd_cfunc_eq (cmd, while_stepping_pseudocommand))
	{
	  gdb_assert (action->body_list_1 == nullptr);
	  trace_dump_actions (action->body_list_0.get (),
			      1, stepping_frame, from_tty);
	}
      else if (cmd_cfunc_eq (cmd, collect_pseudocommand))
	{
	  /* Display the collected data.
	     For the trap frame, display only what was collected at
	     the trap.  Likewise for stepping frames, display only
	     what was collected while stepping.  This means that the
	     two boolean variables, STEPPING_FRAME and
	     STEPPING_ACTIONS should be equal.  */
	  if (stepping_frame == stepping_actions)
	    {
	      int trace_string = 0;

	      if (*action_exp == '/')
		action_exp = decode_agent_options (action_exp, &trace_string);

	      do
		{		/* Repeat over a comma-separated list.  */
		  QUIT;		/* Allow user to bail out with ^C.  */
		  if (*action_exp == ',')
		    action_exp++;
		  action_exp = skip_spaces (action_exp);

		  next_comma = strchr (action_exp, ',');

		  if (0 == strncasecmp (action_exp, "$reg", 4))
		    registers_info (NULL, from_tty);
		  else if (0 == strncasecmp (action_exp, "$_ret", 5))
		    ;
		  else if (0 == strncasecmp (action_exp, "$loc", 4))
		    info_locals_command (NULL, from_tty);
		  else if (0 == strncasecmp (action_exp, "$arg", 4))
		    info_args_command (NULL, from_tty);
		  else
		    {		/* variable */
		      std::string contents;
		      const char *exp = action_exp;
		      if (next_comma != NULL)
			{
			  size_t len = next_comma - action_exp;
			  contents = std::string (action_exp, len);
			  exp = contents.c_str ();
			}

		      printf_filtered ("%s = ", exp);
		      output_command (exp, from_tty);
		      printf_filtered ("\n");
		    }
		  action_exp = next_comma;
		}
	      while (action_exp && *action_exp == ',');
	    }
	}
    }
}

/* Return bp_location of the tracepoint associated with the current
   traceframe.  Set *STEPPING_FRAME_P to 1 if the current traceframe
   is a stepping traceframe.  */

struct bp_location *
get_traceframe_location (int *stepping_frame_p)
{
  struct tracepoint *t;
  struct bp_location *tloc;
  struct regcache *regcache;

  if (tracepoint_number == -1)
    error (_("No current trace frame."));

  t = get_tracepoint (tracepoint_number);

  if (t == NULL)
    error (_("No known tracepoint matches 'current' tracepoint #%d."),
	   tracepoint_number);

  /* The current frame is a trap frame if the frame PC is equal to the
     tracepoint PC.  If not, then the current frame was collected
     during single-stepping.  */
  regcache = get_current_regcache ();

  /* If the traceframe's address matches any of the tracepoint's
     locations, assume it is a direct hit rather than a while-stepping
     frame.  (FIXME this is not reliable, should record each frame's
     type.)  */
  for (tloc = t->loc; tloc; tloc = tloc->next)
    if (tloc->address == regcache_read_pc (regcache))
      {
	*stepping_frame_p = 0;
	return tloc;
      }

  /* If this is a stepping frame, we don't know which location
     triggered.  The first is as good (or bad) a guess as any...  */
  *stepping_frame_p = 1;
  return t->loc;
}

/* Return the default collect actions of a tracepoint T.  */

static counted_command_line
all_tracepoint_actions (struct breakpoint *t)
{
  counted_command_line actions (nullptr, command_lines_deleter ());

  /* If there are default expressions to collect, make up a collect
     action and prepend to the action list to encode.  Note that since
     validation is per-tracepoint (local var "xyz" might be valid for
     one tracepoint and not another, etc), we make up the action on
     the fly, and don't cache it.  */
  if (*default_collect)
    {
      gdb::unique_xmalloc_ptr<char> default_collect_line
	(xstrprintf ("collect %s", default_collect));

      validate_actionline (default_collect_line.get (), t);
      actions.reset (new struct command_line (simple_control,
					      default_collect_line.release ()),
		     command_lines_deleter ());
    }

  return actions;
}

/* The tdump command.  */

static void
tdump_command (const char *args, int from_tty)
{
  int stepping_frame = 0;
  struct bp_location *loc;

  /* This throws an error is not inspecting a trace frame.  */
  loc = get_traceframe_location (&stepping_frame);

  printf_filtered ("Data collected at tracepoint %d, trace frame %d:\n",
		   tracepoint_number, traceframe_number);

  /* This command only makes sense for the current frame, not the
     selected frame.  */
  scoped_restore_current_thread restore_thread;

  select_frame (get_current_frame ());

  counted_command_line actions = all_tracepoint_actions (loc->owner);

  trace_dump_actions (actions.get (), 0, stepping_frame, from_tty);
  trace_dump_actions (breakpoint_commands (loc->owner), 0, stepping_frame,
		      from_tty);
}

/* Encode a piece of a tracepoint's source-level definition in a form
   that is suitable for both protocol and saving in files.  */
/* This version does not do multiple encodes for long strings; it should
   return an offset to the next piece to encode.  FIXME  */

int
encode_source_string (int tpnum, ULONGEST addr,
		      const char *srctype, const char *src,
		      char *buf, int buf_size)
{
  if (80 + strlen (srctype) > buf_size)
    error (_("Buffer too small for source encoding"));
  sprintf (buf, "%x:%s:%s:%x:%x:",
	   tpnum, phex_nz (addr, sizeof (addr)),
	   srctype, 0, (int) strlen (src));
  if (strlen (buf) + strlen (src) * 2 >= buf_size)
    error (_("Source string too long for buffer"));
  bin2hex ((gdb_byte *) src, buf + strlen (buf), strlen (src));
  return -1;
}

/* Tell the target what to do with an ongoing tracing run if GDB
   disconnects for some reason.  */

static void
set_disconnected_tracing (const char *args, int from_tty,
			  struct cmd_list_element *c)
{
  target_set_disconnected_tracing (disconnected_tracing);
}

static void
set_circular_trace_buffer (const char *args, int from_tty,
			   struct cmd_list_element *c)
{
  target_set_circular_trace_buffer (circular_trace_buffer);
}

static void
set_trace_buffer_size (const char *args, int from_tty,
			   struct cmd_list_element *c)
{
  target_set_trace_buffer_size (trace_buffer_size);
}

static void
set_trace_user (const char *args, int from_tty,
		struct cmd_list_element *c)
{
  int ret;

  ret = target_set_trace_notes (trace_user, NULL, NULL);

  if (!ret)
    warning (_("Target does not support trace notes, user ignored"));
}

static void
set_trace_notes (const char *args, int from_tty,
		 struct cmd_list_element *c)
{
  int ret;

  ret = target_set_trace_notes (NULL, trace_notes, NULL);

  if (!ret)
    warning (_("Target does not support trace notes, note ignored"));
}

static void
set_trace_stop_notes (const char *args, int from_tty,
		      struct cmd_list_element *c)
{
  int ret;

  ret = target_set_trace_notes (NULL, NULL, trace_stop_notes);

  if (!ret)
    warning (_("Target does not support trace notes, stop note ignored"));
}

/* Convert the memory pointed to by mem into hex, placing result in buf.
 * Return a pointer to the last char put in buf (null)
 * "stolen" from sparc-stub.c
 */

static const char hexchars[] = "0123456789abcdef";

static char *
mem2hex (gdb_byte *mem, char *buf, int count)
{
  gdb_byte ch;

  while (count-- > 0)
    {
      ch = *mem++;

      *buf++ = hexchars[ch >> 4];
      *buf++ = hexchars[ch & 0xf];
    }

  *buf = 0;

  return buf;
}

int
get_traceframe_number (void)
{
  return traceframe_number;
}

int
get_tracepoint_number (void)
{
  return tracepoint_number;
}

/* Make the traceframe NUM be the current trace frame.  Does nothing
   if NUM is already current.  */

void
set_current_traceframe (int num)
{
  int newnum;

  if (traceframe_number == num)
    {
      /* Nothing to do.  */
      return;
    }

  newnum = target_trace_find (tfind_number, num, 0, 0, NULL);

  if (newnum != num)
    warning (_("could not change traceframe"));

  set_traceframe_num (newnum);

  /* Changing the traceframe changes our view of registers and of the
     frame chain.  */
  registers_changed ();

  clear_traceframe_info ();
}

scoped_restore_current_traceframe::scoped_restore_current_traceframe ()
: m_traceframe_number (traceframe_number)
{}

/* Given a number and address, return an uploaded tracepoint with that
   number, creating if necessary.  */

struct uploaded_tp *
get_uploaded_tp (int num, ULONGEST addr, struct uploaded_tp **utpp)
{
  struct uploaded_tp *utp;

  for (utp = *utpp; utp; utp = utp->next)
    if (utp->number == num && utp->addr == addr)
      return utp;

  utp = new uploaded_tp;
  utp->number = num;
  utp->addr = addr;
  utp->next = *utpp;
  *utpp = utp;

  return utp;
}

void
free_uploaded_tps (struct uploaded_tp **utpp)
{
  struct uploaded_tp *next_one;

  while (*utpp)
    {
      next_one = (*utpp)->next;
      delete *utpp;
      *utpp = next_one;
    }
}

/* Given a number and address, return an uploaded tracepoint with that
   number, creating if necessary.  */

struct uploaded_tsv *
get_uploaded_tsv (int num, struct uploaded_tsv **utsvp)
{
  struct uploaded_tsv *utsv;

  for (utsv = *utsvp; utsv; utsv = utsv->next)
    if (utsv->number == num)
      return utsv;

  utsv = XCNEW (struct uploaded_tsv);
  utsv->number = num;
  utsv->next = *utsvp;
  *utsvp = utsv;

  return utsv;
}

void
free_uploaded_tsvs (struct uploaded_tsv **utsvp)
{
  struct uploaded_tsv *next_one;

  while (*utsvp)
    {
      next_one = (*utsvp)->next;
      xfree (*utsvp);
      *utsvp = next_one;
    }
}

/* FIXME this function is heuristic and will miss the cases where the
   conditional is semantically identical but differs in whitespace,
   such as "x == 0" vs "x==0".  */

static int
cond_string_is_same (char *str1, char *str2)
{
  if (str1 == NULL || str2 == NULL)
    return (str1 == str2);

  return (strcmp (str1, str2) == 0);
}

/* Look for an existing tracepoint that seems similar enough to the
   uploaded one.  Enablement isn't compared, because the user can
   toggle that freely, and may have done so in anticipation of the
   next trace run.  Return the location of matched tracepoint.  */

static struct bp_location *
find_matching_tracepoint_location (struct uploaded_tp *utp)
{
  struct bp_location *loc;

  for (breakpoint *b : all_tracepoints ())
    {
      struct tracepoint *t = (struct tracepoint *) b;

      if (b->type == utp->type
	  && t->step_count == utp->step
	  && t->pass_count == utp->pass
	  && cond_string_is_same (t->cond_string,
				  utp->cond_string.get ())
	  /* FIXME also test actions.  */
	  )
	{
	  /* Scan the locations for an address match.  */
	  for (loc = b->loc; loc; loc = loc->next)
	    {
	      if (loc->address == utp->addr)
		return loc;
	    }
	}
    }
  return NULL;
}

/* Given a list of tracepoints uploaded from a target, attempt to
   match them up with existing tracepoints, and create new ones if not
   found.  */

void
merge_uploaded_tracepoints (struct uploaded_tp **uploaded_tps)
{
  struct uploaded_tp *utp;
  /* A set of tracepoints which are modified.  */
  std::vector<breakpoint *> modified_tp;

  /* Look for GDB tracepoints that match up with our uploaded versions.  */
  for (utp = *uploaded_tps; utp; utp = utp->next)
    {
      struct bp_location *loc;
      struct tracepoint *t;

      loc = find_matching_tracepoint_location (utp);
      if (loc)
	{
	  int found = 0;

	  /* Mark this location as already inserted.  */
	  loc->inserted = 1;
	  t = (struct tracepoint *) loc->owner;
	  printf_filtered (_("Assuming tracepoint %d is same "
			     "as target's tracepoint %d at %s.\n"),
			   loc->owner->number, utp->number,
			   paddress (loc->gdbarch, utp->addr));

	  /* The tracepoint LOC->owner was modified (the location LOC
	     was marked as inserted in the target).  Save it in
	     MODIFIED_TP if not there yet.  The 'breakpoint-modified'
	     observers will be notified later once for each tracepoint
	     saved in MODIFIED_TP.  */
	  for (breakpoint *b : modified_tp)
	    if (b == loc->owner)
	      {
		found = 1;
		break;
	      }
	  if (!found)
	    modified_tp.push_back (loc->owner);
	}
      else
	{
	  t = create_tracepoint_from_upload (utp);
	  if (t)
	    printf_filtered (_("Created tracepoint %d for "
			       "target's tracepoint %d at %s.\n"),
			     t->number, utp->number,
			     paddress (get_current_arch (), utp->addr));
	  else
	    printf_filtered (_("Failed to create tracepoint for target's "
			       "tracepoint %d at %s, skipping it.\n"),
			     utp->number,
			     paddress (get_current_arch (), utp->addr));
	}
      /* Whether found or created, record the number used by the
	 target, to help with mapping target tracepoints back to their
	 counterparts here.  */
      if (t)
	t->number_on_target = utp->number;
    }

  /* Notify 'breakpoint-modified' observer that at least one of B's
     locations was changed.  */
  for (breakpoint *b : modified_tp)
    gdb::observers::breakpoint_modified.notify (b);

  free_uploaded_tps (uploaded_tps);
}

/* Trace state variables don't have much to identify them beyond their
   name, so just use that to detect matches.  */

static struct trace_state_variable *
find_matching_tsv (struct uploaded_tsv *utsv)
{
  if (!utsv->name)
    return NULL;

  return find_trace_state_variable (utsv->name);
}

static struct trace_state_variable *
create_tsv_from_upload (struct uploaded_tsv *utsv)
{
  const char *namebase;
  std::string buf;
  int try_num = 0;
  struct trace_state_variable *tsv;

  if (utsv->name)
    {
      namebase = utsv->name;
      buf = namebase;
    }
  else
    {
      namebase = "__tsv";
      buf = string_printf ("%s_%d", namebase, try_num++);
    }

  /* Fish for a name that is not in use.  */
  /* (should check against all internal vars?)  */
  while (find_trace_state_variable (buf.c_str ()))
    buf = string_printf ("%s_%d", namebase, try_num++);

  /* We have an available name, create the variable.  */
  tsv = create_trace_state_variable (buf.c_str ());
  tsv->initial_value = utsv->initial_value;
  tsv->builtin = utsv->builtin;

  gdb::observers::tsv_created.notify (tsv);

  return tsv;
}

/* Given a list of uploaded trace state variables, try to match them
   up with existing variables, or create additional ones.  */

void
merge_uploaded_trace_state_variables (struct uploaded_tsv **uploaded_tsvs)
{
  struct uploaded_tsv *utsv;
  int highest;

  /* Most likely some numbers will have to be reassigned as part of
     the merge, so clear them all in anticipation.  */
  for (trace_state_variable &tsv : tvariables)
    tsv.number = 0;

  for (utsv = *uploaded_tsvs; utsv; utsv = utsv->next)
    {
      struct trace_state_variable *tsv = find_matching_tsv (utsv);
      if (tsv)
	{
	  if (info_verbose)
	    printf_filtered (_("Assuming trace state variable $%s "
			       "is same as target's variable %d.\n"),
			     tsv->name.c_str (), utsv->number);
	}
      else
	{
	  tsv = create_tsv_from_upload (utsv);
	  if (info_verbose)
	    printf_filtered (_("Created trace state variable "
			       "$%s for target's variable %d.\n"),
			     tsv->name.c_str (), utsv->number);
	}
      /* Give precedence to numberings that come from the target.  */
      if (tsv)
	tsv->number = utsv->number;
    }

  /* Renumber everything that didn't get a target-assigned number.  */
  highest = 0;
  for (const trace_state_variable &tsv : tvariables)
    highest = std::max (tsv.number, highest);

  ++highest;
  for (trace_state_variable &tsv : tvariables)
    if (tsv.number == 0)
      tsv.number = highest++;

  free_uploaded_tsvs (uploaded_tsvs);
}

/* Parse the part of trace status syntax that is shared between
   the remote protocol and the trace file reader.  */

void
parse_trace_status (const char *line, struct trace_status *ts)
{
  const char *p = line, *p1, *p2, *p3, *p_temp;
  int end;
  ULONGEST val;

  ts->running_known = 1;
  ts->running = (*p++ == '1');
  ts->stop_reason = trace_stop_reason_unknown;
  xfree (ts->stop_desc);
  ts->stop_desc = NULL;
  ts->traceframe_count = -1;
  ts->traceframes_created = -1;
  ts->buffer_free = -1;
  ts->buffer_size = -1;
  ts->disconnected_tracing = 0;
  ts->circular_buffer = 0;
  xfree (ts->user_name);
  ts->user_name = NULL;
  xfree (ts->notes);
  ts->notes = NULL;
  ts->start_time = ts->stop_time = 0;

  while (*p++)
    {
      p1 = strchr (p, ':');
      if (p1 == NULL)
	error (_("Malformed trace status, at %s\n\
Status line: '%s'\n"), p, line);
      p3 = strchr (p, ';');
      if (p3 == NULL)
	p3 = p + strlen (p);
      if (strncmp (p, stop_reason_names[trace_buffer_full], p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->stop_reason = trace_buffer_full;
	}
      else if (strncmp (p, stop_reason_names[trace_never_run], p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->stop_reason = trace_never_run;
	}
      else if (strncmp (p, stop_reason_names[tracepoint_passcount],
			p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->stop_reason = tracepoint_passcount;
	  ts->stopping_tracepoint = val;
	}
      else if (strncmp (p, stop_reason_names[trace_stop_command], p1 - p) == 0)
	{
	  p2 = strchr (++p1, ':');
	  if (!p2 || p2 > p3)
	    {
	      /*older style*/
	      p2 = p1;
	    }
	  else if (p2 != p1)
	    {
	      ts->stop_desc = (char *) xmalloc (strlen (line));
	      end = hex2bin (p1, (gdb_byte *) ts->stop_desc, (p2 - p1) / 2);
	      ts->stop_desc[end] = '\0';
	    }
	  else
	    ts->stop_desc = xstrdup ("");

	  p = unpack_varlen_hex (++p2, &val);
	  ts->stop_reason = trace_stop_command;
	}
      else if (strncmp (p, stop_reason_names[trace_disconnected], p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->stop_reason = trace_disconnected;
	}
      else if (strncmp (p, stop_reason_names[tracepoint_error], p1 - p) == 0)
	{
	  p2 = strchr (++p1, ':');
	  if (p2 != p1)
	    {
	      ts->stop_desc = (char *) xmalloc ((p2 - p1) / 2 + 1);
	      end = hex2bin (p1, (gdb_byte *) ts->stop_desc, (p2 - p1) / 2);
	      ts->stop_desc[end] = '\0';
	    }
	  else
	    ts->stop_desc = xstrdup ("");

	  p = unpack_varlen_hex (++p2, &val);
	  ts->stopping_tracepoint = val;
	  ts->stop_reason = tracepoint_error;
	}
      else if (strncmp (p, "tframes", p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->traceframe_count = val;
	}
      else if (strncmp (p, "tcreated", p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->traceframes_created = val;
	}
      else if (strncmp (p, "tfree", p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->buffer_free = val;
	}
      else if (strncmp (p, "tsize", p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->buffer_size = val;
	}
      else if (strncmp (p, "disconn", p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->disconnected_tracing = val;
	}
      else if (strncmp (p, "circular", p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->circular_buffer = val;
	}
      else if (strncmp (p, "starttime", p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->start_time = val;
	}
      else if (strncmp (p, "stoptime", p1 - p) == 0)
	{
	  p = unpack_varlen_hex (++p1, &val);
	  ts->stop_time = val;
	}
      else if (strncmp (p, "username", p1 - p) == 0)
	{
	  ++p1;
	  ts->user_name = (char *) xmalloc (strlen (p) / 2);
	  end = hex2bin (p1, (gdb_byte *) ts->user_name, (p3 - p1)  / 2);
	  ts->user_name[end] = '\0';
	  p = p3;
	}
      else if (strncmp (p, "notes", p1 - p) == 0)
	{
	  ++p1;
	  ts->notes = (char *) xmalloc (strlen (p) / 2);
	  end = hex2bin (p1, (gdb_byte *) ts->notes, (p3 - p1) / 2);
	  ts->notes[end] = '\0';
	  p = p3;
	}
      else
	{
	  /* Silently skip unknown optional info.  */
	  p_temp = strchr (p1 + 1, ';');
	  if (p_temp)
	    p = p_temp;
	  else
	    /* Must be at the end.  */
	    break;
	}
    }
}

void
parse_tracepoint_status (const char *p, struct breakpoint *bp,
			 struct uploaded_tp *utp)
{
  ULONGEST uval;
  struct tracepoint *tp = (struct tracepoint *) bp;

  p = unpack_varlen_hex (p, &uval);
  if (tp)
    tp->hit_count += uval;
  else
    utp->hit_count += uval;
  p = unpack_varlen_hex (p + 1, &uval);
  if (tp)
    tp->traceframe_usage += uval;
  else
    utp->traceframe_usage += uval;
  /* Ignore any extra, allowing for future extensions.  */
}

/* Given a line of text defining a part of a tracepoint, parse it into
   an "uploaded tracepoint".  */

void
parse_tracepoint_definition (const char *line, struct uploaded_tp **utpp)
{
  const char *p;
  char piece;
  ULONGEST num, addr, step, pass, orig_size, xlen, start;
  int enabled, end;
  enum bptype type;
  const char *srctype;
  char *buf;
  struct uploaded_tp *utp = NULL;

  p = line;
  /* Both tracepoint and action definitions start with the same number
     and address sequence.  */
  piece = *p++;
  p = unpack_varlen_hex (p, &num);
  p++;  /* skip a colon */
  p = unpack_varlen_hex (p, &addr);
  p++;  /* skip a colon */
  if (piece == 'T')
    {
      gdb::unique_xmalloc_ptr<char[]> cond;

      enabled = (*p++ == 'E');
      p++;  /* skip a colon */
      p = unpack_varlen_hex (p, &step);
      p++;  /* skip a colon */
      p = unpack_varlen_hex (p, &pass);
      type = bp_tracepoint;
      /* Thumb through optional fields.  */
      while (*p == ':')
	{
	  p++;  /* skip a colon */
	  if (*p == 'F')
	    {
	      type = bp_fast_tracepoint;
	      p++;
	      p = unpack_varlen_hex (p, &orig_size);
	    }
	  else if (*p == 'S')
	    {
	      type = bp_static_tracepoint;
	      p++;
	    }
	  else if (*p == 'X')
	    {
	      p++;
	      p = unpack_varlen_hex (p, &xlen);
	      p++;  /* skip a comma */
	      cond.reset ((char *) xmalloc (2 * xlen + 1));
	      strncpy (&cond[0], p, 2 * xlen);
	      cond[2 * xlen] = '\0';
	      p += 2 * xlen;
	    }
	  else
	    warning (_("Unrecognized char '%c' in tracepoint "
		       "definition, skipping rest"), *p);
	}
      utp = get_uploaded_tp (num, addr, utpp);
      utp->type = type;
      utp->enabled = enabled;
      utp->step = step;
      utp->pass = pass;
      utp->cond = std::move (cond);
    }
  else if (piece == 'A')
    {
      utp = get_uploaded_tp (num, addr, utpp);
      utp->actions.emplace_back (xstrdup (p));
    }
  else if (piece == 'S')
    {
      utp = get_uploaded_tp (num, addr, utpp);
      utp->step_actions.emplace_back (xstrdup (p));
    }
  else if (piece == 'Z')
    {
      /* Parse a chunk of source form definition.  */
      utp = get_uploaded_tp (num, addr, utpp);
      srctype = p;
      p = strchr (p, ':');
      p++;  /* skip a colon */
      p = unpack_varlen_hex (p, &start);
      p++;  /* skip a colon */
      p = unpack_varlen_hex (p, &xlen);
      p++;  /* skip a colon */

      buf = (char *) alloca (strlen (line));

      end = hex2bin (p, (gdb_byte *) buf, strlen (p) / 2);
      buf[end] = '\0';

      if (startswith (srctype, "at:"))
	utp->at_string.reset (xstrdup (buf));
      else if (startswith (srctype, "cond:"))
	utp->cond_string.reset (xstrdup (buf));
      else if (startswith (srctype, "cmd:"))
	utp->cmd_strings.emplace_back (xstrdup (buf));
    }
  else if (piece == 'V')
    {
      utp = get_uploaded_tp (num, addr, utpp);

      parse_tracepoint_status (p, NULL, utp);
    }
  else
    {
      /* Don't error out, the target might be sending us optional
	 info that we don't care about.  */
      warning (_("Unrecognized tracepoint piece '%c', ignoring"), piece);
    }
}

/* Convert a textual description of a trace state variable into an
   uploaded object.  */

void
parse_tsv_definition (const char *line, struct uploaded_tsv **utsvp)
{
  const char *p;
  char *buf;
  ULONGEST num, initval, builtin;
  int end;
  struct uploaded_tsv *utsv = NULL;

  buf = (char *) alloca (strlen (line));

  p = line;
  p = unpack_varlen_hex (p, &num);
  p++; /* skip a colon */
  p = unpack_varlen_hex (p, &initval);
  p++; /* skip a colon */
  p = unpack_varlen_hex (p, &builtin);
  p++; /* skip a colon */
  end = hex2bin (p, (gdb_byte *) buf, strlen (p) / 2);
  buf[end] = '\0';

  utsv = get_uploaded_tsv (num, utsvp);
  utsv->initial_value = initval;
  utsv->builtin = builtin;
  utsv->name = xstrdup (buf);
}

/* Given a line of text defining a static tracepoint marker, parse it
   into a "static tracepoint marker" object.  Throws an error is
   parsing fails.  If PP is non-null, it points to one past the end of
   the parsed marker definition.  */

void
parse_static_tracepoint_marker_definition (const char *line, const char **pp,
					   static_tracepoint_marker *marker)
{
  const char *p, *endp;
  ULONGEST addr;

  p = line;
  p = unpack_varlen_hex (p, &addr);
  p++;  /* skip a colon */

  marker->gdbarch = target_gdbarch ();
  marker->address = (CORE_ADDR) addr;

  endp = strchr (p, ':');
  if (endp == NULL)
    error (_("bad marker definition: %s"), line);

  marker->str_id = hex2str (p, (endp - p) / 2);

  p = endp;
  p++; /* skip a colon */

  /* This definition may be followed by another one, separated by a comma.  */
  int hex_len;
  endp = strchr (p, ',');
  if (endp != nullptr)
    hex_len = endp - p;
  else
    hex_len = strlen (p);

  marker->extra = hex2str (p, hex_len / 2);

  if (pp != nullptr)
    *pp = p + hex_len;
}

/* Print MARKER to gdb_stdout.  */

static void
print_one_static_tracepoint_marker (int count,
				    const static_tracepoint_marker &marker)
{
  struct symbol *sym;

  char wrap_indent[80];
  char extra_field_indent[80];
  struct ui_out *uiout = current_uiout;

  symtab_and_line sal;
  sal.pc = marker.address;

  std::vector<breakpoint *> tracepoints
    = static_tracepoints_here (marker.address);

  ui_out_emit_tuple tuple_emitter (uiout, "marker");

  /* A counter field to help readability.  This is not a stable
     identifier!  */
  uiout->field_signed ("count", count);

  uiout->field_string ("marker-id", marker.str_id.c_str ());

  uiout->field_fmt ("enabled", "%c",
		    !tracepoints.empty () ? 'y' : 'n');
  uiout->spaces (2);

  strcpy (wrap_indent, "                                   ");

  if (gdbarch_addr_bit (marker.gdbarch) <= 32)
    strcat (wrap_indent, "           ");
  else
    strcat (wrap_indent, "                   ");

  strcpy (extra_field_indent, "         ");

  uiout->field_core_addr ("addr", marker.gdbarch, marker.address);

  sal = find_pc_line (marker.address, 0);
  sym = find_pc_sect_function (marker.address, NULL);
  if (sym)
    {
      uiout->text ("in ");
      uiout->field_string ("func", sym->print_name (),
			   function_name_style.style ());
      uiout->wrap_hint (wrap_indent);
      uiout->text (" at ");
    }
  else
    uiout->field_skip ("func");

  if (sal.symtab != NULL)
    {
      uiout->field_string ("file",
			   symtab_to_filename_for_display (sal.symtab),
			   file_name_style.style ());
      uiout->text (":");

      if (uiout->is_mi_like_p ())
	{
	  const char *fullname = symtab_to_fullname (sal.symtab);

	  uiout->field_string ("fullname", fullname);
	}
      else
	uiout->field_skip ("fullname");

      uiout->field_signed ("line", sal.line);
    }
  else
    {
      uiout->field_skip ("fullname");
      uiout->field_skip ("line");
    }

  uiout->text ("\n");
  uiout->text (extra_field_indent);
  uiout->text (_("Data: \""));
  uiout->field_string ("extra-data", marker.extra.c_str ());
  uiout->text ("\"\n");

  if (!tracepoints.empty ())
    {
      int ix;

      {
	ui_out_emit_tuple inner_tuple_emitter (uiout, "tracepoints-at");

	uiout->text (extra_field_indent);
	uiout->text (_("Probed by static tracepoints: "));
	for (ix = 0; ix < tracepoints.size (); ix++)
	  {
	    if (ix > 0)
	      uiout->text (", ");
	    uiout->text ("#");
	    uiout->field_signed ("tracepoint-id", tracepoints[ix]->number);
	  }
      }

      if (uiout->is_mi_like_p ())
	uiout->field_signed ("number-of-tracepoints", tracepoints.size ());
      else
	uiout->text ("\n");
    }
}

static void
info_static_tracepoint_markers_command (const char *arg, int from_tty)
{
  struct ui_out *uiout = current_uiout;
  std::vector<static_tracepoint_marker> markers
    = target_static_tracepoint_markers_by_strid (NULL);

  /* We don't have to check target_can_use_agent and agent's capability on
     static tracepoint here, in order to be compatible with older GDBserver.
     We don't check USE_AGENT is true or not, because static tracepoints
     don't work without in-process agent, so we don't bother users to type
     `set agent on' when to use static tracepoint.  */

  ui_out_emit_table table_emitter (uiout, 5, -1,
				   "StaticTracepointMarkersTable");

  uiout->table_header (7, ui_left, "counter", "Cnt");

  uiout->table_header (40, ui_left, "marker-id", "ID");

  uiout->table_header (3, ui_left, "enabled", "Enb");
  if (gdbarch_addr_bit (target_gdbarch ()) <= 32)
    uiout->table_header (10, ui_left, "addr", "Address");
  else
    uiout->table_header (18, ui_left, "addr", "Address");
  uiout->table_header (40, ui_noalign, "what", "What");

  uiout->table_body ();

  for (int i = 0; i < markers.size (); i++)
    print_one_static_tracepoint_marker (i + 1, markers[i]);
}

/* The $_sdata convenience variable is a bit special.  We don't know
   for sure type of the value until we actually have a chance to fetch
   the data --- the size of the object depends on what has been
   collected.  We solve this by making $_sdata be an internalvar that
   creates a new value on access.  */

/* Return a new value with the correct type for the sdata object of
   the current trace frame.  Return a void value if there's no object
   available.  */

static struct value *
sdata_make_value (struct gdbarch *gdbarch, struct internalvar *var,
		  void *ignore)
{
  /* We need to read the whole object before we know its size.  */
  gdb::optional<gdb::byte_vector> buf
    = target_read_alloc (current_top_target (), TARGET_OBJECT_STATIC_TRACE_DATA,
			 NULL);
  if (buf)
    {
      struct value *v;
      struct type *type;

      type = init_vector_type (builtin_type (gdbarch)->builtin_true_char,
			       buf->size ());
      v = allocate_value (type);
      memcpy (value_contents_raw (v), buf->data (), buf->size ());
      return v;
    }
  else
    return allocate_value (builtin_type (gdbarch)->builtin_void);
}

#if !defined(HAVE_LIBEXPAT)

struct std::unique_ptr<traceframe_info>
parse_traceframe_info (const char *tframe_info)
{
  static int have_warned;

  if (!have_warned)
    {
      have_warned = 1;
      warning (_("Can not parse XML trace frame info; XML support "
		 "was disabled at compile time"));
    }

  return NULL;
}

#else /* HAVE_LIBEXPAT */

#include "xml-support.h"

/* Handle the start of a <memory> element.  */

static void
traceframe_info_start_memory (struct gdb_xml_parser *parser,
			      const struct gdb_xml_element *element,
			      void *user_data,
			      std::vector<gdb_xml_value> &attributes)
{
  struct traceframe_info *info = (struct traceframe_info *) user_data;
  ULONGEST *start_p, *length_p;

  start_p
    = (ULONGEST *) xml_find_attribute (attributes, "start")->value.get ();
  length_p
    = (ULONGEST *) xml_find_attribute (attributes, "length")->value.get ();

  info->memory.emplace_back (*start_p, *length_p);
}

/* Handle the start of a <tvar> element.  */

static void
traceframe_info_start_tvar (struct gdb_xml_parser *parser,
			     const struct gdb_xml_element *element,
			     void *user_data,
			     std::vector<gdb_xml_value> &attributes)
{
  struct traceframe_info *info = (struct traceframe_info *) user_data;
  const char *id_attrib
    = (const char *) xml_find_attribute (attributes, "id")->value.get ();
  int id = gdb_xml_parse_ulongest (parser, id_attrib);

  info->tvars.push_back (id);
}

/* The allowed elements and attributes for an XML memory map.  */

static const struct gdb_xml_attribute memory_attributes[] = {
  { "start", GDB_XML_AF_NONE, gdb_xml_parse_attr_ulongest, NULL },
  { "length", GDB_XML_AF_NONE, gdb_xml_parse_attr_ulongest, NULL },
  { NULL, GDB_XML_AF_NONE, NULL, NULL }
};

static const struct gdb_xml_attribute tvar_attributes[] = {
  { "id", GDB_XML_AF_NONE, NULL, NULL },
  { NULL, GDB_XML_AF_NONE, NULL, NULL }
};

static const struct gdb_xml_element traceframe_info_children[] = {
  { "memory", memory_attributes, NULL,
    GDB_XML_EF_REPEATABLE | GDB_XML_EF_OPTIONAL,
    traceframe_info_start_memory, NULL },
  { "tvar", tvar_attributes, NULL,
    GDB_XML_EF_REPEATABLE | GDB_XML_EF_OPTIONAL,
    traceframe_info_start_tvar, NULL },
  { NULL, NULL, NULL, GDB_XML_EF_NONE, NULL, NULL }
};

static const struct gdb_xml_element traceframe_info_elements[] = {
  { "traceframe-info", NULL, traceframe_info_children, GDB_XML_EF_NONE,
    NULL, NULL },
  { NULL, NULL, NULL, GDB_XML_EF_NONE, NULL, NULL }
};

/* Parse a traceframe-info XML document.  */

traceframe_info_up
parse_traceframe_info (const char *tframe_info)
{
  traceframe_info_up result (new traceframe_info);

  if (gdb_xml_parse_quick (_("trace frame info"),
			   "traceframe-info.dtd", traceframe_info_elements,
			   tframe_info, result.get ()) == 0)
    return result;

  return NULL;
}

#endif /* HAVE_LIBEXPAT */

/* Returns the traceframe_info object for the current traceframe.
   This is where we avoid re-fetching the object from the target if we
   already have it cached.  */

struct traceframe_info *
get_traceframe_info (void)
{
  if (current_traceframe_info == NULL)
    current_traceframe_info = target_traceframe_info ();

  return current_traceframe_info.get ();
}

/* If the target supports the query, return in RESULT the set of
   collected memory in the current traceframe, found within the LEN
   bytes range starting at MEMADDR.  Returns true if the target
   supports the query, otherwise returns false, and RESULT is left
   undefined.  */

int
traceframe_available_memory (std::vector<mem_range> *result,
			     CORE_ADDR memaddr, ULONGEST len)
{
  struct traceframe_info *info = get_traceframe_info ();

  if (info != NULL)
    {
      result->clear ();

      for (mem_range &r : info->memory)
	if (mem_ranges_overlap (r.start, r.length, memaddr, len))
	  {
	    ULONGEST lo1, hi1, lo2, hi2;

	    lo1 = memaddr;
	    hi1 = memaddr + len;

	    lo2 = r.start;
	    hi2 = r.start + r.length;

	    CORE_ADDR start = std::max (lo1, lo2);
	    int length = std::min (hi1, hi2) - start;

	    result->emplace_back (start, length);
	  }

      normalize_mem_ranges (result);
      return 1;
    }

  return 0;
}

/* Implementation of `sdata' variable.  */

static const struct internalvar_funcs sdata_funcs =
{
  sdata_make_value,
  NULL,
  NULL
};

/* See tracepoint.h.  */
cmd_list_element *while_stepping_cmd_element = nullptr;

/* module initialization */
void _initialize_tracepoint ();
void
_initialize_tracepoint ()
{
  struct cmd_list_element *c;

  /* Explicitly create without lookup, since that tries to create a
     value with a void typed value, and when we get here, gdbarch
     isn't initialized yet.  At this point, we're quite sure there
     isn't another convenience variable of the same name.  */
  create_internalvar_type_lazy ("_sdata", &sdata_funcs, NULL);

  traceframe_number = -1;
  tracepoint_number = -1;

  add_info ("scope", info_scope_command,
	    _("List the variables local to a scope."));

  add_cmd ("tracepoints", class_trace,
	   _("Tracing of program execution without stopping the program."),
	   &cmdlist);

  add_com ("tdump", class_trace, tdump_command,
	   _("Print everything collected at the current tracepoint."));

  c = add_com ("tvariable", class_trace, trace_variable_command,_("\
Define a trace state variable.\n\
Argument is a $-prefixed name, optionally followed\n\
by '=' and an expression that sets the initial value\n\
at the start of tracing."));
  set_cmd_completer (c, expression_completer);

  add_cmd ("tvariable", class_trace, delete_trace_variable_command, _("\
Delete one or more trace state variables.\n\
Arguments are the names of the variables to delete.\n\
If no arguments are supplied, delete all variables."), &deletelist);
  /* FIXME add a trace variable completer.  */

  add_info ("tvariables", info_tvariables_command, _("\
Status of trace state variables and their values."));

  add_info ("static-tracepoint-markers",
	    info_static_tracepoint_markers_command, _("\
List target static tracepoints markers."));

  add_prefix_cmd ("tfind", class_trace, tfind_command, _("\
Select a trace frame.\n\
No argument means forward by one frame; '-' means backward by one frame."),
		  &tfindlist, "tfind ", 1, &cmdlist);

  add_cmd ("outside", class_trace, tfind_outside_command, _("\
Select a trace frame whose PC is outside the given range (exclusive).\n\
Usage: tfind outside ADDR1, ADDR2"),
	   &tfindlist);

  add_cmd ("range", class_trace, tfind_range_command, _("\
Select a trace frame whose PC is in the given range (inclusive).\n\
Usage: tfind range ADDR1, ADDR2"),
	   &tfindlist);

  add_cmd ("line", class_trace, tfind_line_command, _("\
Select a trace frame by source line.\n\
Argument can be a line number (with optional source file),\n\
a function name, or '*' followed by an address.\n\
Default argument is 'the next source line that was traced'."),
	   &tfindlist);

  add_cmd ("tracepoint", class_trace, tfind_tracepoint_command, _("\
Select a trace frame by tracepoint number.\n\
Default is the tracepoint for the current trace frame."),
	   &tfindlist);

  add_cmd ("pc", class_trace, tfind_pc_command, _("\
Select a trace frame by PC.\n\
Default is the current PC, or the PC of the current trace frame."),
	   &tfindlist);

  add_cmd ("end", class_trace, tfind_end_command, _("\
De-select any trace frame and resume 'live' debugging."),
	   &tfindlist);

  add_alias_cmd ("none", "end", class_trace, 0, &tfindlist);

  add_cmd ("start", class_trace, tfind_start_command,
	   _("Select the first trace frame in the trace buffer."),
	   &tfindlist);

  add_com ("tstatus", class_trace, tstatus_command,
	   _("Display the status of the current trace data collection."));

  add_com ("tstop", class_trace, tstop_command, _("\
Stop trace data collection.\n\
Usage: tstop [NOTES]...\n\
Any arguments supplied are recorded with the trace as a stop reason and\n\
reported by tstatus (if the target supports trace notes)."));

  add_com ("tstart", class_trace, tstart_command, _("\
Start trace data collection.\n\
Usage: tstart [NOTES]...\n\
Any arguments supplied are recorded with the trace as a note and\n\
reported by tstatus (if the target supports trace notes)."));

  add_com ("end", class_trace, end_actions_pseudocommand, _("\
Ends a list of commands or actions.\n\
Several GDB commands allow you to enter a list of commands or actions.\n\
Entering \"end\" on a line by itself is the normal way to terminate\n\
such a list.\n\n\
Note: the \"end\" command cannot be used at the gdb prompt."));

  while_stepping_cmd_element = add_com ("while-stepping", class_trace,
					while_stepping_pseudocommand, _("\
Specify single-stepping behavior at a tracepoint.\n\
Argument is number of instructions to trace in single-step mode\n\
following the tracepoint.  This command is normally followed by\n\
one or more \"collect\" commands, to specify what to collect\n\
while single-stepping.\n\n\
Note: this command can only be used in a tracepoint \"actions\" list."));

  add_com_alias ("ws", "while-stepping", class_trace, 0);
  add_com_alias ("stepping", "while-stepping", class_trace, 0);

  add_com ("collect", class_trace, collect_pseudocommand, _("\
Specify one or more data items to be collected at a tracepoint.\n\
Accepts a comma-separated list of (one or more) expressions.  GDB will\n\
collect all data (variables, registers) referenced by that expression.\n\
Also accepts the following special arguments:\n\
    $regs   -- all registers.\n\
    $args   -- all function arguments.\n\
    $locals -- all variables local to the block/function scope.\n\
    $_sdata -- static tracepoint data (ignored for non-static tracepoints).\n\
Note: this command can only be used in a tracepoint \"actions\" list."));

  add_com ("teval", class_trace, teval_pseudocommand, _("\
Specify one or more expressions to be evaluated at a tracepoint.\n\
Accepts a comma-separated list of (one or more) expressions.\n\
The result of each evaluation will be discarded.\n\
Note: this command can only be used in a tracepoint \"actions\" list."));

  add_com ("actions", class_trace, actions_command, _("\
Specify the actions to be taken at a tracepoint.\n\
Tracepoint actions may include collecting of specified data,\n\
single-stepping, or enabling/disabling other tracepoints,\n\
depending on target's capabilities."));

  default_collect = xstrdup ("");
  add_setshow_string_cmd ("default-collect", class_trace,
			  &default_collect, _("\
Set the list of expressions to collect by default."), _("\
Show the list of expressions to collect by default."), NULL,
			  NULL, NULL,
			  &setlist, &showlist);

  add_setshow_boolean_cmd ("disconnected-tracing", no_class,
			   &disconnected_tracing, _("\
Set whether tracing continues after GDB disconnects."), _("\
Show whether tracing continues after GDB disconnects."), _("\
Use this to continue a tracing run even if GDB disconnects\n\
or detaches from the target.  You can reconnect later and look at\n\
trace data collected in the meantime."),
			   set_disconnected_tracing,
			   NULL,
			   &setlist,
			   &showlist);

  add_setshow_boolean_cmd ("circular-trace-buffer", no_class,
			   &circular_trace_buffer, _("\
Set target's use of circular trace buffer."), _("\
Show target's use of circular trace buffer."), _("\
Use this to make the trace buffer into a circular buffer,\n\
which will discard traceframes (oldest first) instead of filling\n\
up and stopping the trace run."),
			   set_circular_trace_buffer,
			   NULL,
			   &setlist,
			   &showlist);

  add_setshow_zuinteger_unlimited_cmd ("trace-buffer-size", no_class,
				       &trace_buffer_size, _("\
Set requested size of trace buffer."), _("\
Show requested size of trace buffer."), _("\
Use this to choose a size for the trace buffer.  Some targets\n\
may have fixed or limited buffer sizes.  Specifying \"unlimited\" or -1\n\
disables any attempt to set the buffer size and lets the target choose."),
				       set_trace_buffer_size, NULL,
				       &setlist, &showlist);

  add_setshow_string_cmd ("trace-user", class_trace,
			  &trace_user, _("\
Set the user name to use for current and future trace runs."), _("\
Show the user name to use for current and future trace runs."), NULL,
			  set_trace_user, NULL,
			  &setlist, &showlist);

  add_setshow_string_cmd ("trace-notes", class_trace,
			  &trace_notes, _("\
Set notes string to use for current and future trace runs."), _("\
Show the notes string to use for current and future trace runs."), NULL,
			  set_trace_notes, NULL,
			  &setlist, &showlist);

  add_setshow_string_cmd ("trace-stop-notes", class_trace,
			  &trace_stop_notes, _("\
Set notes string to use for future tstop commands."), _("\
Show the notes string to use for future tstop commands."), NULL,
			  set_trace_stop_notes, NULL,
			  &setlist, &showlist);
}
