/* Handle set and show GDB commands.
- Copyright (C) 2000-2021 Free Software Foundation, Inc.
+ Copyright (C) 2000-2022 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
/* Return true if the change of command parameter should be notified. */
-static int
-notify_command_param_changed_p (int param_changed, struct cmd_list_element *c)
+static bool
+notify_command_param_changed_p (bool param_changed, struct cmd_list_element *c)
{
- if (param_changed == 0)
- return 0;
-
- if (c->theclass == class_maintenance || c->theclass == class_deprecated
- || c->theclass == class_obscure)
- return 0;
+ if (!param_changed)
+ return false;
- return 1;
+ return c->theclass != class_maintenance && c->theclass != class_obscure;
}
\f
/* 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);
- switch (c->var_type)
+
+ gdb_assert (c->var.has_value ());
+
+ switch (c->var->type ())
{
case var_string:
case var_string_noescape:
case var_optional_filename:
case var_filename:
case var_enum:
- printf_filtered ((" is \"%s\".\n"), value);
+ gdb_printf ((" is \"%s\".\n"), value);
break;
+
default:
- printf_filtered ((" is %s.\n"), value);
+ gdb_printf ((" is %s.\n"), value);
break;
}
}
if (*arg == nullptr || **arg == '\0')
{
if (var_type == var_uinteger)
- error_no_arg (_("integer to set it to, or \"unlimited\"."));
+ error_no_arg (_("integer to set it to, or \"unlimited\""));
else
- error_no_arg (_("integer to set it to."));
+ error_no_arg (_("integer to set it to"));
}
if (var_type == var_uinteger && is_unlimited_literal (arg, expression))
LONGEST val;
if (*arg == nullptr || **arg == '\0')
- error_no_arg (_("integer to set it to, or \"unlimited\"."));
+ error_no_arg (_("integer to set it to, or \"unlimited\""));
if (is_unlimited_literal (arg, expression))
val = -1;
do_set_command (const char *arg, int from_tty, struct cmd_list_element *c)
{
/* A flag to indicate the option is changed or not. */
- int option_changed = 0;
+ bool option_changed = false;
gdb_assert (c->type == set_cmd);
if (arg == NULL)
arg = "";
- switch (c->var_type)
+ gdb_assert (c->var.has_value ());
+
+ switch (c->var->type ())
{
case var_string:
{
*q++ = '\0';
newobj = (char *) xrealloc (newobj, q - newobj);
- if (*(char **) c->var == NULL
- || strcmp (*(char **) c->var, newobj) != 0)
- {
- xfree (*(char **) c->var);
- *(char **) c->var = newobj;
-
- option_changed = 1;
- }
- else
- xfree (newobj);
+ option_changed = c->var->set<std::string> (std::string (newobj));
+ xfree (newobj);
}
break;
case var_string_noescape:
- if (*(char **) c->var == NULL || strcmp (*(char **) c->var, arg) != 0)
- {
- xfree (*(char **) c->var);
- *(char **) c->var = xstrdup (arg);
-
- option_changed = 1;
- }
+ option_changed = c->var->set<std::string> (std::string (arg));
break;
case var_filename:
if (*arg == '\0')
{
/* Clear trailing whitespace of filename. */
const char *ptr = arg + strlen (arg) - 1;
- char *copy;
while (ptr >= arg && (*ptr == ' ' || *ptr == '\t'))
ptr--;
- copy = xstrndup (arg, ptr + 1 - arg);
+ gdb::unique_xmalloc_ptr<char> copy
+ = make_unique_xstrndup (arg, ptr + 1 - arg);
- val = tilde_expand (copy);
- xfree (copy);
+ val = tilde_expand (copy.get ());
}
else
val = xstrdup ("");
- if (*(char **) c->var == NULL
- || strcmp (*(char **) c->var, val) != 0)
- {
- xfree (*(char **) c->var);
- *(char **) c->var = val;
-
- option_changed = 1;
- }
- else
- xfree (val);
+ option_changed
+ = c->var->set<std::string> (std::string (val));
+ xfree (val);
}
break;
case var_boolean:
if (val < 0)
error (_("\"on\" or \"off\" expected."));
- if (val != *(bool *) c->var)
- {
- *(bool *) c->var = val;
- option_changed = 1;
- }
+ option_changed = c->var->set<bool> (val);
}
break;
case var_auto_boolean:
- {
- enum auto_boolean val = parse_auto_binary_operation (arg);
-
- if (*(enum auto_boolean *) c->var != val)
- {
- *(enum auto_boolean *) c->var = val;
-
- option_changed = 1;
- }
- }
+ option_changed = c->var->set<enum auto_boolean> (parse_auto_binary_operation (arg));
break;
case var_uinteger:
case var_zuinteger:
- {
- unsigned int val = parse_cli_var_uinteger (c->var_type, &arg, true);
-
- if (*(unsigned int *) c->var != val)
- {
- *(unsigned int *) c->var = val;
-
- option_changed = 1;
- }
- }
+ option_changed
+ = c->var->set<unsigned int> (parse_cli_var_uinteger (c->var->type (),
+ &arg, true));
break;
case var_integer:
case var_zinteger:
if (*arg == '\0')
{
- if (c->var_type == var_integer)
- error_no_arg (_("integer to set it to, or \"unlimited\"."));
+ if (c->var->type () == var_integer)
+ error_no_arg (_("integer to set it to, or \"unlimited\""));
else
- error_no_arg (_("integer to set it to."));
+ error_no_arg (_("integer to set it to"));
}
- if (c->var_type == var_integer && is_unlimited_literal (&arg, true))
+ if (c->var->type () == var_integer && is_unlimited_literal (&arg, true))
val = 0;
else
val = parse_and_eval_long (arg);
- if (val == 0 && c->var_type == var_integer)
+ if (val == 0 && c->var->type () == var_integer)
val = INT_MAX;
else if (val < INT_MIN
/* For var_integer, don't let the user set the value
to INT_MAX directly, as that exposes an
implementation detail to the user interface. */
- || (c->var_type == var_integer && val >= INT_MAX)
- || (c->var_type == var_zinteger && val > INT_MAX))
+ || (c->var->type () == var_integer && val >= INT_MAX)
+ || (c->var->type () == var_zinteger && val > INT_MAX))
error (_("integer %s out of range"), plongest (val));
- if (*(int *) c->var != val)
- {
- *(int *) c->var = val;
-
- option_changed = 1;
- }
- break;
+ option_changed = c->var->set<int> (val);
}
+ break;
case var_enum:
{
const char *end_arg = arg;
if (*after != '\0')
error (_("Junk after item \"%.*s\": %s"), len, arg, after);
- if (*(const char **) c->var != match)
- {
- *(const char **) c->var = match;
-
- option_changed = 1;
- }
+ option_changed = c->var->set<const char *> (match);
}
break;
case var_zuinteger_unlimited:
- {
- int val = parse_cli_var_zuinteger_unlimited (&arg, true);
-
- if (*(int *) c->var != val)
- {
- *(int *) c->var = val;
- option_changed = 1;
- }
- }
+ option_changed = c->var->set<int>
+ (parse_cli_var_zuinteger_unlimited (&arg, true));
break;
default:
error (_("gdb internal error: bad var_type in do_setshow_command"));
}
- c->func (c, NULL, from_tty);
+
+ c->func (NULL, from_tty, c);
if (notify_command_param_changed_p (option_changed, c))
{
xfree (cmds);
- switch (c->var_type)
+ switch (c->var->type ())
{
case var_string:
case var_string_noescape:
case var_filename:
case var_optional_filename:
+ gdb::observers::command_param_changed.notify
+ (name, c->var->get<std::string> ().c_str ());
+ break;
case var_enum:
- gdb::observers::command_param_changed.notify (name, *(char **) c->var);
+ gdb::observers::command_param_changed.notify
+ (name, c->var->get<const char *> ());
break;
case var_boolean:
{
- const char *opt = *(bool *) c->var ? "on" : "off";
+ const char *opt = c->var->get<bool> () ? "on" : "off";
gdb::observers::command_param_changed.notify (name, opt);
}
break;
case var_auto_boolean:
{
- const char *s = auto_boolean_enums[*(enum auto_boolean *) c->var];
+ const char *s
+ = auto_boolean_enums[c->var->get<enum auto_boolean> ()];
gdb::observers::command_param_changed.notify (name, s);
}
{
char s[64];
- xsnprintf (s, sizeof s, "%u", *(unsigned int *) c->var);
+ xsnprintf (s, sizeof s, "%u", c->var->get<unsigned int> ());
gdb::observers::command_param_changed.notify (name, s);
}
break;
{
char s[64];
- xsnprintf (s, sizeof s, "%d", *(int *) c->var);
+ xsnprintf (s, sizeof s, "%d", c->var->get<int> ());
gdb::observers::command_param_changed.notify (name, s);
}
break;
/* See cli/cli-setshow.h. */
std::string
-get_setshow_command_value_string (const cmd_list_element *c)
+get_setshow_command_value_string (const setting &var)
{
string_file stb;
- switch (c->var_type)
+ switch (var.type ())
{
case var_string:
- if (*(char **) c->var)
- stb.putstr (*(char **) c->var, '"');
+ {
+ 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:
- if (*(char **) c->var)
- stb.puts (*(char **) c->var);
+ {
+ const char *value = var.get<const char *> ();
+ if (value != nullptr)
+ stb.puts (value);
+ }
break;
case var_boolean:
- stb.puts (*(bool *) c->var ? "on" : "off");
+ stb.puts (var.get<bool> () ? "on" : "off");
break;
case var_auto_boolean:
- switch (*(enum auto_boolean*) c->var)
+ switch (var.get<enum auto_boolean> ())
{
case AUTO_BOOLEAN_TRUE:
stb.puts ("on");
break;
case var_uinteger:
case var_zuinteger:
- if (c->var_type == var_uinteger
- && *(unsigned int *) c->var == UINT_MAX)
- stb.puts ("unlimited");
- else
- stb.printf ("%u", *(unsigned int *) c->var);
+ {
+ const unsigned int value = var.get<unsigned int> ();
+
+ if (var.type () == var_uinteger
+ && value == UINT_MAX)
+ stb.puts ("unlimited");
+ else
+ stb.printf ("%u", value);
+ }
break;
case var_integer:
case var_zinteger:
- if (c->var_type == var_integer
- && *(int *) c->var == INT_MAX)
- stb.puts ("unlimited");
- else
- stb.printf ("%d", *(int *) c->var);
+ {
+ const int value = var.get<int> ();
+
+ if (var.type () == var_integer
+ && value == INT_MAX)
+ stb.puts ("unlimited");
+ else
+ stb.printf ("%d", value);
+ }
break;
case var_zuinteger_unlimited:
{
- if (*(int *) c->var == -1)
+ const int value = var.get<int> ();
+ if (value == -1)
stb.puts ("unlimited");
else
- stb.printf ("%d", *(int *) c->var);
+ stb.printf ("%d", value);
}
break;
default:
gdb_assert_not_reached ("bad var_type");
}
- return std::move (stb.string ());
+ return stb.release ();
}
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);
+ 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. */
deprecated_show_value_hack (gdb_stdout, from_tty, c, val.c_str ());
}
- c->func (c, NULL, from_tty);
+ c->func (NULL, from_tty, c);
}
/* Show all the settings in a list of show commands. */