This is the mail archive of the gdb-cvs@sourceware.org mailing list for the GDB project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[binutils-gdb] Avoid gdb.base/fork-running-state.exp lingering processes


https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=14897d65b5a279684289bf6b99136de60c31f1c0

commit 14897d65b5a279684289bf6b99136de60c31f1c0
Author: Pedro Alves <palves@redhat.com>
Date:   Thu Jun 14 17:47:03 2018 +0100

    Avoid gdb.base/fork-running-state.exp lingering processes
    
    Currently, the gdb.base/fork-running-state.exp testcase leaves a few
    processes lingering until a 3 minutes alarm kills them:
    
     pedro    28308     1  0 13:55 ?        00:00:00 /home/pedro/gdb/binutils-gdb/build/gdb/testsuite/outputs/gdb.base/fork-running-state/fork-running-state
     pedro    28340     1  0 13:55 ?        00:00:00 /home/pedro/gdb/binutils-gdb/build/gdb/testsuite/outputs/gdb.base/fork-running-state/fork-running-state
     pedro    28372     1  0 13:55 ?        00:00:00 /home/pedro/gdb/binutils-gdb/build/gdb/testsuite/outputs/gdb.base/fork-running-state/fork-running-state
     pedro    28400     1  0 13:55 ?        00:00:00 /home/pedro/gdb/binutils-gdb/build/gdb/testsuite/outputs/gdb.base/fork-running-state/fork-running-state
     pedro    28431     1  0 13:55 ?        00:00:00 /home/pedro/gdb/binutils-gdb/build/gdb/testsuite/outputs/gdb.base/fork-running-state/fork-running-state
     pedro    28463     1  0 13:55 ?        00:00:00 /home/pedro/gdb/binutils-gdb/build/gdb/testsuite/outputs/gdb.base/fork-running-state/fork-running-state
    
    Those processes used to kill themselves, but that was changed by
    commit f50d8a2eaea0 ("Fix gdb.base/fork-running-state.exp race").
    
    This commit restores the self-killing, but only in the cases gdb won't
    try killing the processes, thus avoiding the old race.
    
    (The restored code in fork_parent isn't exactly the same as it was.
    In this version, we're exiting immediately when 'wait' returns
    success, while in the old version we'd loop again and end up in the
    perror call.  The output from that perror call is not expected by the
    "kill inferior" tests, and would result in a test FAIL.)
    
    gdb/testsuite/ChangeLog:
    2018-06-14  Pedro Alves  <palves@redhat.com>
    
    	* gdb.base/fork-running-state.c: Include <errno.h>.
    	(exit_if_relative_exits): New.
    	(fork_child): If 'exit_if_relative_exits' is true, exit if the parent
    	exits.
    	(fork_parent): If 'exit_if_relative_exits' is true, exit if the
    	child exits.

Diff:
---
 gdb/testsuite/ChangeLog                       |  9 +++++++
 gdb/testsuite/gdb.base/fork-running-state.c   | 39 +++++++++++++++++++++++++--
 gdb/testsuite/gdb.base/fork-running-state.exp |  7 +++++
 3 files changed, 53 insertions(+), 2 deletions(-)

diff --git a/gdb/testsuite/ChangeLog b/gdb/testsuite/ChangeLog
index 1c98bbd..6d1f5f7 100644
--- a/gdb/testsuite/ChangeLog
+++ b/gdb/testsuite/ChangeLog
@@ -1,3 +1,12 @@
+2018-06-14  Pedro Alves  <palves@redhat.com>
+
+	* gdb.base/fork-running-state.c: Include <errno.h>.
+	(exit_if_relative_exits): New.
+	(fork_child): If 'exit_if_relative_exits' is true, exit if the parent
+	exits.
+	(fork_parent): If 'exit_if_relative_exits' is true, exit if the
+	child exits.
+
 2018-06-14  Tom de Vries  <tdevries@suse.de>
 
 	PR cli/22573
diff --git a/gdb/testsuite/gdb.base/fork-running-state.c b/gdb/testsuite/gdb.base/fork-running-state.c
index 65ca942..0037cb5 100644
--- a/gdb/testsuite/gdb.base/fork-running-state.c
+++ b/gdb/testsuite/gdb.base/fork-running-state.c
@@ -19,9 +19,15 @@
 #include <stdio.h>
 #include <sys/types.h>
 #include <sys/wait.h>
+#include <errno.h>
 
 int save_parent;
 
+/* Variable set by GDB.  If true, then a fork child (or parent) exits
+   if its parent (or child) exits.  Otherwise the process waits
+   forever until either GDB or the alarm kills it.  */
+volatile int exit_if_relative_exits = 0;
+
 /* The fork child.  Just runs forever.  */
 
 static int
@@ -31,7 +37,20 @@ fork_child (void)
   alarm (180);
 
   while (1)
-    pause ();
+    {
+      if (exit_if_relative_exits)
+	{
+	  sleep (1);
+
+	  /* Exit if GDB kills the parent.  */
+	  if (getppid () != save_parent)
+	    break;
+	  if (kill (getppid (), 0) != 0)
+	    break;
+	}
+      else
+	pause ();
+    }
 
   return 0;
 }
@@ -45,7 +64,23 @@ fork_parent (void)
   alarm (180);
 
   while (1)
-    pause ();
+    {
+      if (exit_if_relative_exits)
+	{
+	  int res = wait (NULL);
+	  if (res == -1 && errno == EINTR)
+	    continue;
+	  else if (res == -1)
+	    {
+	      perror ("wait");
+	      return 1;
+	    }
+	  else
+	    return 0;
+	}
+      else
+	pause ();
+    }
 
   return 0;
 }
diff --git a/gdb/testsuite/gdb.base/fork-running-state.exp b/gdb/testsuite/gdb.base/fork-running-state.exp
index 27ed8a4..c15bc53 100644
--- a/gdb/testsuite/gdb.base/fork-running-state.exp
+++ b/gdb/testsuite/gdb.base/fork-running-state.exp
@@ -70,6 +70,13 @@ proc do_test { detach_on_fork follow_fork non_stop schedule_multiple } {
 	gdb_test_no_output "set schedule-multiple $schedule_multiple"
     }
 
+    # If we're detaching from the parent (or child), then tell it to
+    # exit itself when its child (or parent) exits.  If we stay
+    # attached, we take care of killing it.
+    if {$detach_on_fork == "on"} {
+	gdb_test "print exit_if_relative_exits = 1" " = 1"
+    }
+
     set test "continue &"
     gdb_test_multiple $test $test {
 	-re "$gdb_prompt " {


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]