/* Handle set and show GDB commands.

   Copyright (C) 2000-2024 Free Software Foundation, Inc.

   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 "readline/tilde.h"
#include "value.h"
#include <ctype.h>
#include "arch-utils.h"
#include "observable.h"
#include "interps.h"

#include "ui-out.h"

#include "cli/cli-decode.h"
#include "cli/cli-cmds.h"
#include "cli/cli-setshow.h"
#include "cli/cli-style.h"
#include "cli/cli-utils.h"

/* Return true if the change of command parameter should be notified.  */

static bool
notify_command_param_changed_p (bool param_changed, struct cmd_list_element *c)
{
  if (!param_changed)
    return false;

  return c->theclass != class_maintenance && c->theclass != class_obscure;
}


static enum auto_boolean
parse_auto_binary_operation (const char *arg)
{
  if (arg != NULL && *arg != '\0')
    {
      int length = strlen (arg);

      while (isspace (arg[length - 1]) && length > 0)
	length--;

      /* Note that "o" is ambiguous.  */

      if ((length == 2 && strncmp (arg, "on", length) == 0)
	  || strncmp (arg, "1", length) == 0
	  || strncmp (arg, "yes", length) == 0
	  || strncmp (arg, "enable", length) == 0)
	return AUTO_BOOLEAN_TRUE;
      else if ((length >= 2 && strncmp (arg, "off", length) == 0)
	       || strncmp (arg, "0", length) == 0
	       || strncmp (arg, "no", length) == 0
	       || strncmp (arg, "disable", length) == 0)
	return AUTO_BOOLEAN_FALSE;
      else if (strncmp (arg, "auto", length) == 0
	       || (length > 1 && strncmp (arg, "-1", length) == 0))
	return AUTO_BOOLEAN_AUTO;
    }
  error (_("\"on\", \"off\" or \"auto\" expected."));
  return AUTO_BOOLEAN_AUTO; /* Pacify GCC.  */
}

/* See cli-setshow.h.  */

int
parse_cli_boolean_value (const char **arg)
{
  const char *p = skip_to_space (*arg);
  size_t length = p - *arg;

  /* Note that "o" is ambiguous.  */

  if ((length == 2 && strncmp (*arg, "on", length) == 0)
      || strncmp (*arg, "1", length) == 0
      || strncmp (*arg, "yes", length) == 0
      || strncmp (*arg, "enable", length) == 0)
    {
      *arg = skip_spaces (*arg + length);
      return 1;
    }
  else if ((length >= 2 && strncmp (*arg, "off", length) == 0)
	   || strncmp (*arg, "0", length) == 0
	   || strncmp (*arg, "no", length) == 0
	   || strncmp (*arg, "disable", length) == 0)
    {
      *arg = skip_spaces (*arg + length);
      return 0;
    }
  else
    return -1;
}

/* See cli-setshow.h.  */

int
parse_cli_boolean_value (const char *arg)
{
  if (!arg || !*arg)
    return 1;

  int b = parse_cli_boolean_value (&arg);
  if (b >= 0 && *arg != '\0')
    return -1;

  return b;
}


static void
deprecated_show_value_hack (struct ui_file *ignore_file,
			    int ignore_from_tty,
			    struct cmd_list_element *c,
			    const char *value)
{
  /* If there's no command or value, don't try to print it out.  */
  if (c == NULL || value == NULL)
    return;

  /* Print doc minus "Show " at start.  Tell print_doc_line that
     this is for a 'show value' prefix.  */
  print_doc_line (gdb_stdout, c->doc + 5, true);

  gdb_assert (c->var.has_value ());

  switch (c->var->type ())
    {
    case var_string:
    case var_string_noescape:
    case var_enum:
      gdb_printf ((" is \"%s\".\n"), value);
      break;

    case var_optional_filename:
    case var_filename:
      gdb_printf ((" is \"%ps\".\n"),
		  styled_string (file_name_style.style (), value));
      break;

    default:
      gdb_printf ((" is %s.\n"), value);
      break;
    }
}

/* Returns true and the value in VAL if ARG is an accepted literal.  */

