/* GDB parameters implemented in Python

   Copyright (C) 2008-2023 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 "value.h"
#include "python-internal.h"
#include "charset.h"
#include "gdbcmd.h"
#include "cli/cli-decode.h"
#include "completer.h"
#include "language.h"
#include "arch-utils.h"

/* Python parameter types as in PARM_CONSTANTS below.  */

enum param_types
{
  param_boolean,
  param_auto_boolean,
  param_uinteger,
  param_integer,
  param_string,
  param_string_noescape,
  param_optional_filename,
  param_filename,
  param_zinteger,
  param_zuinteger,
  param_zuinteger_unlimited,
  param_enum,
} param_types;

/* Translation from Python parameters to GDB variable types.  Keep in the
   same order as PARAM_TYPES due to C++'s lack of designated initializers.  */

static const struct
{
  /* The type of the parameter.  */
  enum var_types type;

  /* Extra literals, such as `unlimited', accepted in lieu of a number.  */
  const literal_def *extra_literals;
} param_to_var[] = { { var_boolean },
		     { var_auto_boolean },
		     { var_uinteger, uinteger_unlimited_literals },
		     { var_integer, integer_unlimited_literals },
		     { var_string },
		     { var_string_noescape },
		     { var_optional_filename },
		     { var_filename },
		     { var_integer },
		     { var_uinteger },
		     { var_pinteger, pinteger_unlimited_literals },
		     { var_enum } };

/* Parameter constants and their values.  */
static struct
{
  const char *name;
  int value;
} parm_constants[]
  = { { "PARAM_BOOLEAN", param_boolean }, /* ARI: param_boolean */
      { "PARAM_AUTO_BOOLEAN", param_auto_boolean },
      { "PARAM_UINTEGER", param_uinteger },
      { "PARAM_INTEGER", param_integer },
      { "PARAM_STRING", param_string },
      { "PARAM_STRING_NOESCAPE", param_string_noescape },
      { "PARAM_OPTIONAL_FILENAME", param_optional_filename },
      { "PARAM_FILENAME", param_filename },
      { "PARAM_ZINTEGER", param_zinteger },
      { "PARAM_ZUINTEGER", param_zuinteger },
      { "PARAM_ZUINTEGER_UNLIMITED", param_zuinteger_unlimited },
      { "PARAM_ENUM", param_enum },
      { NULL, 0 } };

/* A union that can hold anything described by enum var_types.  */
union parmpy_variable
{
  /* Hold a boolean value.  */
  bool boolval;

  /* Hold an integer value.  */
  int intval;

  /* Hold an auto_boolean.  */
  enum auto_boolean autoboolval;

  /* Hold an unsigned integer value, for uinteger.  */
  unsigned int uintval;

  /* Hold a string, for the various string types.  The std::string is
     new-ed.  */
  std::string *stringval;

  /* Hold a string, for enums.  */
  const char *cstringval;
};

/* A GDB parameter.  */
struct parmpy_object
{
  PyObject_HEAD

    /* The type of the parameter.  */
    enum var_types type;

  /* Extra literals, such as `unlimited', accepted in lieu of a number.  */
  const literal_def *extra_literals;

  /* The value of the parameter.  */
  union parmpy_variable value;

  /* For an enum command, the possible values.  The vector is
     allocated with xmalloc, as is each element.  It is
     NULL-terminated.  */
  const char **enumeration;
};

/* Wraps a setting around an existing parmpy_object.  This abstraction
   is used to manipulate the value in S->VALUE in a type safe manner using
   the setting interface.  */

static setting
make_setting (parmpy_object *s)
{
  enum var_types type = s->type;

  if (var_type_uses<bool> (type))
    return setting (type, &s->value.boolval);
  else if (var_type_uses<int> (type))
    return setting (type, &s->value.intval, s->extra_literals);
  else if (var_type_uses<auto_boolean> (type))
    return setting (type, &s->value.autoboolval);
  else if (var_type_uses<unsigned int> (type))
    return setting (type, &s->value.uintval, s->extra_literals);
  else if (var_type_uses<std::string> (type))
    return setting (type, s->value.stringval);
  else if (var_type_uses<const char *> (type))
    return setting (type, &s->value.cstringval);
  else
    gdb_assert_not_reached ("unhandled var type");
}

