From dev-return-4673-apmail-apr-dev-archive=apr.apache.org@apr.apache.org Mon Oct 15 17:38:55 2001 Return-Path: Delivered-To: apmail-apr-dev-archive@apr.apache.org Received: (qmail 35863 invoked by uid 500); 15 Oct 2001 17:38:55 -0000 Mailing-List: contact dev-help@apr.apache.org; run by ezmlm Precedence: bulk List-Post: List-Help: List-Unsubscribe: List-Subscribe: Delivered-To: mailing list dev@apr.apache.org Received: (qmail 35841 invoked from network); 15 Oct 2001 17:38:54 -0000 X-Authentication-Warning: rdu88-250-106.nc.rr.com: trawick set sender to trawick@attglobal.net using -f Sender: trawick@rdu88-250-106.nc.rr.com To: Kevin Pilch-Bisson Cc: Justin Erenkrantz , dev@apr.apache.org Subject: [PATCH] Re: cvs commit: apr/threadproc/unix proc.c References: <20010921161450.26587.qmail@icarus.apache.org> <20011013080658.G2149@ebuilt.com> <20011013171410.A1378@pilch-bisson.net> From: Jeff Trawick Date: 15 Oct 2001 13:38:59 -0400 In-Reply-To: Message-ID: Lines: 201 User-Agent: Gnus/5.0808 (Gnus v5.8.8) Emacs/20.7 MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii X-Spam-Rating: daedalus.apache.org 1.6.2 0/1000/N This patch implements (for Unix, at least) what I mentioned in a previous post, namely, to make available all information about a terminated child but to classify it so that a portable app doesn't have to play games with WIFEXITED() et al. As I mentioned before, I don't know if we're doing the right thing on Unix w.r.t. capturing information about processes which are stopped. Index: server/mpm_common.c =================================================================== RCS file: /home/cvs/httpd-2.0/server/mpm_common.c,v retrieving revision 1.69 diff -u -r1.69 mpm_common.c --- server/mpm_common.c 2001/09/21 14:29:33 1.69 +++ server/mpm_common.c 2001/10/15 17:24:42 @@ -124,7 +124,7 @@ continue; proc.pid = pid; - waitret = apr_proc_wait(&proc, NULL, APR_NOWAIT); + waitret = apr_proc_wait(&proc, APR_NOWAIT); if (waitret != APR_CHILD_NOTDONE) { MPM_NOTE_CHILD_KILLED(i); continue; @@ -204,12 +204,13 @@ if (wait_or_timeout_counter == INTERVAL_OF_WRITABLE_PROBES) { wait_or_timeout_counter = 0; } - rv = apr_proc_wait_all_procs(ret, status, APR_NOWAIT, p); + rv = apr_proc_wait_all_procs(ret, APR_NOWAIT, p); if (APR_STATUS_IS_EINTR(rv)) { ret->pid = -1; return; } if (APR_STATUS_IS_CHILD_DONE(rv)) { + *status = ret->native_exit_status; return; } #ifdef NEED_WAITPID Index: srclib/apr/include/apr_thread_proc.h =================================================================== RCS file: /home/cvs/apr/include/apr_thread_proc.h,v retrieving revision 1.75 diff -u -r1.75 apr_thread_proc.h --- srclib/apr/include/apr_thread_proc.h 2001/09/20 08:59:30 1.75 +++ srclib/apr/include/apr_thread_proc.h 2001/10/15 17:25:09 @@ -81,6 +81,7 @@ typedef enum {APR_SHELLCMD, APR_PROGRAM} apr_cmdtype_e; typedef enum {APR_WAIT, APR_NOWAIT} apr_wait_how_e; +typedef enum {APR_CHILD_NORMAL_EXIT, APR_CHILD_SIGNAL_EXIT, APR_CHILD_STOPPED} apr_exit_how_e; #define APR_NO_PIPE 0 #define APR_FULL_BLOCK 1 @@ -124,6 +125,17 @@ apr_file_t *out; /** Parent's side of pipe to child's stdouterr */ apr_file_t *err; + /** How did the child exit? (normally, via uncaught signal, etc.) */ + apr_exit_how_e exit_how; + /** What did the OS return for the child exit status? */ + apr_wait_t native_exit_status; + /** What is the exit code (for normal exit) or terminating signal? */ + union { + int exit_code; +#ifdef WIFSIGNALED + int signal; +#endif + } exit_status; #ifdef WIN32 /** Must retain the handle as any clone may not have the * the same permissions @@ -481,11 +493,6 @@ /** * Wait for a child process to die * @param proc The process handle that corresponds to the desired child process - * @param exitcode The returned exit status of the child, if a child process - * dies. On platforms that don't support obtaining this - * information, the exitcode parameter will be returned as - * APR_ENOTIMPL. This parameter may be NULL if the exit code - * is not needed. * @param waithow How should we wait. One of: *
  *            APR_WAIT   -- block until the child process dies.