static bool
get_literal_val (LONGEST &val, const literal_def *extra_literals,
		 const char **arg, bool expression)
{
  *arg = skip_spaces (*arg);

  const char *unl_start = *arg;

  const char *p = skip_to_space (*arg);

  size_t len = p - *arg;

  if (len > 0 && extra_literals != nullptr)
    for (const literal_def *l = extra_literals;
	 l->literal != nullptr;
	 l++)
      if (strncmp (l->literal, *arg, len) == 0)
	{
	  *arg += len;

	  /* If parsing an expression (i.e., parsing for a "set" command),
	     anything after the literal is junk.  For options, anything
	     after the literal might be a command argument or another
	     option.  */
	  if (expression)
	    {
	      const char *after = skip_spaces (*arg);
	      if (*after != '\0')
		error (_("Junk after \"%.*s\": %s"),
		       (int) len, unl_start, after);
	    }

	  val = l->use;
	  return true;
	}

  return false;
}

/* See cli-setshow.h.  */

LONGEST
parse_cli_var_integer (var_types var_type, const literal_def *extra_literals,
		       const char **arg, bool expression)
{
  LONGEST val;

  if (*arg == nullptr || **arg == '\0')
    {
      if (extra_literals == nullptr)
	error_no_arg (_("integer to set it to"));
      else
	{
	  std::string buffer = "";
	  size_t count = 0;

	  for (const literal_def *l = extra_literals;
	       l->literal != nullptr;
	       l++, count++)
	    {
	      if (count != 0)
		buffer += ", ";
	      buffer = buffer + '"' + l->literal + '"';
	    }
	  if (count > 1)
	    error_no_arg
	      (string_printf (_("integer to set it to, or one of: %s"),
			      buffer.c_str ()).c_str ());
	  else
	    error_no_arg
	      (string_printf (_("integer to set it to, or %s"),
			      buffer.c_str ()).c_str ());
	}
    }

  if (!get_literal_val (val, extra_literals, arg, expression))
    {
      if (expression)
	val = parse_and_eval_long (*arg);
      else
	val = get_ulongest (arg);

      enum tribool allowed = TRIBOOL_UNKNOWN;
      if (extra_literals != nullptr)
	{
	  for (const literal_def *l = extra_literals;
	       l->literal != nullptr;
	       l++)
	    if (l->val.has_value () && val == *l->val)
	      {
		allowed = TRIBOOL_TRUE;
		val = l->use;
		break;
	      }
	    else if (val == l->use)
	      allowed = TRIBOOL_FALSE;
	}

      if (allowed == TRIBOOL_UNKNOWN)
	{
	  if (val > UINT_MAX || val < INT_MIN
	      || (var_type == var_uinteger && val < 0)
	      || (var_type == var_integer && val > INT_MAX)
	      || (var_type == var_pinteger && val < 0)
	      || (var_type == var_pinteger && val > INT_MAX))
	    allowed = TRIBOOL_FALSE;
	}
      if (allowed == TRIBOOL_FALSE)
	error (_("integer %s out of range"), plongest (val));
    }

  return val;
}

/* See cli-setshow.h.  */

const char *
parse_cli_var_enum (const char **args, const char *const *enums)
{
  /* If no argument was supplied, print an informative error
     message.  */
  if (args == NULL || *args == NULL || **args == '\0')
    {
      std::string msg;

      for (size_t i = 0; enums[i]; i++)
	{
	  if (i != 0)
	    msg += ", ";
	  msg += enums[i];
	}
      error (_("Requires an argument. Valid arguments are %s."),
	     msg.c_str ());
    }

  const char *p = skip_to_space (*args);
  size_t len = p - *args;

  int nmatches = 0;
  const char *match = NULL;
  for (size_t i = 0; enums[i]; i++)
    if (strncmp (*args, enums[i], len) == 0)
      {
	if (enums[i][len] == '\0')
	  {
	    match = enums[i];
	    nmatches = 1;
	    break; /* Exact match.  */
	  }
	else
	  {
	    match = enums[i];
	    nmatches++;
	  }
      }

  if (nmatches == 0)
    error (_("Undefined item: \"%.*s\"."), (int) len, *args);

  if (nmatches > 1)
    error (_("Ambiguous item \"%.*s\"."), (int) len, *args);

  *args += len;
  return match;
}

