Processus & Threads · Section 2
wait4(2)
Attend un changement d'état d'un processus enfant et récupère son statut de sortie et son utilisation des ressources.
Signature
#include <sys/wait.h>
#include <sys/resource.h>
pid_t wait4(pid_t pid, int * wstatus, int options, struct rusage * rusage);- pid
- Cible. > 0 : PID enfant spécifique. 0 : tout enfant du groupe. -1 : tout enfant. < -1 : enfant du groupe |pid|.
- wstatus
- Si non-NULL, reçoit le statut encodé. Décoder avec WIFEXITED, WEXITSTATUS, WIFSIGNALED, WTERMSIG, WCOREDUMP.
- options
- OU bit-à-bit de WNOHANG (sans bloquer), WUNTRACED (signaler les arrêts), WCONTINUED (signaler les reprises), __WCLONE / __WALL (contrôler quels enfants sont éligibles — pour ptrace et clone()).
- rusage
- Si non-NULL, reçoit l'usage des ressources. NULL convient si seul le statut intéresse.
Description
wait4() bloque l'appelant jusqu'à ce qu'un processus enfant change d'état — sortie, tué par signal, ou (avec WUNTRACED / WCONTINUED) arrêté ou repris. Retourne le PID de l'enfant concerné et, via wstatus, un entier encodant la cause (décodé par WIFEXITED, WEXITSTATUS, WIFSIGNALED, WTERMSIG…). Si rusage est non-NULL, le temps CPU et l'usage mémoire de l'enfant sont écrits dans *rusage. pid > 0 attend cet enfant précis ; pid == 0 attend tout enfant du groupe de processus de l'appelant ; pid == -1 attend n'importe quel enfant ; pid < -1 attend tout enfant du groupe |pid|. wait4() est le mécanisme noyau canonique qui transforme les zombies en notifications de sortie collectées. wait() et waitpid() sont des wrappers libc ; waitid() est l'alternative moderne plus flexible.
Numéros par architecture
| Architecture | Numéro | ABI | Point d'entrée |
|---|---|---|---|
| x86 (i386) | 114 | i386 | sys_wait4 |
| x64 (x86_64) | 61 | common | sys_wait4 |
| ARM64 (aarch64) | 260 | — | — |
Historique noyau
Introduit dans Linux 1.0.
1.0
wait4() est présent dans Linux depuis 1.0, hérité de BSD comme surensemble de wait() POSIX (BSD ajoutait rusage).
2.6.9
waitid() a été ajouté comme variante plus capable avec un idtype plus fin (P_PID, P_PGID, P_ALL, P_PIDFD) et une sortie siginfo_t plus riche — le remplaçant moderne, bien que wait4() reste ubiquitaire car waitpid() de la glibc l'utilise en interne.
seccomp & conteneurs
Docker default profile
Autorisé
Podman default profile
Autorisé
wait4() et waitid() sont autorisés par les profils Docker / Podman. Les bloquer est rarement utile — tout processus qui lance des enfants doit les collecter ou le noyau accumule des zombies indéfiniment (jusqu'à ce que le parent meure et qu'ils soient adoptés par init).
libseccomp
seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(wait4), 0);
seccomp_rule_add(ctx, SCMP_ACT_ALLOW, SCMP_SYS(waitid), 0);Exemple strace
$ strace -f -e wait4 bash -c 'sleep 0.1 &; wait'
wait4(-1, [{WIFEXITED(s) && WEXITSTATUS(s) == 0}], 0, NULL) = 13284
+++ exited with 0 +++wait4() dans strace affiche les macros WIF* décodées : '{WIFEXITED(s) && WEXITSTATUS(s) == 42}' ou '{WIFSIGNALED(s) && WTERMSIG(s) == SIGSEGV}'. Un retour 0 sur WNOHANG est normal en boucle de polling ; un ECHILD persistant avec des enfants actifs trahit un piège SIGCHLD-à-SIG_IGN.
Sécurité & observabilité
wait4() n'est pas directement une primitive de sécurité mais sa présence fait partie du cycle de vie : un processus qui fork()/execve() ses enfants sans wait4() laisse des zombies dans /proc — signature de fuite. Les init de conteneur (tini, dumb-init, pause du Pod) existent principalement pour collecter les orphelins ; sans, les defunct s'accumulent. Le tracepoint eBPF sched_process_exit couvre le même événement de cycle de vie côté noyau et est préféré pour la supervision car il ne dépend pas du parent appelant wait4().
Erreurs
- ECHILD
- Aucun enfant correspondant — il n'y en a aucun, ils ont tous été collectés, ou l'appelant a positionné SIGCHLD à SIG_IGN (qui auto-collecte).
- EINTR
- Interrompu par un signal sans SA_RESTART.
- EINVAL
- —
Drapeaux
- WNOHANG
- 1
- Retourner 0 immédiatement si aucun enfant n'a changé d'état, plutôt que de bloquer. L'idiome boucle de polling.
- WUNTRACED
- 2
- Signaler aussi les enfants arrêtés (par ex. par SIGSTOP). Utilisé par les débogueurs et les shells de contrôle de job.
- WCONTINUED
- 8
- Signaler aussi les enfants ayant repris après arrêt (SIGCONT).
- __WCLONE
- 0x80000000
- —
- __WALL
- 0x40000000
- Attendre tout enfant indépendamment de la sémantique clone (le défaut exclut certains clones de type thread noyau). Utilisé par strace et gdb.