/* Python interface to values.

   Copyright (C) 2008-2022 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 "charset.h"
#include "value.h"
#include "language.h"
#include "target-float.h"
#include "valprint.h"
#include "infcall.h"
#include "expression.h"
#include "cp-abi.h"
#include "python.h"

#include "python-internal.h"

/* Even though Python scalar types directly map to host types, we use
   target types here to remain consistent with the values system in
   GDB (which uses target arithmetic).  */

/* Python's integer type corresponds to C's long type.  */
#define builtin_type_pyint \
  builtin_type (gdbpy_enter::get_gdbarch ())->builtin_long

/* Python's float type corresponds to C's double type.  */
#define builtin_type_pyfloat \
  builtin_type (gdbpy_enter::get_gdbarch ())->builtin_double

/* Python's long type corresponds to C's long long type.  */
#define builtin_type_pylong \
  builtin_type (gdbpy_enter::get_gdbarch ())->builtin_long_long

/* Python's long type corresponds to C's long long type.  Unsigned version.  */
#define builtin_type_upylong builtin_type \
  (gdbpy_enter::get_gdbarch ())->builtin_unsigned_long_long

#define builtin_type_pybool \
  language_bool_type (current_language, gdbpy_enter::get_gdbarch ())

#define builtin_type_pychar \
  language_string_char_type (current_language, gdbpy_enter::get_gdbarch ())

struct value_object {
  PyObject_HEAD
  struct value_object *next;
  struct value_object *prev;
  struct value *value;
  PyObject *address;
  PyObject *type;
  PyObject *dynamic_type;
};

/* List of all values which are currently exposed to Python. It is
   maintained so that when an objfile is discarded, preserve_values
   can copy the values' types if needed.  */
/* This variable is unnecessarily initialized to NULL in order to
   work around a linker bug on MacOS.  */
static value_object *values_in_python = NULL;

/* Clear out an old GDB value stored within SELF, and reset the fields to
   nullptr.  This should be called when a gdb.Value is deallocated, and
   also if a gdb.Value is reinitialized with a new value.  */

static void
valpy_clear_value (value_object *self)
{
  /* Indicate we are no longer interested in the value object.  */
  value_decref (self->value);
  self->value = nullptr;

  Py_CLEAR (self->address);
  Py_CLEAR (self->type);
  Py_CLEAR (self->dynamic_type);
}

/* Called by the Python interpreter when deallocating a value object.  */
static void
valpy_dealloc (PyObject *obj)
{
  value_object *self = (value_object *) obj;

  /* If SELF failed to initialize correctly then it may not have a value
     contained within it.  */
  if (self->value != nullptr)
    {
      /* Remove SELF from the global list of values.  */
      if (self->prev != nullptr)
	self->prev->next = self->next;
      else
	{
	  gdb_assert (values_in_python == self);
	  values_in_python = self->next;
	}
      if (self->next != nullptr)
	self->next->prev = self->prev;

      /* Release the value object and any cached Python objects.  */
      valpy_clear_value (self);
    }

  Py_TYPE (self)->tp_free (self);
}

/* Helper to push a gdb.Value object on to the global list of values.  If
   VALUE_OBJ is already on the lit then this does nothing.  */

static void
note_value (value_object *value_obj)
{
  if (value_obj->next == nullptr)
    {
      gdb_assert (value_obj->prev == nullptr);
      value_obj->next = values_in_python;
      if (value_obj->next != nullptr)
	value_obj->next->prev = value_obj;
      values_in_python = value_obj;
    }
}

/* Convert a python object OBJ with type TYPE to a gdb value.  The
   python object in question must conform to the python buffer
   protocol.  On success, return the converted value, otherwise
   nullptr.  */

static struct value *
convert_buffer_and_type_to_value (PyObject *obj, struct type *type)
{
  Py_buffer_up buffer_up;
  Py_buffer py_buf;

  if (PyObject_CheckBuffer (obj) 
      && PyObject_GetBuffer (obj, &py_buf, PyBUF_SIMPLE) == 0)
    {
      /* Got a buffer, py_buf, out of obj.  Cause it to be released
	 when it goes out of scope.  */
      buffer_up.reset (&py_buf);
    }
  else
    {
      PyErr_SetString (PyExc_TypeError,
		       _("Object must support the python buffer protocol."));
      return nullptr;
    }

  if (type->length () > py_buf.len)
    {
      PyErr_SetString (PyExc_ValueError,
		       _("Size of type is larger than that of buffer object."));
      return nullptr;
    }

  return value_from_contents (type, (const gdb_byte *) py_buf.buf);
}

/* Implement gdb.Value.__init__.  */

static int
valpy_init (PyObject *self, PyObject *args, PyObject *kwds)
{
  static const char *keywords[] = { "val", "type", NULL };
  PyObject *val_obj = nullptr;
  PyObject *type_obj = nullptr;

  if (!gdb_PyArg_ParseTupleAndKeywords (args, kwds, "O|O", keywords,
					&val_obj, &type_obj))
    return -1;

  struct type *type = nullptr;
  if (type_obj != nullptr && type_obj != Py_None)
    {
      type = type_object_to_type (type_obj);
      if (type == nullptr)
	{
	  PyErr_SetString (PyExc_TypeError,
			   _("type argument must be a gdb.Type."));
	  return -1;
	}
    }

  struct value *value;
  if (type == nullptr)
    value = convert_value_from_python (val_obj);
  else
    value = convert_buffer_and_type_to_value (val_obj, type);
  if (value == nullptr)
    {
      gdb_assert (PyErr_Occurred ());
      return -1;
    }

  /* There might be a previous value here.  */
  value_object *value_obj = (value_object *) self;
  if (value_obj->value != nullptr)
    valpy_clear_value (value_obj);

  /* Store the value into this Python object.  */
  value_obj->value = release_value (value).release ();

  /* Ensure that this gdb.Value is in the set of all gdb.Value objects.  If
     we are already in the set then this is call does nothing.  */
  note_value (value_obj);

  return 0;
}

/* Iterate over all the Value objects, calling preserve_one_value on
   each.  */
void
gdbpy_preserve_values (const struct extension_language_defn *extlang,
		       struct objfile *objfile, htab_t copied_types)
{
  value_object *iter;

  for (iter = values_in_python; iter; iter = iter->next)
    preserve_one_value (iter->value, objfile, copied_types);
}