/* Do a "set" command.  ARG is NULL if no argument, or the
   text of the argument, and FROM_TTY is nonzero if this command is
   being entered directly by the user (i.e. these are just like any
   other command).  C is the command list element for the command.  */

void
do_set_command (const char *arg, int from_tty, struct cmd_list_element *c)
{
  /* A flag to indicate the option is changed or not.  */
  bool option_changed = false;

  gdb_assert (c->type == set_cmd);

  if (arg == NULL)
    arg = "";

  gdb_assert (c->var.has_value ());

  switch (c->var->type ())
    {
    case var_string:
      {
	std::string newobj;
	const char *p;
	int ch;

	newobj.reserve (strlen (arg));
	p = arg;
	while ((ch = *p++) != '\000')
	  {
	    if (ch == '\\')
	      {
		/* \ at end of argument is used after spaces
		   so they won't be lost.  */
		/* This is obsolete now that we no longer strip
		   trailing whitespace and actually, the backslash
		   didn't get here in my test, readline or
		   something did something funky with a backslash
		   right before a newline.  */
		if (*p == 0)
		  break;
		ch = parse_escape (get_current_arch (), &p);
		if (ch == 0)
		  break;	/* C loses */
		else if (ch > 0)
		  newobj.push_back (ch);
	      }
	    else
	      newobj.push_back (ch);
	  }
	newobj.shrink_to_fit ();

	option_changed = c->var->set<std::string> (std::move (newobj));
      }
      break;
    case var_string_noescape:
      option_changed = c->var->set<std::string> (std::string (arg));
      break;
    case var_filename:
      if (*arg == '\0')
	error_no_arg (_("filename to set it to."));
      [[fallthrough]];
    case var_optional_filename:
      {
	char *val = NULL;

	if (*arg != '\0')
	  {
	    /* Clear trailing whitespace of filename.  */
	    const char *ptr = arg + strlen (arg) - 1;

	    while (ptr >= arg && (*ptr == ' ' || *ptr == '\t'))
	      ptr--;
	    gdb::unique_xmalloc_ptr<char> copy
	      = make_unique_xstrndup (arg, ptr + 1 - arg);

	    val = tilde_expand (copy.get ());
	  }
	else
	  val = xstrdup ("");

	option_changed
	  = c->var->set<std::string> (std::string (val));
	xfree (val);
      }
      break;
    case var_boolean:
      {
	int val = parse_cli_boolean_value (arg);

	if (val < 0)
	  error (_("\"on\" or \"off\" expected."));

	option_changed = c->var->set<bool> (val);
      }
      break;
    case var_auto_boolean:
      option_changed = c->var->set<enum auto_boolean> (parse_auto_binary_operation (arg));
      break;
    case var_uinteger:
      option_changed
	= c->var->set<unsigned int> (parse_cli_var_integer (c->var->type (),
							    c->var->
							    extra_literals (),
							    &arg, true));
      break;
    case var_integer:
    case var_pinteger:
      option_changed
	= c->var->set<int> (parse_cli_var_integer (c->var->type (),
						   c->var->extra_literals (),
						   &arg, true));
      break;
    case var_enum:
      {
	const char *end_arg = arg;
	const char *match = parse_cli_var_enum (&end_arg, c->enums);

	int len = end_arg - arg;
	const char *after = skip_spaces (end_arg);
	if (*after != '\0')
	  error (_("Junk after item \"%.*s\": %s"), len, arg, after);

	option_changed = c->var->set<const char *> (match);
      }
      break;
    case var_color:
      {
	ui_file_style::color color = parse_var_color (arg);
	ui_file_style::color approx_color = color.approximate (colorsupport ());
	option_changed = c->var->set<ui_file_style::color> (approx_color);
      }
      break;
    default:
      error (_("gdb internal error: bad var_type in do_setshow_command"));
    }

  c->func (NULL, from_tty, c);

  if (notify_command_param_changed_p (option_changed, c))
    {
      char *name, *cp;
      struct cmd_list_element **cmds;
      struct cmd_list_element *p;
      int i;
      int length = 0;

      /* Compute the whole multi-word command options.  If user types command
	 'set foo bar baz on', c->name is 'baz', and GDB can't pass "bar" to
	 command option change notification, because it is confusing.  We can
	 trace back through field 'prefix' to compute the whole options,
	 and pass "foo bar baz" to notification.  */

      for (i = 0, p = c; p != NULL; i++)
	{
	  length += strlen (p->name);
	  length++;

	  p = p->prefix;
	}
      cp = name = (char *) xmalloc (length);
      cmds = XNEWVEC (struct cmd_list_element *, i);

      /* Track back through filed 'prefix' and cache them in CMDS.  */
      for (i = 0, p = c; p != NULL; i++)
	{
	  cmds[i] = p;
	  p = p->prefix;
	}

      /* Don't trigger any observer notification if subcommands is not
	 setlist.  */
      i--;
      if (cmds[i]->subcommands != &setlist)
	{
	  xfree (cmds);
	  xfree (name);

	  return;
	}
      /* Traverse them in the reversed order, and copy their names into
	 NAME.  */
      for (i--; i >= 0; i--)
	{
	  memcpy (cp, cmds[i]->name, strlen (cmds[i]->name));
	  cp += strlen (cmds[i]->name);

	  if (i != 0)
	    {
	      cp[0] = ' ';
	      cp++;
	    }
	}
      cp[0] = 0;

      xfree (cmds);

      switch (c->var->type ())
	{
	case var_string:
	case var_string_noescape:
	case var_filename:
	case var_optional_filename:
	  interps_notify_param_changed
	    (name, c->var->get<std::string> ().c_str ());
	  break;
	case var_enum:
	  interps_notify_param_changed
	    (name, c->var->get<const char *> ());
	  break;
	case var_color:
	  {
	    const ui_file_style::color &color
	      = c->var->get<ui_file_style::color> ();
	    interps_notify_param_changed
	      (name, color.to_string ().c_str ());
	  }
	  break;
	case var_boolean:
	  {
	    const char *opt = c->var->get<bool> () ? "on" : "off";

	    interps_notify_param_changed (name, opt);
	  }
	  break;
	case var_auto_boolean:
	  {
	    const char *s
	      = auto_boolean_enums[c->var->get<enum auto_boolean> ()];

	    interps_notify_param_changed (name, s);
	  }
	  break;
	case var_uinteger:
	  {
	    char s[64];

	    xsnprintf (s, sizeof s, "%u", c->var->get<unsigned int> ());
	    interps_notify_param_changed (name, s);
	  }
	  break;
	case var_integer:
	case var_pinteger:
	  {
	    char s[64];

	    xsnprintf (s, sizeof s, "%d", c->var->get<int> ());
	    interps_notify_param_changed (name, s);
	  }
	  break;
	}
      xfree (name);
    }
}

