]> git.ipfire.org Git - thirdparty/binutils-gdb.git/commitdiff
gdb/testsuite/gdb.python/py-symbol.exp: accept either rr static symbol when calling...
authorSimon Marchi <simon.marchi@efficios.com>
Tue, 7 Oct 2025 18:42:53 +0000 (14:42 -0400)
committerSimon Marchi <simon.marchi@efficios.com>
Tue, 21 Oct 2025 17:23:22 +0000 (13:23 -0400)
Since commit dad36cf91992 ("gdb/dwarf: use dynamic partitioning for
DWARF CU indexing"), we get the intermittent failures:

    python print (gdb.lookup_static_symbol ('rr').line)
    18
    (gdb) FAIL: gdb.python/py-symbol.exp: print line number of rr
    python print (gdb.lookup_static_symbol ('rr').value ())
    99
    (gdb) FAIL: gdb.python/py-symbol.exp: print value of rr

The situation is:

 - The program isn't running.
 - Two compilation units define a static symbol named `rr`.
 - The test does:

     gdb.lookup_static_symbol ('rr')

The test expects this to return one specific (out of the two) `rr`
static symbols.  Since dad36cf91992, the call sometimes returns the
wrong symbol.

The documentation for gdb.lookup_static_symbol says this:

    There can be multiple global symbols with static linkage with the
    same name. This function will only return the first matching symbol
    that it finds. Which symbol is found depends on where GDB is
    currently stopped, as GDB will first search for matching symbols in
    the current object file, and then search all other object files. If
    the application is not yet running then GDB will search all object
    files in the order they appear in the debug information.

cooked_index_functions::search searches index shards linearly and
returns the first matching symbol.  Before dad36cf91992, the work was
split statically among threads, so symbols would end up in shards
deterministically.  Since the first part of the debug info ends up in
the first shard, it happens to work as described in the doc.

Since dad36cf91992, symbols end up in random shards, based on which
thread happened to pop their CU from the work queue.

I don't think that specifying which of the multiple matching static
symbols is returned is really useful, as it unnecessarily restricts the
implementation.  If multiple static symbols match the criteria, I think
it makes sense that you'll get an unspecified one.  Code that needs to
deal with the possibility of multiple static symbols of the same name
should use gdb.lookup_static_symbols.

I propose to remove this guarantee from gdb.lookup_static_symbol.  I
understand that this is a breaking change, but I think it's easy enough
to deal with it.

Update the test to accept either symbol.

Update the doc to say that an unspecified symbol will be returned if the
program is not running and there are multiple matching symbols.  The
previous text also seemed a bit wrong about its use of the term "object
file".  GDB searches a static symbol for the current compilation unit
first.  It then falls back to searching all symbols.

Change-Id: I22f81c186b1483a488ea7614fb81fd102db3c7f1
Approved-By: Tom Tromey <tom@tromey.com>
Reviewed-By: Tom de Vries <tdevries@suse.de>
Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=33518
Approved-By: Andrew Burgess <aburgess@redhat.com>
Reviewed-By: Eli Zaretskii <eliz@gnu.org>
gdb/doc/python.texi
gdb/testsuite/gdb.python/py-symbol.exp

index 9df2c58f210dc0ea6b7219de12ae58872a33cdf2..13ffde253d38dba2072b56cc9b39fa605a9b5aad 100644 (file)
@@ -6418,12 +6418,14 @@ up such variables, iterate over the variables of the function's
 
 There can be multiple global symbols with static linkage with the same
 name.  This function will only return the first matching symbol that
-it finds.  Which symbol is found depends on where @value{GDBN} is
+it finds.  Which symbol is found depends on where the program is
 currently stopped, as @value{GDBN} will first search for matching
-symbols in the current object file, and then search all other object
-files.  If the application is not yet running then @value{GDBN} will
-search all object files in the order they appear in the debug
-information.
+symbols in the current compilation unit.  If it finds no match, or if
+there is no current compilation unit (perhaps because the program is
+not running), then @code{gdb.lookup_static_symbol} will return an
+unspecified matching symbol.  To safely handle the case of multiple
+static symbols with the same name, an application can use
+@code{gdb.lookup_static_symbols}.
 @end defun
 
 @defun gdb.lookup_static_symbols (name @r{[}, domain@r{]})
index 2029c286599f116a78380fe87bceea3c05ae1469..6f0fceee8f5f29c6b333253f67da86a714189516 100644 (file)
@@ -70,36 +70,14 @@ gdb_test "python print (gdb.lookup_global_symbol('qq').needs_frame)" \
     "print whether qq needs a frame"
 
 # Similarly, test looking up a static symbol before we runto_main.
-set rr_line [gdb_get_line_number "line of rr"]
-set rr_line_alt [gdb_get_line_number "line of other rr" py-symbol-2.c]
 gdb_test "python print (gdb.lookup_global_symbol ('qqrr') is None)" "True" \
     "lookup_global_symbol for static var"
 
-set cmd "python print (gdb.lookup_static_symbol ('rr').line)"
-gdb_test_multiple $cmd "print line number of rr" {
-    -re -wrap "$rr_line" {
-       pass $gdb_test_name
-    }
-    -re -wrap "$rr_line_alt" {
-       if { $readnow_p } {
-           setup_kfail "symtab/25857" *-*-*
-       }
-       fail $gdb_test_name
-    }
-}
-
-set cmd "python print (gdb.lookup_static_symbol ('rr').value ())"
-gdb_test_multiple $cmd "print value of rr" {
-    -re -wrap "42" {
-       pass $gdb_test_name
-    }
-    -re -wrap "99" {
-       if { $readnow_p } {
-           setup_kfail "symtab/25857" *-*-*
-       }
-       fail $gdb_test_name
-    }
-}
+# Either "rr" static symbol is a valid result.
+set rr_line_1 [gdb_get_line_number "line of rr"]
+set rr_line_2 [gdb_get_line_number "line of other rr" py-symbol-2.c]
+gdb_test "python print (gdb.lookup_static_symbol ('rr').line)" "($rr_line_1|$rr_line_2)"
+gdb_test "python print (gdb.lookup_static_symbol ('rr').value ())" "(42|99)"
 
 gdb_test "python print (gdb.lookup_static_symbol ('rr').needs_frame)" \
     "False" \