extern PyTypeObject
  parmpy_object_type CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("parmpy_object");

/* Some handy string constants.  */
static PyObject *set_doc_cst;
static PyObject *show_doc_cst;

/* Get an attribute.  */
static PyObject *
get_attr (PyObject *obj, PyObject *attr_name)
{
  if (PyUnicode_Check (attr_name)
      && !PyUnicode_CompareWithASCIIString (attr_name, "value"))
    {
      parmpy_object *self = (parmpy_object *) obj;

      return gdbpy_parameter_value (make_setting (self));
    }

  return PyObject_GenericGetAttr (obj, attr_name);
}

/* Set a parameter value from a Python value.  Return 0 on success.  Returns
   -1 on error, with a python exception set.  */
static int
set_parameter_value (parmpy_object *self, PyObject *value)
{
  int cmp;

  switch (self->type)
    {
    case var_string:
    case var_string_noescape:
    case var_optional_filename:
    case var_filename:
      if (!gdbpy_is_string (value)
	  && (self->type == var_filename || value != Py_None))
	{
	  PyErr_SetString (PyExc_RuntimeError,
			   _ ("String required for filename."));

	  return -1;
	}
      if (value == Py_None)
	self->value.stringval->clear ();
      else
	{
	  gdb::unique_xmalloc_ptr<char> string (
	    python_string_to_host_string (value));
	  if (string == NULL)
	    return -1;

	  *self->value.stringval = string.get ();
	}
      break;

    case var_enum:
      {
	int i;

	if (!gdbpy_is_string (value))
	  {
	    PyErr_SetString (PyExc_RuntimeError,
			     _ ("ENUM arguments must be a string."));
	    return -1;
	  }

	gdb::unique_xmalloc_ptr<char> str (
	  python_string_to_host_string (value));
	if (str == NULL)
	  return -1;
	for (i = 0; self->enumeration[i]; ++i)
	  if (!strcmp (self->enumeration[i], str.get ()))
	    break;
	if (!self->enumeration[i])
	  {
	    PyErr_SetString (
	      PyExc_RuntimeError,
	      _ ("The value must be member of an enumeration."));
	    return -1;
	  }
	self->value.cstringval = self->enumeration[i];
	break;
      }

    case var_boolean:
      if (!PyBool_Check (value))
	{
	  PyErr_SetString (PyExc_RuntimeError,
			   _ ("A boolean argument is required."));
	  return -1;
	}
      cmp = PyObject_IsTrue (value);
      if (cmp < 0)
	return -1;
      self->value.boolval = cmp;
      break;

    case var_auto_boolean:
      if (!PyBool_Check (value) && value != Py_None)
	{
	  PyErr_SetString (PyExc_RuntimeError,
			   _ ("A boolean or None is required"));
	  return -1;
	}

      if (value == Py_None)
	self->value.autoboolval = AUTO_BOOLEAN_AUTO;
      else
	{
	  cmp = PyObject_IsTrue (value);
	  if (cmp < 0)
	    return -1;
	  if (cmp == 1)
	    self->value.autoboolval = AUTO_BOOLEAN_TRUE;
	  else
	    self->value.autoboolval = AUTO_BOOLEAN_FALSE;
	}
      break;

    case var_uinteger:
    case var_integer:
    case var_pinteger:
      {
	const literal_def *extra_literals = self->extra_literals;
	enum tribool allowed = TRIBOOL_UNKNOWN;
	enum var_types var_type = self->type;
	std::string buffer = "";
	size_t count = 0;
	LONGEST val;

	if (extra_literals != nullptr)
	  {
	    gdb::unique_xmalloc_ptr<char> str (
	      python_string_to_host_string (value));
	    const char *s = str != nullptr ? str.get () : nullptr;
	    PyErr_Clear ();

	    for (const literal_def *l = extra_literals; l->literal != nullptr;
		 l++, count++)
	      {
		if (count != 0)
		  buffer += ", ";
		buffer = buffer + "'" + l->literal + "'";
		if (allowed == TRIBOOL_UNKNOWN
		    && ((value == Py_None && !strcmp ("unlimited", l->literal))
			|| (s != nullptr && !strcmp (s, l->literal))))
		  {
		    val = l->use;
		    allowed = TRIBOOL_TRUE;
		  }
	      }
	  }

	if (allowed == TRIBOOL_UNKNOWN)
	  {
	    val = PyLong_AsLongLong (value);

	    if (PyErr_Occurred ())
	      {
		if (extra_literals == nullptr)
		  PyErr_SetString (PyExc_RuntimeError,
				   _ ("The value must be integer."));
		else if (count > 1)
		  PyErr_SetString (PyExc_RuntimeError,
				   string_printf (_ ("integer or one of: %s"),
						  buffer.c_str ())
				     .c_str ());
		else
		  PyErr_SetString (PyExc_RuntimeError,
				   string_printf (_ ("integer or %s"),
						  buffer.c_str ())
				     .c_str ());
		return -1;
	      }

	    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)
	  {
	    PyErr_SetString (PyExc_RuntimeError, _ ("Range exceeded."));
	    return -1;
	  }

	if (self->type == var_uinteger)
	  self->value.uintval = (unsigned) val;
	else
	  self->value.intval = (int) val;
	break;
      }

    default:
      PyErr_SetString (PyExc_RuntimeError,
		       _ ("Unhandled type in parameter value."));
      return -1;
    }

  return 0;
}

