From: Tulio A M Mendes Date: Sun, 15 Feb 2026 00:48:48 +0000 (-0300) Subject: feat: waitid syscall (P_ALL, P_PID) with siginfo_t output X-Git-Url: https://projects.tadryanom.me/docs/static/gitweb.js?a=commitdiff_plain;h=bd67b526435c739c7cfe28b3cec7ee3bc780f649;p=AdrOS.git feat: waitid syscall (P_ALL, P_PID) with siginfo_t output - SYSCALL_WAITID = 94, wraps process_waitpid internally - Fills minimal siginfo: si_signo=SIGCHLD, si_code=CLD_EXITED, si_pid, si_status - Supports P_ALL (idtype=0) and P_PID (idtype=1) - 35/35 smoke tests pass, cppcheck clean --- diff --git a/include/syscall.h b/include/syscall.h index c2b4b0c..d2f8de9 100644 --- a/include/syscall.h +++ b/include/syscall.h @@ -117,6 +117,7 @@ enum { SYSCALL_SETEGID = 91, SYSCALL_SETITIMER = 92, SYSCALL_GETITIMER = 93, + SYSCALL_WAITID = 94, }; #endif diff --git a/src/kernel/syscall.c b/src/kernel/syscall.c index 3cd4bf4..6453072 100644 --- a/src/kernel/syscall.c +++ b/src/kernel/syscall.c @@ -2190,6 +2190,56 @@ void syscall_handler(struct registers* regs) { return; } + if (syscall_no == SYSCALL_WAITID) { + /* waitid(idtype, id, siginfo_t* infop, options) + * idtype: 0=P_ALL, 1=P_PID, 2=P_PGID */ + uint32_t idtype = sc_arg0(regs); + uint32_t id = sc_arg1(regs); + void* user_infop = (void*)sc_arg2(regs); + uint32_t options = (uint32_t)((int32_t)sc_arg3(regs)); + + int wait_pid_arg; + if (idtype == 0) wait_pid_arg = -1; /* P_ALL */ + else if (idtype == 1) wait_pid_arg = (int)id; /* P_PID */ + else { sc_ret(regs) = (uint32_t)-EINVAL; return; } + + if (user_infop && user_range_ok(user_infop, 16) == 0) { + sc_ret(regs) = (uint32_t)-EFAULT; + return; + } + + int status = 0; + int retpid = process_waitpid(wait_pid_arg, &status, options); + if (retpid < 0) { + sc_ret(regs) = (uint32_t)retpid; + return; + } + if (retpid == 0) { + /* WNOHANG, no child changed state yet */ + if (user_infop) { + uint32_t zero[4] = {0, 0, 0, 0}; + (void)copy_to_user(user_infop, zero, 16); + } + sc_ret(regs) = 0; + return; + } + if (user_infop) { + /* Fill minimal siginfo: si_signo=SIGCHLD(17), si_code=CLD_EXITED(1), + * si_pid, si_status */ + uint32_t info[4]; + info[0] = 17; /* si_signo = SIGCHLD */ + info[1] = 1; /* si_code = CLD_EXITED */ + info[2] = (uint32_t)retpid; /* si_pid */ + info[3] = (uint32_t)status; /* si_status */ + if (copy_to_user(user_infop, info, 16) < 0) { + sc_ret(regs) = (uint32_t)-EFAULT; + return; + } + } + sc_ret(regs) = 0; + return; + } + if (syscall_no == SYSCALL_LSEEK) { int fd = (int)sc_arg0(regs); int32_t off = (int32_t)sc_arg1(regs);