[comp.sys.sgi] wait3

tim@ZORAC.ARPA (Tim Pointing) (12/08/87)

Often, the only reason why wait3() is used instead of wait() is so that
a wait can be done without delaying if there is no child process have status
to report (where wait() would just sit around until one did have status to
report.) The way that I have kludged around this deficiency in the past is
with my own hack which sort-of simulates wait3().

Good Luck!
	Tim

Caveats: I am typing this in off the top of my head - it may not work
	as typed (additional #include's may be required); it will not work
	when the option "WUNTRACED" is used; care must be taken if alarm's
	are already being used in the program. No guarantees!

The fake goes something like (this at least compiles)...
-------------cut-here-----------------------------------cut-here------------
#include <errno.h>

#include <sys/types.h>
#include <sys/time.h>
#include <sys/signal.h>

#include <sys/wait.h>
#include <sys/resource.h>

typedef int (*PFI)();	/* make declarations easier to read */

wait3(status, options, rusage)
union wait *status;
int options;
struct resource *rusage;	/* not altered so declaration doesn't matter */
{
	extern int wait3_timeout();
	PFI old_alarm, signal();
	int pid;
	extern int errno;
	int err_code;
	unsigned  time_left;

	/* fake the WNOHANG option by using time-out's */
	if (options & WNOHANG)
	{
		old_alarm = signal(SIGALRM, wait3_timeout);
		time_left = alarm(1);
	}

	errno = 0;
	pid = wait(status);
	err_code = errno;

	if (options & WNOHANG)
	{
		(void) signal(SIGALRM, old_alarm);
		alarm(time_left);
	}

	/* pid == -1 means either no process to wait for or alarm */
	/* interupted the wait() system call.			  */

	if (pid == -1 && err_code == EINTR)
		return(0);

	return(pid);
}

static wait3_timeout() {}

vjs@rhyolite.SGI.COM (Vernon Schryver) (12/11/87)

In article <8712081347.AA20022@zorac.ARPA>, tim@ZORAC.ARPA (Tim Pointing) writes:
> Often, the only reason why wait3() is used instead of wait() is so that
> a wait can be done without delaying if there is no child process have status
> to report (where wait() would just sit around until one did have status to
> report.)

Mr. Pointing seems to be on the right track.

The SGI TCP/IP/UDP code is 4.3 BSD based.  As you might guess, when we
did the ports for 3.5 and 1.0 we encountered uses of wait3(2).
Whenever we port more 4.x compatible code, we find more uses of wait3.
However, instead of using alarm(2) and SIGALRM, we use SIGCHLD.  Your
process can get SIGCHLD when one of its children exits.

(Note: beware the surprising effect of setting SIGCHLD to SIG_IGN in SYS V.)