/* Set an attribute.  Returns -1 on error, with a python exception set.  */
static int
set_attr (PyObject *obj, PyObject *attr_name, PyObject *val)
{
  if (PyUnicode_Check (attr_name)
      && !PyUnicode_CompareWithASCIIString (attr_name, "value"))
    {
      if (!val)
	{
	  PyErr_SetString (PyExc_RuntimeError,
			   _ ("Cannot delete a parameter's value."));
	  return -1;
	}
      return set_parameter_value ((parmpy_object *) obj, val);
    }

  return PyObject_GenericSetAttr (obj, attr_name, val);
}

/* Build up the path to command C, but drop the first component of the
   command prefix.  This is only intended for use with the set/show
   parameters this file deals with, the first prefix should always be
   either 'set' or 'show'.

   As an example, if this full command is 'set prefix_a prefix_b command'
   this function will return the string 'prefix_a prefix_b command'.  */

static std::string
full_cmd_name_without_first_prefix (struct cmd_list_element *c)
{
  std::vector<std::string> components = c->command_components ();
  gdb_assert (components.size () > 1);
  std::string result = components[1];
  for (int i = 2; i < components.size (); ++i)
    result += " " + components[i];
  return result;
}

/* The different types of documentation string.  */

enum doc_string_type
{
  doc_string_set,
  doc_string_show,
  doc_string_description
};

/* A helper function which returns a documentation string for an
   object. */

static gdb::unique_xmalloc_ptr<char>
get_doc_string (PyObject *object, enum doc_string_type doc_type,
		const char *cmd_name)
{
  gdb::unique_xmalloc_ptr<char> result;

  PyObject *attr = nullptr;
  switch (doc_type)
    {
    case doc_string_set:
      attr = set_doc_cst;
      break;
    case doc_string_show:
      attr = show_doc_cst;
      break;
    case doc_string_description:
      attr = gdbpy_doc_cst;
      break;
    }
  gdb_assert (attr != nullptr);

  if (PyObject_HasAttr (object, attr))
    {
      gdbpy_ref<> ds_obj (PyObject_GetAttr (object, attr));

      if (ds_obj != NULL && gdbpy_is_string (ds_obj.get ()))
	{
	  result = python_string_to_host_string (ds_obj.get ());
	  if (result == NULL)
	    gdbpy_print_stack ();
	  else if (doc_type == doc_string_description)
	    result = gdbpy_fix_doc_string_indentation (std::move (result));
	}
    }

  if (result == nullptr)
    {
      if (doc_type == doc_string_description)
	result.reset (xstrdup (_ ("This command is not documented.")));
      else
	{
	  if (doc_type == doc_string_show)
	    result
	      = xstrprintf (_ ("Show the current value of '%s'."), cmd_name);
	  else
	    result
	      = xstrprintf (_ ("Set the current value of '%s'."), cmd_name);
	}
    }
  return result;
}

