Support rvalue references in the gdb python module (includes doc/)
[deliverable/binutils-gdb.git] / gdb / python / py-xmethods.c
index 0a7fc381e61736678e4f5e459766e91143439418..e061da2192b1c7f25e9db29bc0dcda91c8b16f2f 100644 (file)
@@ -1,6 +1,6 @@
 /* Support for debug methods in Python.
 
-   Copyright (C) 2013-2015 Free Software Foundation, Inc.
+   Copyright (C) 2013-2017 Free Software Foundation, Inc.
 
    This file is part of GDB.
 
 
 #include "python.h"
 #include "python-internal.h"
+#include "py-ref.h"
 
 static const char enabled_field_name[] = "enabled";
 static const char match_method_name[] = "match";
 static const char get_arg_types_method_name[] = "get_arg_types";
-static const char invoke_method_name[] = "invoke";
+static const char get_result_type_method_name[] = "get_result_type";
 static const char matchers_attr_str[] = "xmethods";
 
 static PyObject *py_match_method_name = NULL;
 static PyObject *py_get_arg_types_method_name = NULL;
-static PyObject *py_invoke_method_name = NULL;
 
 struct gdbpy_worker_data
 {
@@ -52,19 +52,16 @@ void
 gdbpy_free_xmethod_worker_data (const struct extension_language_defn *extlang,
                                void *data)
 {
-  struct gdbpy_worker_data *worker_data = data;
-  struct cleanup *cleanups;
+  struct gdbpy_worker_data *worker_data = (struct gdbpy_worker_data *) data;
 
   gdb_assert (worker_data->worker != NULL && worker_data->this_type != NULL);
 
   /* We don't do much here, but we still need the GIL.  */
-  cleanups = ensure_python_env (get_current_arch (), current_language);
+  gdbpy_enter enter_py (get_current_arch (), current_language);
 
   Py_DECREF (worker_data->worker);
   Py_DECREF (worker_data->this_type);
   xfree (worker_data);
-
-  do_cleanups (cleanups);
 }
 
 /* Implementation of clone_xmethod_worker_data for Python.  */
