[PATCH v2 17/47] gdb, infrun, ze: allow resuming unavailable threads

Tankut Baris Aktemur
2024-12-13T16:21:32Z

From: Markus Metzger <markus.t.metzger@intel.com>

On GPUs, threads may not always respond to interrupt requests when we try
to stabilize threads on an all-stop target. In order to still be able to
support all-stop model on those targets, we allow this case and model such
threads as unavailable.

They do exist but we cannot interact with them. In particular, they do
not have registers, including PC.

In some cases, all threads on a target may be unavailable. This can
happen when we currently do not have any work scheduled on that device.
One particular instance of this is during startup when we newly attach to
the device.

We still need to allow 'continuing' those threads to make GDB listen to
events from that target.

Update gdb.threads/killed-outside.exp by adding another case to the
expected messages when killing the inferior. It already contained cases
with and without thread exited messages. Add another one for an exited
thread but no pc-not-available message.
---
gdb/infrun.c | 11 ++++++++++-
gdb/testsuite/gdb.threads/killed-outside.exp | 4 ++++
2 files changed, 14 insertions(+), 1 deletion(-)

diff --git a/gdb/infrun.c b/gdb/infrun.c
index 2abc2331e1821f3058ae00ee8908209dd7be020d..5d9dd1cbaf3f0cb5a56c52227ae818237958cd90 100644
--- a/gdb/infrun.c
+++ b/gdb/infrun.c
@@ -2733,7 +2733,16 @@ resume_1 (enum gdb_signal sig)
step = false;
}

- CORE_ADDR pc = regcache_read_pc (regcache);
+ /* Allow resuming threads that do not have registers available.
+
+ This may happen on GPUs for threads that we tried to stop but that
+ did not respond. We model them as unavailable threads.
+
+ PC will be zero in that case and we do not expect any breakpoints at
+ this address so we're not adding any extra checks. */
+ CORE_ADDR pc = step
+ ? regcache_read_pc (regcache)
+ : regcache_read_pc_protected (regcache);

infrun_debug_printf ("step=%d, signal=%s, trap_expected=%d, "
"current thread [%s] at %s",
diff --git a/gdb/testsuite/gdb.threads/killed-outside.exp b/gdb/testsuite/gdb.threads/killed-outside.exp
index 35f7dc13896c1e653d0ffdb73301632e91783289..daa714beded981bea1bf7ddbc200eea799a44990 100644
--- a/gdb/testsuite/gdb.threads/killed-outside.exp
+++ b/gdb/testsuite/gdb.threads/killed-outside.exp
@@ -58,4 +58,8 @@ gdb_test_multiple "continue" "prompt after first continue" {
-re -wrap ".*$killed_msg.*$no_longer_exists_msg" {
pass $gdb_test_name
}
+ -re "Continuing\.\r\n\r\n$killed_msg\r\n$no_longer_exists_msg\r\n$gdb_prompt $" {
+ pass $gdb_test_name
+ gdb_test "continue" $not_being_run_msg "second continue"
+ }
}