/* Helper function which will execute a METHOD in OBJ passing the
   argument ARG.  ARG can be NULL.  METHOD should return a Python
   string.  If this function returns NULL, there has been an error and
   the appropriate exception set.  */
static gdb::unique_xmalloc_ptr<char>
call_doc_function (PyObject *obj, PyObject *method, PyObject *arg)
{
  gdb::unique_xmalloc_ptr<char> data;
  gdbpy_ref<> result (PyObject_CallMethodObjArgs (obj, method, arg, NULL));

  if (result == NULL)
    return NULL;

  if (gdbpy_is_string (result.get ()))
    {
      data = python_string_to_host_string (result.get ());
      if (!data)
	return NULL;
    }
  else
    {
      PyErr_SetString (PyExc_RuntimeError,
		       _ ("Parameter must return a string value."));
      return NULL;
    }

  return data;
}

/* A callback function that is registered against the respective
   add_setshow_* set_doc prototype.  This function calls the Python function
   "get_set_string" if it exists, which will return a string.  That string
   is then printed.  If "get_set_string" does not exist, or returns an
   empty string, then nothing is printed.  */
static void
get_set_value (const char *args, int from_tty, struct cmd_list_element *c)
{
  PyObject *obj = (PyObject *) c->context ();
  gdb::unique_xmalloc_ptr<char> set_doc_string;

  gdbpy_enter enter_py;
  gdbpy_ref<> set_doc_func (PyUnicode_FromString ("get_set_string"));

  if (set_doc_func == NULL)
    {
      gdbpy_print_stack ();
      return;
    }

  if (PyObject_HasAttr (obj, set_doc_func.get ()))
    {
      set_doc_string = call_doc_function (obj, set_doc_func.get (), NULL);
      if (!set_doc_string)
	gdbpy_handle_exception ();
    }

  const char *str = set_doc_string.get ();
  if (str != nullptr && str[0] != '\0')
    gdb_printf ("%s\n", str);
}

/* A callback function that is registered against the respective
   add_setshow_* show_doc prototype.  This function will either call
   the Python function "get_show_string" or extract the Python
   attribute "show_doc" and return the contents as a string.  If
   neither exist, insert a string indicating the Parameter is not
   documented.  */
static void
get_show_value (struct ui_file *file, int from_tty, struct cmd_list_element *c,
		const char *value)
{
  PyObject *obj = (PyObject *) c->context ();
  gdb::unique_xmalloc_ptr<char> show_doc_string;

  gdbpy_enter enter_py;
  gdbpy_ref<> show_doc_func (PyUnicode_FromString ("get_show_string"));

  if (show_doc_func == NULL)
    {
      gdbpy_print_stack ();
      return;
    }

  if (PyObject_HasAttr (obj, show_doc_func.get ()))
    {
      gdbpy_ref<> val_obj (PyUnicode_FromString (value));

      if (val_obj == NULL)
	{
	  gdbpy_print_stack ();
	  return;
	}

      show_doc_string
	= call_doc_function (obj, show_doc_func.get (), val_obj.get ());
      if (!show_doc_string)
	{
	  gdbpy_print_stack ();
	  return;
	}

      gdb_printf (file, "%s\n", show_doc_string.get ());
    }
  else
    {
      /* If there is no 'get_show_string' callback then we want to show
	 something sensible here.  In older versions of GDB (< 7.3) we
	 didn't support 'get_show_string', and instead we just made use of
	 GDB's builtin use of the show_doc.  However, GDB's builtin
	 show_doc adjustment is not i18n friendly, so, instead, we just
	 print this generic string.  */
      std::string cmd_path = full_cmd_name_without_first_prefix (c);
      gdb_printf (file, _ ("The current value of '%s' is \"%s\".\n"),
		  cmd_path.c_str (), value);
    }
}

