[v5,3/4] Print only process ptids from linux-fork.c

Message ID 20241210020313.584564-4-kevinb@redhat.com
State New
Headers
Series Make linux checkpoints work with multiple inferiors |

Checks

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

Commit Message

Kevin Buettner Dec. 10, 2024, 1:54 a.m. UTC
  This commit causes a "process ptid" to be passed to all calls
of target_pid_to_str in linux-fork.c.  A "process ptid" is one
in which only the pid component is set to a non-zero value;
both the lwp  and tid components are zero.

The reason for doing this is that pids associated with checkpoints can
never be a thread due to the fact that checkpoints (which are
implemented by forking a process) can only (reasonably) work with
single-threaded processes.

Without this commit, many of the "info checkpoints" commands
in gdb.multi/checkpoint-multi.exp will incorrectly show some
of the checkpoints as threads.  E.g...

  Id  Active Target Id                          Frame
* 1.0 y      Thread 0x7ffff7cb5740 (LWP 581704) at 0x401199, file hello.c, line 51
  1.2 n      process 581716                     at 0x401199, file hello.c, line 51
  1.3 n      process 581717                     at 0x401199, file hello.c, line 51
  2.1 n      process 581708                     at 0x401258, file goodbye.c, line 62
  2.2 y      Thread 0x7ffff7cb5740 (LWP 581712) at 0x401258, file goodbye.c, line 62
  3.0 y      Thread 0x7ffff7cb5740 (LWP 581713) at 0x40115c, file hangout.c, line 31
  3.2 n      process 581715                     at 0x40115c, file hangout.c, line 31
(gdb

With this commit in place, the output looks like this instead:

  Id  Active Target Id      Frame
* 1.0 y      process 535276 at 0x401199, file hello.c, line 51
  1.2 n      process 535288 at 0x401199, file hello.c, line 51
  1.3 n      process 535289 at 0x401199, file hello.c, line 51
  2.1 n      process 535280 at 0x401258, file goodbye.c, line 62
  2.2 y      process 535284 at 0x401258, file goodbye.c, line 62
  3.0 y      process 535285 at 0x40115c, file hangout.c, line 31
  3.2 n      process 535287 at 0x40115c, file hangout.c, line 31

(For brevity, I've removed the directory elements in each of the paths
above.)

The testcase, gdb.multi/checkpoint-multi.exp, has been updated to
reflect the fact that only "process" should now appear in output
from "info checkpoints".
---
 gdb/linux-fork.c                             | 39 ++++++++++++++------
 gdb/testsuite/gdb.multi/checkpoint-multi.exp |  2 +-
 2 files changed, 28 insertions(+), 13 deletions(-)
  

Patch

diff --git a/gdb/linux-fork.c b/gdb/linux-fork.c
index af7d4b60819..f93e14bcac7 100644
--- a/gdb/linux-fork.c
+++ b/gdb/linux-fork.c
@@ -429,6 +429,17 @@  fork_save_infrun_state (struct fork_info *fp)
     }
 }
 
+/* Given a ptid, return a "process ptid" in which only the pid member
+   is present.  This is used in calls to target_pid_to_str() to ensure
+   that only process ptids are printed by this file.  */
+
+static inline ptid_t
+proc_ptid (ptid_t ptid)
+{
+  ptid_t process_ptid (ptid.pid ());
+  return process_ptid;
+}
+
 /* Kill 'em all, let God sort 'em out...  */
 
 void
@@ -492,7 +503,7 @@  linux_fork_mourn_inferior ()
   last = find_last_fork (inf);
   fork_load_infrun_state (last);
   gdb_printf (_("[Switching to %s]\n"),
-	      target_pid_to_str (inferior_ptid).c_str ());
+	      target_pid_to_str (proc_ptid (inferior_ptid)).c_str ());
 
   /* If there's only one fork, switch back to non-fork mode.  */
   if (one_fork_p (inf))
@@ -520,7 +531,7 @@  linux_fork_detach (int from_tty, lwp_info *lp, inferior *inf)
     {
       if (ptrace (PTRACE_DETACH, inferior_ptid.pid (), 0, 0))
 	error (_("Unable to detach %s"),
-	       target_pid_to_str (inferior_ptid).c_str ());
+	       target_pid_to_str (proc_ptid (inferior_ptid)).c_str ());
     }
 
   delete_fork (inferior_ptid, inf);
@@ -535,7 +546,7 @@  linux_fork_detach (int from_tty, lwp_info *lp, inferior *inf)
 
   if (from_tty)
     gdb_printf (_("[Switching to %s]\n"),
-		target_pid_to_str (inferior_ptid).c_str ());
+		target_pid_to_str (proc_ptid (inferior_ptid)).c_str ());
 
   /* If there's only one fork, switch back to non-fork mode.  */
   if (one_fork_p (inf))
