gdb/python: test exception case for gdb.solib_name

Message ID 856ee4315d2d615388efe8352b29379feefa4054.1710503245.git.aburgess@redhat.com
State New
Headers
Series gdb/python: test exception case for gdb.solib_name |

Checks

Context Check Description
linaro-tcwg-bot/tcwg_gdb_build--master-aarch64 success Testing passed
linaro-tcwg-bot/tcwg_gdb_build--master-arm success Testing passed
linaro-tcwg-bot/tcwg_gdb_check--master-arm success Testing passed
linaro-tcwg-bot/tcwg_gdb_check--master-aarch64 success Testing passed

Commit Message

Andrew Burgess March 15, 2024, 11:47 a.m. UTC
  I noticed that gdb.solib_name() and Progspace.solib_name() were not
documented as being able to throw an exception, but in some cases it
is possible to get an exception from these functions.  An exception
can occur when the address argument can't be converted to an unsigned
integer.

This commit extends the documentation to mention the exception case,
and I've added a couple of tests to cover this case.

There's no changes to GDB itself in this commit.
---
 gdb/doc/python.texi                    | 10 ++++++++--
 gdb/testsuite/gdb.python/py-shared.exp | 15 +++++++++++++++
 2 files changed, 23 insertions(+), 2 deletions(-)


base-commit: 9fe07b7f95fbfdaf34d5b69e6d73cae000b43eea
  

Comments

Eli Zaretskii March 15, 2024, 12:39 p.m. UTC | #1
> From: Andrew Burgess <aburgess@redhat.com>
> Cc: Andrew Burgess <aburgess@redhat.com>
> Date: Fri, 15 Mar 2024 11:47:45 +0000
> 
> I noticed that gdb.solib_name() and Progspace.solib_name() were not
> documented as being able to throw an exception, but in some cases it
> is possible to get an exception from these functions.  An exception
> can occur when the address argument can't be converted to an unsigned
> integer.
> 
> This commit extends the documentation to mention the exception case,
> and I've added a couple of tests to cover this case.

Thanks.

> --- a/gdb/doc/python.texi
> +++ b/gdb/doc/python.texi
> @@ -521,7 +521,11 @@
>  
>  @defun gdb.solib_name (address)
>  Return the name of the shared library holding the given @var{address}
> -as a string, or @code{None}.  This is identical to
> +as a string, or @code{None} if there is no library containing
> +@var{address}.  If @var{address} can't be converted to a unsigned
                                                          ^^^^^^^^^^
"an unsigned"

> +integer address then an exception will be raised.

Btw, what does it mean for ADDRESS to not be convertible to an
unsigned integer address?  Does it mean ADDRESS is not an integral
number or something?  Maybe we should say that explicitly.

>  @defun Progspace.solib_name (address)
>  Return the name of the shared library holding the given @var{address}
> -as a string, or @code{None}.
> +as a string, or @code{None} if there is no library containing
> +@var{address}.  If @var{address} can't be converted to a unsigned
> +integer address then an exception will be raised.

Same here.

Reviewed-By: Eli Zaretskii <eliz@gnu.org>
  
Tom Tromey March 15, 2024, 1:16 p.m. UTC | #2
>>>>> "Andrew" == Andrew Burgess <aburgess@redhat.com> writes:

Andrew> I noticed that gdb.solib_name() and Progspace.solib_name() were not
Andrew> documented as being able to throw an exception, but in some cases it
Andrew> is possible to get an exception from these functions.  An exception
Andrew> can occur when the address argument can't be converted to an unsigned
Andrew> integer.

Andrew> This commit extends the documentation to mention the exception case,
Andrew> and I've added a couple of tests to cover this case.

Maybe the Basic Python node should have a note explaining that there's a
general rule allowing for type errors and the like.

Tom
  
Andrew Burgess March 19, 2024, 9:38 a.m. UTC | #3
Tom Tromey <tom@tromey.com> writes:

>>>>>> "Andrew" == Andrew Burgess <aburgess@redhat.com> writes:
>
> Andrew> I noticed that gdb.solib_name() and Progspace.solib_name() were not
> Andrew> documented as being able to throw an exception, but in some cases it
> Andrew> is possible to get an exception from these functions.  An exception
> Andrew> can occur when the address argument can't be converted to an unsigned
> Andrew> integer.
>
> Andrew> This commit extends the documentation to mention the exception case,
> Andrew> and I've added a couple of tests to cover this case.
>
> Maybe the Basic Python node should have a note explaining that there's a
> general rule allowing for type errors and the like.

I think you are right, such general exception cases probably don't need
documenting.

I still think it's worth testing these cases though.

How about the patch below, there's no documentation changes, just adding
a couple of additional tests.

Thanks,
Andrew

---

commit cb695b43ec06bf5b222272f76066b8f546f6ab1e
Author: Andrew Burgess <aburgess@redhat.com>
Date:   Fri Mar 15 11:14:05 2024 +0000

    gdb/python: test exception case for gdb.solib_name
    
    The gdb.solib_name() and Progspace.solib_name() functions can throw an
    exception if the address argument is not a valid address, but this is
    not currently tested.
    
    This commit adds a couple of tests to check that exceptions are thrown
    correctly.
    
    An early version of this commit updated the documentation, but it was
    pointed out that lots of functions throw an exception if passed an
    argument of the wrong type, and we don't document all of these, it's
    kind-of assumed that passing an object of the incorrect type might
    result in an exception, so this updated version leaves the docs alone,
    but I do think adding the extra tests has value.
    
    There's no changes to GDB itself in this commit.