/* A helper function that dispatches to the appropriate add_setshow
   function.  */
static void
add_setshow_generic (enum var_types type, const literal_def *extra_literals,
		     enum command_class cmdclass,
		     gdb::unique_xmalloc_ptr<char> cmd_name,
		     parmpy_object *self, const char *set_doc,
		     const char *show_doc, const char *help_doc,
		     struct cmd_list_element **set_list,
		     struct cmd_list_element **show_list)
{
  set_show_commands commands;

  switch (type)
    {
    case var_boolean:
      commands = add_setshow_boolean_cmd (cmd_name.get (), cmdclass,
					  &self->value.boolval, set_doc,
					  show_doc, help_doc, get_set_value,
					  get_show_value, set_list, show_list);

      break;

    case var_auto_boolean:
      commands
	= add_setshow_auto_boolean_cmd (cmd_name.get (), cmdclass,
					&self->value.autoboolval, set_doc,
					show_doc, help_doc, get_set_value,
					get_show_value, set_list, show_list);
      break;

    case var_uinteger:
      commands
	= add_setshow_uinteger_cmd (cmd_name.get (), cmdclass,
				    &self->value.uintval, extra_literals,
				    set_doc, show_doc, help_doc, get_set_value,
				    get_show_value, set_list, show_list);
      break;

    case var_integer:
      commands
	= add_setshow_integer_cmd (cmd_name.get (), cmdclass,
				   &self->value.intval, extra_literals,
				   set_doc, show_doc, help_doc, get_set_value,
				   get_show_value, set_list, show_list);
      break;

    case var_pinteger:
      commands
	= add_setshow_pinteger_cmd (cmd_name.get (), cmdclass,
				    &self->value.intval, extra_literals,
				    set_doc, show_doc, help_doc, get_set_value,
				    get_show_value, set_list, show_list);
      break;

    case var_string:
      commands = add_setshow_string_cmd (cmd_name.get (), cmdclass,
					 self->value.stringval, set_doc,
					 show_doc, help_doc, get_set_value,
					 get_show_value, set_list, show_list);
      break;

    case var_string_noescape:
      commands = add_setshow_string_noescape_cmd (
	cmd_name.get (), cmdclass, self->value.stringval, set_doc, show_doc,
	help_doc, get_set_value, get_show_value, set_list, show_list);
      break;

    case var_optional_filename:
      commands = add_setshow_optional_filename_cmd (
	cmd_name.get (), cmdclass, self->value.stringval, set_doc, show_doc,
	help_doc, get_set_value, get_show_value, set_list, show_list);
      break;

    case var_filename:
      commands
	= add_setshow_filename_cmd (cmd_name.get (), cmdclass,
				    self->value.stringval, set_doc, show_doc,
				    help_doc, get_set_value, get_show_value,
				    set_list, show_list);
      break;

    case var_enum:
      /* Initialize the value, just in case.  */
      self->value.cstringval = self->enumeration[0];
      commands
	= add_setshow_enum_cmd (cmd_name.get (), cmdclass, self->enumeration,
				&self->value.cstringval, set_doc, show_doc,
				help_doc, get_set_value, get_show_value,
				set_list, show_list);
      break;

    default:
      gdb_assert_not_reached ("Unhandled parameter class.");
    }

  /* Register Python objects in both commands' context.  */
  commands.set->set_context (self);
  commands.show->set_context (self);

  /* We (unfortunately) currently leak the command name.  */
  cmd_name.release ();
}

/* A helper which computes enum values.  Returns 1 on success.  Returns 0 on
   error, with a python exception set.  */
