[RFA] Fix PR python/17386 - add __index__ method to gdb.Value

Message ID 1463616830-12259-1-git-send-email-tom@tromey.com
State New, archived
Headers

Commit Message

Tom Tromey May 19, 2016, 12:13 a.m. UTC
  This patch fixes PR python/17386.

The bug is that gdb.Value does not implement the Python __index__
method.  This method is needed to convert a Python object to an index
and is used by various operations in Python, such as indexing an
array.

The fix is to implement the nb_index method for gdb.Value.

While doing this I discovered that value_object_as_number was missing
an entry.  This patch fixes this.

nb_index was added in Python 2.5.  I don't have a good way to test
Python 2.4, but I made an attempt.

I chose to use valpy_long in all cases because this simplifies porting
to Python 3, and because there didn't seem to be any harm.

Built and regtested on x86-64 Fedora 23.

2016-05-18  Tom Tromey  <tom@tromey.com>

	PR python/17386:
	* python/py-value.c (value_object_as_number): Add
	nb_inplace_divide entry, nb_inplace_floor_divide,
	nb_inplace_true_divide, nb_index.

2016-05-18  Tom Tromey  <tom@tromey.com>

	PR python/17386:
	* gdb.python/py-value.exp (test_value_numeric_ops): Add test that
	uses value as an index.
---
 gdb/ChangeLog                         | 7 +++++++
 gdb/python/py-value.c                 | 9 ++++++++-
 gdb/testsuite/ChangeLog               | 6 ++++++
 gdb/testsuite/gdb.python/py-value.exp | 3 +++
 4 files changed, 24 insertions(+), 1 deletion(-)
  

Comments

Yao Qi May 23, 2016, 8:33 a.m. UTC | #1
Tom Tromey <tom@tromey.com> writes:

> While doing this I discovered that value_object_as_number was missing
> an entry.  This patch fixes this.
>