@@ -610,7 +621,7 @@  class scoped_switch_fork_info
 	catch (const gdb_exception &ex)
 	  {
 	    warning (_("Couldn't restore checkpoint state in %s: %s"),
-		     target_pid_to_str (m_oldfp->ptid).c_str (),
+		     target_pid_to_str (proc_ptid (m_oldfp->ptid)).c_str (),
 		     ex.what ());
 	  }
       }
@@ -688,10 +699,12 @@  delete_checkpoint_command (const char *args, int from_tty)
     error (_("Cannot delete active checkpoint"));
 
   if (ptrace (PTRACE_KILL, ptid.pid (), 0, 0))
-    error (_("Unable to kill pid %s"), target_pid_to_str (ptid).c_str ());
+    error (_("Unable to kill pid %s"),
+	   target_pid_to_str (proc_ptid (ptid)).c_str ());
 
   if (from_tty)
-    gdb_printf (_("Killed %s\n"), target_pid_to_str (ptid).c_str ());
+    gdb_printf (_("Killed %s\n"),
+		target_pid_to_str (proc_ptid (ptid)).c_str ());
 
   delete_fork (ptid, inf);
 
@@ -716,7 +729,7 @@  delete_checkpoint_command (const char *args, int from_tty)
     {
       if (inferior_call_waitpid (pptid, ptid.pid ()))
 	warning (_("Unable to wait pid %s"),
-		 target_pid_to_str (ptid).c_str ());
+		 target_pid_to_str (proc_ptid (ptid)).c_str ());
     }
 }
 
@@ -736,10 +749,12 @@  detach_checkpoint_command (const char *args, int from_tty)
 Please switch to another checkpoint before detaching the current one"));
 
   if (ptrace (PTRACE_DETACH, ptid.pid (), 0, 0))
-    error (_("Unable to detach %s"), target_pid_to_str (ptid).c_str ());
+    error (_("Unable to detach %s"),
+	   target_pid_to_str (proc_ptid (ptid)).c_str ());
 
   if (from_tty)
-    gdb_printf (_("Detached %s\n"), target_pid_to_str (ptid).c_str ());
+    gdb_printf (_("Detached %s\n"),
+	        target_pid_to_str (proc_ptid (ptid)).c_str ());
 
   delete_fork (ptid, current_inferior ());
 }
@@ -790,7 +805,7 @@  info_checkpoints_command (const char *arg, int from_tty)
 			  + (print_inf ? 1 : 0));
 	  targid_width
 	    = std::max (targid_width,
-			target_pid_to_str (fi.ptid).size ());
+			target_pid_to_str (proc_ptid (fi.ptid)).size ());
 	}
     }
 
@@ -847,7 +862,7 @@  info_checkpoints_command (const char *arg, int from_tty)
 
 	  /* Print target id.  */
 	  gdb_printf ("%-*s", (int) targid_width,
-		      target_pid_to_str (fi.ptid).c_str ());
+		      target_pid_to_str (proc_ptid (fi.ptid)).c_str ());
 
 	  if (t->state == THREAD_RUNNING && is_current)
 	    gdb_printf (_(" (running)"));
@@ -1013,7 +1028,7 @@  linux_fork_context (struct fork_info *newfp, int from_tty, inferior *newinf)
       insert_breakpoints ();
       if (!inferior_changed)
 	gdb_printf (_("Switching to %s\n"),
-		    target_pid_to_str (inferior_ptid).c_str ());
+		    target_pid_to_str (proc_ptid (inferior_ptid)).c_str ());
     }
 
   notify_user_selected_context_changed
diff --git a/gdb/testsuite/gdb.multi/checkpoint-multi.exp b/gdb/testsuite/gdb.multi/checkpoint-multi.exp
index 4860608e704..e401e5e9555 100644
--- a/gdb/testsuite/gdb.multi/checkpoint-multi.exp
+++ b/gdb/testsuite/gdb.multi/checkpoint-multi.exp
@@ -23,7 +23,7 @@  require {istarget "*-*-linux*"}
 require gdb_protocol_is_native
 
 set checkpoints_header_re " +Id +Active Target Id +Frame.*?"
-set proc_re "(?:process $::decimal|Thread $::hex \\(LWP $::decimal\\))"
+set proc_re "(?:process $::decimal)"
 set ckpt_re "Checkpoint"
 set main_proc "\\(main process\\)"
 set hello_c "hello\\.c"