static int
compute_enum_values (parmpy_object *self, PyObject *enum_values)
{
  Py_ssize_t size, i;

  if (!enum_values)
    {
      PyErr_SetString (PyExc_RuntimeError,
		       _ ("An enumeration is required for PARAM_ENUM."));
      return 0;
    }

  if (!PySequence_Check (enum_values))
    {
      PyErr_SetString (PyExc_RuntimeError,
		       _ ("The enumeration is not a sequence."));
      return 0;
    }

  size = PySequence_Size (enum_values);
  if (size < 0)
    return 0;
  if (size == 0)
    {
      PyErr_SetString (PyExc_RuntimeError, _ ("The enumeration is empty."));
      return 0;
    }

  gdb_argv holder (XCNEWVEC (char *, size + 1));
  char **enumeration = holder.get ();

  for (i = 0; i < size; ++i)
    {
      gdbpy_ref<> item (PySequence_GetItem (enum_values, i));

      if (item == NULL)
	return 0;
      if (!gdbpy_is_string (item.get ()))
	{
	  PyErr_SetString (PyExc_RuntimeError,
			   _ ("The enumeration item not a string."));
	  return 0;
	}
      enumeration[i] = python_string_to_host_string (item.get ()).release ();
      if (enumeration[i] == NULL)
	return 0;
    }

  self->enumeration = const_cast<const char **> (holder.release ());
  return 1;
}

/* Object initializer; sets up gdb-side structures for command.

   Use: __init__(NAME, CMDCLASS, PARMCLASS, [ENUM])

   NAME is the name of the parameter.  It may consist of multiple
   words, in which case the final word is the name of the new command,
   and earlier words must be prefix commands.

   CMDCLASS is the kind of command.  It should be one of the COMMAND_*
   constants defined in the gdb module.

   PARMCLASS is the type of the parameter.  It should be one of the
   PARAM_* constants defined in the gdb module.

   If PARMCLASS is PARAM_ENUM, then the final argument should be a
   collection of strings.  These strings are the valid values for this
   parameter.

   The documentation for the parameter is taken from the doc string
   for the python class.

   Returns -1 on error, with a python exception set.  */

static int
parmpy_init (PyObject *self, PyObject *args, PyObject *kwds)
{
  parmpy_object *obj = (parmpy_object *) self;
  const char *name;
  gdb::unique_xmalloc_ptr<char> set_doc, show_doc, doc;
  int parmclass, cmdtype;
  PyObject *enum_values = NULL;
  struct cmd_list_element **set_list, **show_list;
  const literal_def *extra_literals;
  enum var_types type;

  if (!PyArg_ParseTuple (args, "sii|O", &name, &cmdtype, &parmclass,
			 &enum_values))
    return -1;

  if (cmdtype != no_class && cmdtype != class_run && cmdtype != class_vars
      && cmdtype != class_stack && cmdtype != class_files
      && cmdtype != class_support && cmdtype != class_info
      && cmdtype != class_breakpoint && cmdtype != class_trace
      && cmdtype != class_obscure && cmdtype != class_maintenance)
    {
      PyErr_Format (PyExc_RuntimeError, _ ("Invalid command class argument."));
      return -1;
    }

  if (parmclass != param_boolean /* ARI: param_boolean */
      && parmclass != param_auto_boolean && parmclass != param_uinteger
      && parmclass != param_integer && parmclass != param_string
      && parmclass != param_string_noescape
      && parmclass != param_optional_filename && parmclass != param_filename
      && parmclass != param_zinteger && parmclass != param_zuinteger
      && parmclass != param_zuinteger_unlimited && parmclass != param_enum)
    {
      PyErr_SetString (PyExc_RuntimeError,
		       _ ("Invalid parameter class argument."));
      return -1;
    }

  if (enum_values && parmclass != param_enum)
    {
      PyErr_SetString (PyExc_RuntimeError,
		       _ ("Only PARAM_ENUM accepts a fourth argument."));
      return -1;
    }
  if (parmclass == param_enum)
    {
      if (!compute_enum_values (obj, enum_values))
	return -1;
    }
  else
    obj->enumeration = NULL;
  type = param_to_var[parmclass].type;
  extra_literals = param_to_var[parmclass].extra_literals;
  obj->type = type;
  obj->extra_literals = extra_literals;
  memset (&obj->value, 0, sizeof (obj->value));

  if (var_type_uses<std::string> (obj->type))
    obj->value.stringval = new std::string;

  gdb::unique_xmalloc_ptr<char> cmd_name
    = gdbpy_parse_command_name (name, &set_list, &setlist);
  if (cmd_name == nullptr)
    return -1;

  cmd_name = gdbpy_parse_command_name (name, &show_list, &showlist);
  if (cmd_name == nullptr)
    return -1;

  set_doc = get_doc_string (self, doc_string_set, name);
  show_doc = get_doc_string (self, doc_string_show, name);
  doc = get_doc_string (self, doc_string_description, cmd_name.get ());

  Py_INCREF (self);

  try
    {
      add_setshow_generic (type, extra_literals, (enum command_class) cmdtype,
			   std::move (cmd_name), obj, set_doc.get (),
			   show_doc.get (), doc.get (), set_list, show_list);
    }
  catch (const gdb_exception &except)
    {
      Py_DECREF (self);
      gdbpy_convert_exception (except);
      return -1;
    }

  return 0;
}

