1 /* $NetBSD: sys_sig.c,v 1.8 2007/07/09 21:10:56 ad Exp $ */ 2 3 /*- 4 * Copyright (c) 2006, 2007 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Andrew Doran. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions 12 * are met: 13 * 1. Redistributions of source code must retain the above copyright 14 * notice, this list of conditions and the following disclaimer. 15 * 2. Redistributions in binary form must reproduce the above copyright 16 * notice, this list of conditions and the following disclaimer in the 17 * documentation and/or other materials provided with the distribution. 18 * 3. All advertising materials mentioning features or use of this software 19 * must display the following acknowledgement: 20 * This product includes software developed by the NetBSD 21 * Foundation, Inc. and its contributors. 22 * 4. Neither the name of The NetBSD Foundation nor the names of its 23 * contributors may be used to endorse or promote products derived 24 * from this software without specific prior written permission. 25 * 26 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 27 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 28 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 29 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 30 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 31 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 32 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 33 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 34 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 35 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 36 * POSSIBILITY OF SUCH DAMAGE. 37 */ 38 39 /* 40 * Copyright (c) 1982, 1986, 1989, 1991, 1993 41 * The Regents of the University of California. All rights reserved. 42 * (c) UNIX System Laboratories, Inc. 43 * All or some portions of this file are derived from material licensed 44 * to the University of California by American Telephone and Telegraph 45 * Co. or Unix System Laboratories, Inc. and are reproduced herein with 46 * the permission of UNIX System Laboratories, Inc. 47 * 48 * Redistribution and use in source and binary forms, with or without 49 * modification, are permitted provided that the following conditions 50 * are met: 51 * 1. Redistributions of source code must retain the above copyright 52 * notice, this list of conditions and the following disclaimer. 53 * 2. Redistributions in binary form must reproduce the above copyright 54 * notice, this list of conditions and the following disclaimer in the 55 * documentation and/or other materials provided with the distribution. 56 * 3. Neither the name of the University nor the names of its contributors 57 * may be used to endorse or promote products derived from this software 58 * without specific prior written permission. 59 * 60 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 61 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 62 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 63 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 64 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 65 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 66 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 67 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 68 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 69 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 70 * SUCH DAMAGE. 71 * 72 * @(#)kern_sig.c 8.14 (Berkeley) 5/14/95 73 */ 74 75 #include <sys/cdefs.h> 76 __KERNEL_RCSID(0, "$NetBSD: sys_sig.c,v 1.8 2007/07/09 21:10:56 ad Exp $"); 77 78 #include "opt_ptrace.h" 79 #include "opt_compat_netbsd.h" 80 #include "opt_compat_netbsd32.h" 81 82 #include <sys/param.h> 83 #include <sys/kernel.h> 84 #include <sys/signalvar.h> 85 #include <sys/proc.h> 86 #include <sys/pool.h> 87 #include <sys/syscallargs.h> 88 #include <sys/kauth.h> 89 #include <sys/wait.h> 90 #include <sys/kmem.h> 91 92 #ifdef COMPAT_16 93 /* ARGSUSED */ 94 int 95 compat_16_sys___sigaction14(struct lwp *l, void *v, register_t *retval) 96 { 97 struct compat_16_sys___sigaction14_args /* { 98 syscallarg(int) signum; 99 syscallarg(const struct sigaction *) nsa; 100 syscallarg(struct sigaction *) osa; 101 } */ *uap = v; 102 struct sigaction nsa, osa; 103 int error; 104 105 if (SCARG(uap, nsa)) { 106 error = copyin(SCARG(uap, nsa), &nsa, sizeof(nsa)); 107 if (error) 108 return (error); 109 } 110 error = sigaction1(l, SCARG(uap, signum), 111 SCARG(uap, nsa) ? &nsa : 0, SCARG(uap, osa) ? &osa : 0, 112 NULL, 0); 113 if (error) 114 return (error); 115 if (SCARG(uap, osa)) { 116 error = copyout(&osa, SCARG(uap, osa), sizeof(osa)); 117 if (error) 118 return (error); 119 } 120 return (0); 121 } 122 #endif 123 124 /* ARGSUSED */ 125 int 126 sys___sigaction_sigtramp(struct lwp *l, void *v, register_t *retval) 127 { 128 struct sys___sigaction_sigtramp_args /* { 129 syscallarg(int) signum; 130 syscallarg(const struct sigaction *) nsa; 131 syscallarg(struct sigaction *) osa; 132 syscallarg(void *) tramp; 133 syscallarg(int) vers; 134 } */ *uap = v; 135 struct sigaction nsa, osa; 136 int error; 137 138 if (SCARG(uap, nsa)) { 139 error = copyin(SCARG(uap, nsa), &nsa, sizeof(nsa)); 140 if (error) 141 return (error); 142 } 143 error = sigaction1(l, SCARG(uap, signum), 144 SCARG(uap, nsa) ? &nsa : 0, SCARG(uap, osa) ? &osa : 0, 145 SCARG(uap, tramp), SCARG(uap, vers)); 146 if (error) 147 return (error); 148 if (SCARG(uap, osa)) { 149 error = copyout(&osa, SCARG(uap, osa), sizeof(osa)); 150 if (error) 151 return (error); 152 } 153 return (0); 154 } 155 156 /* 157 * Manipulate signal mask. Note that we receive new mask, not pointer, and 158 * return old mask as return value; the library stub does the rest. 159 */ 160 int 161 sys___sigprocmask14(struct lwp *l, void *v, register_t *retval) 162 { 163 struct sys___sigprocmask14_args /* { 164 syscallarg(int) how; 165 syscallarg(const sigset_t *) set; 166 syscallarg(sigset_t *) oset; 167 } */ *uap = v; 168 struct proc *p = l->l_proc; 169 sigset_t nss, oss; 170 int error; 171 172 if (SCARG(uap, set)) { 173 error = copyin(SCARG(uap, set), &nss, sizeof(nss)); 174 if (error) 175 return (error); 176 } 177 mutex_enter(&p->p_smutex); 178 error = sigprocmask1(l, SCARG(uap, how), 179 SCARG(uap, set) ? &nss : 0, SCARG(uap, oset) ? &oss : 0); 180 mutex_exit(&p->p_smutex); 181 if (error) 182 return (error); 183 if (SCARG(uap, oset)) { 184 error = copyout(&oss, SCARG(uap, oset), sizeof(oss)); 185 if (error) 186 return (error); 187 } 188 return (0); 189 } 190 191 /* ARGSUSED */ 192 int 193 sys___sigpending14(struct lwp *l, void *v, register_t *retval) 194 { 195 struct sys___sigpending14_args /* { 196 syscallarg(sigset_t *) set; 197 } */ *uap = v; 198 sigset_t ss; 199 200 sigpending1(l, &ss); 201 return (copyout(&ss, SCARG(uap, set), sizeof(ss))); 202 } 203 204 /* 205 * Suspend process until signal, providing mask to be set in the meantime. 206 * Note nonstandard calling convention: libc stub passes mask, not pointer, 207 * to save a copyin. 208 */ 209 /* ARGSUSED */ 210 int 211 sys___sigsuspend14(struct lwp *l, void *v, register_t *retval) 212 { 213 struct sys___sigsuspend14_args /* { 214 syscallarg(const sigset_t *) set; 215 } */ *uap = v; 216 sigset_t ss; 217 int error; 218 219 if (SCARG(uap, set)) { 220 error = copyin(SCARG(uap, set), &ss, sizeof(ss)); 221 if (error) 222 return (error); 223 } 224 225 return (sigsuspend1(l, SCARG(uap, set) ? &ss : 0)); 226 } 227 228 /* ARGSUSED */ 229 int 230 sys___sigaltstack14(struct lwp *l, void *v, register_t *retval) 231 { 232 struct sys___sigaltstack14_args /* { 233 syscallarg(const struct sigaltstack *) nss; 234 syscallarg(struct sigaltstack *) oss; 235 } */ *uap = v; 236 struct sigaltstack nss, oss; 237 int error; 238 239 if (SCARG(uap, nss)) { 240 error = copyin(SCARG(uap, nss), &nss, sizeof(nss)); 241 if (error) 242 return (error); 243 } 244 error = sigaltstack1(l, 245 SCARG(uap, nss) ? &nss : 0, SCARG(uap, oss) ? &oss : 0); 246 if (error) 247 return (error); 248 if (SCARG(uap, oss)) { 249 error = copyout(&oss, SCARG(uap, oss), sizeof(oss)); 250 if (error) 251 return (error); 252 } 253 return (0); 254 } 255 256 /* ARGSUSED */ 257 int 258 sys_kill(struct lwp *l, void *v, register_t *retval) 259 { 260 struct sys_kill_args /* { 261 syscallarg(int) pid; 262 syscallarg(int) signum; 263 } */ *uap = v; 264 struct proc *p; 265 ksiginfo_t ksi; 266 int signum = SCARG(uap, signum); 267 int error; 268 269 if ((u_int)signum >= NSIG) 270 return (EINVAL); 271 KSI_INIT(&ksi); 272 ksi.ksi_signo = signum; 273 ksi.ksi_code = SI_USER; 274 ksi.ksi_pid = l->l_proc->p_pid; 275 ksi.ksi_uid = kauth_cred_geteuid(l->l_cred); 276 if (SCARG(uap, pid) > 0) { 277 /* kill single process */ 278 if ((p = p_find(SCARG(uap, pid), PFIND_UNLOCK_FAIL)) == NULL) 279 return (ESRCH); 280 mutex_enter(&p->p_mutex); 281 error = kauth_authorize_process(l->l_cred, 282 KAUTH_PROCESS_CANSIGNAL, p, (void *)(uintptr_t)signum, 283 NULL, NULL); 284 if (!error && signum) { 285 mutex_enter(&proclist_mutex); 286 mutex_enter(&p->p_smutex); 287 kpsignal2(p, &ksi); 288 mutex_exit(&p->p_smutex); 289 mutex_exit(&proclist_mutex); 290 } 291 mutex_exit(&p->p_mutex); 292 mutex_exit(&proclist_lock); 293 return (error); 294 } 295 switch (SCARG(uap, pid)) { 296 case -1: /* broadcast signal */ 297 return (killpg1(l, &ksi, 0, 1)); 298 case 0: /* signal own process group */ 299 return (killpg1(l, &ksi, 0, 0)); 300 default: /* negative explicit process group */ 301 return (killpg1(l, &ksi, -SCARG(uap, pid), 0)); 302 } 303 /* NOTREACHED */ 304 } 305 306 /* ARGSUSED */ 307 int 308 sys_getcontext(struct lwp *l, void *v, register_t *retval) 309 { 310 struct sys_getcontext_args /* { 311 syscallarg(struct __ucontext *) ucp; 312 } */ *uap = v; 313 struct proc *p = l->l_proc; 314 ucontext_t uc; 315 316 mutex_enter(&p->p_smutex); 317 getucontext(l, &uc); 318 mutex_exit(&p->p_smutex); 319 320 return (copyout(&uc, SCARG(uap, ucp), sizeof (*SCARG(uap, ucp)))); 321 } 322 323 /* ARGSUSED */ 324 int 325 sys_setcontext(struct lwp *l, void *v, register_t *retval) 326 { 327 struct sys_setcontext_args /* { 328 syscallarg(const ucontext_t *) ucp; 329 } */ *uap = v; 330 struct proc *p = l->l_proc; 331 ucontext_t uc; 332 int error; 333 334 error = copyin(SCARG(uap, ucp), &uc, sizeof (uc)); 335 if (error) 336 return (error); 337 if (!(uc.uc_flags & _UC_CPU)) 338 return (EINVAL); 339 mutex_enter(&p->p_smutex); 340 error = setucontext(l, &uc); 341 mutex_exit(&p->p_smutex); 342 if (error) 343 return (error); 344 345 return (EJUSTRETURN); 346 } 347 348 /* 349 * sigtimedwait(2) system call, used also for implementation 350 * of sigwaitinfo() and sigwait(). 351 * 352 * This only handles single LWP in signal wait. libpthread provides 353 * it's own sigtimedwait() wrapper to DTRT WRT individual threads. 354 */ 355 int 356 sys___sigtimedwait(struct lwp *l, void *v, register_t *retval) 357 { 358 359 return __sigtimedwait1(l, v, retval, copyout, copyin, copyout); 360 } 361 362 int 363 sigaction1(struct lwp *l, int signum, const struct sigaction *nsa, 364 struct sigaction *osa, const void *tramp, int vers) 365 { 366 struct proc *p; 367 struct sigacts *ps; 368 sigset_t tset; 369 int prop, error; 370 ksiginfoq_t kq; 371 372 if (signum <= 0 || signum >= NSIG) 373 return (EINVAL); 374 375 p = l->l_proc; 376 error = 0; 377 ksiginfo_queue_init(&kq); 378 379 /* 380 * Trampoline ABI version 0 is reserved for the legacy kernel 381 * provided on-stack trampoline. Conversely, if we are using a 382 * non-0 ABI version, we must have a trampoline. Only validate the 383 * vers if a new sigaction was supplied. Emulations use legacy 384 * kernel trampolines with version 0, alternatively check for that 385 * too. 386 */ 387 if ((vers != 0 && tramp == NULL) || 388 #ifdef SIGTRAMP_VALID 389 (nsa != NULL && 390 ((vers == 0) ? 391 (p->p_emul->e_sigcode == NULL) : 392 !SIGTRAMP_VALID(vers))) || 393 #endif 394 (vers == 0 && tramp != NULL)) { 395 return (EINVAL); 396 } 397 398 mutex_enter(&p->p_mutex); /* p_flag */ 399 mutex_enter(&p->p_smutex); 400 401 ps = p->p_sigacts; 402 if (osa) 403 *osa = SIGACTION_PS(ps, signum); 404 if (!nsa) 405 goto out; 406 407 prop = sigprop[signum]; 408 if ((nsa->sa_flags & ~SA_ALLBITS) || (prop & SA_CANTMASK)) { 409 error = EINVAL; 410 goto out; 411 } 412 413 SIGACTION_PS(ps, signum) = *nsa; 414 ps->sa_sigdesc[signum].sd_tramp = tramp; 415 ps->sa_sigdesc[signum].sd_vers = vers; 416 sigminusset(&sigcantmask, &SIGACTION_PS(ps, signum).sa_mask); 417 418 if ((prop & SA_NORESET) != 0) 419 SIGACTION_PS(ps, signum).sa_flags &= ~SA_RESETHAND; 420 421 if (signum == SIGCHLD) { 422 if (nsa->sa_flags & SA_NOCLDSTOP) 423 p->p_sflag |= PS_NOCLDSTOP; 424 else 425 p->p_sflag &= ~PS_NOCLDSTOP; 426 if (nsa->sa_flags & SA_NOCLDWAIT) { 427 /* 428 * Paranoia: since SA_NOCLDWAIT is implemented by 429 * reparenting the dying child to PID 1 (and trust 430 * it to reap the zombie), PID 1 itself is forbidden 431 * to set SA_NOCLDWAIT. 432 */ 433 if (p->p_pid == 1) 434 p->p_flag &= ~PK_NOCLDWAIT; 435 else 436 p->p_flag |= PK_NOCLDWAIT; 437 } else 438 p->p_flag &= ~PK_NOCLDWAIT; 439 440 if (nsa->sa_handler == SIG_IGN) { 441 /* 442 * Paranoia: same as above. 443 */ 444 if (p->p_pid == 1) 445 p->p_flag &= ~PK_CLDSIGIGN; 446 else 447 p->p_flag |= PK_CLDSIGIGN; 448 } else 449 p->p_flag &= ~PK_CLDSIGIGN; 450 } 451 452 if ((nsa->sa_flags & SA_NODEFER) == 0) 453 sigaddset(&SIGACTION_PS(ps, signum).sa_mask, signum); 454 else 455 sigdelset(&SIGACTION_PS(ps, signum).sa_mask, signum); 456 457 /* 458 * Set bit in p_sigctx.ps_sigignore for signals that are set to 459 * SIG_IGN, and for signals set to SIG_DFL where the default is to 460 * ignore. However, don't put SIGCONT in p_sigctx.ps_sigignore, as 461 * we have to restart the process. 462 */ 463 if (nsa->sa_handler == SIG_IGN || 464 (nsa->sa_handler == SIG_DFL && (prop & SA_IGNORE) != 0)) { 465 /* Never to be seen again. */ 466 sigemptyset(&tset); 467 sigaddset(&tset, signum); 468 sigclearall(p, &tset, &kq); 469 if (signum != SIGCONT) { 470 /* Easier in psignal */ 471 sigaddset(&p->p_sigctx.ps_sigignore, signum); 472 } 473 sigdelset(&p->p_sigctx.ps_sigcatch, signum); 474 } else { 475 sigdelset(&p->p_sigctx.ps_sigignore, signum); 476 if (nsa->sa_handler == SIG_DFL) 477 sigdelset(&p->p_sigctx.ps_sigcatch, signum); 478 else 479 sigaddset(&p->p_sigctx.ps_sigcatch, signum); 480 } 481 482 /* 483 * Previously held signals may now have become visible. Ensure that 484 * we check for them before returning to userspace. 485 */ 486 if (sigispending(l, 0)) { 487 lwp_lock(l); 488 l->l_flag |= LW_PENDSIG; 489 lwp_unlock(l); 490 } 491 out: 492 mutex_exit(&p->p_smutex); 493 mutex_exit(&p->p_mutex); 494 ksiginfo_queue_drain(&kq); 495 496 return (error); 497 } 498 499 int 500 sigprocmask1(struct lwp *l, int how, const sigset_t *nss, sigset_t *oss) 501 { 502 int more; 503 504 KASSERT(mutex_owned(&l->l_proc->p_smutex)); 505 506 if (oss) 507 *oss = l->l_sigmask; 508 if (nss) { 509 switch (how) { 510 case SIG_BLOCK: 511 sigplusset(nss, &l->l_sigmask); 512 more = 0; 513 break; 514 case SIG_UNBLOCK: 515 sigminusset(nss, &l->l_sigmask); 516 more = 1; 517 break; 518 case SIG_SETMASK: 519 l->l_sigmask = *nss; 520 more = 1; 521 break; 522 default: 523 return (EINVAL); 524 } 525 sigminusset(&sigcantmask, &l->l_sigmask); 526 if (more && sigispending(l, 0)) { 527 /* 528 * Check for pending signals on return to user. 529 */ 530 lwp_lock(l); 531 l->l_flag |= LW_PENDSIG; 532 lwp_unlock(l); 533 } 534 } 535 536 return (0); 537 } 538 539 void 540 sigpending1(struct lwp *l, sigset_t *ss) 541 { 542 struct proc *p = l->l_proc; 543 544 mutex_enter(&p->p_smutex); 545 *ss = l->l_sigpend.sp_set; 546 sigplusset(&p->p_sigpend.sp_set, ss); 547 sigminusset(&l->l_sigmask, ss); 548 mutex_exit(&p->p_smutex); 549 } 550 551 int 552 sigsuspend1(struct lwp *l, const sigset_t *ss) 553 { 554 struct proc *p; 555 556 p = l->l_proc; 557 558 if (ss) { 559 /* 560 * When returning from sigpause, we want 561 * the old mask to be restored after the 562 * signal handler has finished. Thus, we 563 * save it here and mark the sigctx structure 564 * to indicate this. 565 */ 566 mutex_enter(&p->p_smutex); 567 l->l_sigrestore = 1; 568 l->l_sigoldmask = l->l_sigmask; 569 l->l_sigmask = *ss; 570 sigminusset(&sigcantmask, &l->l_sigmask); 571 572 /* Check for pending signals when sleeping. */ 573 if (sigispending(l, 0)) { 574 lwp_lock(l); 575 l->l_flag |= LW_PENDSIG; 576 lwp_unlock(l); 577 } 578 mutex_exit(&p->p_smutex); 579 } 580 581 while (kpause("pause", true, 0, NULL) == 0) 582 ; 583 584 /* always return EINTR rather than ERESTART... */ 585 return (EINTR); 586 } 587 588 int 589 sigaltstack1(struct lwp *l, const struct sigaltstack *nss, 590 struct sigaltstack *oss) 591 { 592 struct proc *p = l->l_proc; 593 int error = 0; 594 595 mutex_enter(&p->p_smutex); 596 597 if (oss) 598 *oss = l->l_sigstk; 599 600 if (nss) { 601 if (nss->ss_flags & ~SS_ALLBITS) 602 error = EINVAL; 603 else if (nss->ss_flags & SS_DISABLE) { 604 if (l->l_sigstk.ss_flags & SS_ONSTACK) 605 error = EINVAL; 606 } else if (nss->ss_size < MINSIGSTKSZ) 607 error = ENOMEM; 608 609 if (!error) 610 l->l_sigstk = *nss; 611 } 612 613 mutex_exit(&p->p_smutex); 614 615 return (error); 616 } 617 618 int 619 __sigtimedwait1(struct lwp *l, void *v, register_t *retval, 620 copyout_t put_info, copyin_t fetch_timeout, copyout_t put_timeout) 621 { 622 struct sys___sigtimedwait_args /* { 623 syscallarg(const sigset_t *) set; 624 syscallarg(siginfo_t *) info; 625 syscallarg(struct timespec *) timeout; 626 } */ *uap = v; 627 struct proc *p = l->l_proc; 628 int error, signum; 629 int timo = 0; 630 struct timespec ts, tsstart, tsnow; 631 ksiginfo_t *ksi; 632 633 memset(&tsstart, 0, sizeof tsstart); /* XXX gcc */ 634 635 /* 636 * Calculate timeout, if it was specified. 637 */ 638 if (SCARG(uap, timeout)) { 639 uint64_t ms; 640 641 if ((error = (*fetch_timeout)(SCARG(uap, timeout), &ts, sizeof(ts)))) 642 return (error); 643 644 ms = (ts.tv_sec * 1000) + (ts.tv_nsec / 1000000); 645 timo = mstohz(ms); 646 if (timo == 0 && ts.tv_sec == 0 && ts.tv_nsec > 0) 647 timo = 1; 648 if (timo <= 0) 649 return (EAGAIN); 650 651 /* 652 * Remember current uptime, it would be used in 653 * ECANCELED/ERESTART case. 654 */ 655 getnanouptime(&tsstart); 656 } 657 658 error = copyin(SCARG(uap, set), &l->l_sigwaitset, 659 sizeof(l->l_sigwaitset)); 660 if (error != 0) 661 return (error); 662 663 /* 664 * Silently ignore SA_CANTMASK signals. psignal1() would ignore 665 * SA_CANTMASK signals in waitset, we do this only for the below 666 * siglist check. 667 */ 668 sigminusset(&sigcantmask, &l->l_sigwaitset); 669 670 /* 671 * Allocate a ksi up front. We can't sleep with the mutex held. 672 */ 673 KERNEL_LOCK(1, l); /* XXXSMP ksiginfo_alloc() -> pool_get() */ 674 ksi = ksiginfo_alloc(p, NULL, PR_WAITOK); 675 KERNEL_UNLOCK_ONE(l); /* XXXSMP */ 676 if (ksi == NULL) 677 return (ENOMEM); 678 679 mutex_enter(&p->p_smutex); 680 681 if ((signum = sigget(&p->p_sigpend, ksi, 0, &l->l_sigwaitset)) == 0) 682 signum = sigget(&l->l_sigpend, ksi, 0, &l->l_sigwaitset); 683 684 if (signum != 0) { 685 /* 686 * We found a pending signal - copy it out to the user. 687 */ 688 mutex_exit(&p->p_smutex); 689 goto out; 690 } 691 692 /* 693 * Set up the sigwait list. 694 */ 695 l->l_sigwaited = ksi; 696 LIST_INSERT_HEAD(&p->p_sigwaiters, l, l_sigwaiter); 697 698 /* 699 * Wait for signal to arrive. We can either be woken up or time out. 700 */ 701 error = cv_timedwait_sig(&l->l_sigcv, &p->p_smutex, timo); 702 703 /* 704 * Need to find out if we woke as a result of lwp_wakeup() or a 705 * signal outside our wait set. 706 */ 707 if (l->l_sigwaited != NULL) { 708 if (error == EINTR) { 709 /* wakeup via _lwp_wakeup() */ 710 error = ECANCELED; 711 } else if (!error) { 712 /* spurious wakeup - arrange for syscall restart */ 713 error = ERESTART; 714 } 715 l->l_sigwaited = NULL; 716 LIST_REMOVE(l, l_sigwaiter); 717 } 718 719 mutex_exit(&p->p_smutex); 720 721 /* 722 * If the sleep was interrupted (either by signal or wakeup), update 723 * the timeout and copyout new value back. It would be used when 724 * the syscall would be restarted or called again. 725 */ 726 if (timo && (error == ERESTART || error == ECANCELED)) { 727 getnanouptime(&tsnow); 728 729 /* compute how much time has passed since start */ 730 timespecsub(&tsnow, &tsstart, &tsnow); 731 /* substract passed time from timeout */ 732 timespecsub(&ts, &tsnow, &ts); 733 734 if (ts.tv_sec < 0) 735 error = EAGAIN; 736 else { 737 /* copy updated timeout to userland */ 738 error = (*put_timeout)(&ts, SCARG(uap, timeout), 739 sizeof(ts)); 740 } 741 } 742 743 /* 744 * If a signal from the wait set arrived, copy it to userland. 745 * Copy only the used part of siginfo, the padding part is 746 * left unchanged (userland is not supposed to touch it anyway). 747 */ 748 out: 749 if (error == 0) 750 error = (*put_info)(&ksi->ksi_info, SCARG(uap, info), 751 sizeof(ksi->ksi_info)); 752 753 KERNEL_LOCK(1, l); /* XXXSMP ksiginfo_free() -> pool_put() */ 754 ksiginfo_free(ksi); 755 KERNEL_UNLOCK_ONE(l); /* XXXSMP */ 756 757 return error; 758 } 759