/* See cli/cli-setshow.h.  */

std::string
get_setshow_command_value_string (const setting &var)
{
  string_file stb;

  switch (var.type ())
    {
    case var_string:
      {
	std::string value = var.get<std::string> ();
	if (!value.empty ())
	  stb.putstr (value.c_str (), '"');
      }
      break;
    case var_string_noescape:
    case var_optional_filename:
    case var_filename:
      stb.puts (var.get<std::string> ().c_str ());
      break;
    case var_enum:
      {
	const char *value = var.get<const char *> ();
	if (value != nullptr)
	  stb.puts (value);
      }
      break;
    case var_color:
      {
	const ui_file_style::color &value = var.get<ui_file_style::color> ();
	stb.puts (value.to_string ().c_str ());
      }
      break;
    case var_boolean:
      stb.puts (var.get<bool> () ? "on" : "off");
      break;
    case var_auto_boolean:
      switch (var.get<enum auto_boolean> ())
	{
	case AUTO_BOOLEAN_TRUE:
	  stb.puts ("on");
	  break;
	case AUTO_BOOLEAN_FALSE:
	  stb.puts ("off");
	  break;
	case AUTO_BOOLEAN_AUTO:
	  stb.puts ("auto");
	  break;
	default:
	  gdb_assert_not_reached ("invalid var_auto_boolean");
	  break;
	}
      break;
    case var_uinteger:
    case var_integer:
    case var_pinteger:
      {
	bool printed = false;
	const LONGEST value
	  = (var.type () == var_uinteger
	     ? static_cast<LONGEST> (var.get<unsigned int> ())
	     : static_cast<LONGEST> (var.get<int> ()));

	if (var.extra_literals () != nullptr)
	  for (const literal_def *l = var.extra_literals ();
	       l->literal != nullptr;
	       l++)
	    if (value == l->use)
	      {
		stb.puts (l->literal);
		printed = true;
		break;
	      }
	if (!printed)
	  {
	    if (var.type () == var_uinteger)
	      stb.printf ("%u", static_cast<unsigned int> (value));
	    else
	      stb.printf ("%d", static_cast<int> (value));
	  }
      }
      break;
    default:
      gdb_assert_not_reached ("bad var_type");
    }

  return stb.release ();
}


