1 /*- 2 * SPDX-License-Identifier: BSD-2-Clause 3 * 4 * Copyright (c) 1994-1995 Søren Schmidt 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 19 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 * SUCH DAMAGE. 27 */ 28 29 #include <sys/cdefs.h> 30 __FBSDID("$FreeBSD$"); 31 32 #include <sys/param.h> 33 #include <sys/systm.h> 34 #include <sys/ktr.h> 35 #include <sys/lock.h> 36 #include <sys/mutex.h> 37 #include <sys/sx.h> 38 #include <sys/proc.h> 39 #include <sys/signalvar.h> 40 #include <sys/syscallsubr.h> 41 #include <sys/sysproto.h> 42 43 #include <security/audit/audit.h> 44 45 #include "opt_compat.h" 46 47 #ifdef COMPAT_LINUX32 48 #include <machine/../linux32/linux.h> 49 #include <machine/../linux32/linux32_proto.h> 50 #else 51 #include <machine/../linux/linux.h> 52 #include <machine/../linux/linux_proto.h> 53 #endif 54 #include <compat/linux/linux_mib.h> 55 #include <compat/linux/linux_signal.h> 56 #include <compat/linux/linux_timer.h> 57 #include <compat/linux/linux_util.h> 58 #include <compat/linux/linux_emul.h> 59 #include <compat/linux/linux_misc.h> 60 61 static int linux_do_tkill(struct thread *td, struct thread *tdt, 62 ksiginfo_t *ksi); 63 static void sicode_to_lsicode(int si_code, int *lsi_code); 64 static int linux_common_rt_sigtimedwait(struct thread *, 65 l_sigset_t *, struct timespec *, l_siginfo_t *, 66 l_size_t); 67 68 static void 69 linux_to_bsd_sigaction(l_sigaction_t *lsa, struct sigaction *bsa) 70 { 71 unsigned long flags; 72 73 linux_to_bsd_sigset(&lsa->lsa_mask, &bsa->sa_mask); 74 bsa->sa_handler = PTRIN(lsa->lsa_handler); 75 bsa->sa_flags = 0; 76 77 flags = lsa->lsa_flags; 78 if (lsa->lsa_flags & LINUX_SA_NOCLDSTOP) { 79 flags &= ~LINUX_SA_NOCLDSTOP; 80 bsa->sa_flags |= SA_NOCLDSTOP; 81 } 82 if (lsa->lsa_flags & LINUX_SA_NOCLDWAIT) { 83 flags &= ~LINUX_SA_NOCLDWAIT; 84 bsa->sa_flags |= SA_NOCLDWAIT; 85 } 86 if (lsa->lsa_flags & LINUX_SA_SIGINFO) { 87 flags &= ~LINUX_SA_SIGINFO; 88 bsa->sa_flags |= SA_SIGINFO; 89 #ifdef notyet 90 /* 91 * XXX: We seem to be missing code to convert 92 * some of the fields in ucontext_t. 93 */ 94 linux_msg(curthread, 95 "partially unsupported sigaction flag SA_SIGINFO"); 96 #endif 97 } 98 if (lsa->lsa_flags & LINUX_SA_RESTORER) { 99 flags &= ~LINUX_SA_RESTORER; 100 /* 101 * We ignore the lsa_restorer and always use our own signal 102 * trampoline instead. It looks like SA_RESTORER is obsolete 103 * in Linux too - it doesn't seem to be used at all on arm64. 104 * In any case: see Linux sigreturn(2). 105 */ 106 } 107 if (lsa->lsa_flags & LINUX_SA_ONSTACK) { 108 flags &= ~LINUX_SA_ONSTACK; 109 bsa->sa_flags |= SA_ONSTACK; 110 } 111 if (lsa->lsa_flags & LINUX_SA_RESTART) { 112 flags &= ~LINUX_SA_RESTART; 113 bsa->sa_flags |= SA_RESTART; 114 } 115 if (lsa->lsa_flags & LINUX_SA_INTERRUPT) { 116 flags &= ~LINUX_SA_INTERRUPT; 117 /* Documented to be a "historical no-op". */ 118 } 119 if (lsa->lsa_flags & LINUX_SA_ONESHOT) { 120 flags &= ~LINUX_SA_ONESHOT; 121 bsa->sa_flags |= SA_RESETHAND; 122 } 123 if (lsa->lsa_flags & LINUX_SA_NOMASK) { 124 flags &= ~LINUX_SA_NOMASK; 125 bsa->sa_flags |= SA_NODEFER; 126 } 127 128 if (flags != 0) 129 linux_msg(curthread, "unsupported sigaction flag %#lx", flags); 130 } 131 132 static void 133 bsd_to_linux_sigaction(struct sigaction *bsa, l_sigaction_t *lsa) 134 { 135 136 bsd_to_linux_sigset(&bsa->sa_mask, &lsa->lsa_mask); 137 #ifdef COMPAT_LINUX32 138 lsa->lsa_handler = (uintptr_t)bsa->sa_handler; 139 #else 140 lsa->lsa_handler = bsa->sa_handler; 141 #endif 142 lsa->lsa_restorer = 0; /* unsupported */ 143 lsa->lsa_flags = 0; 144 if (bsa->sa_flags & SA_NOCLDSTOP) 145 lsa->lsa_flags |= LINUX_SA_NOCLDSTOP; 146 if (bsa->sa_flags & SA_NOCLDWAIT) 147 lsa->lsa_flags |= LINUX_SA_NOCLDWAIT; 148 if (bsa->sa_flags & SA_SIGINFO) 149 lsa->lsa_flags |= LINUX_SA_SIGINFO; 150 if (bsa->sa_flags & SA_ONSTACK) 151 lsa->lsa_flags |= LINUX_SA_ONSTACK; 152 if (bsa->sa_flags & SA_RESTART) 153 lsa->lsa_flags |= LINUX_SA_RESTART; 154 if (bsa->sa_flags & SA_RESETHAND) 155 lsa->lsa_flags |= LINUX_SA_ONESHOT; 156 if (bsa->sa_flags & SA_NODEFER) 157 lsa->lsa_flags |= LINUX_SA_NOMASK; 158 } 159 160 int 161 linux_do_sigaction(struct thread *td, int linux_sig, l_sigaction_t *linux_nsa, 162 l_sigaction_t *linux_osa) 163 { 164 struct sigaction act, oact, *nsa, *osa; 165 int error, sig; 166 167 if (!LINUX_SIG_VALID(linux_sig)) 168 return (EINVAL); 169 170 osa = (linux_osa != NULL) ? &oact : NULL; 171 if (linux_nsa != NULL) { 172 nsa = &act; 173 linux_to_bsd_sigaction(linux_nsa, nsa); 174 } else 175 nsa = NULL; 176 sig = linux_to_bsd_signal(linux_sig); 177 178 error = kern_sigaction(td, sig, nsa, osa, 0); 179 if (error) 180 return (error); 181 182 if (linux_osa != NULL) 183 bsd_to_linux_sigaction(osa, linux_osa); 184 185 return (0); 186 } 187 188 int 189 linux_sigaltstack(struct thread *td, struct linux_sigaltstack_args *uap) 190 { 191 stack_t ss, oss; 192 l_stack_t lss; 193 int error; 194 195 memset(&lss, 0, sizeof(lss)); 196 LINUX_CTR2(sigaltstack, "%p, %p", uap->uss, uap->uoss); 197 198 if (uap->uss != NULL) { 199 error = copyin(uap->uss, &lss, sizeof(l_stack_t)); 200 if (error != 0) 201 return (error); 202 203 ss.ss_sp = PTRIN(lss.ss_sp); 204 ss.ss_size = lss.ss_size; 205 ss.ss_flags = linux_to_bsd_sigaltstack(lss.ss_flags); 206 } 207 error = kern_sigaltstack(td, (uap->uss != NULL) ? &ss : NULL, 208 (uap->uoss != NULL) ? &oss : NULL); 209 if (error == 0 && uap->uoss != NULL) { 210 lss.ss_sp = PTROUT(oss.ss_sp); 211 lss.ss_size = oss.ss_size; 212 lss.ss_flags = bsd_to_linux_sigaltstack(oss.ss_flags); 213 error = copyout(&lss, uap->uoss, sizeof(l_stack_t)); 214 } 215 216 return (error); 217 } 218 219 #if defined(__i386__) || (defined(__amd64__) && defined(COMPAT_LINUX32)) 220 int 221 linux_signal(struct thread *td, struct linux_signal_args *args) 222 { 223 l_sigaction_t nsa, osa; 224 int error; 225 226 nsa.lsa_handler = args->handler; 227 nsa.lsa_flags = LINUX_SA_ONESHOT | LINUX_SA_NOMASK; 228 LINUX_SIGEMPTYSET(nsa.lsa_mask); 229 230 error = linux_do_sigaction(td, args->sig, &nsa, &osa); 231 td->td_retval[0] = (int)(intptr_t)osa.lsa_handler; 232 233 return (error); 234 } 235 #endif /* __i386__ || (__amd64__ && COMPAT_LINUX32) */ 236 237 int 238 linux_rt_sigaction(struct thread *td, struct linux_rt_sigaction_args *args) 239 { 240 l_sigaction_t nsa, osa; 241 int error; 242 243 if (args->sigsetsize != sizeof(l_sigset_t)) 244 return (EINVAL); 245 246 if (args->act != NULL) { 247 error = copyin(args->act, &nsa, sizeof(l_sigaction_t)); 248 if (error) 249 return (error); 250 } 251 252 error = linux_do_sigaction(td, args->sig, 253 args->act ? &nsa : NULL, 254 args->oact ? &osa : NULL); 255 256 if (args->oact != NULL && !error) { 257 error = copyout(&osa, args->oact, sizeof(l_sigaction_t)); 258 } 259 260 return (error); 261 } 262 263 static int 264 linux_do_sigprocmask(struct thread *td, int how, l_sigset_t *new, 265 l_sigset_t *old) 266 { 267 sigset_t omask, nmask; 268 sigset_t *nmaskp; 269 int error; 270 271 td->td_retval[0] = 0; 272 273 switch (how) { 274 case LINUX_SIG_BLOCK: 275 how = SIG_BLOCK; 276 break; 277 case LINUX_SIG_UNBLOCK: 278 how = SIG_UNBLOCK; 279 break; 280 case LINUX_SIG_SETMASK: 281 how = SIG_SETMASK; 282 break; 283 default: 284 return (EINVAL); 285 } 286 if (new != NULL) { 287 linux_to_bsd_sigset(new, &nmask); 288 nmaskp = &nmask; 289 } else 290 nmaskp = NULL; 291 error = kern_sigprocmask(td, how, nmaskp, &omask, 0); 292 if (error == 0 && old != NULL) 293 bsd_to_linux_sigset(&omask, old); 294 295 return (error); 296 } 297 298 #if defined(__i386__) || (defined(__amd64__) && defined(COMPAT_LINUX32)) 299 int 300 linux_sigprocmask(struct thread *td, struct linux_sigprocmask_args *args) 301 { 302 l_osigset_t mask; 303 l_sigset_t set, oset; 304 int error; 305 306 if (args->mask != NULL) { 307 error = copyin(args->mask, &mask, sizeof(l_osigset_t)); 308 if (error) 309 return (error); 310 LINUX_SIGEMPTYSET(set); 311 set.__mask = mask; 312 } 313 314 error = linux_do_sigprocmask(td, args->how, 315 args->mask ? &set : NULL, 316 args->omask ? &oset : NULL); 317 318 if (args->omask != NULL && !error) { 319 mask = oset.__mask; 320 error = copyout(&mask, args->omask, sizeof(l_osigset_t)); 321 } 322 323 return (error); 324 } 325 #endif /* __i386__ || (__amd64__ && COMPAT_LINUX32) */ 326 327 int 328 linux_rt_sigprocmask(struct thread *td, struct linux_rt_sigprocmask_args *args) 329 { 330 l_sigset_t set, oset; 331 int error; 332 333 if (args->sigsetsize != sizeof(l_sigset_t)) 334 return (EINVAL); 335 336 if (args->mask != NULL) { 337 error = copyin(args->mask, &set, sizeof(l_sigset_t)); 338 if (error) 339 return (error); 340 } 341 342 error = linux_do_sigprocmask(td, args->how, 343 args->mask ? &set : NULL, 344 args->omask ? &oset : NULL); 345 346 if (args->omask != NULL && !error) { 347 error = copyout(&oset, args->omask, sizeof(l_sigset_t)); 348 } 349 350 return (error); 351 } 352 353 #if defined(__i386__) || (defined(__amd64__) && defined(COMPAT_LINUX32)) 354 int 355 linux_sgetmask(struct thread *td, struct linux_sgetmask_args *args) 356 { 357 struct proc *p = td->td_proc; 358 l_sigset_t mask; 359 360 PROC_LOCK(p); 361 bsd_to_linux_sigset(&td->td_sigmask, &mask); 362 PROC_UNLOCK(p); 363 td->td_retval[0] = mask.__mask; 364 return (0); 365 } 366 367 int 368 linux_ssetmask(struct thread *td, struct linux_ssetmask_args *args) 369 { 370 struct proc *p = td->td_proc; 371 l_sigset_t lset; 372 sigset_t bset; 373 374 PROC_LOCK(p); 375 bsd_to_linux_sigset(&td->td_sigmask, &lset); 376 td->td_retval[0] = lset.__mask; 377 LINUX_SIGEMPTYSET(lset); 378 lset.__mask = args->mask; 379 linux_to_bsd_sigset(&lset, &bset); 380 td->td_sigmask = bset; 381 SIG_CANTMASK(td->td_sigmask); 382 signotify(td); 383 PROC_UNLOCK(p); 384 return (0); 385 } 386 387 int 388 linux_sigpending(struct thread *td, struct linux_sigpending_args *args) 389 { 390 struct proc *p = td->td_proc; 391 sigset_t bset; 392 l_sigset_t lset; 393 l_osigset_t mask; 394 395 PROC_LOCK(p); 396 bset = p->p_siglist; 397 SIGSETOR(bset, td->td_siglist); 398 SIGSETAND(bset, td->td_sigmask); 399 PROC_UNLOCK(p); 400 bsd_to_linux_sigset(&bset, &lset); 401 mask = lset.__mask; 402 return (copyout(&mask, args->mask, sizeof(mask))); 403 } 404 #endif /* __i386__ || (__amd64__ && COMPAT_LINUX32) */ 405 406 /* 407 * MPSAFE 408 */ 409 int 410 linux_rt_sigpending(struct thread *td, struct linux_rt_sigpending_args *args) 411 { 412 struct proc *p = td->td_proc; 413 sigset_t bset; 414 l_sigset_t lset; 415 416 if (args->sigsetsize > sizeof(lset)) 417 return (EINVAL); 418 /* NOT REACHED */ 419 420 PROC_LOCK(p); 421 bset = p->p_siglist; 422 SIGSETOR(bset, td->td_siglist); 423 SIGSETAND(bset, td->td_sigmask); 424 PROC_UNLOCK(p); 425 bsd_to_linux_sigset(&bset, &lset); 426 return (copyout(&lset, args->set, args->sigsetsize)); 427 } 428 429 int 430 linux_rt_sigtimedwait(struct thread *td, 431 struct linux_rt_sigtimedwait_args *args) 432 { 433 struct timespec ts, *tsa; 434 struct l_timespec lts; 435 int error; 436 437 if (args->timeout) { 438 if ((error = copyin(args->timeout, <s, sizeof(lts)))) 439 return (error); 440 error = linux_to_native_timespec(&ts, <s); 441 if (error != 0) 442 return (error); 443 tsa = &ts; 444 } else 445 tsa = NULL; 446 447 return (linux_common_rt_sigtimedwait(td, args->mask, tsa, 448 args->ptr, args->sigsetsize)); 449 } 450 451 static int 452 linux_common_rt_sigtimedwait(struct thread *td, l_sigset_t *mask, 453 struct timespec *tsa, l_siginfo_t *ptr, l_size_t sigsetsize) 454 { 455 int error, sig; 456 l_sigset_t lset; 457 sigset_t bset; 458 l_siginfo_t lsi; 459 ksiginfo_t ksi; 460 461 if (sigsetsize != sizeof(l_sigset_t)) 462 return (EINVAL); 463 464 if ((error = copyin(mask, &lset, sizeof(lset)))) 465 return (error); 466 linux_to_bsd_sigset(&lset, &bset); 467 468 ksiginfo_init(&ksi); 469 error = kern_sigtimedwait(td, bset, &ksi, tsa); 470 if (error) 471 return (error); 472 473 sig = bsd_to_linux_signal(ksi.ksi_signo); 474 475 if (ptr) { 476 memset(&lsi, 0, sizeof(lsi)); 477 siginfo_to_lsiginfo(&ksi.ksi_info, &lsi, sig); 478 error = copyout(&lsi, ptr, sizeof(lsi)); 479 } 480 if (error == 0) 481 td->td_retval[0] = sig; 482 483 return (error); 484 } 485 486 #if defined(__i386__) || (defined(__amd64__) && defined(COMPAT_LINUX32)) 487 int 488 linux_rt_sigtimedwait_time64(struct thread *td, 489 struct linux_rt_sigtimedwait_time64_args *args) 490 { 491 struct timespec ts, *tsa; 492 struct l_timespec64 lts; 493 int error; 494 495 if (args->timeout) { 496 if ((error = copyin(args->timeout, <s, sizeof(lts)))) 497 return (error); 498 error = linux_to_native_timespec64(&ts, <s); 499 if (error != 0) 500 return (error); 501 tsa = &ts; 502 } else 503 tsa = NULL; 504 505 return (linux_common_rt_sigtimedwait(td, args->mask, tsa, 506 args->ptr, args->sigsetsize)); 507 } 508 #endif /* __i386__ || (__amd64__ && COMPAT_LINUX32) */ 509 510 int 511 linux_kill(struct thread *td, struct linux_kill_args *args) 512 { 513 int l_signum; 514 515 /* 516 * Allow signal 0 as a means to check for privileges 517 */ 518 if (!LINUX_SIG_VALID(args->signum) && args->signum != 0) 519 return (EINVAL); 520 521 if (args->signum > 0) 522 l_signum = linux_to_bsd_signal(args->signum); 523 else 524 l_signum = 0; 525 526 return (kern_kill(td, args->pid, l_signum)); 527 } 528 529 static int 530 linux_do_tkill(struct thread *td, struct thread *tdt, ksiginfo_t *ksi) 531 { 532 struct proc *p; 533 int error; 534 535 p = tdt->td_proc; 536 AUDIT_ARG_SIGNUM(ksi->ksi_signo); 537 AUDIT_ARG_PID(p->p_pid); 538 AUDIT_ARG_PROCESS(p); 539 540 error = p_cansignal(td, p, ksi->ksi_signo); 541 if (error != 0 || ksi->ksi_signo == 0) 542 goto out; 543 544 tdksignal(tdt, ksi->ksi_signo, ksi); 545 546 out: 547 PROC_UNLOCK(p); 548 return (error); 549 } 550 551 int 552 linux_tgkill(struct thread *td, struct linux_tgkill_args *args) 553 { 554 struct thread *tdt; 555 ksiginfo_t ksi; 556 int sig; 557 558 if (args->pid <= 0 || args->tgid <=0) 559 return (EINVAL); 560 561 /* 562 * Allow signal 0 as a means to check for privileges 563 */ 564 if (!LINUX_SIG_VALID(args->sig) && args->sig != 0) 565 return (EINVAL); 566 567 if (args->sig > 0) 568 sig = linux_to_bsd_signal(args->sig); 569 else 570 sig = 0; 571 572 tdt = linux_tdfind(td, args->pid, args->tgid); 573 if (tdt == NULL) 574 return (ESRCH); 575 576 ksiginfo_init(&ksi); 577 ksi.ksi_signo = sig; 578 ksi.ksi_code = SI_LWP; 579 ksi.ksi_errno = 0; 580 ksi.ksi_pid = td->td_proc->p_pid; 581 ksi.ksi_uid = td->td_proc->p_ucred->cr_ruid; 582 return (linux_do_tkill(td, tdt, &ksi)); 583 } 584 585 /* 586 * Deprecated since 2.5.75. Replaced by tgkill(). 587 */ 588 int 589 linux_tkill(struct thread *td, struct linux_tkill_args *args) 590 { 591 struct thread *tdt; 592 ksiginfo_t ksi; 593 int sig; 594 595 if (args->tid <= 0) 596 return (EINVAL); 597 598 if (!LINUX_SIG_VALID(args->sig)) 599 return (EINVAL); 600 601 sig = linux_to_bsd_signal(args->sig); 602 603 tdt = linux_tdfind(td, args->tid, -1); 604 if (tdt == NULL) 605 return (ESRCH); 606 607 ksiginfo_init(&ksi); 608 ksi.ksi_signo = sig; 609 ksi.ksi_code = SI_LWP; 610 ksi.ksi_errno = 0; 611 ksi.ksi_pid = td->td_proc->p_pid; 612 ksi.ksi_uid = td->td_proc->p_ucred->cr_ruid; 613 return (linux_do_tkill(td, tdt, &ksi)); 614 } 615 616 static void 617 sicode_to_lsicode(int si_code, int *lsi_code) 618 { 619 620 switch (si_code) { 621 case SI_USER: 622 *lsi_code = LINUX_SI_USER; 623 break; 624 case SI_KERNEL: 625 *lsi_code = LINUX_SI_KERNEL; 626 break; 627 case SI_QUEUE: 628 *lsi_code = LINUX_SI_QUEUE; 629 break; 630 case SI_TIMER: 631 *lsi_code = LINUX_SI_TIMER; 632 break; 633 case SI_MESGQ: 634 *lsi_code = LINUX_SI_MESGQ; 635 break; 636 case SI_ASYNCIO: 637 *lsi_code = LINUX_SI_ASYNCIO; 638 break; 639 case SI_LWP: 640 *lsi_code = LINUX_SI_TKILL; 641 break; 642 default: 643 *lsi_code = si_code; 644 break; 645 } 646 } 647 648 void 649 siginfo_to_lsiginfo(const siginfo_t *si, l_siginfo_t *lsi, l_int sig) 650 { 651 652 /* sig alredy converted */ 653 lsi->lsi_signo = sig; 654 sicode_to_lsicode(si->si_code, &lsi->lsi_code); 655 656 switch (si->si_code) { 657 case SI_LWP: 658 lsi->lsi_pid = si->si_pid; 659 lsi->lsi_uid = si->si_uid; 660 break; 661 662 case SI_TIMER: 663 lsi->lsi_int = si->si_value.sival_int; 664 lsi->lsi_ptr = PTROUT(si->si_value.sival_ptr); 665 lsi->lsi_tid = si->si_timerid; 666 break; 667 668 case SI_QUEUE: 669 lsi->lsi_pid = si->si_pid; 670 lsi->lsi_uid = si->si_uid; 671 lsi->lsi_ptr = PTROUT(si->si_value.sival_ptr); 672 break; 673 674 case SI_ASYNCIO: 675 lsi->lsi_int = si->si_value.sival_int; 676 lsi->lsi_ptr = PTROUT(si->si_value.sival_ptr); 677 break; 678 679 default: 680 switch (sig) { 681 case LINUX_SIGPOLL: 682 /* XXX si_fd? */ 683 lsi->lsi_band = si->si_band; 684 break; 685 686 case LINUX_SIGCHLD: 687 lsi->lsi_errno = 0; 688 lsi->lsi_pid = si->si_pid; 689 lsi->lsi_uid = si->si_uid; 690 691 if (si->si_code == CLD_STOPPED) 692 lsi->lsi_status = bsd_to_linux_signal(si->si_status); 693 else if (si->si_code == CLD_CONTINUED) 694 lsi->lsi_status = bsd_to_linux_signal(SIGCONT); 695 else 696 lsi->lsi_status = si->si_status; 697 break; 698 699 case LINUX_SIGBUS: 700 case LINUX_SIGILL: 701 case LINUX_SIGFPE: 702 case LINUX_SIGSEGV: 703 lsi->lsi_addr = PTROUT(si->si_addr); 704 break; 705 706 default: 707 lsi->lsi_pid = si->si_pid; 708 lsi->lsi_uid = si->si_uid; 709 if (sig >= LINUX_SIGRTMIN) { 710 lsi->lsi_int = si->si_value.sival_int; 711 lsi->lsi_ptr = PTROUT(si->si_value.sival_ptr); 712 } 713 break; 714 } 715 break; 716 } 717 } 718 719 int 720 lsiginfo_to_siginfo(struct thread *td, const l_siginfo_t *lsi, 721 siginfo_t *si, int sig) 722 { 723 724 switch (lsi->lsi_code) { 725 case LINUX_SI_TKILL: 726 if (linux_kernver(td) >= LINUX_KERNVER_2006039) { 727 linux_msg(td, "SI_TKILL forbidden since 2.6.39"); 728 return (EPERM); 729 } 730 si->si_code = SI_LWP; 731 case LINUX_SI_QUEUE: 732 si->si_code = SI_QUEUE; 733 break; 734 case LINUX_SI_TIMER: 735 si->si_code = SI_TIMER; 736 break; 737 case LINUX_SI_MESGQ: 738 si->si_code = SI_MESGQ; 739 break; 740 case LINUX_SI_ASYNCIO: 741 si->si_code = SI_ASYNCIO; 742 break; 743 default: 744 si->si_code = lsi->lsi_code; 745 break; 746 } 747 748 si->si_signo = sig; 749 si->si_pid = td->td_proc->p_pid; 750 si->si_uid = td->td_ucred->cr_ruid; 751 si->si_value.sival_ptr = PTRIN(lsi->lsi_value.sival_ptr); 752 return (0); 753 } 754 755 int 756 linux_rt_sigqueueinfo(struct thread *td, struct linux_rt_sigqueueinfo_args *args) 757 { 758 l_siginfo_t linfo; 759 struct proc *p; 760 ksiginfo_t ksi; 761 int error; 762 int sig; 763 764 if (!LINUX_SIG_VALID(args->sig)) 765 return (EINVAL); 766 767 error = copyin(args->info, &linfo, sizeof(linfo)); 768 if (error != 0) 769 return (error); 770 771 if (linfo.lsi_code >= 0) 772 /* SI_USER, SI_KERNEL */ 773 return (EPERM); 774 775 sig = linux_to_bsd_signal(args->sig); 776 ksiginfo_init(&ksi); 777 error = lsiginfo_to_siginfo(td, &linfo, &ksi.ksi_info, sig); 778 if (error != 0) 779 return (error); 780 781 error = ESRCH; 782 if ((p = pfind_any(args->pid)) != NULL) { 783 error = p_cansignal(td, p, sig); 784 if (error != 0) { 785 PROC_UNLOCK(p); 786 return (error); 787 } 788 error = tdsendsignal(p, NULL, sig, &ksi); 789 PROC_UNLOCK(p); 790 } 791 792 return (error); 793 } 794 795 int 796 linux_rt_tgsigqueueinfo(struct thread *td, struct linux_rt_tgsigqueueinfo_args *args) 797 { 798 l_siginfo_t linfo; 799 struct thread *tds; 800 ksiginfo_t ksi; 801 int error; 802 int sig; 803 804 if (!LINUX_SIG_VALID(args->sig)) 805 return (EINVAL); 806 807 error = copyin(args->uinfo, &linfo, sizeof(linfo)); 808 if (error != 0) 809 return (error); 810 811 if (linfo.lsi_code >= 0) 812 return (EPERM); 813 814 sig = linux_to_bsd_signal(args->sig); 815 ksiginfo_init(&ksi); 816 error = lsiginfo_to_siginfo(td, &linfo, &ksi.ksi_info, sig); 817 if (error != 0) 818 return (error); 819 820 tds = linux_tdfind(td, args->tid, args->tgid); 821 if (tds == NULL) 822 return (ESRCH); 823 824 return (linux_do_tkill(td, tds, &ksi)); 825 } 826 827 int 828 linux_rt_sigsuspend(struct thread *td, struct linux_rt_sigsuspend_args *uap) 829 { 830 l_sigset_t lmask; 831 sigset_t sigmask; 832 int error; 833 834 if (uap->sigsetsize != sizeof(l_sigset_t)) 835 return (EINVAL); 836 837 error = copyin(uap->newset, &lmask, sizeof(l_sigset_t)); 838 if (error != 0) 839 return (error); 840 841 linux_to_bsd_sigset(&lmask, &sigmask); 842 return (kern_sigsuspend(td, sigmask)); 843 } 844