16d1724ecSThomas Weißschuh /* SPDX-License-Identifier: LGPL-2.1 OR MIT */
26d1724ecSThomas Weißschuh /*
36d1724ecSThomas Weißschuh * wait definitions for NOLIBC
46d1724ecSThomas Weißschuh * Copyright (C) 2017-2021 Willy Tarreau <w@1wt.eu>
56d1724ecSThomas Weißschuh */
66d1724ecSThomas Weißschuh
73785289fSThomas Weißschuh /* make sure to include all global symbols */
83785289fSThomas Weißschuh #include "../nolibc.h"
93785289fSThomas Weißschuh
106d1724ecSThomas Weißschuh #ifndef _NOLIBC_SYS_WAIT_H
116d1724ecSThomas Weißschuh #define _NOLIBC_SYS_WAIT_H
126d1724ecSThomas Weißschuh
136d1724ecSThomas Weißschuh #include "../arch.h"
146d1724ecSThomas Weißschuh #include "../std.h"
156d1724ecSThomas Weißschuh #include "../types.h"
166d1724ecSThomas Weißschuh
176d1724ecSThomas Weißschuh /*
186d1724ecSThomas Weißschuh * pid_t wait(int *status);
196d1724ecSThomas Weißschuh * pid_t wait4(pid_t pid, int *status, int options, struct rusage *rusage);
206d1724ecSThomas Weißschuh * pid_t waitpid(pid_t pid, int *status, int options);
210c89abf5SThomas Weißschuh * int waitid(idtype_t idtype, id_t id, siginfo_t *infop, int options);
226d1724ecSThomas Weißschuh */
236d1724ecSThomas Weißschuh
246d1724ecSThomas Weißschuh static __attribute__((unused))
sys_wait4(pid_t pid,int * status,int options,struct rusage * rusage)256d1724ecSThomas Weißschuh pid_t sys_wait4(pid_t pid, int *status, int options, struct rusage *rusage)
266d1724ecSThomas Weißschuh {
276d1724ecSThomas Weißschuh #ifdef __NR_wait4
286d1724ecSThomas Weißschuh return my_syscall4(__NR_wait4, pid, status, options, rusage);
296d1724ecSThomas Weißschuh #else
306d1724ecSThomas Weißschuh return __nolibc_enosys(__func__, pid, status, options, rusage);
316d1724ecSThomas Weißschuh #endif
326d1724ecSThomas Weißschuh }
336d1724ecSThomas Weißschuh
346d1724ecSThomas Weißschuh static __attribute__((unused))
wait4(pid_t pid,int * status,int options,struct rusage * rusage)356d1724ecSThomas Weißschuh pid_t wait4(pid_t pid, int *status, int options, struct rusage *rusage)
366d1724ecSThomas Weißschuh {
376d1724ecSThomas Weißschuh return __sysret(sys_wait4(pid, status, options, rusage));
386d1724ecSThomas Weißschuh }
396d1724ecSThomas Weißschuh
406d1724ecSThomas Weißschuh static __attribute__((unused))
sys_waitid(int which,pid_t pid,siginfo_t * infop,int options,struct rusage * rusage)416d1724ecSThomas Weißschuh int sys_waitid(int which, pid_t pid, siginfo_t *infop, int options, struct rusage *rusage)
426d1724ecSThomas Weißschuh {
436d1724ecSThomas Weißschuh return my_syscall5(__NR_waitid, which, pid, infop, options, rusage);
446d1724ecSThomas Weißschuh }
456d1724ecSThomas Weißschuh
466d1724ecSThomas Weißschuh static __attribute__((unused))
waitid(int which,pid_t pid,siginfo_t * infop,int options)476d1724ecSThomas Weißschuh int waitid(int which, pid_t pid, siginfo_t *infop, int options)
486d1724ecSThomas Weißschuh {
496d1724ecSThomas Weißschuh return __sysret(sys_waitid(which, pid, infop, options, NULL));
506d1724ecSThomas Weißschuh }
516d1724ecSThomas Weißschuh
526d1724ecSThomas Weißschuh
530c89abf5SThomas Weißschuh static __attribute__((unused))
waitpid(pid_t pid,int * status,int options)540c89abf5SThomas Weißschuh pid_t waitpid(pid_t pid, int *status, int options)
550c89abf5SThomas Weißschuh {
560c89abf5SThomas Weißschuh int idtype, ret;
570c89abf5SThomas Weißschuh siginfo_t info;
580c89abf5SThomas Weißschuh pid_t id;
590c89abf5SThomas Weißschuh
600c89abf5SThomas Weißschuh if (pid == INT_MIN) {
610c89abf5SThomas Weißschuh SET_ERRNO(ESRCH);
620c89abf5SThomas Weißschuh return -1;
630c89abf5SThomas Weißschuh } else if (pid < -1) {
640c89abf5SThomas Weißschuh idtype = P_PGID;
650c89abf5SThomas Weißschuh id = -pid;
660c89abf5SThomas Weißschuh } else if (pid == -1) {
670c89abf5SThomas Weißschuh idtype = P_ALL;
680c89abf5SThomas Weißschuh id = 0;
690c89abf5SThomas Weißschuh } else if (pid == 0) {
700c89abf5SThomas Weißschuh idtype = P_PGID;
710c89abf5SThomas Weißschuh id = 0;
720c89abf5SThomas Weißschuh } else {
730c89abf5SThomas Weißschuh idtype = P_PID;
740c89abf5SThomas Weißschuh id = pid;
750c89abf5SThomas Weißschuh }
760c89abf5SThomas Weißschuh
770c89abf5SThomas Weißschuh options |= WEXITED;
780c89abf5SThomas Weißschuh
790c89abf5SThomas Weißschuh ret = waitid(idtype, id, &info, options);
800c89abf5SThomas Weißschuh if (ret)
810c89abf5SThomas Weißschuh return ret;
820c89abf5SThomas Weißschuh
830c89abf5SThomas Weißschuh switch (info.si_code) {
840c89abf5SThomas Weißschuh case 0:
850c89abf5SThomas Weißschuh *status = 0;
860c89abf5SThomas Weißschuh break;
870c89abf5SThomas Weißschuh case CLD_EXITED:
880c89abf5SThomas Weißschuh *status = (info.si_status & 0xff) << 8;
890c89abf5SThomas Weißschuh break;
900c89abf5SThomas Weißschuh case CLD_KILLED:
910c89abf5SThomas Weißschuh *status = info.si_status & 0x7f;
920c89abf5SThomas Weißschuh break;
930c89abf5SThomas Weißschuh case CLD_DUMPED:
940c89abf5SThomas Weißschuh *status = (info.si_status & 0x7f) | 0x80;
950c89abf5SThomas Weißschuh break;
960c89abf5SThomas Weißschuh case CLD_STOPPED:
970c89abf5SThomas Weißschuh case CLD_TRAPPED:
980c89abf5SThomas Weißschuh *status = (info.si_status << 8) + 0x7f;
990c89abf5SThomas Weißschuh break;
1000c89abf5SThomas Weißschuh case CLD_CONTINUED:
1010c89abf5SThomas Weißschuh *status = 0xffff;
1020c89abf5SThomas Weißschuh break;
1030c89abf5SThomas Weißschuh default:
1040c89abf5SThomas Weißschuh return -1;
1050c89abf5SThomas Weißschuh }
1060c89abf5SThomas Weißschuh
1070c89abf5SThomas Weißschuh return info.si_pid;
1080c89abf5SThomas Weißschuh }
1090c89abf5SThomas Weißschuh
110*59303930SThomas Weißschuh static __attribute__((unused))
wait(int * status)111*59303930SThomas Weißschuh pid_t wait(int *status)
112*59303930SThomas Weißschuh {
113*59303930SThomas Weißschuh return waitpid(-1, status, 0);
114*59303930SThomas Weißschuh }
115*59303930SThomas Weißschuh
1166d1724ecSThomas Weißschuh #endif /* _NOLIBC_SYS_WAIT_H */
117