> diff --git a/gdb/python/py-value.c b/gdb/python/py-value.c
> index 7dba0ad..d34428d 100644
> --- a/gdb/python/py-value.c
> +++ b/gdb/python/py-value.c
> @@ -1827,6 +1827,7 @@ static PyNumberMethods value_object_as_number = {
>    NULL,                       /* nb_inplace_add */
>    NULL,                       /* nb_inplace_subtract */
>    NULL,                       /* nb_inplace_multiply */
> +  NULL,                       /* nb_inplace_divide */
>    NULL,                       /* nb_inplace_remainder */
>    NULL,                       /* nb_inplace_power */
>    NULL,                       /* nb_inplace_lshift */

This change should be in a separate patch.  Could you split it?  It is
obvious and can be applied.

> diff --git a/gdb/testsuite/gdb.python/py-value.exp b/gdb/testsuite/gdb.python/py-value.exp
> index a9dbe97..019e45b 100644
> --- a/gdb/testsuite/gdb.python/py-value.exp
> +++ b/gdb/testsuite/gdb.python/py-value.exp
> @@ -124,6 +124,9 @@ proc test_value_numeric_ops {} {
>    gdb_test "python print ('result = ' + str(b-2))" " = 0x3( <.*>)?" "subtract python integer from pointer value"
>    gdb_test "python print ('result = ' + str(b-a))" " = 3" "subtract two pointer values"
>  
> +  gdb_test "python print ('result = ' + 'result'\[gdb.Value(0)\])" \
> +    "result = r" "use value as an index"
> +

I tried the test patch on master, and it triggers the exception.
However, the exception is "string indices must be integers, not
gdb.Value", which is different from the exception in the PR.

python print ('result = ' + 'result'[gdb.Value(0)])
Traceback (most recent call last):
  File "<string>", line 1, in <module>
TypeError: string indices must be integers, not gdb.Value
Error while executing Python code.
(gdb) FAIL: gdb.python/py-value.exp: use value as an index

These two exceptions look quite similar but can you add a test that
triggers "'gdb.Value' object cannot be interpreted as an integer"?
because that is the symptom this patch is to fix.
  
Tom Tromey May 23, 2016, 5:22 p.m. UTC | #2
Yao> This change should be in a separate patch.  Could you split it?  It is
Yao> obvious and can be applied.

I'll send v2 shortly.  The original patch was wrong, due to me not
building against Python 3.  With the new patch I've done it both ways.

Yao> These two exceptions look quite similar but can you add a test that
Yao> triggers "'gdb.Value' object cannot be interpreted as an integer"?
Yao> because that is the symptom this patch is to fix.

v2 has this.

Tom
  

Patch

diff --git a/gdb/ChangeLog b/gdb/ChangeLog
index 92024b6..7656a34 100644
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,5 +1,12 @@ 
 2016-05-18  Tom Tromey  <tom@tromey.com>
 
+	PR python/17386:
+	* python/py-value.c (value_object_as_number): Add
+	nb_inplace_divide entry, nb_inplace_floor_divide,
+	nb_inplace_true_divide, nb_index.
+
+2016-05-18  Tom Tromey  <tom@tromey.com>
+
 	* rust-lang.c (rust_subscript): Initialize "high".
 
 2016-05-17  Simon Marchi  <simon.marchi@ericsson.com>
diff --git a/gdb/python/py-value.c b/gdb/python/py-value.c
index 7dba0ad..d34428d 100644
--- a/gdb/python/py-value.c
+++ b/gdb/python/py-value.c
@@ -1827,6 +1827,7 @@  static PyNumberMethods value_object_as_number = {
   NULL,                       /* nb_inplace_add */
   NULL,                       /* nb_inplace_subtract */
   NULL,                       /* nb_inplace_multiply */
+  NULL,                       /* nb_inplace_divide */
   NULL,                       /* nb_inplace_remainder */
   NULL,                       /* nb_inplace_power */
   NULL,                       /* nb_inplace_lshift */
@@ -1835,7 +1836,13 @@  static PyNumberMethods value_object_as_number = {
   NULL,                       /* nb_inplace_xor */
   NULL,                       /* nb_inplace_or */
   NULL,                       /* nb_floor_divide */
-  valpy_divide                /* nb_true_divide */
+  valpy_divide,               /* nb_true_divide */
+  NULL,			      /* nb_inplace_floor_divide */
+  NULL			      /* nb_inplace_true_divide */
+#ifndef HAVE_LIBPYTHON_2_4
+  /* This was added in Python 2.5.  */
+  , valpy_long		      /* nb_index */
+#endif /* HAVE_LIBPYTHON_2_4 */
 };
 
 static PyMappingMethods value_object_as_mapping = {
diff --git a/gdb/testsuite/ChangeLog b/gdb/testsuite/ChangeLog
index a773c63..5441877 100644
--- a/gdb/testsuite/ChangeLog
+++ b/gdb/testsuite/ChangeLog
@@ -1,3 +1,9 @@ 
+2016-05-18  Tom Tromey  <tom@tromey.com>
+
+	PR python/17386:
+	* gdb.python/py-value.exp (test_value_numeric_ops): Add test that
+	uses value as an index.
+
 2016-05-18  Simon Marchi  <simon.marchi@ericsson.com>
 
 	* gdb.mi/mi-threads-interrupt.c: New file.
diff --git a/gdb/testsuite/gdb.python/py-value.exp b/gdb/testsuite/gdb.python/py-value.exp
index a9dbe97..019e45b 100644
--- a/gdb/testsuite/gdb.python/py-value.exp
+++ b/gdb/testsuite/gdb.python/py-value.exp
@@ -124,6 +124,9 @@  proc test_value_numeric_ops {} {
   gdb_test "python print ('result = ' + str(b-2))" " = 0x3( <.*>)?" "subtract python integer from pointer value"
   gdb_test "python print ('result = ' + str(b-a))" " = 3" "subtract two pointer values"
 
+  gdb_test "python print ('result = ' + 'result'\[gdb.Value(0)\])" \
+    "result = r" "use value as an index"
+
   # Test some invalid operations.
 
   gdb_test_multiple "python print ('result = ' + str(i+'foo'))" "catch error in python type conversion" {