@@ -499,7 +506,6 @@
  * 
*/ APR_DECLARE(apr_status_t) apr_proc_wait(apr_proc_t *proc, - apr_wait_t *exitcode, apr_wait_how_e waithow); /** @@ -507,9 +513,6 @@ * about that child. * @param proc Pointer to NULL on entry, will be filled out with child's * information - * @param status The returned exit status of the child, if a child process dies - * On platforms that don't support obtaining this information, - * the status parameter will be returned as APR_ENOTIMPL. * @param waithow How should we wait. One of: *
  *            APR_WAIT   -- block until the child process dies.
@@ -519,9 +522,8 @@
  * @param p Pool to allocate child information out of.
  */
 APR_DECLARE(apr_status_t) apr_proc_wait_all_procs(apr_proc_t *proc,
-                                             apr_wait_t *status,
-                                             apr_wait_how_e waithow,
-                                             apr_pool_t *p);
+                                                  apr_wait_how_e waithow,
+                                                  apr_pool_t *p);
 
 /**
  * Detach the process from the controlling terminal.
Index: srclib/apr/memory/unix/apr_pools.c
===================================================================
RCS file: /home/cvs/apr/memory/unix/apr_pools.c,v
retrieving revision 1.113
diff -u -r1.113 apr_pools.c
--- srclib/apr/memory/unix/apr_pools.c	2001/09/28 15:22:35	1.113
+++ srclib/apr/memory/unix/apr_pools.c	2001/10/15 17:25:17
@@ -1505,7 +1505,7 @@
 #ifndef NEED_WAITPID
     /* Pick up all defunct processes */
     for (p = procs; p; p = p->next) {
-        if (apr_proc_wait(p->pid, NULL, APR_NOWAIT) != APR_CHILD_NOTDONE) {
+        if (apr_proc_wait(p->pid, APR_NOWAIT) != APR_CHILD_NOTDONE) {
             p->kill_how = kill_never;
         }
     }
@@ -1550,7 +1550,7 @@
     /* Now wait for all the signaled processes to die */
     for (p = procs; p; p = p->next) {
 	if (p->kill_how != kill_never) {
-	    (void) apr_proc_wait(p->pid, NULL, APR_WAIT);
+	    (void) apr_proc_wait(p->pid, APR_WAIT);
 	}
     }
 #ifdef WIN32
Index: srclib/apr/threadproc/unix/proc.c
===================================================================
RCS file: /home/cvs/apr/threadproc/unix/proc.c,v
retrieving revision 1.49
diff -u -r1.49 proc.c
--- srclib/apr/threadproc/unix/proc.c	2001/09/21 16:14:50	1.49
+++ srclib/apr/threadproc/unix/proc.c	2001/10/15 17:25:23
@@ -362,16 +362,14 @@
 }
 
 APR_DECLARE(apr_status_t) apr_proc_wait_all_procs(apr_proc_t *proc, 
-                                                  apr_wait_t *status,
                                                   apr_wait_how_e waithow, 
                                                   apr_pool_t *p)
 {
     proc->pid = -1;
-    return apr_proc_wait(proc, status, waithow);
+    return apr_proc_wait(proc, waithow);
 } 
 
 APR_DECLARE(apr_status_t) apr_proc_wait(apr_proc_t *proc, 
-                                        apr_wait_t *exitcode,
                                         apr_wait_how_e waithow)
 {
     pid_t pstatus;
@@ -383,16 +381,21 @@
     }
     
     if ((pstatus = waitpid(proc->pid, &exit_int, waitpid_options)) > 0) {
-        if (proc->pid == -1) {
-            proc->pid = pstatus;
-        }
+        proc->pid = pstatus;
+        proc->native_exit_status = exit_int;
         if (WIFEXITED(exit_int)) {
-            if (exitcode != NULL) {
-                *exitcode = WEXITSTATUS(exit_int);
-            }
-            return APR_CHILD_DONE;
+            proc->exit_how = APR_CHILD_NORMAL_EXIT;
+            proc->exit_status.exit_code = WEXITSTATUS(exit_int);
+        }
+        else if (WIFSIGNALED(exit_int)) {
+            proc->exit_how = APR_CHILD_SIGNAL_EXIT;
+            proc->exit_status.signal = WTERMSIG(exit_int);
+        }
+        else if (WIFSTOPPED(exit_int)) {
+            proc->exit_how = APR_CHILD_STOPPED;
+            proc->exit_status.signal = WSTOPSIG(exit_int);
         }
-        return APR_CHILD_NOTDONE;
+        return APR_CHILD_DONE;
     }
     else if (pstatus == 0) {
         return APR_CHILD_NOTDONE;



-- 
Jeff Trawick | trawick@attglobal.net | PGP public key at web site:
       http://www.geocities.com/SiliconValley/Park/9289/
             Born in Roswell... married an alien...