wait() — Wait for a child process to end

Standards

Standards / Extensions C or C++ Dependencies

POSIX.1
XPG4
XPG4.2
Single UNIX Specification, Version 3

both  

Format

#define _POSIX_SOURCE
#include <sys/wait.h>

pid_t wait(int *status_ptr);

General description

Suspends the calling process until any one of its child processes ends. More precisely, wait() suspends the calling process until the system obtains status information on the ended child. If the system already has status information on a completed child process when wait() is called, wait() returns immediately. wait() is also ended if the calling process receives a signal whose action is either to execute a signal handler or to end the process.

The argument status_ptr points to a location where wait() can store a status value. This status value is zero if the child process explicitly returns zero status. If it is not zero, it can be analyzed with the status analysis macros, described in “Status Analysis Macros,” below.

The status_ptr pointer may also be NULL, in which case wait() ignores the child's return status.

The following function calls are equivalent:
wait(status_ptr);
waitpid(-1,status_ptr,0);
wait3(status_ptr,0,NULL);

For more information, see waitpid() — Wait for a specific child process to end.

Special behavior for XPG4.2: If the calling process has SA_NOCLDWAIT set or has SIGCHLD set to SIG_IGN, and the process has no unwaited for children that were transformed into zombie processes, it will block until all of the children terminate, and wait() will fail and set errno to ECHILD.

Status analysis macros: If the status_ptr argument is not NULL, wait() places the child's return status in *status_ptr. You can analyze this return status with the following macros, defined in the sys/wait.h header file:
WIFEXITED(*status_ptr)
This macro evaluates to a nonzero (true) value if the child process ended normally, that is, if it returned from main() or called one of the exit() or _exit() functions.
WEXITSTATUS(*status_ptr)
When WIFEXITED() is nonzero, WEXITSTATUS() evaluates to the low-order 8 bits of the child's return status passed on the exit() or _exit() function.
WIFSIGNALED(*status_ptr)
This macro evaluates to a nonzero (true) value if the child process ended because of a signal that was not caught.
WIFSTOPPED(*status_ptr)
This macro evaluates to a nonzero (true) value if the child process is currently stopped. This should only be used after a waitpid() with the WUNTRACED option.
WSTOPSIG(*status_ptr)
When WIFSTOPPED() is nonzero, WSTOPSIG() evaluates to the number of the signal that stopped the child.
WTERMSIG(*status_ptr)
When WIFSIGNALED() is nonzero, WTERMSIG() evaluates to the number of the signal that ended the child process.

Returned value

If successful, wait() returns a value that is the process ID (PID) of the child whose status information has been obtained.

If unsuccessful, wait() returns -1 and sets errno to one of the following values:
Error Code
Description
ECHILD
The caller has no appropriate child processes, that is, it has no child processes whose status has not been obtained by previous calls to wait(), waitid(), waitpid(), or wait3(). ECHILD is also returned when the SA_NOCLDWAIT flag is set.
EINTR
wait() was interrupted by a signal. The value of *status_ptr is undefined.

Example

CELEBW01
⁄* CELEBW01

   This example suspends the calling process until any child processes ends.

 *⁄
#define _POSIX_SOURCE
#include <sys⁄types.h>
#include <sys⁄wait.h>
#include <unistd.h>
#include <stdio.h>
#include <time.h>

main() {
  pid_t pid;
  time_t t;
  int status;

  if ((pid = fork()) < 0)
    perror("fork() error");
  else if (pid == 0) {
    time(&t);
    printf("child (pid %d) started at %s", (int) getpid(), ctime(&t));
    sleep(5);
    time(&t);
    printf("child exiting at %s", ctime(&t));
    exit(42);
  }
  else {
    printf("parent has forked child with pid of %d\n", (int) pid);
    time(&t);
    printf("parent is starting wait at %s", ctime(&t));
    if ((pid = wait(&status)) == -1)
      perror("wait() error");
    else {
      time(&t);
      printf("parent is done waiting at %s", ctime(&t));
      printf("the pid of the process that ended was %d\n", (int) pid);
      if (WIFEXITED(status))
        printf("child exited with status of %d\n", WEXITSTATUS(status));
      else if (WIFSIGNALED(status))
        printf("child was terminated by signal %d\n",
               WTERMSIG(status));
      else if (WIFSTOPPED(status))
        printf("child was stopped by signal %d\n", WSTOPSIG(status));
      else puts("reason unknown for child termination");
    }
  }
}
Output:
parent has forked child with pid of 65546
parent is starting wait at Fri Jun 16 10:53:03 2001
child (pid 65546) started at Fri Jun 16 10:53:04 2001
child exiting at Fri Jun 16 10:53:09 2001
parent is done waiting at Fri Jun 16 10:53:10 2001
the pid of the process that ended was 65546
child exited with status of 42

Related information