Fix "target extended-remote" + "maint set target-non-stop" + "attach"
With "target extended-remote" + "maint set target-non-stop", attaching
hangs like so:
(gdb) attach
1244450
Attaching to process
1244450
[New Thread
1244450.
1244450]
[New Thread
1244450.
1244453]
[New Thread
1244450.
1244454]
[New Thread
1244450.
1244455]
[New Thread
1244450.
1244456]
[New Thread
1244450.
1244457]
[New Thread
1244450.
1244458]
[New Thread
1244450.
1244459]
[New Thread
1244450.
1244461]
[New Thread
1244450.
1244462]
[New Thread
1244450.
1244463]
* hang *
Attaching to the hung GDB shows that GDB is busy in an infinite loop
in stop_all_threads:
(top-gdb) bt
#0 stop_all_threads () at /home/pedro/gdb/binutils-gdb/src/gdb/infrun.c:4755
#1 0x000055555597b424 in stop_waiting (ecs=0x7fffffffd930) at /home/pedro/gdb/binutils-gdb/src/gdb/infrun.c:7738
#2 0x0000555555976fba in handle_signal_stop (ecs=0x7fffffffd930) at /home/pedro/gdb/binutils-gdb/src/gdb/infrun.c:5868
#3 0x0000555555975f6a in handle_inferior_event (ecs=0x7fffffffd930) at /home/pedro/gdb/binutils-gdb/src/gdb/infrun.c:5527
#4 0x0000555555971da4 in fetch_inferior_event () at /home/pedro/gdb/binutils-gdb/src/gdb/infrun.c:3910
#5 0x00005555559540b2 in inferior_event_handler (event_type=INF_REG_EVENT) at /home/pedro/gdb/binutils-gdb/src/gdb/inf-loop.c:42
#6 0x000055555597e825 in infrun_async_inferior_event_handler (data=0x0) at /home/pedro/gdb/binutils-gdb/src/gdb/infrun.c:9162
#7 0x0000555555687d1d in check_async_event_handlers () at /home/pedro/gdb/binutils-gdb/src/gdb/async-event.c:328
#8 0x0000555555e48284 in gdb_do_one_event () at /home/pedro/gdb/binutils-gdb/src/gdbsupport/event-loop.cc:216
#9 0x00005555559e7512 in start_event_loop () at /home/pedro/gdb/binutils-gdb/src/gdb/main.c:347
#10 0x00005555559e765d in captured_command_loop () at /home/pedro/gdb/binutils-gdb/src/gdb/main.c:407
#11 0x00005555559e8f80 in captured_main (data=0x7fffffffdb70) at /home/pedro/gdb/binutils-gdb/src/gdb/main.c:1239
#12 0x00005555559e8ff2 in gdb_main (args=0x7fffffffdb70) at /home/pedro/gdb/binutils-gdb/src/gdb/main.c:1254
#13 0x0000555555627c86 in main (argc=12, argv=0x7fffffffdc88) at /home/pedro/gdb/binutils-gdb/src/gdb/gdb.c:32
The problem is that the remote sends stops for all the threads:
Packet received: l/home/pedro/gdb/binutils-gdb/build/gdb/testsuite/outputs/gdb.threads/attach-non-stop/attach-non-stop
Sending packet: $vStopped#55...Packet received: T0006:
f06e25edec7f0000;07:
f06e25edec7f0000;10:
f14190ccf4550000;thread:p12fd22.12fd2f;core:15;
Sending packet: $vStopped#55...Packet received: T0006:
f0dea5f0ec7f0000;07:
f0dea5f0ec7f0000;10:
e84190ccf4550000;thread:p12fd22.12fd27;core:4;
Sending packet: $vStopped#55...Packet received: T0006:
f0ee25f1ec7f0000;07:
f0ee25f1ec7f0000;10:
f14190ccf4550000;thread:p12fd22.12fd26;core:5;
Sending packet: $vStopped#55...Packet received: T0006:
f0bea5efec7f0000;07:
f0bea5efec7f0000;10:
f14190ccf4550000;thread:p12fd22.12fd29;core:1;
Sending packet: $vStopped#55...Packet received: T0006:
f0ce25f0ec7f0000;07:
f0ce25f0ec7f0000;10:
e84190ccf4550000;thread:p12fd22.12fd28;core:a;
Sending packet: $vStopped#55...Packet received: T0006:
f07ea5edec7f0000;07:
f07ea5edec7f0000;10:
e84190ccf4550000;thread:p12fd22.12fd2e;core:f;
Sending packet: $vStopped#55...Packet received: T0006:
f0ae25efec7f0000;07:
f0ae25efec7f0000;10:
df4190ccf4550000;thread:p12fd22.12fd2a;core:6;
Sending packet: $vStopped#55...Packet received: T0006:
0000000000000000;07:
c0e8a381fe7f0000;10:
bf43b4f1ec7f0000;thread:p12fd22.12fd22;core:2;
Sending packet: $vStopped#55...Packet received: T0006:
f0fea5f1ec7f0000;07:
f0fea5f1ec7f0000;10:
df4190ccf4550000;thread:p12fd22.12fd25;core:8;
Sending packet: $vStopped#55...Packet received: T0006:
f09ea5eeec7f0000;07:
f09ea5eeec7f0000;10:
e84190ccf4550000;thread:p12fd22.12fd2b;core:b;
Sending packet: $vStopped#55...Packet received: OK
But then wait_one never consumes them, always hitting this path:
4473 if (nfds == 0)
4474 {
4475 /* No waitable targets left. All must be stopped. */
4476 return {NULL, minus_one_ptid, {TARGET_WAITKIND_NO_RESUMED}};
4477 }
Resulting in GDB constanly calling target_stop to stop threads, but
the remote target never reporting back the stops to infrun.
That TARGET_WAITKIND_NO_RESUMED path shown above is always taken
because here, in wait_one too, just above:
4428 for (inferior *inf : all_inferiors ())
4429 {
4430 process_stratum_target *target = inf->process_target ();
4431 if (target == NULL
4432 || !target->is_async_p ()
^^^^^^^^^^^^^^^^^^^^^
4433 || !target->threads_executing)
4434 continue;
... the remote target is not async.
And in turn that happened because extended_remote_target::attach
misses enabling async in the target-non-stop path.
A testcase exercising this will be added in a following patch.
gdb/ChangeLog:
* remote.c (extended_remote_target::attach): Set target async in
the target-non-stop path too.