Support rvalue references in the gdb python module (includes doc/)
authorArtemiy Volkov <artemiyv@acm.org>
Mon, 20 Mar 2017 20:47:52 +0000 (13:47 -0700)
committerKeith Seitz <keiths@redhat.com>
Mon, 20 Mar 2017 20:47:52 +0000 (13:47 -0700)
This patch adds the ability to inspect rvalue reference types and values using
the gdb python module. This is achieved by creating two wrappers for
valpy_reference_value(), using the ReferenceExplorer class to handle the
objects of rvalue reference types and placing necessary checks for a
TYPE_CODE_RVALUE_REF type code next to the checks for a TYPE_CODE_REF type
code.

gdb/ChangeLog

PR gdb/14441
* doc/python.texi (Types in Python): Add TYPE_CODE_RVALUE_REF to
table of constants.
* python/lib/gdb/command/explore.py: Support exploring values
of rvalue reference types.
* python/lib/gdb/types.py: Implement get_basic_type() for
rvalue reference types.
* python/py-type.c (pyty_codes) <TYPE_CODE_RVALUE_REF>: New
constant.
* python/py-value.c (valpy_getitem): Add an rvalue reference
check.
(valpy_reference_value): Add new parameter "refcode".
(valpy_lvalue_reference_value, valpy_rvalue_reference_value):
New wrappers for valpy_reference_value().
* python/py-xmethods.c (gdbpy_get_xmethod_result_type)
(gdbpy_invoke_xmethod): Likewise.

gdb/ChangeLog
gdb/doc/python.texi
gdb/python/lib/gdb/command/explore.py
gdb/python/lib/gdb/types.py
gdb/python/py-type.c
gdb/python/py-value.c
gdb/python/py-xmethods.c

index 30cb60b..dfedc83 100644 (file)
@@ -1,6 +1,25 @@
 2017-03-20  Artemiy Volkov  <artemiyv@acm.org>
 
        PR gdb/14441
+       * doc/python.texi (Types in Python): Add TYPE_CODE_RVALUE_REF to
+       table of constants.
+       * python/lib/gdb/command/explore.py: Support exploring values
+       of rvalue reference types.
+       * python/lib/gdb/types.py: Implement get_basic_type() for
+       rvalue reference types.
+       * python/py-type.c (pyty_codes) <TYPE_CODE_RVALUE_REF>: New
+       constant.
+       * python/py-value.c (valpy_getitem): Add an rvalue reference
+       check.
+       (valpy_reference_value): Add new parameter "refcode".
+       (valpy_lvalue_reference_value, valpy_rvalue_reference_value):
+       New wrappers for valpy_reference_value().
+       * python/py-xmethods.c (gdbpy_get_xmethod_result_type)
+       (gdbpy_invoke_xmethod): Likewise.
+
+2017-03-20  Artemiy Volkov  <artemiyv@acm.org>
+
+       PR gdb/14441
        * dwarf2read.c (process_die, read_type_die_1): Handle the
        DW_TAG_rvalue_reference_type DIE.
        (read_tag_reference_type): Add new parameter "refcode".
index d00bc6f..f6ec08c 100644 (file)
@@ -1162,6 +1162,10 @@ A pointer-to-member.
 @item gdb.TYPE_CODE_REF
 A reference type.
 
+@vindex TYPE_CODE_RVALUE_REF
+@item gdb.TYPE_CODE_RVALUE_REF
+A C@t{++}11 rvalue reference type.
+
 @vindex TYPE_CODE_CHAR
 @item gdb.TYPE_CODE_CHAR
 A character type.
index b2878b9..4eb2e24 100644 (file)
@@ -132,6 +132,7 @@ class Explorer(object):
             gdb.TYPE_CODE_UNION : CompoundExplorer,
             gdb.TYPE_CODE_PTR : PointerExplorer,
             gdb.TYPE_CODE_REF : ReferenceExplorer,
+            gdb.TYPE_CODE_RVALUE_REF : ReferenceExplorer,
             gdb.TYPE_CODE_TYPEDEF : TypedefExplorer,
             gdb.TYPE_CODE_ARRAY : ArrayExplorer
         }
@@ -318,7 +319,6 @@ class ReferenceExplorer(object):
         Explorer.explore_type(name, target_type, is_child)
         return False
 
-
 class ArrayExplorer(object):
     """Internal class used to explore arrays."""
 
index 799a07d..26a5027 100644 (file)
@@ -31,8 +31,10 @@ def get_basic_type(type_):
     """
 
     while (type_.code == gdb.TYPE_CODE_REF or
+           type_.code == gdb.TYPE_CODE_RVALUE_REF or
            type_.code == gdb.TYPE_CODE_TYPEDEF):
-        if type_.code == gdb.TYPE_CODE_REF:
+        if (type_.code == gdb.TYPE_CODE_REF or
+            type_.code == gdb.TYPE_CODE_RVALUE_REF):
             type_ = type_.target()
         else:
             type_ = type_.strip_typedefs()
index 0249cbb..c063d2c 100644 (file)
@@ -106,6 +106,7 @@ static struct pyty_code pyty_codes[] =
   ENTRY (TYPE_CODE_METHODPTR),
   ENTRY (TYPE_CODE_MEMBERPTR),
   ENTRY (TYPE_CODE_REF),
+  ENTRY (TYPE_CODE_RVALUE_REF),
   ENTRY (TYPE_CODE_CHAR),
   ENTRY (TYPE_CODE_BOOL),
   ENTRY (TYPE_CODE_COMPLEX),
index c848f0f..fc42197 100644 (file)
@@ -238,7 +238,7 @@ valpy_referenced_value (PyObject *self, PyObject *args)
 /* Return a value which is a reference to the value.  */
 
 static PyObject *
-valpy_reference_value (PyObject *self, PyObject *args)
+valpy_reference_value (PyObject *self, PyObject *args, enum type_code refcode)
 {
   PyObject *result = NULL;
 
@@ -248,7 +248,7 @@ valpy_reference_value (PyObject *self, PyObject *args)
       scoped_value_mark free_values;
 
       self_val = ((value_object *) self)->value;
-      result = value_to_value_object (value_ref (self_val, TYPE_CODE_REF));
+      result = value_to_value_object (value_ref (self_val, refcode));
     }
   CATCH (except, RETURN_MASK_ALL)
     {
@@ -259,6 +259,18 @@ valpy_reference_value (PyObject *self, PyObject *args)
   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 *
@@ -645,8 +657,7 @@ value_has_field (struct value *v, PyObject *field)
     {
       val_type = value_type (v);
       val_type = check_typedef (val_type);
-      if (TYPE_CODE (val_type) == TYPE_CODE_REF
-         || TYPE_CODE (val_type) == TYPE_CODE_PTR)
+      if (TYPE_IS_REFERENCE (val_type) || TYPE_CODE (val_type) == TYPE_CODE_PTR)
       val_type = check_typedef (TYPE_TARGET_TYPE (val_type));
 
       type_code = TYPE_CODE (val_type);
@@ -803,6 +814,9 @@ valpy_getitem (PyObject *self, PyObject *key)
          else if (TYPE_CODE (val_type) == TYPE_CODE_REF)
            res_val = value_cast (lookup_lvalue_reference_type (base_class_type),
                                  tmp);
+         else if (TYPE_CODE (val_type) == 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);
        }
@@ -1784,8 +1798,10 @@ 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_reference_value, METH_NOARGS,
+  { "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,
index d01488f..e061da2 100644 (file)
@@ -464,9 +464,10 @@ gdbpy_get_xmethod_result_type (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_lvalue_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);