/* Given a value of a pointer type, apply the C unary * operator to it.  */
static PyObject *
valpy_dereference (PyObject *self, PyObject *args)
{
  PyObject *result = NULL;

  try
    {
      struct value *res_val;
      scoped_value_mark free_values;

      res_val = value_ind (((value_object *) self)->value);
      result = value_to_value_object (res_val);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return result;
}

/* Given a value of a pointer type or a reference type, return the value
   referenced. The difference between this function and valpy_dereference is
   that the latter applies * unary operator to a value, which need not always
   result in the value referenced. For example, for a value which is a reference
   to an 'int' pointer ('int *'), valpy_dereference will result in a value of
   type 'int' while valpy_referenced_value will result in a value of type
   'int *'.  */

static PyObject *
valpy_referenced_value (PyObject *self, PyObject *args)
{
  PyObject *result = NULL;

  try
    {
      struct value *self_val, *res_val;
      scoped_value_mark free_values;

      self_val = ((value_object *) self)->value;
      switch (check_typedef (value_type (self_val))->code ())
	{
	case TYPE_CODE_PTR:
	  res_val = value_ind (self_val);
	  break;
	case TYPE_CODE_REF:
	case TYPE_CODE_RVALUE_REF:
	  res_val = coerce_ref (self_val);
	  break;
	default:
	  error(_("Trying to get the referenced value from a value which is "
		  "neither a pointer nor a reference."));
	}

      result = value_to_value_object (res_val);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return result;
}

/* Return a value which is a reference to the value.  */

static PyObject *
valpy_reference_value (PyObject *self, PyObject *args, enum type_code refcode)
{
  PyObject *result = NULL;

  try
    {
      struct value *self_val;
      scoped_value_mark free_values;

      self_val = ((value_object *) self)->value;
      result = value_to_value_object (value_ref (self_val, refcode));
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return result;
}

static PyObject *
valpy_lvalue_reference_value (PyObject *self, PyObject *args)
{
  return valpy_reference_value (self, args, TYPE_CODE_REF);
}

static PyObject *
valpy_rvalue_reference_value (PyObject *self, PyObject *args)
{
  return valpy_reference_value (self, args, TYPE_CODE_RVALUE_REF);
}

/* Return a "const" qualified version of the value.  */

static PyObject *
valpy_const_value (PyObject *self, PyObject *args)
{
  PyObject *result = NULL;

  try
    {
      struct value *self_val, *res_val;
      scoped_value_mark free_values;

      self_val = ((value_object *) self)->value;
      res_val = make_cv_value (1, 0, self_val);
      result = value_to_value_object (res_val);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return result;
}

/* Return "&value".  */
static PyObject *
valpy_get_address (PyObject *self, void *closure)
{
  value_object *val_obj = (value_object *) self;

  if (!val_obj->address)
    {
      try
	{
	  struct value *res_val;
	  scoped_value_mark free_values;

	  res_val = value_addr (val_obj->value);
	  val_obj->address = value_to_value_object (res_val);
	}
      catch (const gdb_exception &except)
	{
	  val_obj->address = Py_None;
	  Py_INCREF (Py_None);
	}
    }

  Py_XINCREF (val_obj->address);

  return val_obj->address;
}

/* Return type of the value.  */
static PyObject *
valpy_get_type (PyObject *self, void *closure)
{
  value_object *obj = (value_object *) self;

  if (!obj->type)
    {
      obj->type = type_to_type_object (value_type (obj->value));
      if (!obj->type)
	return NULL;
    }
  Py_INCREF (obj->type);
  return obj->type;
}

/* Return dynamic type of the value.  */

static PyObject *
valpy_get_dynamic_type (PyObject *self, void *closure)
{
  value_object *obj = (value_object *) self;
  struct type *type = NULL;

  if (obj->dynamic_type != NULL)
    {
      Py_INCREF (obj->dynamic_type);
      return obj->dynamic_type;
    }

  try
    {
      struct value *val = obj->value;
      scoped_value_mark free_values;

      type = value_type (val);
      type = check_typedef (type);

      if (type->is_pointer_or_reference ()
	  && (type->target_type ()->code () == TYPE_CODE_STRUCT))
	{
	  struct value *target;
	  int was_pointer = type->code () == TYPE_CODE_PTR;

	  if (was_pointer)
	    target = value_ind (val);
	  else
	    target = coerce_ref (val);
	  type = value_rtti_type (target, NULL, NULL, NULL);

	  if (type)
	    {
	      if (was_pointer)
		type = lookup_pointer_type (type);
	      else
		type = lookup_lvalue_reference_type (type);
	    }
	}
      else if (type->code () == TYPE_CODE_STRUCT)
	type = value_rtti_type (val, NULL, NULL, NULL);
      else
	{
	  /* Re-use object's static type.  */
	  type = NULL;
	}
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  if (type == NULL)
    obj->dynamic_type = valpy_get_type (self, NULL);
  else
    obj->dynamic_type = type_to_type_object (type);

  Py_XINCREF (obj->dynamic_type);
  return obj->dynamic_type;
}

/* Implementation of gdb.Value.lazy_string ([encoding] [, length]) ->
   string.  Return a PyObject representing a lazy_string_object type.
   A lazy string is a pointer to a string with an optional encoding and
   length.  If ENCODING is not given, encoding is set to None.  If an
   ENCODING is provided the encoding parameter is set to ENCODING, but
   the string is not encoded.
   If LENGTH is provided then the length parameter is set to LENGTH.
   Otherwise if the value is an array of known length then the array's length
   is used.  Otherwise the length will be set to -1 (meaning first null of
   appropriate with).

   Note: In order to not break any existing uses this allows creating
   lazy strings from anything.  PR 20769.  E.g.,
   gdb.parse_and_eval("my_int_variable").lazy_string().
   "It's easier to relax restrictions than it is to impose them after the
   fact."  So we should be flagging any unintended uses as errors, but it's
   perhaps too late for that.  */

static PyObject *
valpy_lazy_string (PyObject *self, PyObject *args, PyObject *kw)
{
  gdb_py_longest length = -1;
  struct value *value = ((value_object *) self)->value;
  const char *user_encoding = NULL;
  static const char *keywords[] = { "encoding", "length", NULL };
  PyObject *str_obj = NULL;

  if (!gdb_PyArg_ParseTupleAndKeywords (args, kw, "|s" GDB_PY_LL_ARG,
					keywords, &user_encoding, &length))
    return NULL;

  if (length < -1)
    {
      PyErr_SetString (PyExc_ValueError, _("Invalid length."));
      return NULL;
    }

  try
    {
      scoped_value_mark free_values;
      struct type *type, *realtype;
      CORE_ADDR addr;

      type = value_type (value);
      realtype = check_typedef (type);

      switch (realtype->code ())
	{
	case TYPE_CODE_ARRAY:
	  {
	    LONGEST array_length = -1;
	    LONGEST low_bound, high_bound;

	    /* PR 20786: There's no way to specify an array of length zero.
	       Record a length of [0,-1] which is how Ada does it.  Anything
	       we do is broken, but this one possible solution.  */
	    if (get_array_bounds (realtype, &low_bound, &high_bound))
	      array_length = high_bound - low_bound + 1;
	    if (length == -1)
	      length = array_length;
	    else if (array_length == -1)
	      {
		type = lookup_array_range_type (realtype->target_type (),
						0, length - 1);
	      }
	    else if (length != array_length)
	      {
		/* We need to create a new array type with the
		   specified length.  */
		if (length > array_length)
		  error (_("Length is larger than array size."));
		type = lookup_array_range_type (realtype->target_type (),
						low_bound,
						low_bound + length - 1);
	      }
	    addr = value_address (value);
	    break;
	  }
	case TYPE_CODE_PTR:
	  /* If a length is specified we defer creating an array of the
	     specified width until we need to.  */
	  addr = value_as_address (value);
	  break;
	default:
	  /* Should flag an error here.  PR 20769.  */
	  addr = value_address (value);
	  break;
	}

      str_obj = gdbpy_create_lazy_string_object (addr, length, user_encoding,
						 type);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return str_obj;
}

/* Implementation of gdb.Value.string ([encoding] [, errors]
   [, length]) -> string.  Return Unicode string with value contents.
   If ENCODING is not given, the string is assumed to be encoded in
   the target's charset.  If LENGTH is provided, only fetch string to
   the length provided.  */

static PyObject *
valpy_string (PyObject *self, PyObject *args, PyObject *kw)
{
  int length = -1;
  gdb::unique_xmalloc_ptr<gdb_byte> buffer;
  struct value *value = ((value_object *) self)->value;
  const char *encoding = NULL;
  const char *errors = NULL;
  const char *user_encoding = NULL;
  const char *la_encoding = NULL;
  struct type *char_type;
  static const char *keywords[] = { "encoding", "errors", "length", NULL };

  if (!gdb_PyArg_ParseTupleAndKeywords (args, kw, "|ssi", keywords,
					&user_encoding, &errors, &length))
    return NULL;

  try
    {
      c_get_string (value, &buffer, &length, &char_type, &la_encoding);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  encoding = (user_encoding && *user_encoding) ? user_encoding : la_encoding;
  return PyUnicode_Decode ((const char *) buffer.get (),
			   length * char_type->length (),
			   encoding, errors);
}

/* Given a Python object, copy its truth value to a C bool (the value
   pointed by dest).
   If src_obj is NULL, then *dest is not modified.

   Return true in case of success (including src_obj being NULL), false
   in case of error.  */

static bool
copy_py_bool_obj (bool *dest, PyObject *src_obj)
{
  if (src_obj)
    {
      int cmp = PyObject_IsTrue (src_obj);
      if (cmp < 0)
	return false;
      *dest = cmp;
    }

  return true;
}

/* Implementation of gdb.Value.format_string (...) -> string.
   Return Unicode string with value contents formatted using the
   keyword-only arguments.  */

static PyObject *
valpy_format_string (PyObject *self, PyObject *args, PyObject *kw)
{
  static const char *keywords[] =
    {
      /* Basic C/C++ options.  */
      "raw",			/* See the /r option to print.  */
      "pretty_arrays",		/* See set print array on|off.  */
      "pretty_structs",		/* See set print pretty on|off.  */
      "array_indexes",		/* See set print array-indexes on|off.  */
      "symbols",		/* See set print symbol on|off.  */
      "unions",			/* See set print union on|off.  */
      "address",		/* See set print address on|off.  */
      "styling",		/* Should we apply styling.  */
      "nibbles",		/* See set print nibbles on|off.  */
      "summary",		/* Summary mode for non-scalars.  */
      /* C++ options.  */
      "deref_refs",		/* No corresponding setting.  */
      "actual_objects",		/* See set print object on|off.  */
      "static_members",		/* See set print static-members on|off.  */
      /* C non-bool options.  */
      "max_elements", 		/* See set print elements N.  */
      "max_depth",		/* See set print max-depth N.  */
      "repeat_threshold",	/* See set print repeats.  */
      "format",			/* The format passed to the print command.  */
      NULL
    };

  /* This function has too many arguments to be useful as positionals, so
     the user should specify them all as keyword arguments.
     Python 3.3 and later have a way to specify it (both in C and Python
     itself), but we could be compiled with older versions, so we just
     check that the args tuple is empty.  */
  Py_ssize_t positional_count = PyObject_Length (args);
  if (positional_count < 0)
    return NULL;
  else if (positional_count > 0)
    {
      /* This matches the error message that Python 3.3 raises when
	 passing positionals to functions expecting keyword-only
	 arguments.  */
      PyErr_Format (PyExc_TypeError,
		    "format_string() takes 0 positional arguments but %zu were given",
		    positional_count);
      return NULL;
    }

  struct value_print_options opts;
  gdbpy_get_print_options (&opts);
  opts.deref_ref = 0;

  /* We need objects for booleans as the "p" flag for bools is new in
     Python 3.3.  */
  PyObject *raw_obj = NULL;
  PyObject *pretty_arrays_obj = NULL;
  PyObject *pretty_structs_obj = NULL;
  PyObject *array_indexes_obj = NULL;
  PyObject *symbols_obj = NULL;
  PyObject *unions_obj = NULL;
  PyObject *address_obj = NULL;
  PyObject *styling_obj = Py_False;
  PyObject *nibbles_obj = NULL;
  PyObject *deref_refs_obj = NULL;
  PyObject *actual_objects_obj = NULL;
  PyObject *static_members_obj = NULL;
  PyObject *summary_obj = NULL;
  char *format = NULL;
  if (!gdb_PyArg_ParseTupleAndKeywords (args,
					kw,
					"|O!O!O!O!O!O!O!O!O!O!O!O!O!IIIs",
					keywords,
					&PyBool_Type, &raw_obj,
					&PyBool_Type, &pretty_arrays_obj,
					&PyBool_Type, &pretty_structs_obj,
					&PyBool_Type, &array_indexes_obj,
					&PyBool_Type, &symbols_obj,
					&PyBool_Type, &unions_obj,
					&PyBool_Type, &address_obj,
					&PyBool_Type, &styling_obj,
					&PyBool_Type, &nibbles_obj,
					&PyBool_Type, &summary_obj,
					&PyBool_Type, &deref_refs_obj,
					&PyBool_Type, &actual_objects_obj,
					&PyBool_Type, &static_members_obj,
					&opts.print_max,
					&opts.max_depth,
					&opts.repeat_count_threshold,
					&format))
    return NULL;

  /* Set boolean arguments.  */
  if (!copy_py_bool_obj (&opts.raw, raw_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.prettyformat_arrays, pretty_arrays_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.prettyformat_structs, pretty_structs_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.print_array_indexes, array_indexes_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.symbol_print, symbols_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.unionprint, unions_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.addressprint, address_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.nibblesprint, nibbles_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.deref_ref, deref_refs_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.objectprint, actual_objects_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.static_field_print, static_members_obj))
    return NULL;
  if (!copy_py_bool_obj (&opts.summary, summary_obj))
    return nullptr;

  /* Numeric arguments for which 0 means unlimited (which we represent as
     UINT_MAX).  Note that the max-depth numeric argument uses -1 as
     unlimited, and 0 is a valid choice.  */
  if (opts.print_max == 0)
    opts.print_max = UINT_MAX;
  if (opts.repeat_count_threshold == 0)
    opts.repeat_count_threshold = UINT_MAX;

  /* Other arguments.  */
  if (format != NULL)
    {
      if (strlen (format) == 1)
	opts.format = format[0];
      else
	{
	  /* Mimic the message on standard Python ones for similar
	     errors.  */
	  PyErr_SetString (PyExc_ValueError,
			   "a single character is required");
	  return NULL;
	}
    }

  string_file stb (PyObject_IsTrue (styling_obj));

  try
    {
      common_val_print (((value_object *) self)->value, &stb, 0,
			&opts, current_language);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return PyUnicode_Decode (stb.c_str (), stb.size (), host_charset (), NULL);
}

/* A helper function that implements the various cast operators.  */

static PyObject *
valpy_do_cast (PyObject *self, PyObject *args, enum exp_opcode op)
{
  PyObject *type_obj, *result = NULL;
  struct type *type;

  if (! PyArg_ParseTuple (args, "O", &type_obj))
    return NULL;

  type = type_object_to_type (type_obj);
  if (! type)
    {
      PyErr_SetString (PyExc_RuntimeError,
		       _("Argument must be a type."));
      return NULL;
    }

  try
    {
      struct value *val = ((value_object *) self)->value;
      struct value *res_val;
      scoped_value_mark free_values;

      if (op == UNOP_DYNAMIC_CAST)
	res_val = value_dynamic_cast (type, val);
      else if (op == UNOP_REINTERPRET_CAST)
	res_val = value_reinterpret_cast (type, val);
      else
	{
	  gdb_assert (op == UNOP_CAST);
	  res_val = value_cast (type, val);
	}

      result = value_to_value_object (res_val);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return result;
}

/* Implementation of the "cast" method.  */

static PyObject *
valpy_cast (PyObject *self, PyObject *args)
{
  return valpy_do_cast (self, args, UNOP_CAST);
}

/* Implementation of the "dynamic_cast" method.  */

static PyObject *
valpy_dynamic_cast (PyObject *self, PyObject *args)
{
  return valpy_do_cast (self, args, UNOP_DYNAMIC_CAST);
}

/* Implementation of the "reinterpret_cast" method.  */

static PyObject *
valpy_reinterpret_cast (PyObject *self, PyObject *args)
{
  return valpy_do_cast (self, args, UNOP_REINTERPRET_CAST);
}

static Py_ssize_t
valpy_length (PyObject *self)
{
  /* We don't support getting the number of elements in a struct / class.  */
  PyErr_SetString (PyExc_NotImplementedError,
		   _("Invalid operation on gdb.Value."));
  return -1;
}

/* Return 1 if the gdb.Field object FIELD is present in the value V.
   Returns 0 otherwise.  If any Python error occurs, -1 is returned.  */

static int
value_has_field (struct value *v, PyObject *field)
{
  struct type *parent_type, *val_type;
  enum type_code type_code;
  gdbpy_ref<> type_object (PyObject_GetAttrString (field, "parent_type"));
  int has_field = 0;

  if (type_object == NULL)
    return -1;

  parent_type = type_object_to_type (type_object.get ());
  if (parent_type == NULL)
    {
      PyErr_SetString (PyExc_TypeError,
		       _("'parent_type' attribute of gdb.Field object is not a"
			 "gdb.Type object."));
      return -1;
    }

  try
    {
      val_type = value_type (v);
      val_type = check_typedef (val_type);
      if (val_type->is_pointer_or_reference ())
	val_type = check_typedef (val_type->target_type ());

      type_code = val_type->code ();
      if ((type_code == TYPE_CODE_STRUCT || type_code == TYPE_CODE_UNION)
	  && types_equal (val_type, parent_type))
	has_field = 1;
      else
	has_field = 0;
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_SET_HANDLE_EXCEPTION (except);
    }

  return has_field;
}

/* Return the value of a flag FLAG_NAME in a gdb.Field object FIELD.
   Returns 1 if the flag value is true, 0 if it is false, and -1 if
   a Python error occurs.  */

static int
get_field_flag (PyObject *field, const char *flag_name)
{
  gdbpy_ref<> flag_object (PyObject_GetAttrString (field, flag_name));

  if (flag_object == NULL)
    return -1;

  return PyObject_IsTrue (flag_object.get ());
}

/* Return the "type" attribute of a gdb.Field object.
   Returns NULL on error, with a Python exception set.  */

static struct type *
get_field_type (PyObject *field)
{
  gdbpy_ref<> ftype_obj (PyObject_GetAttrString (field, "type"));
  struct type *ftype;

  if (ftype_obj == NULL)
    return NULL;
  ftype = type_object_to_type (ftype_obj.get ());
  if (ftype == NULL)
    PyErr_SetString (PyExc_TypeError,
		     _("'type' attribute of gdb.Field object is not a "
		       "gdb.Type object."));

  return ftype;
}

/* Given string name or a gdb.Field object corresponding to an element inside
   a structure, return its value object.  Returns NULL on error, with a python
   exception set.  */

static PyObject *
valpy_getitem (PyObject *self, PyObject *key)
{
  struct gdb_exception except;
  value_object *self_value = (value_object *) self;
  gdb::unique_xmalloc_ptr<char> field;
  struct type *base_class_type = NULL, *field_type = NULL;
  long bitpos = -1;
  PyObject *result = NULL;

  if (gdbpy_is_string (key))
    {
      field = python_string_to_host_string (key);
      if (field == NULL)
	return NULL;
    }
  else if (gdbpy_is_field (key))
    {
      int is_base_class, valid_field;

      valid_field = value_has_field (self_value->value, key);
      if (valid_field < 0)
	return NULL;
      else if (valid_field == 0)
	{
	  PyErr_SetString (PyExc_TypeError,
			   _("Invalid lookup for a field not contained in "
			     "the value."));

	  return NULL;
	}

      is_base_class = get_field_flag (key, "is_base_class");
      if (is_base_class < 0)
	return NULL;
      else if (is_base_class > 0)
	{
	  base_class_type = get_field_type (key);
	  if (base_class_type == NULL)
	    return NULL;
	}
      else
	{
	  gdbpy_ref<> name_obj (PyObject_GetAttrString (key, "name"));

	  if (name_obj == NULL)
	    return NULL;

	  if (name_obj != Py_None)
	    {
	      field = python_string_to_host_string (name_obj.get ());
	      if (field == NULL)
		return NULL;
	    }
	  else
	    {
	      if (!PyObject_HasAttrString (key, "bitpos"))
		{
		  PyErr_SetString (PyExc_AttributeError,
				   _("gdb.Field object has no name and no "
				     "'bitpos' attribute."));

		  return NULL;
		}
	      gdbpy_ref<> bitpos_obj (PyObject_GetAttrString (key, "bitpos"));
	      if (bitpos_obj == NULL)
		return NULL;
	      if (!gdb_py_int_as_long (bitpos_obj.get (), &bitpos))
		return NULL;

	      field_type = get_field_type (key);
	      if (field_type == NULL)
		return NULL;
	    }
	}
    }

  try
    {
      struct value *tmp = self_value->value;
      struct value *res_val = NULL;
      scoped_value_mark free_values;

      if (field)
	res_val = value_struct_elt (&tmp, {}, field.get (), NULL,
				    "struct/class/union");
      else if (bitpos >= 0)
	res_val = value_struct_elt_bitpos (&tmp, bitpos, field_type,
					   "struct/class/union");
      else if (base_class_type != NULL)
	{
	  struct type *val_type;

	  val_type = check_typedef (value_type (tmp));
	  if (val_type->code () == TYPE_CODE_PTR)
	    res_val = value_cast (lookup_pointer_type (base_class_type), tmp);
	  else if (val_type->code () == TYPE_CODE_REF)
	    res_val = value_cast (lookup_lvalue_reference_type (base_class_type),
				  tmp);
	  else if (val_type->code () == TYPE_CODE_RVALUE_REF)
	    res_val = value_cast (lookup_rvalue_reference_type (base_class_type),
				  tmp);
	  else
	    res_val = value_cast (base_class_type, tmp);
	}
      else
	{
	  /* Assume we are attempting an array access, and let the
	     value code throw an exception if the index has an invalid
	     type.  */
	  struct value *idx = convert_value_from_python (key);

	  if (idx != NULL)
	    {
	      /* Check the value's type is something that can be accessed via
		 a subscript.  */
	      struct type *type;

	      tmp = coerce_ref (tmp);
	      type = check_typedef (value_type (tmp));
	      if (type->code () != TYPE_CODE_ARRAY
		  && type->code () != TYPE_CODE_PTR)
		  error (_("Cannot subscript requested type."));
	      else
		res_val = value_subscript (tmp, value_as_long (idx));
	    }
	}

      if (res_val)
	result = value_to_value_object (res_val);
    }
  catch (gdb_exception &ex)
    {
      except = std::move (ex);
    }

  GDB_PY_HANDLE_EXCEPTION (except);

  return result;
}

static int
valpy_setitem (PyObject *self, PyObject *key, PyObject *value)
{
  PyErr_Format (PyExc_NotImplementedError,
		_("Setting of struct elements is not currently supported."));
  return -1;
}

/* Called by the Python interpreter to perform an inferior function
   call on the value.  Returns NULL on error, with a python exception set.  */
static PyObject *
valpy_call (PyObject *self, PyObject *args, PyObject *keywords)
{
  Py_ssize_t args_count;
  struct value *function = ((value_object *) self)->value;
  struct value **vargs = NULL;
  struct type *ftype = NULL;
  PyObject *result = NULL;

  try
    {
      ftype = check_typedef (value_type (function));
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  if (ftype->code () != TYPE_CODE_FUNC)
    {
      PyErr_SetString (PyExc_RuntimeError,
		       _("Value is not callable (not TYPE_CODE_FUNC)."));
      return NULL;
    }

  if (! PyTuple_Check (args))
    {
      PyErr_SetString (PyExc_TypeError,
		       _("Inferior arguments must be provided in a tuple."));
      return NULL;
    }

  args_count = PyTuple_Size (args);
  if (args_count > 0)
    {
      int i;

      vargs = XALLOCAVEC (struct value *, args_count);
      for (i = 0; i < args_count; i++)
	{
	  PyObject *item = PyTuple_GetItem (args, i);

	  if (item == NULL)
	    return NULL;

	  vargs[i] = convert_value_from_python (item);
	  if (vargs[i] == NULL)
	    return NULL;
	}
    }

  try
    {
      scoped_value_mark free_values;

      value *return_value
	= call_function_by_hand (function, NULL,
				 gdb::make_array_view (vargs, args_count));
      result = value_to_value_object (return_value);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return result;
}

/* Called by the Python interpreter to obtain string representation
   of the object.  */
static PyObject *
valpy_str (PyObject *self)
{
  struct value_print_options opts;

  gdbpy_get_print_options (&opts);
  opts.deref_ref = 0;

  string_file stb;

  try
    {
      common_val_print (((value_object *) self)->value, &stb, 0,
			&opts, current_language);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return PyUnicode_Decode (stb.c_str (), stb.size (), host_charset (), NULL);
}

/* Implements gdb.Value.is_optimized_out.  */
static PyObject *
valpy_get_is_optimized_out (PyObject *self, void *closure)
{
  struct value *value = ((value_object *) self)->value;
  int opt = 0;

  try
    {
      opt = value_optimized_out (value);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  if (opt)
    Py_RETURN_TRUE;

  Py_RETURN_FALSE;
}

/* Implements gdb.Value.is_lazy.  */
static PyObject *
valpy_get_is_lazy (PyObject *self, void *closure)
{
  struct value *value = ((value_object *) self)->value;
  int opt = 0;

  try
    {
      opt = value_lazy (value);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  if (opt)
    Py_RETURN_TRUE;

  Py_RETURN_FALSE;
}

/* Implements gdb.Value.fetch_lazy ().  */
static PyObject *
valpy_fetch_lazy (PyObject *self, PyObject *args)
{
  struct value *value = ((value_object *) self)->value;

  try
    {
      if (value_lazy (value))
	value_fetch_lazy (value);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  Py_RETURN_NONE;
}

/* Calculate and return the address of the PyObject as the value of
   the builtin __hash__ call.  */
static Py_hash_t
valpy_hash (PyObject *self)
{
  return (intptr_t) self;
}

enum valpy_opcode
{
  VALPY_ADD,
  VALPY_SUB,
  VALPY_MUL,
  VALPY_DIV,
  VALPY_REM,
  VALPY_POW,
  VALPY_LSH,
  VALPY_RSH,
  VALPY_BITAND,
  VALPY_BITOR,
  VALPY_BITXOR
};

/* If TYPE is a reference, return the target; otherwise return TYPE.  */
#define STRIP_REFERENCE(TYPE) \
  (TYPE_IS_REFERENCE (TYPE) ? ((TYPE)->target_type ()) : (TYPE))

/* Helper for valpy_binop.  Returns a value object which is the result
   of applying the operation specified by OPCODE to the given
   arguments.  Throws a GDB exception on error.  */

static PyObject *
valpy_binop_throw (enum valpy_opcode opcode, PyObject *self, PyObject *other)
{
  PyObject *result = NULL;

  struct value *arg1, *arg2;
  struct value *res_val = NULL;
  enum exp_opcode op = OP_NULL;
  int handled = 0;

  scoped_value_mark free_values;

  /* If the gdb.Value object is the second operand, then it will be
     passed to us as the OTHER argument, and SELF will be an entirely
     different kind of object, altogether.  Because of this, we can't
     assume self is a gdb.Value object and need to convert it from
     python as well.  */
  arg1 = convert_value_from_python (self);
  if (arg1 == NULL)
    return NULL;

  arg2 = convert_value_from_python (other);
  if (arg2 == NULL)
    return NULL;

  switch (opcode)
    {
    case VALPY_ADD:
      {
	struct type *ltype = value_type (arg1);
	struct type *rtype = value_type (arg2);

	ltype = check_typedef (ltype);
	ltype = STRIP_REFERENCE (ltype);
	rtype = check_typedef (rtype);
	rtype = STRIP_REFERENCE (rtype);

	handled = 1;
	if (ltype->code () == TYPE_CODE_PTR
	    && is_integral_type (rtype))
	  res_val = value_ptradd (arg1, value_as_long (arg2));
	else if (rtype->code () == TYPE_CODE_PTR
		 && is_integral_type (ltype))
	  res_val = value_ptradd (arg2, value_as_long (arg1));
	else
	  {
	    handled = 0;
	    op = BINOP_ADD;
	  }
      }
      break;
    case VALPY_SUB:
      {
	struct type *ltype = value_type (arg1);
	struct type *rtype = value_type (arg2);

	ltype = check_typedef (ltype);
	ltype = STRIP_REFERENCE (ltype);
	rtype = check_typedef (rtype);
	rtype = STRIP_REFERENCE (rtype);

	handled = 1;
	if (ltype->code () == TYPE_CODE_PTR
	    && rtype->code () == TYPE_CODE_PTR)
	  /* A ptrdiff_t for the target would be preferable here.  */
	  res_val = value_from_longest (builtin_type_pyint,
					value_ptrdiff (arg1, arg2));
	else if (ltype->code () == TYPE_CODE_PTR
		 && is_integral_type (rtype))
	  res_val = value_ptradd (arg1, - value_as_long (arg2));
	else
	  {
	    handled = 0;
	    op = BINOP_SUB;
	  }
      }
      break;
    case VALPY_MUL:
      op = BINOP_MUL;
      break;
    case VALPY_DIV:
      op = BINOP_DIV;
      break;
    case VALPY_REM:
      op = BINOP_REM;
      break;
    case VALPY_POW:
      op = BINOP_EXP;
      break;
    case VALPY_LSH:
      op = BINOP_LSH;
      break;
    case VALPY_RSH:
      op = BINOP_RSH;
      break;
    case VALPY_BITAND:
      op = BINOP_BITWISE_AND;
      break;
    case VALPY_BITOR:
      op = BINOP_BITWISE_IOR;
      break;
    case VALPY_BITXOR:
      op = BINOP_BITWISE_XOR;
      break;
    }

  if (!handled)
    {
      if (binop_user_defined_p (op, arg1, arg2))
	res_val = value_x_binop (arg1, arg2, op, OP_NULL, EVAL_NORMAL);
      else
	res_val = value_binop (arg1, arg2, op);
    }

  if (res_val)
    result = value_to_value_object (res_val);

  return result;
}

/* Returns a value object which is the result of applying the operation
   specified by OPCODE to the given arguments.  Returns NULL on error, with
   a python exception set.  */
static PyObject *
valpy_binop (enum valpy_opcode opcode, PyObject *self, PyObject *other)
{
  PyObject *result = NULL;

  try
    {
      result = valpy_binop_throw (opcode, self, other);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return result;
}

static PyObject *
valpy_add (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_ADD, self, other);
}

static PyObject *
valpy_subtract (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_SUB, self, other);
}

static PyObject *
valpy_multiply (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_MUL, self, other);
}

static PyObject *
valpy_divide (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_DIV, self, other);
}

static PyObject *
valpy_remainder (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_REM, self, other);
}

static PyObject *
valpy_power (PyObject *self, PyObject *other, PyObject *unused)
{
  /* We don't support the ternary form of pow.  I don't know how to express
     that, so let's just throw NotImplementedError to at least do something
     about it.  */
  if (unused != Py_None)
    {
      PyErr_SetString (PyExc_NotImplementedError,
		       "Invalid operation on gdb.Value.");
      return NULL;
    }

  return valpy_binop (VALPY_POW, self, other);
}

static PyObject *
valpy_negative (PyObject *self)
{
  PyObject *result = NULL;

  try
    {
      /* Perhaps overkill, but consistency has some virtue.  */
      scoped_value_mark free_values;
      struct value *val;

      val = value_neg (((value_object *) self)->value);
      result = value_to_value_object (val);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return result;
}

static PyObject *
valpy_positive (PyObject *self)
{
  return value_to_value_object (((value_object *) self)->value);
}

static PyObject *
valpy_absolute (PyObject *self)
{
  struct value *value = ((value_object *) self)->value;
  int isabs = 1;

  try
    {
      scoped_value_mark free_values;

      if (value_less (value, value_zero (value_type (value), not_lval)))
	isabs = 0;
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  if (isabs)
    return valpy_positive (self);
  else
    return valpy_negative (self);
}

/* Implements boolean evaluation of gdb.Value.  */
static int
valpy_nonzero (PyObject *self)
{
  struct gdb_exception except;
  value_object *self_value = (value_object *) self;
  struct type *type;
  int nonzero = 0; /* Appease GCC warning.  */

  try
    {
      type = check_typedef (value_type (self_value->value));

      if (is_integral_type (type) || type->code () == TYPE_CODE_PTR)
	nonzero = !!value_as_long (self_value->value);
      else if (is_floating_value (self_value->value))
	nonzero = !target_float_is_zero
	  (value_contents (self_value->value).data (), type);
      else
	/* All other values are True.  */
	nonzero = 1;
    }
  catch (gdb_exception &ex)
    {
      except = std::move (ex);
    }

  /* This is not documented in the Python documentation, but if this
     function fails, return -1 as slot_nb_nonzero does (the default
     Python nonzero function).  */
  GDB_PY_SET_HANDLE_EXCEPTION (except);

  return nonzero;
}

/* Implements ~ for value objects.  */
static PyObject *
valpy_invert (PyObject *self)
{
  struct value *val = NULL;

  try
    {
      val = value_complement (((value_object *) self)->value);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return value_to_value_object (val);
}

/* Implements left shift for value objects.  */
static PyObject *
valpy_lsh (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_LSH, self, other);
}

/* Implements right shift for value objects.  */
static PyObject *
valpy_rsh (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_RSH, self, other);
}

/* Implements bitwise and for value objects.  */
static PyObject *
valpy_and (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_BITAND, self, other);
}

/* Implements bitwise or for value objects.  */
static PyObject *
valpy_or (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_BITOR, self, other);
}

/* Implements bitwise xor for value objects.  */
static PyObject *
valpy_xor (PyObject *self, PyObject *other)
{
  return valpy_binop (VALPY_BITXOR, self, other);
}

/* Helper for valpy_richcompare.  Implements comparison operations for
   value objects.  Returns true/false on success.  Returns -1 with a
   Python exception set if a Python error is detected.  Throws a GDB
   exception on other errors (memory error, etc.).  */

static int
valpy_richcompare_throw (PyObject *self, PyObject *other, int op)
{
  int result;
  struct value *value_other;
  struct value *value_self;

  scoped_value_mark free_values;

  value_other = convert_value_from_python (other);
  if (value_other == NULL)
    return -1;

  value_self = ((value_object *) self)->value;

  switch (op)
    {
    case Py_LT:
      result = value_less (value_self, value_other);
      break;
    case Py_LE:
      result = value_less (value_self, value_other)
	|| value_equal (value_self, value_other);
      break;
    case Py_EQ:
      result = value_equal (value_self, value_other);
      break;
    case Py_NE:
      result = !value_equal (value_self, value_other);
      break;
    case Py_GT:
      result = value_less (value_other, value_self);
      break;
    case Py_GE:
      result = (value_less (value_other, value_self)
		|| value_equal (value_self, value_other));
      break;
    default:
      /* Can't happen.  */
      PyErr_SetString (PyExc_NotImplementedError,
		       _("Invalid operation on gdb.Value."));
      result = -1;
      break;
    }

  return result;
}


/* Implements comparison operations for value objects.  Returns NULL on error,
   with a python exception set.  */
static PyObject *
valpy_richcompare (PyObject *self, PyObject *other, int op)
{
  int result = 0;

  if (other == Py_None)
    /* Comparing with None is special.  From what I can tell, in Python
       None is smaller than anything else.  */
    switch (op) {
      case Py_LT:
      case Py_LE:
      case Py_EQ:
	Py_RETURN_FALSE;
      case Py_NE:
      case Py_GT:
      case Py_GE:
	Py_RETURN_TRUE;
      default:
	/* Can't happen.  */
	PyErr_SetString (PyExc_NotImplementedError,
			 _("Invalid operation on gdb.Value."));
	return NULL;
    }

  try
    {
      result = valpy_richcompare_throw (self, other, op);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  /* In this case, the Python exception has already been set.  */
  if (result < 0)
    return NULL;

  if (result == 1)
    Py_RETURN_TRUE;

  Py_RETURN_FALSE;
}

/* Implements conversion to long.  */
static PyObject *
valpy_long (PyObject *self)
{
  struct value *value = ((value_object *) self)->value;
  struct type *type = value_type (value);
  LONGEST l = 0;

  try
    {
      if (is_floating_value (value))
	{
	  type = builtin_type_pylong;
	  value = value_cast (type, value);
	}

      type = check_typedef (type);

      if (!is_integral_type (type)
	  && type->code () != TYPE_CODE_PTR)
	error (_("Cannot convert value to long."));

      l = value_as_long (value);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  if (type->is_unsigned ())
    return gdb_py_object_from_ulongest (l).release ();
  else
    return gdb_py_object_from_longest (l).release ();
}

/* Implements conversion to float.  */
static PyObject *
valpy_float (PyObject *self)
{
  struct value *value = ((value_object *) self)->value;
  struct type *type = value_type (value);
  double d = 0;

  try
    {
      type = check_typedef (type);

      if (type->code () == TYPE_CODE_FLT && is_floating_value (value))
	d = target_float_to_host_double (value_contents (value).data (), type);
      else if (type->code () == TYPE_CODE_INT)
	{
	  /* Note that valpy_long accepts TYPE_CODE_PTR and some
	     others here here -- but casting a pointer or bool to a
	     float seems wrong.  */
	  d = value_as_long (value);
	}
      else
	error (_("Cannot convert value to float."));
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return PyFloat_FromDouble (d);
}

/* Returns an object for a value which is released from the all_values chain,
   so its lifetime is not bound to the execution of a command.  */
PyObject *
value_to_value_object (struct value *val)
{
  value_object *val_obj;

  val_obj = PyObject_New (value_object, &value_object_type);
  if (val_obj != NULL)
    {
      val_obj->value = release_value (val).release ();
      val_obj->next = nullptr;
      val_obj->prev = nullptr;
      val_obj->address = NULL;
      val_obj->type = NULL;
      val_obj->dynamic_type = NULL;
      note_value (val_obj);
    }

  return (PyObject *) val_obj;
}

/* Returns an object for a value, but without releasing it from the
   all_values chain.  */
PyObject *
value_to_value_object_no_release (struct value *val)
{
  value_object *val_obj;

  val_obj = PyObject_New (value_object, &value_object_type);
  if (val_obj != NULL)
    {
      value_incref (val);
      val_obj->value = val;
      val_obj->next = nullptr;
      val_obj->prev = nullptr;
      val_obj->address = NULL;
      val_obj->type = NULL;
      val_obj->dynamic_type = NULL;
      note_value (val_obj);
    }

  return (PyObject *) val_obj;
}

/* Returns a borrowed reference to the struct value corresponding to
   the given value object.  */
struct value *
value_object_to_value (PyObject *self)
{
  value_object *real;

  if (! PyObject_TypeCheck (self, &value_object_type))
    return NULL;
  real = (value_object *) self;
  return real->value;
}

/* Try to convert a Python value to a gdb value.  If the value cannot
   be converted, set a Python exception and return NULL.  Returns a
   reference to a new value on the all_values chain.  */

struct value *
convert_value_from_python (PyObject *obj)
{
  struct value *value = NULL; /* -Wall */
  int cmp;

  gdb_assert (obj != NULL);

  try
    {
      if (PyBool_Check (obj))
	{
	  cmp = PyObject_IsTrue (obj);
	  if (cmp >= 0)
	    value = value_from_longest (builtin_type_pybool, cmp);
	}
      else if (PyLong_Check (obj))
	{
	  LONGEST l = PyLong_AsLongLong (obj);

	  if (PyErr_Occurred ())
	    {
	      /* If the error was an overflow, we can try converting to
		 ULONGEST instead.  */
	      if (PyErr_ExceptionMatches (PyExc_OverflowError))
		{
		  gdbpy_err_fetch fetched_error;
		  gdbpy_ref<> zero = gdb_py_object_from_longest (0);

		  /* Check whether obj is positive.  */
		  if (PyObject_RichCompareBool (obj, zero.get (), Py_GT) > 0)
		    {
		      ULONGEST ul;

		      ul = PyLong_AsUnsignedLongLong (obj);
		      if (! PyErr_Occurred ())
			value = value_from_ulongest (builtin_type_upylong, ul);
		    }
		  else
		    {
		      /* There's nothing we can do.  */
		      fetched_error.restore ();
		    }
		}
	    }
	  else
	    value = value_from_longest (builtin_type_pylong, l);
	}
      else if (PyFloat_Check (obj))
	{
	  double d = PyFloat_AsDouble (obj);

	  if (! PyErr_Occurred ())
	    value = value_from_host_double (builtin_type_pyfloat, d);
	}
      else if (gdbpy_is_string (obj))
	{
	  gdb::unique_xmalloc_ptr<char> s
	    = python_string_to_target_string (obj);
	  if (s != NULL)
	    value = value_cstring (s.get (), strlen (s.get ()),
				   builtin_type_pychar);
	}
      else if (PyObject_TypeCheck (obj, &value_object_type))
	value = value_copy (((value_object *) obj)->value);
      else if (gdbpy_is_lazy_string (obj))
	{
	  PyObject *result;

	  result = PyObject_CallMethodObjArgs (obj, gdbpy_value_cst,  NULL);
	  value = value_copy (((value_object *) result)->value);
	}
      else
	PyErr_Format (PyExc_TypeError,
		      _("Could not convert Python object: %S."), obj);
    }
  catch (const gdb_exception &except)
    {
      gdbpy_convert_exception (except);
      return NULL;
    }

  return value;
}

/* Returns value object in the ARGth position in GDB's history.  */
PyObject *
gdbpy_history (PyObject *self, PyObject *args)
{
  int i;
  struct value *res_val = NULL;	  /* Initialize to appease gcc warning.  */

  if (!PyArg_ParseTuple (args, "i", &i))
    return NULL;

  try
    {
      res_val = access_value_history (i);
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return value_to_value_object (res_val);
}

/* Add a gdb.Value into GDB's history, and return (as an integer) the
   position of the newly added value.  */
PyObject *
gdbpy_add_history (PyObject *self, PyObject *args)
{
  PyObject *value_obj;

  if (!PyArg_ParseTuple (args, "O", &value_obj))
    return nullptr;

  struct value *value = convert_value_from_python (value_obj);
  if (value == nullptr)
    return nullptr;

  try
    {
      int idx = record_latest_value (value);
      return gdb_py_object_from_longest (idx).release ();
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  return nullptr;
}

/* Return an integer, the number of items in GDB's history.  */

PyObject *
gdbpy_history_count (PyObject *self, PyObject *args)
{
  return gdb_py_object_from_ulongest (value_history_count ()).release ();
}

/* Return the value of a convenience variable.  */
PyObject *
gdbpy_convenience_variable (PyObject *self, PyObject *args)
{
  const char *varname;
  struct value *res_val = NULL;

  if (!PyArg_ParseTuple (args, "s", &varname))
    return NULL;

  try
    {
      struct internalvar *var = lookup_only_internalvar (varname);

      if (var != NULL)
	{
	  res_val = value_of_internalvar (gdbpy_enter::get_gdbarch (), var);
	  if (value_type (res_val)->code () == TYPE_CODE_VOID)
	    res_val = NULL;
	}
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  if (res_val == NULL)
    Py_RETURN_NONE;

  return value_to_value_object (res_val);
}

/* Set the value of a convenience variable.  */
PyObject *
gdbpy_set_convenience_variable (PyObject *self, PyObject *args)
{
  const char *varname;
  PyObject *value_obj;
  struct value *value = NULL;

  if (!PyArg_ParseTuple (args, "sO", &varname, &value_obj))
    return NULL;

  /* None means to clear the variable.  */
  if (value_obj != Py_None)
    {
      value = convert_value_from_python (value_obj);
      if (value == NULL)
	return NULL;
    }

  try
    {
      if (value == NULL)
	{
	  struct internalvar *var = lookup_only_internalvar (varname);

	  if (var != NULL)
	    clear_internalvar (var);
	}
      else
	{
	  struct internalvar *var = lookup_internalvar (varname);

	  set_internalvar (var, value);
	}
    }
  catch (const gdb_exception &except)
    {
      GDB_PY_HANDLE_EXCEPTION (except);
    }

  Py_RETURN_NONE;
}

/* Returns 1 in OBJ is a gdb.Value object, 0 otherwise.  */

int
gdbpy_is_value_object (PyObject *obj)
{
  return PyObject_TypeCheck (obj, &value_object_type);
}

int
gdbpy_initialize_values (void)
{
  if (PyType_Ready (&value_object_type) < 0)
    return -1;

  return gdb_pymodule_addobject (gdb_module, "Value",
				 (PyObject *) &value_object_type);
}



static gdb_PyGetSetDef value_object_getset[] = {
  { "address", valpy_get_address, NULL, "The address of the value.",
    NULL },
  { "is_optimized_out", valpy_get_is_optimized_out, NULL,
    "Boolean telling whether the value is optimized "
    "out (i.e., not available).",
    NULL },
  { "type", valpy_get_type, NULL, "Type of the value.", NULL },
  { "dynamic_type", valpy_get_dynamic_type, NULL,
    "Dynamic type of the value.", NULL },
  { "is_lazy", valpy_get_is_lazy, NULL,
    "Boolean telling whether the value is lazy (not fetched yet\n\
from the inferior).  A lazy value is fetched when needed, or when\n\
the \"fetch_lazy()\" method is called.", NULL },
  {NULL}  /* Sentinel */
};

static PyMethodDef value_object_methods[] = {
  { "cast", valpy_cast, METH_VARARGS, "Cast the value to the supplied type." },
  { "dynamic_cast", valpy_dynamic_cast, METH_VARARGS,
    "dynamic_cast (gdb.Type) -> gdb.Value\n\
Cast the value to the supplied type, as if by the C++ dynamic_cast operator."
  },
  { "reinterpret_cast", valpy_reinterpret_cast, METH_VARARGS,
    "reinterpret_cast (gdb.Type) -> gdb.Value\n\
Cast the value to the supplied type, as if by the C++\n\
reinterpret_cast operator."
  },
  { "dereference", valpy_dereference, METH_NOARGS, "Dereferences the value." },
  { "referenced_value", valpy_referenced_value, METH_NOARGS,
    "Return the value referenced by a TYPE_CODE_REF or TYPE_CODE_PTR value." },
  { "reference_value", valpy_lvalue_reference_value, METH_NOARGS,
    "Return a value of type TYPE_CODE_REF referencing this value." },
  { "rvalue_reference_value", valpy_rvalue_reference_value, METH_NOARGS,
    "Return a value of type TYPE_CODE_RVALUE_REF referencing this value." },
  { "const_value", valpy_const_value, METH_NOARGS,
    "Return a 'const' qualied version of the same value." },
  { "lazy_string", (PyCFunction) valpy_lazy_string,
    METH_VARARGS | METH_KEYWORDS,
    "lazy_string ([encoding]  [, length]) -> lazy_string\n\
Return a lazy string representation of the value." },
  { "string", (PyCFunction) valpy_string, METH_VARARGS | METH_KEYWORDS,
    "string ([encoding] [, errors] [, length]) -> string\n\
Return Unicode string representation of the value." },
  { "fetch_lazy", valpy_fetch_lazy, METH_NOARGS,
    "Fetches the value from the inferior, if it was lazy." },
  { "format_string", (PyCFunction) valpy_format_string,
    METH_VARARGS | METH_KEYWORDS,
    "format_string (...) -> string\n\
Return a string representation of the value using the specified\n\
formatting options" },
  {NULL}  /* Sentinel */
};

static PyNumberMethods value_object_as_number = {
  valpy_add,
  valpy_subtract,
  valpy_multiply,
  valpy_remainder,
  NULL,			      /* nb_divmod */
  valpy_power,		      /* nb_power */
  valpy_negative,	      /* nb_negative */
  valpy_positive,	      /* nb_positive */
  valpy_absolute,	      /* nb_absolute */
  valpy_nonzero,	      /* nb_nonzero */
  valpy_invert,		      /* nb_invert */
  valpy_lsh,		      /* nb_lshift */
  valpy_rsh,		      /* nb_rshift */
  valpy_and,		      /* nb_and */
  valpy_xor,		      /* nb_xor */
  valpy_or,		      /* nb_or */
  valpy_long,		      /* nb_int */
  NULL,			      /* reserved */
  valpy_float,		      /* nb_float */
  NULL,                       /* nb_inplace_add */
  NULL,                       /* nb_inplace_subtract */
  NULL,                       /* nb_inplace_multiply */
  NULL,                       /* nb_inplace_remainder */
  NULL,                       /* nb_inplace_power */
  NULL,                       /* nb_inplace_lshift */
  NULL,                       /* nb_inplace_rshift */
  NULL,                       /* nb_inplace_and */
  NULL,                       /* nb_inplace_xor */
  NULL,                       /* nb_inplace_or */
  NULL,                       /* nb_floor_divide */
  valpy_divide,               /* nb_true_divide */
  NULL,			      /* nb_inplace_floor_divide */
  NULL,			      /* nb_inplace_true_divide */
  valpy_long,		      /* nb_index */
};

static PyMappingMethods value_object_as_mapping = {
  valpy_length,
  valpy_getitem,
  valpy_setitem
};

PyTypeObject value_object_type = {
  PyVarObject_HEAD_INIT (NULL, 0)
  "gdb.Value",			  /*tp_name*/
  sizeof (value_object),	  /*tp_basicsize*/
  0,				  /*tp_itemsize*/
  valpy_dealloc,		  /*tp_dealloc*/
  0,				  /*tp_print*/
  0,				  /*tp_getattr*/
  0,				  /*tp_setattr*/
  0,				  /*tp_compare*/
  0,				  /*tp_repr*/
  &value_object_as_number,	  /*tp_as_number*/
  0,				  /*tp_as_sequence*/
  &value_object_as_mapping,	  /*tp_as_mapping*/
  valpy_hash,		          /*tp_hash*/
  valpy_call,	                  /*tp_call*/
  valpy_str,			  /*tp_str*/
  0,				  /*tp_getattro*/
  0,				  /*tp_setattro*/
  0,				  /*tp_as_buffer*/
  Py_TPFLAGS_DEFAULT | Py_TPFLAGS_CHECKTYPES
  | Py_TPFLAGS_BASETYPE,	  /*tp_flags*/
  "GDB value object",		  /* tp_doc */
  0,				  /* tp_traverse */
  0,				  /* tp_clear */
  valpy_richcompare,		  /* tp_richcompare */
  0,				  /* tp_weaklistoffset */
  0,				  /* tp_iter */
  0,				  /* tp_iternext */
  value_object_methods,		  /* tp_methods */
  0,				  /* tp_members */
  value_object_getset,		  /* tp_getset */
  0,				  /* tp_base */
  0,				  /* tp_dict */
  0,				  /* tp_descr_get */
  0,				  /* tp_descr_set */
  0,				  /* tp_dictoffset */
  valpy_init,			  /* tp_init */
  0,				  /* tp_alloc */
  PyType_GenericNew,		  /* tp_new */
};
