HOST: Implement timeouts on Hurd.
authorBen Pfaff <blp@cs.stanford.edu>
Mon, 7 Sep 2020 21:18:14 +0000 (14:18 -0700)
committerBen Pfaff <blp@cs.stanford.edu>
Mon, 7 Sep 2020 21:21:04 +0000 (14:21 -0700)
The existing implementation didn't work and I do not know why.
Hurd isn't documented to have different behavior for signals on
execl().  The timeouts were not firing, however.

This implementation does work.

Thanks to Friedrich Beckmann for reporting the issue (via Debian
buildd).

src/language/utilities/host.c

index 1ab7cc1d02eef6a530ddd7159a3dcf342ad159af..6298db2d8b5e581dddefc9648a849e97db473918 100644 (file)
@@ -122,6 +122,11 @@ run_command (const char *command, struct timespec timeout)
     {
       /* Running in the child. */
 
+#if __GNU__
+      /* Hurd doesn't support inheriting process timers in a way that works. */
+      if (setpgid (0, 0) < 0)
+        error (1, errno, _("Failed to set process group."));
+#else
       /* Set up timeout. */
       if (timeout.tv_sec < TYPE_MAXIMUM (time_t))
         {
@@ -140,6 +145,7 @@ run_command (const char *command, struct timespec timeout)
           if (setitimer (ITIMER_REAL, &it, NULL) < 0)
             error (1, errno, _("Failed to set timeout."));
         }
+#endif
 
       /* Set up file descriptors:
          - /dev/null for stdin
@@ -174,7 +180,15 @@ run_command (const char *command, struct timespec timeout)
   int error = 0;
   for (;;)
     {
-      pid_t retval = waitpid (pid, &status, 0);
+#if __GNU__
+      if (timespec_cmp (current_timespec (), timeout) >= 0)
+        kill (-pid, SIGALRM);
+
+      int flags = WNOHANG;
+#else
+      int flags = 0;
+#endif
+      pid_t retval = waitpid (pid, &status, flags);
       if (retval == pid)
         break;
       else if (retval < 0)
@@ -185,6 +199,10 @@ run_command (const char *command, struct timespec timeout)
               break;
             }
         }
+#if __GNU__
+      else if (retval == 0)
+        sleep (1);
+#endif
       else
         NOT_REACHED ();
     }