/* Do a "show" command.  ARG is NULL if no argument, or the
   text of the argument, and FROM_TTY is nonzero if this command is
   being entered directly by the user (i.e. these are just like any
   other command).  C is the command list element for the command.  */

void
do_show_command (const char *arg, int from_tty, struct cmd_list_element *c)
{
  struct ui_out *uiout = current_uiout;

  gdb_assert (c->type == show_cmd);
  gdb_assert (c->var.has_value ());

  std::string val = get_setshow_command_value_string (*c->var);

  /* FIXME: cagney/2005-02-10: There should be MI and CLI specific
     versions of code to print the value out.  */

  if (uiout->is_mi_like_p ())
    uiout->field_string ("value", val);
  else
    {
      if (c->show_value_func != NULL)
	c->show_value_func (gdb_stdout, from_tty, c, val.c_str ());
      else
	deprecated_show_value_hack (gdb_stdout, from_tty, c, val.c_str ());
    }

  c->func (NULL, from_tty, c);
}

/* Show all the settings in a list of show commands.  */

void
cmd_show_list (struct cmd_list_element *list, int from_tty)
{
  struct ui_out *uiout = current_uiout;

  ui_out_emit_tuple tuple_emitter (uiout, "showlist");
  const ui_file_style cmd_style = command_style.style ();
  for (; list != NULL; list = list->next)
    {
      /* We skip show command aliases to avoid showing duplicated values.  */

      /* If we find a prefix, run its list, prefixing our output by its
	 prefix (with "show " skipped).  */
      if (list->is_prefix () && !list->is_alias ())
	{
	  ui_out_emit_tuple optionlist_emitter (uiout, "optionlist");
	  std::string prefixname = list->prefixname ();
	  const char *new_prefix = strstr (prefixname.c_str (), "show ") + 5;

	  if (uiout->is_mi_like_p ())
	    uiout->field_string ("prefix", new_prefix);
	  cmd_show_list (*list->subcommands, from_tty);
	}
      else if (list->theclass != no_set_class && !list->is_alias ())
	{
	  ui_out_emit_tuple option_emitter (uiout, "option");

	  if (!uiout->is_mi_like_p () && list->prefix != nullptr)
	    {
	      /* If we find a prefix, output it (with "show " skipped).  */
	      std::string prefixname = list->prefix->prefixname ();
	      if (startswith (prefixname, "show "))
		prefixname = prefixname.substr (5);
	      /* In non-MI mode, we include the full name here.  */
	      prefixname += list->name;
	      uiout->field_string ("name", prefixname, cmd_style);
	    }
	  else
	    uiout->field_string ("name", list->name, cmd_style);
	  uiout->text (":  ");
	  if (list->type == show_cmd)
	    do_show_command (NULL, from_tty, list);
	  else
	    cmd_func (list, NULL, from_tty);
	}
    }
}