diff --git a/gdb/testsuite/gdb.python/py-shared.exp b/gdb/testsuite/gdb.python/py-shared.exp
index 6faa6cde521..9be5aa467e2 100644
--- a/gdb/testsuite/gdb.python/py-shared.exp
+++ b/gdb/testsuite/gdb.python/py-shared.exp
@@ -64,3 +64,18 @@ gdb_test "python print (gdb.solib_name(int(main)))" "None" "test main solib loca
 if {[is_lp64_target]} {
     gdb_test "python print (len(\[gdb.solib_name(0xffffffffffffffff)\]))" "1"
 }
+
+gdb_test "python print(gdb.solib_name(-1))" \
+    [multi_line \
+	 "Python Exception <class 'OverflowError'>: can't convert negative int to unsigned" \
+	 "Error occurred in Python: can't convert negative int to unsigned"]
+
+gdb_test "python print(gdb.current_progspace().solib_name(-1))" \
+    [multi_line \
+	 "Python Exception <class 'OverflowError'>: can't convert negative int to unsigned" \
+	 "Error occurred in Python: can't convert negative int to unsigned"]
+
+gdb_test "python print(gdb.current_progspace().solib_name(\"string\"))" \
+    [multi_line \
+	 "Python Exception <class 'ValueError'>: invalid literal for int\\(\\) with base 10: 'string'" \
+	 "Error occurred in Python: invalid literal for int\\(\\) with base 10: 'string'"]
  
Tom Tromey March 19, 2024, 3:55 p.m. UTC | #4
>>>>> "Andrew" == Andrew Burgess <aburgess@redhat.com> writes:

Andrew> I still think it's worth testing these cases though.

Andrew> How about the patch below, there's no documentation changes, just adding
Andrew> a couple of additional tests.

Seems fine to me.
Approved-By: Tom Tromey <tom@tromey.com>

Tom
  
Andrew Burgess March 19, 2024, 4:04 p.m. UTC | #5
Tom Tromey <tom@tromey.com> writes:

>>>>>> "Andrew" == Andrew Burgess <aburgess@redhat.com> writes:
>
> Andrew> I still think it's worth testing these cases though.
>
> Andrew> How about the patch below, there's no documentation changes, just adding
> Andrew> a couple of additional tests.
>
> Seems fine to me.
> Approved-By: Tom Tromey <tom@tromey.com>

Pushed.

Thanks,
Andrew
  

Patch

diff --git a/gdb/doc/python.texi b/gdb/doc/python.texi
index 4ca3ae4eca4..db681abfcd6 100644
--- a/gdb/doc/python.texi
+++ b/gdb/doc/python.texi
@@ -521,7 +521,11 @@ 
 
 @defun gdb.solib_name (address)
 Return the name of the shared library holding the given @var{address}
-as a string, or @code{None}.  This is identical to
+as a string, or @code{None} if there is no library containing
+@var{address}.  If @var{address} can't be converted to a unsigned
+integer address then an exception will be raised.
+
+This is identical to
 @code{gdb.current_progspace().solib_name(address)} and is included for
 historical compatibility.
 @end defun
@@ -5406,7 +5410,9 @@ 
 
 @defun Progspace.solib_name (address)
 Return the name of the shared library holding the given @var{address}
-as a string, or @code{None}.
+as a string, or @code{None} if there is no library containing
+@var{address}.  If @var{address} can't be converted to a unsigned
+integer address then an exception will be raised.
 @end defun
 
 @defun Progspace.objfile_for_address (address)
diff --git a/gdb/testsuite/gdb.python/py-shared.exp b/gdb/testsuite/gdb.python/py-shared.exp
index 6faa6cde521..9be5aa467e2 100644
--- a/gdb/testsuite/gdb.python/py-shared.exp
+++ b/gdb/testsuite/gdb.python/py-shared.exp
@@ -64,3 +64,18 @@  gdb_test "python print (gdb.solib_name(int(main)))" "None" "test main solib loca
 if {[is_lp64_target]} {
     gdb_test "python print (len(\[gdb.solib_name(0xffffffffffffffff)\]))" "1"
 }
+
+gdb_test "python print(gdb.solib_name(-1))" \
+    [multi_line \
+	 "Python Exception <class 'OverflowError'>: can't convert negative int to unsigned" \
+	 "Error occurred in Python: can't convert negative int to unsigned"]
+
+gdb_test "python print(gdb.current_progspace().solib_name(-1))" \
+    [multi_line \
+	 "Python Exception <class 'OverflowError'>: can't convert negative int to unsigned" \
+	 "Error occurred in Python: can't convert negative int to unsigned"]
+
+gdb_test "python print(gdb.current_progspace().solib_name(\"string\"))" \
+    [multi_line \
+	 "Python Exception <class 'ValueError'>: invalid literal for int\\(\\) with base 10: 'string'" \
+	 "Error occurred in Python: invalid literal for int\\(\\) with base 10: 'string'"]