/* Deallocate function for a gdb.Parameter.  */

static void
parmpy_dealloc (PyObject *obj)
{
  parmpy_object *parm_obj = (parmpy_object *) obj;

  if (var_type_uses<std::string> (parm_obj->type))
    delete parm_obj->value.stringval;
}

/* Initialize the 'parameters' module.  */
int
gdbpy_initialize_parameters (void)
{
  int i;

  parmpy_object_type.tp_new = PyType_GenericNew;
  if (PyType_Ready (&parmpy_object_type) < 0)
    return -1;

  set_doc_cst = PyUnicode_FromString ("set_doc");
  if (!set_doc_cst)
    return -1;
  show_doc_cst = PyUnicode_FromString ("show_doc");
  if (!show_doc_cst)
    return -1;

  for (i = 0; parm_constants[i].name; ++i)
    {
      if (PyModule_AddIntConstant (gdb_module, parm_constants[i].name,
				   parm_constants[i].value)
	  < 0)
	return -1;
    }

  return gdb_pymodule_addobject (gdb_module, "Parameter",
				 (PyObject *) &parmpy_object_type);
}

PyTypeObject parmpy_object_type = {
  PyVarObject_HEAD_INIT (NULL, 0) "gdb.Parameter", /*tp_name*/
  sizeof (parmpy_object),			   /*tp_basicsize*/
  0,						   /*tp_itemsize*/
  parmpy_dealloc,				   /*tp_dealloc*/
  0,						   /*tp_print*/
  0,						   /*tp_getattr*/
  0,						   /*tp_setattr*/
  0,						   /*tp_compare*/
  0,						   /*tp_repr*/
  0,						   /*tp_as_number*/
  0,						   /*tp_as_sequence*/
  0,						   /*tp_as_mapping*/
  0,						   /*tp_hash */
  0,						   /*tp_call*/
  0,						   /*tp_str*/
  get_attr,					   /*tp_getattro*/
  set_attr,					   /*tp_setattro*/
  0,						   /*tp_as_buffer*/
  Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,	   /*tp_flags*/
  "GDB parameter object",			   /* tp_doc */
  0,						   /* tp_traverse */
  0,						   /* tp_clear */
  0,						   /* tp_richcompare */
  0,						   /* tp_weaklistoffset */
  0,						   /* tp_iter */
  0,						   /* tp_iternext */
  0,						   /* tp_methods */
  0,						   /* tp_members */
  0,						   /* tp_getset */
  0,						   /* tp_base */
  0,						   /* tp_dict */
  0,						   /* tp_descr_get */
  0,						   /* tp_descr_set */
  0,						   /* tp_dictoffset */
  parmpy_init,					   /* tp_init */
  0,						   /* tp_alloc */
};