@@ -73,13 +70,13 @@ void *
 gdbpy_clone_xmethod_worker_data (const struct extension_language_defn *extlang,
                                 void *data)
 {
-  struct gdbpy_worker_data *worker_data = data, *new_data;
-  struct cleanup *cleanups;
+  struct gdbpy_worker_data *worker_data
+    = (struct gdbpy_worker_data *) data, *new_data;
 
   gdb_assert (worker_data->worker != NULL && worker_data->this_type != NULL);
 
   /* We don't do much here, but we still need the GIL.  */
-  cleanups = ensure_python_env (get_current_arch (), current_language);
+  gdbpy_enter enter_py (get_current_arch (), current_language);
 
   new_data = XCNEW (struct gdbpy_worker_data);
   new_data->worker = worker_data->worker;
@@ -87,8 +84,6 @@ gdbpy_clone_xmethod_worker_data (const struct extension_language_defn *extlang,
   Py_INCREF (new_data->worker);
   Py_INCREF (new_data->this_type);
 
-  do_cleanups (cleanups);
-
   return new_data;
 }
 
@@ -99,59 +94,34 @@ static PyObject *
 invoke_match_method (PyObject *matcher, PyObject *py_obj_type,
                     const char *xmethod_name)
 {
-  PyObject *py_xmethod_name;
-  PyObject *match_method, *enabled_field, *match_result;
-  struct cleanup *cleanups;
   int enabled;
 
-  cleanups = make_cleanup (null_cleanup, NULL);
-
-  enabled_field = PyObject_GetAttrString (matcher, enabled_field_name);
+  gdbpy_ref<> enabled_field (PyObject_GetAttrString (matcher,
+                                                    enabled_field_name));
   if (enabled_field == NULL)
-    {
-      do_cleanups (cleanups);
-      return NULL;
-    }
-  make_cleanup_py_decref (enabled_field);
+    return NULL;
 
-  enabled = PyObject_IsTrue (enabled_field);
+  enabled = PyObject_IsTrue (enabled_field.get ());
   if (enabled == -1)
-    {
-      do_cleanups (cleanups);
-      return NULL;
-    }
+    return NULL;
   if (enabled == 0)
     {
       /* Return 'None' if the matcher is not enabled.  */
-      do_cleanups (cleanups);
       Py_RETURN_NONE;
     }
 
-  match_method = PyObject_GetAttrString (matcher, match_method_name);
+  gdbpy_ref<> match_method (PyObject_GetAttrString (matcher,
+                                                   match_method_name));
   if (match_method == NULL)
-    {
-      do_cleanups (cleanups);
-      return NULL;
-    }
-  make_cleanup_py_decref (match_method);
+    return NULL;
 
-  py_xmethod_name = PyString_FromString (xmethod_name);
+  gdbpy_ref<> py_xmethod_name (PyString_FromString (xmethod_name));
   if (py_xmethod_name == NULL)
-    {
-      do_cleanups (cleanups);
-      return NULL;
-    }
-  make_cleanup_py_decref (py_xmethod_name);
-
-  match_result = PyObject_CallMethodObjArgs (matcher,
-                                            py_match_method_name,
-                                            py_obj_type,
-                                            py_xmethod_name,
-                                            NULL);
-
-  do_cleanups (cleanups);
+    return NULL;
 
-  return match_result;
+  return PyObject_CallMethodObjArgs (matcher, py_match_method_name,
+                                    py_obj_type, py_xmethod_name.get (),
+                                    NULL);
 }
 
 /* Implementation of get_matching_xmethod_workers for Python.  */
@@ -162,33 +132,26 @@ gdbpy_get_matching_xmethod_workers
    struct type *obj_type, const char *method_name,
    xmethod_worker_vec **dm_vec)
 {
-  struct cleanup *cleanups;
   struct objfile *objfile;
   VEC (xmethod_worker_ptr) *worker_vec = NULL;
-  PyObject *py_type, *py_progspace;
-  PyObject *py_xmethod_matcher_list = NULL, *list_iter, *matcher;
+  PyObject *py_progspace;
 
   gdb_assert (obj_type != NULL && method_name != NULL);
 
-  cleanups = ensure_python_env (get_current_arch (), current_language);
+  gdbpy_enter enter_py (get_current_arch (), current_language);
 
-  py_type = type_to_type_object (obj_type);
+  gdbpy_ref<> py_type (type_to_type_object (obj_type));
   if (py_type == NULL)
     {
       gdbpy_print_stack ();
-      do_cleanups (cleanups);
-
       return EXT_LANG_RC_ERROR;
     }
-  make_cleanup_py_decref (py_type);
 
   /* Create an empty list of debug methods.  */
-  py_xmethod_matcher_list = PyList_New (0);
+  gdbpy_ref<> py_xmethod_matcher_list (PyList_New (0));
   if (py_xmethod_matcher_list == NULL)
     {
       gdbpy_print_stack ();
-      do_cleanups (cleanups);
-
       return EXT_LANG_RC_ERROR;
     }
 
@@ -198,28 +161,23 @@ gdbpy_get_matching_xmethod_workers
   ALL_OBJFILES (objfile)
     {
       PyObject *py_objfile = objfile_to_objfile_object (objfile);
-      PyObject *objfile_matchers, *temp = py_xmethod_matcher_list;
 
       if (py_objfile == NULL)
        {
          gdbpy_print_stack ();
-         Py_DECREF (py_xmethod_matcher_list);
-         do_cleanups (cleanups);
-
          return EXT_LANG_RC_ERROR;
        }
 
-      objfile_matchers = objfpy_get_xmethods (py_objfile, NULL);
-      py_xmethod_matcher_list = PySequence_Concat (temp, objfile_matchers);
-      Py_DECREF (temp);
-      Py_DECREF (objfile_matchers);
-      if (py_xmethod_matcher_list == NULL)
+      gdbpy_ref<> objfile_matchers (objfpy_get_xmethods (py_objfile, NULL));
+      gdbpy_ref<> temp (PySequence_Concat (py_xmethod_matcher_list.get (),
+                                          objfile_matchers.get ()));
+      if (temp == NULL)
        {
          gdbpy_print_stack ();
-         do_cleanups (cleanups);
-
          return EXT_LANG_RC_ERROR;
        }
+
+      py_xmethod_matcher_list = std::move (temp);
     }
 
   /* Gather debug methods matchers registered with the current program
@@ -227,26 +185,21 @@ gdbpy_get_matching_xmethod_workers
   py_progspace = pspace_to_pspace_object (current_program_space);
   if (py_progspace != NULL)
     {
-      PyObject *temp = py_xmethod_matcher_list;
-      PyObject *pspace_matchers = pspy_get_xmethods (py_progspace, NULL);
+      gdbpy_ref<> pspace_matchers (pspy_get_xmethods (py_progspace, NULL));
 
-      py_xmethod_matcher_list = PySequence_Concat (temp, pspace_matchers);
-      Py_DECREF (temp);
-      Py_DECREF (pspace_matchers);
-      if (py_xmethod_matcher_list == NULL)
+      gdbpy_ref<> temp (PySequence_Concat (py_xmethod_matcher_list.get (),
+                                          pspace_matchers.get ()));
+      if (temp == NULL)
        {
          gdbpy_print_stack ();
-         do_cleanups (cleanups);
-
          return EXT_LANG_RC_ERROR;
        }
+
+      py_xmethod_matcher_list = std::move (temp);
     }
   else
     {
       gdbpy_print_stack ();
-      Py_DECREF (py_xmethod_matcher_list);
-      do_cleanups (cleanups);
-
       return EXT_LANG_RC_ERROR;
     }
 
@@ -254,117 +207,96 @@ gdbpy_get_matching_xmethod_workers
   if (gdb_python_module != NULL
       && PyObject_HasAttrString (gdb_python_module, matchers_attr_str))
     {
-      PyObject *gdb_matchers;
-      PyObject *temp = py_xmethod_matcher_list;
-
-      gdb_matchers = PyObject_GetAttrString (gdb_python_module,
-                                            matchers_attr_str);
+      gdbpy_ref<> gdb_matchers (PyObject_GetAttrString (gdb_python_module,
+                                                       matchers_attr_str));
       if (gdb_matchers != NULL)
        {
-         py_xmethod_matcher_list = PySequence_Concat (temp, gdb_matchers);
-         Py_DECREF (temp);
-         Py_DECREF (gdb_matchers);
-         if (py_xmethod_matcher_list == NULL)
+         gdbpy_ref<> temp (PySequence_Concat (py_xmethod_matcher_list.get (),
+                                              gdb_matchers.get ()));
+         if (temp == NULL)
            {
              gdbpy_print_stack ();
-             do_cleanups (cleanups);
-
              return EXT_LANG_RC_ERROR;
            }
+
+         py_xmethod_matcher_list = std::move (temp);
        }
       else
        {
          gdbpy_print_stack ();
-         Py_DECREF (py_xmethod_matcher_list);
-         do_cleanups (cleanups);
-
          return EXT_LANG_RC_ERROR;
        }
     }
 
-  /* Safe to make a cleanup for py_xmethod_matcher_list now as it
-     will not change any more.  */
-  make_cleanup_py_decref (py_xmethod_matcher_list);
-
-  list_iter = PyObject_GetIter (py_xmethod_matcher_list);
+  gdbpy_ref<> list_iter (PyObject_GetIter (py_xmethod_matcher_list.get ()));
   if (list_iter == NULL)
     {
       gdbpy_print_stack ();
-      do_cleanups (cleanups);
-
       return EXT_LANG_RC_ERROR;
     }
-  while ((matcher = PyIter_Next (list_iter)) != NULL)
+  while (true)
     {
-      PyObject *match_result = invoke_match_method (matcher, py_type,
-                                                   method_name);
+      gdbpy_ref<> matcher (PyIter_Next (list_iter.get ()));
+      if (matcher == NULL)
+       {
+         if (PyErr_Occurred ())
+           {
+             gdbpy_print_stack ();
+             return EXT_LANG_RC_ERROR;
+           }
+         break;
+       }
+
+      gdbpy_ref<> match_result (invoke_match_method (matcher.get (),
+                                                    py_type.get (),
+                                                    method_name));
 
       if (match_result == NULL)
        {
          gdbpy_print_stack ();
-         Py_DECREF (matcher);
-         do_cleanups (cleanups);
-
          return EXT_LANG_RC_ERROR;
        }
       if (match_result == Py_None)
        ; /* This means there was no match.  */
-      else if (PySequence_Check (match_result))
+      else if (PySequence_Check (match_result.get ()))
        {
-         PyObject *iter = PyObject_GetIter (match_result);
-         PyObject *py_worker;
+         gdbpy_ref<> iter (PyObject_GetIter (match_result.get ()));
 
          if (iter == NULL)
            {
              gdbpy_print_stack ();
-             Py_DECREF (matcher);
-             Py_DECREF (match_result);
-             do_cleanups (cleanups);
-
              return EXT_LANG_RC_ERROR;
            }
-         while ((py_worker = PyIter_Next (iter)) != NULL)
+         while (true)
            {
              struct xmethod_worker *worker;
 
-             worker = new_python_xmethod_worker (py_worker, py_type);
+             gdbpy_ref<> py_worker (PyIter_Next (iter.get ()));
+             if (py_worker == NULL)
+               {
+                 if (PyErr_Occurred ())
+                   {
+                     gdbpy_print_stack ();
+                     return EXT_LANG_RC_ERROR;
+                   }
+                 break;
+               }
+
+             worker = new_python_xmethod_worker (py_worker.get (),
+                                                 py_type.get ());
              VEC_safe_push (xmethod_worker_ptr, worker_vec, worker);
-             Py_DECREF (py_worker);
-           }
-         Py_DECREF (iter);
-         /* Report any error that could have occurred while iterating.  */
-         if (PyErr_Occurred ())
-           {
-             gdbpy_print_stack ();
-             Py_DECREF (matcher);
-             Py_DECREF (match_result);
-             do_cleanups (cleanups);
-
-             return EXT_LANG_RC_ERROR;
            }
        }
       else
        {
          struct xmethod_worker *worker;
 
-         worker = new_python_xmethod_worker (match_result, py_type);
+         worker = new_python_xmethod_worker (match_result.get (),
+                                             py_type.get ());
          VEC_safe_push (xmethod_worker_ptr, worker_vec, worker);
        }
-
-      Py_DECREF (match_result);
-      Py_DECREF (matcher);
-    }
-  Py_DECREF (list_iter);
-  /* Report any error that could have occurred while iterating.  */
-  if (PyErr_Occurred ())
-    {
-      gdbpy_print_stack ();
-      do_cleanups (cleanups);
-
-      return EXT_LANG_RC_ERROR;
     }
 
-  do_cleanups (cleanups);
   *dm_vec = worker_vec;
 
   return EXT_LANG_RC_OK;
@@ -377,88 +309,88 @@ gdbpy_get_xmethod_arg_types (const struct extension_language_defn *extlang,
                             struct xmethod_worker *worker,
                             int *nargs, struct type ***arg_types)
 {
-  struct gdbpy_worker_data *worker_data = worker->data;
+  /* The gdbpy_enter object needs to be placed first, so that it's the last to
+     be destroyed.  */
+  gdbpy_enter enter_py (get_current_arch (), current_language);
+  struct gdbpy_worker_data *worker_data
+    = (struct gdbpy_worker_data *) worker->data;
   PyObject *py_worker = worker_data->worker;
-  PyObject *get_arg_types_method;
-  PyObject *py_argtype_list, *list_iter = NULL, *item;
-  struct cleanup *cleanups;
-  struct type **type_array, *obj_type;
+  struct type *obj_type;
   int i = 1, arg_count;
+  gdbpy_ref<> list_iter;
 
   /* Set nargs to -1 so that any premature return from this function returns
      an invalid/unusable number of arg types.  */
   *nargs = -1;
 
-  cleanups = ensure_python_env (get_current_arch (), current_language);
-
-  get_arg_types_method =  PyObject_GetAttrString (py_worker,
-                                                 get_arg_types_method_name);
+  gdbpy_ref<> get_arg_types_method
+    (PyObject_GetAttrString (py_worker, get_arg_types_method_name));
   if (get_arg_types_method == NULL)
     {
       gdbpy_print_stack ();
-      do_cleanups (cleanups);
-
       return EXT_LANG_RC_ERROR;
     }
-  make_cleanup_py_decref (get_arg_types_method);
 
-  py_argtype_list = PyObject_CallMethodObjArgs (py_worker,
-                                               py_get_arg_types_method_name,
-                                               NULL);
+  gdbpy_ref<> py_argtype_list
+    (PyObject_CallMethodObjArgs (py_worker, py_get_arg_types_method_name,
+                                NULL));
   if (py_argtype_list == NULL)
     {
       gdbpy_print_stack ();
-      do_cleanups (cleanups);
-
       return EXT_LANG_RC_ERROR;
     }
-  make_cleanup_py_decref (py_argtype_list);
+
   if (py_argtype_list == Py_None)
     arg_count = 0;
-  else if (PySequence_Check (py_argtype_list))
+  else if (PySequence_Check (py_argtype_list.get ()))
     {
-      arg_count = PySequence_Size (py_argtype_list);
+      arg_count = PySequence_Size (py_argtype_list.get ());
       if (arg_count == -1)
        {
          gdbpy_print_stack ();
-         do_cleanups (cleanups);
-
          return EXT_LANG_RC_ERROR;
        }
 
-      list_iter = PyObject_GetIter (py_argtype_list);
+      list_iter.reset (PyObject_GetIter (py_argtype_list.get ()));
       if (list_iter == NULL)
        {
          gdbpy_print_stack ();
-         do_cleanups (cleanups);
-
          return EXT_LANG_RC_ERROR;
        }
-      make_cleanup_py_decref (list_iter);
     }
   else
     arg_count = 1;
 
   /* Include the 'this' argument in the size.  */
-  type_array = XCNEWVEC (struct type *, arg_count + 1);
+  gdb::unique_xmalloc_ptr<struct type *> type_array
+    (XCNEWVEC (struct type *, arg_count + 1));
   i = 1;
   if (list_iter != NULL)
     {
-      while ((item = PyIter_Next (list_iter)) != NULL)
+      while (true)
        {
-         struct type *arg_type = type_object_to_type (item);
+         gdbpy_ref<> item (PyIter_Next (list_iter.get ()));
+         if (item == NULL)
+           {
+             if (PyErr_Occurred ())
+               {
+                 gdbpy_print_stack ();
+                 return EXT_LANG_RC_ERROR;
+               }
+             break;
+           }
 
-         Py_DECREF (item);
+         struct type *arg_type = type_object_to_type (item.get ());
          if (arg_type == NULL)
            {
              PyErr_SetString (PyExc_TypeError,
                               _("Arg type returned by the get_arg_types "
                                 "method of a debug method worker object is "
                                 "not a gdb.Type object."));
-             break;
+             return EXT_LANG_RC_ERROR;
            }
 
-         type_array[i] = arg_type;
+         (type_array.get ())[i] = arg_type;
          i++;
        }
     }
@@ -466,7 +398,7 @@ gdbpy_get_xmethod_arg_types (const struct extension_language_defn *extlang,
     {
       /* py_argtype_list is not actually a list but a single gdb.Type
         object.  */
-      struct type *arg_type = type_object_to_type (py_argtype_list);
+      struct type *arg_type = type_object_to_type (py_argtype_list.get ());
 
       if (arg_type == NULL)
        {
@@ -474,30 +406,124 @@ gdbpy_get_xmethod_arg_types (const struct extension_language_defn *extlang,
                           _("Arg type returned by the get_arg_types method "
                             "of an xmethod worker object is not a gdb.Type "
                             "object."));
+         return EXT_LANG_RC_ERROR;
        }
       else
        {
-         type_array[i] = arg_type;
+         (type_array.get ())[i] = arg_type;
          i++;
        }
     }
-  if (PyErr_Occurred ())
-    {
-      gdbpy_print_stack ();
-      do_cleanups (cleanups);
-      xfree (type_array);
-
-      return EXT_LANG_RC_ERROR;
-    }
 
   /* Add the type of 'this' as the first argument.  The 'this' pointer should
      be a 'const' value.  Hence, create a 'const' variant of the 'this' pointer
      type.  */
   obj_type = type_object_to_type (worker_data->this_type);
-  type_array[0] = make_cv_type (1, 0, lookup_pointer_type (obj_type), NULL);
+  (type_array.get ())[0] = make_cv_type (1, 0, lookup_pointer_type (obj_type),
+                                        NULL);
   *nargs = i;
-  *arg_types = type_array;
-  do_cleanups (cleanups);
+  *arg_types = type_array.release ();
+
+  return EXT_LANG_RC_OK;
+}
+
+/* Implementation of get_xmethod_result_type for Python.  */
+
+enum ext_lang_rc
+gdbpy_get_xmethod_result_type (const struct extension_language_defn *extlang,
+                              struct xmethod_worker *worker,
+                              struct value *obj,
+                              struct value **args, int nargs,
+                              struct type **result_type_ptr)
+{
+  struct gdbpy_worker_data *worker_data
+    = (struct gdbpy_worker_data *) worker->data;
+  PyObject *py_worker = worker_data->worker;
+  struct type *obj_type, *this_type;
+  int i;
+
+  gdbpy_enter enter_py (get_current_arch (), current_language);
+
+  /* First see if there is a get_result_type method.
+     If not this could be an old xmethod (pre 7.9.1).  */
+  gdbpy_ref<> get_result_type_method
+    (PyObject_GetAttrString (py_worker, get_result_type_method_name));
+  if (get_result_type_method == NULL)
+    {
+      PyErr_Clear ();
+      *result_type_ptr = NULL;
+      return EXT_LANG_RC_OK;
+    }
+
+  obj_type = check_typedef (value_type (obj));
+  this_type = check_typedef (type_object_to_type (worker_data->this_type));
+  if (TYPE_CODE (obj_type) == TYPE_CODE_PTR)
+    {
+      struct type *this_ptr = lookup_pointer_type (this_type);
+
+      if (!types_equal (obj_type, this_ptr))
+       obj = value_cast (this_ptr, obj);
+    }
+  else if (TYPE_IS_REFERENCE (obj_type))
+    {
+      struct type *this_ref
+        = lookup_reference_type (this_type, TYPE_CODE (obj_type));
+
+      if (!types_equal (obj_type, this_ref))
+       obj = value_cast (this_ref, obj);
+    }
+  else
+    {
+      if (!types_equal (obj_type, this_type))
+       obj = value_cast (this_type, obj);
+    }
+  gdbpy_ref<> py_value_obj (value_to_value_object (obj));
+  if (py_value_obj == NULL)
+    {
+      gdbpy_print_stack ();
+      return EXT_LANG_RC_ERROR;
+    }
+
+  gdbpy_ref<> py_arg_tuple (PyTuple_New (nargs + 1));
+  if (py_arg_tuple == NULL)
+    {
+      gdbpy_print_stack ();
+      return EXT_LANG_RC_ERROR;
+    }
+
+  /* PyTuple_SET_ITEM steals the reference of the element, hence the
+     release.  */
+  PyTuple_SET_ITEM (py_arg_tuple.get (), 0, py_value_obj.release ());
+
+  for (i = 0; i < nargs; i++)
+    {
+      PyObject *py_value_arg = value_to_value_object (args[i]);
+
+      if (py_value_arg == NULL)
+       {
+         gdbpy_print_stack ();
+         return EXT_LANG_RC_ERROR;
+       }
+      PyTuple_SET_ITEM (py_arg_tuple.get (), i + 1, py_value_arg);
+    }
+
+  gdbpy_ref<> py_result_type
+    (PyObject_CallObject (get_result_type_method.get (), py_arg_tuple.get ()));
+  if (py_result_type == NULL)
+    {
+      gdbpy_print_stack ();
+      return EXT_LANG_RC_ERROR;
+    }
+
+  *result_type_ptr = type_object_to_type (py_result_type.get ());
+  if (*result_type_ptr == NULL)
+    {
+      PyErr_SetString (PyExc_TypeError,
+                      _("Type returned by the get_result_type method of an"
+                        " xmethod worker object is not a gdb.Type object."));
+      gdbpy_print_stack ();
+      return EXT_LANG_RC_ERROR;
+    }
 
   return EXT_LANG_RC_OK;
 }
@@ -510,14 +536,13 @@ gdbpy_invoke_xmethod (const struct extension_language_defn *extlang,
                      struct value *obj, struct value **args, int nargs)
 {
   int i;
-  struct cleanup *cleanups;
-  PyObject *py_value_obj, *py_arg_tuple, *py_result;
   struct type *obj_type, *this_type;
   struct value *res = NULL;
-  struct gdbpy_worker_data *worker_data = worker->data;
+  struct gdbpy_worker_data *worker_data
+    = (struct gdbpy_worker_data *) worker->data;
   PyObject *xmethod_worker = worker_data->worker;
 
-  cleanups = ensure_python_env (get_current_arch (), current_language);
+  gdbpy_enter enter_py (get_current_arch (), current_language);
 
   obj_type = check_typedef (value_type (obj));
   this_type = check_typedef (type_object_to_type (worker_data->this_type));
@@ -528,9 +553,10 @@ gdbpy_invoke_xmethod (const struct extension_language_defn *extlang,
       if (!types_equal (obj_type, this_ptr))
        obj = value_cast (this_ptr, obj);
     }
-  else if (TYPE_CODE (obj_type) == TYPE_CODE_REF)
+  else if (TYPE_IS_REFERENCE (obj_type))
     {
-      struct type *this_ref = lookup_reference_type (this_type);
+      struct type *this_ref
+       = lookup_reference_type (this_type, TYPE_CODE (obj_type));
 
       if (!types_equal (obj_type, this_ref))
        obj = value_cast (this_ref, obj);
@@ -540,26 +566,23 @@ gdbpy_invoke_xmethod (const struct extension_language_defn *extlang,
       if (!types_equal (obj_type, this_type))
        obj = value_cast (this_type, obj);
     }
-  py_value_obj = value_to_value_object (obj);
+  gdbpy_ref<> py_value_obj (value_to_value_object (obj));
   if (py_value_obj == NULL)
     {
       gdbpy_print_stack ();
       error (_("Error while executing Python code."));
     }
-  make_cleanup_py_decref (py_value_obj);
 
-  py_arg_tuple = PyTuple_New (nargs + 1);
+  gdbpy_ref<> py_arg_tuple (PyTuple_New (nargs + 1));
   if (py_arg_tuple == NULL)
     {
       gdbpy_print_stack ();
       error (_("Error while executing Python code."));
     }
-  make_cleanup_py_decref (py_arg_tuple);
 
-  /* PyTuple_SET_ITEM steals the reference of the element.  Hence INCREF the
-     reference to the 'this' object as we have a cleanup to DECREF it.  */
-  Py_INCREF (py_value_obj);
-  PyTuple_SET_ITEM (py_arg_tuple, 0, py_value_obj);
+  /* PyTuple_SET_ITEM steals the reference of the element, hence the
+     release.  */
+  PyTuple_SET_ITEM (py_arg_tuple.get (), 0, py_value_obj.release ());
 
   for (i = 0; i < nargs; i++)
     {
@@ -571,20 +594,20 @@ gdbpy_invoke_xmethod (const struct extension_language_defn *extlang,
          error (_("Error while executing Python code."));
        }
 
-      PyTuple_SET_ITEM (py_arg_tuple, i + 1, py_value_arg);
+      PyTuple_SET_ITEM (py_arg_tuple.get (), i + 1, py_value_arg);
     }
 
-  py_result = PyObject_CallObject (xmethod_worker, py_arg_tuple);
+  gdbpy_ref<> py_result (PyObject_CallObject (xmethod_worker,
+                                             py_arg_tuple.get ()));
   if (py_result == NULL)
     {
       gdbpy_print_stack ();
       error (_("Error while executing Python code."));
     }
-  make_cleanup_py_decref (py_result);
 
   if (py_result != Py_None)
     {
-      res = convert_value_from_python (py_result);
+      res = convert_value_from_python (py_result.get ());
       if (res == NULL)
        {
          gdbpy_print_stack ();
@@ -597,8 +620,6 @@ gdbpy_invoke_xmethod (const struct extension_language_defn *extlang,
                                             "void", NULL, 0));
     }
 
-  do_cleanups (cleanups);
-
   return res;
 }
 
@@ -629,10 +650,6 @@ gdbpy_initialize_xmethods (void)
   if (py_match_method_name == NULL)
     return -1;
 
-  py_invoke_method_name = PyString_FromString (invoke_method_name);
-  if (py_invoke_method_name == NULL)
-    return -1;
-
   py_get_arg_types_method_name
     = PyString_FromString (get_arg_types_method_name);
   if (py_get_arg_types_method_name == NULL)
This page took 0.03393 seconds and 4 git commands to generate.