1 1.55 mlelstv /* $NetBSD: netbsd32_signal.c,v 1.55 2024/11/22 10:41:50 mlelstv Exp $ */ 2 1.1 mrg 3 1.1 mrg /* 4 1.1 mrg * Copyright (c) 1998, 2001 Matthew R. Green 5 1.1 mrg * All rights reserved. 6 1.1 mrg * 7 1.1 mrg * Redistribution and use in source and binary forms, with or without 8 1.1 mrg * modification, are permitted provided that the following conditions 9 1.1 mrg * are met: 10 1.1 mrg * 1. Redistributions of source code must retain the above copyright 11 1.1 mrg * notice, this list of conditions and the following disclaimer. 12 1.1 mrg * 2. Redistributions in binary form must reproduce the above copyright 13 1.1 mrg * notice, this list of conditions and the following disclaimer in the 14 1.1 mrg * documentation and/or other materials provided with the distribution. 15 1.1 mrg * 16 1.1 mrg * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 17 1.1 mrg * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 18 1.1 mrg * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 19 1.1 mrg * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 20 1.1 mrg * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 21 1.1 mrg * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 22 1.1 mrg * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 23 1.1 mrg * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 24 1.1 mrg * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25 1.1 mrg * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 1.1 mrg * SUCH DAMAGE. 27 1.1 mrg */ 28 1.2 lukem 29 1.2 lukem #include <sys/cdefs.h> 30 1.55 mlelstv __KERNEL_RCSID(0, "$NetBSD: netbsd32_signal.c,v 1.55 2024/11/22 10:41:50 mlelstv Exp $"); 31 1.41 christos 32 1.41 christos #if defined(_KERNEL_OPT) 33 1.41 christos #include "opt_ktrace.h" 34 1.41 christos #endif 35 1.1 mrg 36 1.1 mrg #include <sys/param.h> 37 1.1 mrg #include <sys/systm.h> 38 1.1 mrg #include <sys/mount.h> 39 1.1 mrg #include <sys/stat.h> 40 1.1 mrg #include <sys/time.h> 41 1.1 mrg #include <sys/signalvar.h> 42 1.40 martin #include <sys/ktrace.h> 43 1.1 mrg #include <sys/proc.h> 44 1.7 fvdl #include <sys/wait.h> 45 1.11 christos #include <sys/dirent.h> 46 1.53 thorpej #include <sys/module.h> 47 1.53 thorpej #include <sys/exec.h> 48 1.7 fvdl 49 1.7 fvdl #include <uvm/uvm_extern.h> 50 1.1 mrg 51 1.1 mrg #include <compat/netbsd32/netbsd32.h> 52 1.10 cube #include <compat/netbsd32/netbsd32_conv.h> 53 1.53 thorpej #include <compat/netbsd32/netbsd32_exec.h> 54 1.1 mrg #include <compat/netbsd32/netbsd32_syscallargs.h> 55 1.1 mrg 56 1.12 christos #include <compat/sys/signal.h> 57 1.12 christos #include <compat/sys/signalvar.h> 58 1.13 christos #include <compat/sys/siginfo.h> 59 1.12 christos #include <compat/sys/ucontext.h> 60 1.25 dsl #include <compat/common/compat_sigaltstack.h> 61 1.12 christos 62 1.1 mrg int 63 1.28 dsl netbsd32_sigaction(struct lwp *l, const struct netbsd32_sigaction_args *uap, register_t *retval) 64 1.1 mrg { 65 1.28 dsl /* { 66 1.1 mrg syscallarg(int) signum; 67 1.1 mrg syscallarg(const netbsd32_sigactionp_t) nsa; 68 1.1 mrg syscallarg(netbsd32_sigactionp_t) osa; 69 1.28 dsl } */ 70 1.1 mrg struct sigaction nsa, osa; 71 1.38 christos struct netbsd32_sigaction13 *sa32p, sa32; 72 1.1 mrg int error; 73 1.1 mrg 74 1.23 dsl if (SCARG_P32(uap, nsa)) { 75 1.23 dsl sa32p = SCARG_P32(uap, nsa); 76 1.1 mrg if (copyin(sa32p, &sa32, sizeof(sa32))) 77 1.1 mrg return EFAULT; 78 1.5 atatat nsa.sa_handler = (void *)NETBSD32PTR64(sa32.netbsd32_sa_handler); 79 1.38 christos memset(&nsa.sa_mask, 0, sizeof(nsa.sa_mask)); 80 1.38 christos nsa.sa_mask.__bits[0] = sa32.netbsd32_sa_mask; 81 1.5 atatat nsa.sa_flags = sa32.netbsd32_sa_flags; 82 1.1 mrg } 83 1.19 ad error = sigaction1(l, SCARG(uap, signum), 84 1.23 dsl SCARG_P32(uap, nsa) ? &nsa : 0, 85 1.23 dsl SCARG_P32(uap, osa) ? &osa : 0, 86 1.3 thorpej NULL, 0); 87 1.8 perry 88 1.1 mrg if (error) 89 1.51 simonb return error; 90 1.1 mrg 91 1.23 dsl if (SCARG_P32(uap, osa)) { 92 1.52 riastrad memset(&sa32, 0, sizeof(sa32)); 93 1.22 dsl NETBSD32PTR32(sa32.netbsd32_sa_handler, osa.sa_handler); 94 1.38 christos sa32.netbsd32_sa_mask = osa.sa_mask.__bits[0]; 95 1.5 atatat sa32.netbsd32_sa_flags = osa.sa_flags; 96 1.23 dsl sa32p = SCARG_P32(uap, osa); 97 1.1 mrg if (copyout(&sa32, sa32p, sizeof(sa32))) 98 1.1 mrg return EFAULT; 99 1.1 mrg } 100 1.1 mrg 101 1.51 simonb return 0; 102 1.1 mrg } 103 1.1 mrg 104 1.1 mrg int 105 1.28 dsl netbsd32___sigaltstack14(struct lwp *l, const struct netbsd32___sigaltstack14_args *uap, register_t *retval) 106 1.1 mrg { 107 1.28 dsl /* { 108 1.1 mrg syscallarg(const netbsd32_sigaltstackp_t) nss; 109 1.1 mrg syscallarg(netbsd32_sigaltstackp_t) oss; 110 1.28 dsl } */ 111 1.25 dsl compat_sigaltstack(uap, netbsd32_sigaltstack, SS_ONSTACK, SS_DISABLE); 112 1.1 mrg } 113 1.1 mrg 114 1.1 mrg /* ARGSUSED */ 115 1.1 mrg int 116 1.28 dsl netbsd32___sigaction14(struct lwp *l, const struct netbsd32___sigaction14_args *uap, register_t *retval) 117 1.1 mrg { 118 1.28 dsl /* { 119 1.1 mrg syscallarg(int) signum; 120 1.1 mrg syscallarg(const struct sigaction *) nsa; 121 1.1 mrg syscallarg(struct sigaction *) osa; 122 1.28 dsl } */ 123 1.1 mrg struct netbsd32_sigaction sa32; 124 1.1 mrg struct sigaction nsa, osa; 125 1.1 mrg int error; 126 1.1 mrg 127 1.23 dsl if (SCARG_P32(uap, nsa)) { 128 1.23 dsl error = copyin(SCARG_P32(uap, nsa), &sa32, sizeof(sa32)); 129 1.1 mrg if (error) 130 1.51 simonb return error; 131 1.22 dsl nsa.sa_handler = NETBSD32PTR64(sa32.netbsd32_sa_handler); 132 1.5 atatat nsa.sa_mask = sa32.netbsd32_sa_mask; 133 1.5 atatat nsa.sa_flags = sa32.netbsd32_sa_flags; 134 1.1 mrg } 135 1.19 ad error = sigaction1(l, SCARG(uap, signum), 136 1.23 dsl SCARG_P32(uap, nsa) ? &nsa : 0, 137 1.23 dsl SCARG_P32(uap, osa) ? &osa : 0, 138 1.22 dsl NULL, 0); 139 1.1 mrg if (error) 140 1.51 simonb return error; 141 1.23 dsl if (SCARG_P32(uap, osa)) { 142 1.52 riastrad memset(&sa32, 0, sizeof(sa32)); 143 1.22 dsl NETBSD32PTR32(sa32.netbsd32_sa_handler, osa.sa_handler); 144 1.5 atatat sa32.netbsd32_sa_mask = osa.sa_mask; 145 1.5 atatat sa32.netbsd32_sa_flags = osa.sa_flags; 146 1.23 dsl error = copyout(&sa32, SCARG_P32(uap, osa), sizeof(sa32)); 147 1.4 scw if (error) 148 1.51 simonb return error; 149 1.4 scw } 150 1.51 simonb return 0; 151 1.4 scw } 152 1.4 scw 153 1.4 scw /* ARGSUSED */ 154 1.4 scw int 155 1.28 dsl netbsd32___sigaction_sigtramp(struct lwp *l, const struct netbsd32___sigaction_sigtramp_args *uap, register_t *retval) 156 1.4 scw { 157 1.28 dsl /* { 158 1.4 scw syscallarg(int) signum; 159 1.4 scw syscallarg(const netbsd32_sigactionp_t) nsa; 160 1.4 scw syscallarg(netbsd32_sigactionp_t) osa; 161 1.4 scw syscallarg(netbsd32_voidp) tramp; 162 1.4 scw syscallarg(int) vers; 163 1.28 dsl } */ 164 1.4 scw struct netbsd32_sigaction sa32; 165 1.4 scw struct sigaction nsa, osa; 166 1.53 thorpej int error, vers; 167 1.4 scw 168 1.23 dsl if (SCARG_P32(uap, nsa)) { 169 1.23 dsl error = copyin(SCARG_P32(uap, nsa), &sa32, sizeof(sa32)); 170 1.4 scw if (error) 171 1.51 simonb return error; 172 1.22 dsl nsa.sa_handler = NETBSD32PTR64(sa32.netbsd32_sa_handler); 173 1.5 atatat nsa.sa_mask = sa32.netbsd32_sa_mask; 174 1.5 atatat nsa.sa_flags = sa32.netbsd32_sa_flags; 175 1.4 scw } 176 1.53 thorpej vers = SCARG(uap, vers); 177 1.53 thorpej #ifndef __HAVE_MD_NETBSD32_SENDSIG /* XXX paying for yesterday's sins */ 178 1.53 thorpej if (vers < __SIGTRAMP_SIGINFO_VERSION_MIN) { 179 1.53 thorpej /* 180 1.53 thorpej * sigaction1() doesn't enforce sigcontext-ness for 181 1.53 thorpej * __SIGTRAMP_SIGCODE_VERSION because it might be 182 1.53 thorpej * a foreign emulation. However, we know these are 183 1.53 thorpej * native NetBSD 32-bit binaries, so we do. 184 1.53 thorpej */ 185 1.53 thorpej #ifdef __HAVE_STRUCT_SIGCONTEXT 186 1.53 thorpej struct proc *p = l->l_proc; 187 1.54 mlelstv bool sigcontext_valid; 188 1.53 thorpej 189 1.53 thorpej /* 190 1.53 thorpej * We need to ensure the compat_netbsd32_16 module 191 1.53 thorpej * is loaded, because sigaction1() gives a free pass 192 1.53 thorpej * to processes marked PK_32 (it can't be sure which 193 1.53 thorpej * 32-bit compat module is needed). 194 1.53 thorpej */ 195 1.53 thorpej if ((p->p_lflag & PL_SIGCOMPAT) == 0) { 196 1.53 thorpej kernconfig_lock(); 197 1.53 thorpej (void)module_autoload("compat_netbsd32_16", 198 1.53 thorpej MODULE_CLASS_ANY); 199 1.54 mlelstv sigcontext_valid = netbsd32_sendsig_sigcontext_16_hook.hooked; 200 1.53 thorpej mutex_enter(&proc_lock); 201 1.53 thorpej /* 202 1.53 thorpej * Prevent unload of compat module while 203 1.53 thorpej * this process remains. 204 1.53 thorpej */ 205 1.53 thorpej p->p_lflag |= PL_SIGCOMPAT; 206 1.53 thorpej mutex_exit(&proc_lock); 207 1.53 thorpej kernconfig_unlock(); 208 1.54 mlelstv } else { 209 1.54 mlelstv /* 210 1.54 mlelstv * Module is already loaded and locked in memory 211 1.54 mlelstv */ 212 1.54 mlelstv sigcontext_valid = netbsd32_sendsig_sigcontext_16_hook.hooked; 213 1.53 thorpej } 214 1.53 thorpej if (!sigcontext_valid) { 215 1.53 thorpej return EINVAL; 216 1.53 thorpej } 217 1.55 mlelstv // #else /* ! __HAVE_STRUCT_SIGCONTEXT */ 218 1.55 mlelstv // return EINVAL; 219 1.53 thorpej #endif /* __HAVE_STRUCT_SIGCONTEXT */ 220 1.53 thorpej } 221 1.53 thorpej #endif /* __HAVE_MD_NETBSD32_SENDSIG */ 222 1.19 ad error = sigaction1(l, SCARG(uap, signum), 223 1.23 dsl SCARG_P32(uap, nsa) ? &nsa : 0, 224 1.23 dsl SCARG_P32(uap, osa) ? &osa : 0, 225 1.53 thorpej SCARG_P32(uap, tramp), vers); 226 1.4 scw if (error) 227 1.51 simonb return error; 228 1.23 dsl if (SCARG_P32(uap, osa)) { 229 1.52 riastrad memset(&sa32, 0, sizeof(sa32)); 230 1.22 dsl NETBSD32PTR32(sa32.netbsd32_sa_handler, osa.sa_handler); 231 1.5 atatat sa32.netbsd32_sa_mask = osa.sa_mask; 232 1.5 atatat sa32.netbsd32_sa_flags = osa.sa_flags; 233 1.23 dsl error = copyout(&sa32, SCARG_P32(uap, osa), sizeof(sa32)); 234 1.1 mrg if (error) 235 1.51 simonb return error; 236 1.1 mrg } 237 1.51 simonb return 0; 238 1.7 fvdl } 239 1.7 fvdl 240 1.53 thorpej #ifndef __HAVE_MD_NETBSD32_SENDSIG /* XXX paying for yesterday's sins */ 241 1.53 thorpej #ifdef __HAVE_STRUCT_SIGCONTEXT 242 1.53 thorpej struct netbsd32_sendsig_sigcontext_16_hook_t netbsd32_sendsig_sigcontext_16_hook; 243 1.53 thorpej #endif 244 1.53 thorpej 245 1.53 thorpej void 246 1.53 thorpej netbsd32_sendsig(const struct ksiginfo *ksi, const sigset_t *mask) 247 1.53 thorpej { 248 1.53 thorpej struct sigacts *sa; 249 1.53 thorpej int sig; 250 1.53 thorpej 251 1.53 thorpej sig = ksi->ksi_signo; 252 1.53 thorpej sa = curproc->p_sigacts; 253 1.53 thorpej 254 1.53 thorpej switch (sa->sa_sigdesc[sig].sd_vers) { 255 1.53 thorpej #ifdef __HAVE_STRUCT_SIGCONTEXT 256 1.53 thorpej case __SIGTRAMP_SIGCODE_VERSION: 257 1.53 thorpej case __SIGTRAMP_SIGCONTEXT_VERSION_MIN ... 258 1.53 thorpej __SIGTRAMP_SIGCONTEXT_VERSION_MAX: 259 1.53 thorpej /* Compat for 1.6 and earlier. */ 260 1.53 thorpej MODULE_HOOK_CALL_VOID(netbsd32_sendsig_sigcontext_16_hook, 261 1.53 thorpej (ksi, mask), break); 262 1.53 thorpej return; 263 1.53 thorpej #endif /* __HAVE_STRUCT_SIGCONTEXT */ 264 1.53 thorpej case __SIGTRAMP_SIGINFO_VERSION_MIN ... 265 1.53 thorpej __SIGTRAMP_SIGINFO_VERSION_MAX: 266 1.53 thorpej netbsd32_sendsig_siginfo(ksi, mask); 267 1.53 thorpej return; 268 1.53 thorpej default: 269 1.53 thorpej break; 270 1.53 thorpej } 271 1.53 thorpej 272 1.53 thorpej printf("%s: bad version %d\n", __func__, sa->sa_sigdesc[sig].sd_vers); 273 1.53 thorpej sigexit(curlwp, SIGILL); 274 1.53 thorpej } 275 1.53 thorpej #endif /* __HAVE_MD_NETBSD32_SENDSIG */ 276 1.53 thorpej 277 1.39 martin void 278 1.39 martin netbsd32_ksi32_to_ksi(struct _ksiginfo *si, const struct __ksiginfo32 *si32) 279 1.7 fvdl { 280 1.46 rin size_t i; 281 1.46 rin 282 1.7 fvdl memset(si, 0, sizeof (*si)); 283 1.39 martin si->_signo = si32->_signo; 284 1.39 martin si->_code = si32->_code; 285 1.39 martin si->_errno = si32->_errno; 286 1.7 fvdl 287 1.49 rin if (si32->_code == SI_NOINFO) 288 1.49 rin return; 289 1.49 rin else if (si32->_code <= 0) /* codes described in siginfo(2) */ 290 1.49 rin goto fill_rt; 291 1.49 rin 292 1.39 martin switch (si32->_signo) { 293 1.7 fvdl case SIGILL: 294 1.47 rin case SIGFPE: 295 1.7 fvdl case SIGBUS: 296 1.7 fvdl case SIGSEGV: 297 1.46 rin fill_fault: 298 1.42 christos si->_reason._fault._addr = 299 1.42 christos NETBSD32IPTR64(si32->_reason._fault._addr); 300 1.39 martin si->_reason._fault._trap = si32->_reason._fault._trap; 301 1.7 fvdl break; 302 1.46 rin case SIGTRAP: 303 1.48 rin switch (si32->_code) { 304 1.48 rin case TRAP_EXEC: 305 1.50 rin break; 306 1.48 rin case TRAP_CHLD: 307 1.48 rin case TRAP_LWP: 308 1.48 rin si->_reason._ptrace_state._pe_report_event = 309 1.48 rin si32->_reason._ptrace_state._pe_report_event; 310 1.48 rin CTASSERT(sizeof(si->_reason._ptrace_state._option._pe_other_pid) == 311 1.48 rin sizeof(si->_reason._ptrace_state._option._pe_lwp)); 312 1.48 rin si->_reason._ptrace_state._option._pe_other_pid = 313 1.48 rin si32->_reason._ptrace_state._option._pe_other_pid; 314 1.48 rin break; 315 1.48 rin case TRAP_SCE: 316 1.48 rin case TRAP_SCX: 317 1.48 rin si->_reason._syscall._sysnum = 318 1.48 rin si32->_reason._syscall._sysnum; 319 1.48 rin si->_reason._syscall._retval[0] = 320 1.48 rin si32->_reason._syscall._retval[0]; 321 1.48 rin si->_reason._syscall._retval[1] = 322 1.48 rin si32->_reason._syscall._retval[1]; 323 1.48 rin si->_reason._syscall._error = 324 1.48 rin si32->_reason._syscall._error; 325 1.48 rin for (i = 0; 326 1.48 rin i < __arraycount(si->_reason._syscall._args); i++) 327 1.48 rin si->_reason._syscall._args[i] = 328 1.48 rin si32->_reason._syscall._args[i]; 329 1.48 rin break; 330 1.48 rin default: 331 1.46 rin goto fill_fault; 332 1.48 rin } 333 1.46 rin break; 334 1.7 fvdl case SIGALRM: 335 1.7 fvdl case SIGVTALRM: 336 1.7 fvdl case SIGPROF: 337 1.39 martin default: /* see sigqueue() and kill1() */ 338 1.49 rin fill_rt: 339 1.39 martin si->_reason._rt._pid = si32->_reason._rt._pid; 340 1.39 martin si->_reason._rt._uid = si32->_reason._rt._uid; 341 1.42 christos si->_reason._rt._value.sival_int = 342 1.42 christos si32->_reason._rt._value.sival_int; 343 1.7 fvdl break; 344 1.47 rin case SIGURG: 345 1.47 rin case SIGIO: 346 1.47 rin si->_reason._poll._band = si32->_reason._poll._band; 347 1.47 rin si->_reason._poll._fd = si32->_reason._poll._fd; 348 1.47 rin break; 349 1.7 fvdl case SIGCHLD: 350 1.39 martin si->_reason._child._pid = si32->_reason._child._pid; 351 1.39 martin si->_reason._child._uid = si32->_reason._child._uid; 352 1.46 rin si->_reason._child._status = si32->_reason._child._status; 353 1.39 martin si->_reason._child._utime = si32->_reason._child._utime; 354 1.39 martin si->_reason._child._stime = si32->_reason._child._stime; 355 1.7 fvdl break; 356 1.7 fvdl } 357 1.7 fvdl } 358 1.7 fvdl 359 1.47 rin void 360 1.47 rin netbsd32_si32_to_si(siginfo_t *si, const siginfo32_t *si32) 361 1.47 rin { 362 1.47 rin 363 1.47 rin memset(si, 0, sizeof (*si)); 364 1.47 rin netbsd32_ksi32_to_ksi(&si->_info, &si32->_info); 365 1.47 rin } 366 1.47 rin 367 1.40 martin static void 368 1.40 martin netbsd32_ksi_to_ksi32(struct __ksiginfo32 *si32, const struct _ksiginfo *si) 369 1.40 martin { 370 1.46 rin size_t i; 371 1.46 rin 372 1.40 martin memset(si32, 0, sizeof (*si32)); 373 1.40 martin si32->_signo = si->_signo; 374 1.40 martin si32->_code = si->_code; 375 1.40 martin si32->_errno = si->_errno; 376 1.40 martin 377 1.49 rin if (si->_code == SI_NOINFO) 378 1.49 rin return; 379 1.49 rin else if (si->_code <= 0) /* codes described in siginfo(2) */ 380 1.49 rin goto fill_rt; 381 1.49 rin 382 1.40 martin switch (si->_signo) { 383 1.40 martin case SIGILL: 384 1.47 rin case SIGFPE: 385 1.40 martin case SIGBUS: 386 1.40 martin case SIGSEGV: 387 1.46 rin fill_fault: 388 1.40 martin si32->_reason._fault._addr = 389 1.40 martin NETBSD32PTR32I(si->_reason._fault._addr); 390 1.40 martin si32->_reason._fault._trap = si->_reason._fault._trap; 391 1.40 martin break; 392 1.46 rin case SIGTRAP: 393 1.48 rin switch (si->_code) { 394 1.48 rin case TRAP_EXEC: 395 1.50 rin break; 396 1.48 rin case TRAP_CHLD: 397 1.48 rin case TRAP_LWP: 398 1.48 rin si32->_reason._ptrace_state._pe_report_event = 399 1.48 rin si->_reason._ptrace_state._pe_report_event; 400 1.48 rin CTASSERT(sizeof(si32->_reason._ptrace_state._option._pe_other_pid) == 401 1.48 rin sizeof(si32->_reason._ptrace_state._option._pe_lwp)); 402 1.48 rin si32->_reason._ptrace_state._option._pe_other_pid = 403 1.48 rin si->_reason._ptrace_state._option._pe_other_pid; 404 1.48 rin break; 405 1.48 rin case TRAP_SCE: 406 1.48 rin case TRAP_SCX: 407 1.48 rin si32->_reason._syscall._sysnum = 408 1.48 rin si->_reason._syscall._sysnum; 409 1.48 rin si32->_reason._syscall._retval[0] = 410 1.48 rin si->_reason._syscall._retval[0]; 411 1.48 rin si32->_reason._syscall._retval[1] = 412 1.48 rin si->_reason._syscall._retval[1]; 413 1.48 rin si32->_reason._syscall._error = 414 1.48 rin si->_reason._syscall._error; 415 1.48 rin for (i = 0; 416 1.48 rin i < __arraycount(si->_reason._syscall._args); i++) 417 1.48 rin si32->_reason._syscall._args[i] = 418 1.48 rin si->_reason._syscall._args[i]; 419 1.48 rin break; 420 1.48 rin default: 421 1.46 rin goto fill_fault; 422 1.48 rin } 423 1.46 rin break; 424 1.40 martin case SIGALRM: 425 1.40 martin case SIGVTALRM: 426 1.40 martin case SIGPROF: 427 1.40 martin default: /* see sigqueue() and kill1() */ 428 1.49 rin fill_rt: 429 1.40 martin si32->_reason._rt._pid = si->_reason._rt._pid; 430 1.40 martin si32->_reason._rt._uid = si->_reason._rt._uid; 431 1.42 christos si32->_reason._rt._value.sival_int = 432 1.42 christos si->_reason._rt._value.sival_int; 433 1.40 martin break; 434 1.47 rin case SIGURG: 435 1.47 rin case SIGIO: 436 1.47 rin si32->_reason._poll._band = si->_reason._poll._band; 437 1.47 rin si32->_reason._poll._fd = si->_reason._poll._fd; 438 1.47 rin break; 439 1.40 martin case SIGCHLD: 440 1.40 martin si32->_reason._child._pid = si->_reason._child._pid; 441 1.40 martin si32->_reason._child._uid = si->_reason._child._uid; 442 1.46 rin si32->_reason._child._status = si->_reason._child._status; 443 1.40 martin si32->_reason._child._utime = si->_reason._child._utime; 444 1.40 martin si32->_reason._child._stime = si->_reason._child._stime; 445 1.40 martin break; 446 1.40 martin } 447 1.40 martin } 448 1.40 martin 449 1.15 chs void 450 1.9 drochner netbsd32_si_to_si32(siginfo32_t *si32, const siginfo_t *si) 451 1.7 fvdl { 452 1.46 rin 453 1.7 fvdl memset(si32, 0, sizeof (*si32)); 454 1.46 rin netbsd32_ksi_to_ksi32(&si32->_info, &si->_info); 455 1.7 fvdl } 456 1.7 fvdl 457 1.7 fvdl void 458 1.7 fvdl getucontext32(struct lwp *l, ucontext32_t *ucp) 459 1.7 fvdl { 460 1.20 cube struct proc *p = l->l_proc; 461 1.7 fvdl 462 1.29 ad KASSERT(mutex_owned(p->p_lock)); 463 1.7 fvdl 464 1.7 fvdl ucp->uc_flags = 0; 465 1.7 fvdl ucp->uc_link = (uint32_t)(intptr_t)l->l_ctxlink; 466 1.37 rmind ucp->uc_sigmask = l->l_sigmask; 467 1.7 fvdl ucp->uc_flags |= _UC_SIGMASK; 468 1.7 fvdl 469 1.7 fvdl /* 470 1.7 fvdl * The (unsupplied) definition of the `current execution stack' 471 1.7 fvdl * in the System V Interface Definition appears to allow returning 472 1.7 fvdl * the main context stack. 473 1.7 fvdl */ 474 1.19 ad if ((l->l_sigstk.ss_flags & SS_ONSTACK) == 0) { 475 1.7 fvdl ucp->uc_stack.ss_sp = USRSTACK32; 476 1.7 fvdl ucp->uc_stack.ss_size = ctob(p->p_vmspace->vm_ssize); 477 1.7 fvdl ucp->uc_stack.ss_flags = 0; /* XXX, def. is Very Fishy */ 478 1.7 fvdl } else { 479 1.7 fvdl /* Simply copy alternate signal execution stack. */ 480 1.7 fvdl ucp->uc_stack.ss_sp = 481 1.19 ad (uint32_t)(intptr_t)l->l_sigstk.ss_sp; 482 1.19 ad ucp->uc_stack.ss_size = l->l_sigstk.ss_size; 483 1.19 ad ucp->uc_stack.ss_flags = l->l_sigstk.ss_flags; 484 1.7 fvdl } 485 1.7 fvdl ucp->uc_flags |= _UC_STACK; 486 1.29 ad mutex_exit(p->p_lock); 487 1.7 fvdl cpu_getmcontext32(l, &ucp->uc_mcontext, &ucp->uc_flags); 488 1.29 ad mutex_enter(p->p_lock); 489 1.7 fvdl } 490 1.7 fvdl 491 1.7 fvdl int 492 1.28 dsl netbsd32_getcontext(struct lwp *l, const struct netbsd32_getcontext_args *uap, register_t *retval) 493 1.7 fvdl { 494 1.28 dsl /* { 495 1.7 fvdl syscallarg(netbsd32_ucontextp) ucp; 496 1.28 dsl } */ 497 1.20 cube struct proc *p = l->l_proc; 498 1.7 fvdl ucontext32_t uc; 499 1.7 fvdl 500 1.35 joerg memset(&uc, 0, sizeof(uc)); 501 1.35 joerg 502 1.29 ad mutex_enter(p->p_lock); 503 1.7 fvdl getucontext32(l, &uc); 504 1.29 ad mutex_exit(p->p_lock); 505 1.7 fvdl 506 1.23 dsl return copyout(&uc, SCARG_P32(uap, ucp), sizeof (ucontext32_t)); 507 1.7 fvdl } 508 1.7 fvdl 509 1.7 fvdl int 510 1.7 fvdl setucontext32(struct lwp *l, const ucontext32_t *ucp) 511 1.7 fvdl { 512 1.20 cube struct proc *p = l->l_proc; 513 1.20 cube int error; 514 1.20 cube 515 1.29 ad KASSERT(mutex_owned(p->p_lock)); 516 1.20 cube 517 1.20 cube if ((ucp->uc_flags & _UC_SIGMASK) != 0) { 518 1.20 cube error = sigprocmask1(l, SIG_SETMASK, &ucp->uc_sigmask, NULL); 519 1.20 cube if (error != 0) 520 1.20 cube return error; 521 1.20 cube } 522 1.7 fvdl 523 1.29 ad mutex_exit(p->p_lock); 524 1.20 cube error = cpu_setmcontext32(l, &ucp->uc_mcontext, ucp->uc_flags); 525 1.29 ad mutex_enter(p->p_lock); 526 1.20 cube if (error != 0) 527 1.51 simonb return error; 528 1.20 cube 529 1.7 fvdl l->l_ctxlink = (void *)(intptr_t)ucp->uc_link; 530 1.20 cube 531 1.7 fvdl /* 532 1.20 cube * If there was stack information, update whether or not we are 533 1.20 cube * still running on an alternate signal stack. 534 1.7 fvdl */ 535 1.20 cube if ((ucp->uc_flags & _UC_STACK) != 0) { 536 1.20 cube if (ucp->uc_stack.ss_flags & SS_ONSTACK) 537 1.20 cube l->l_sigstk.ss_flags |= SS_ONSTACK; 538 1.20 cube else 539 1.20 cube l->l_sigstk.ss_flags &= ~SS_ONSTACK; 540 1.20 cube } 541 1.7 fvdl 542 1.7 fvdl return 0; 543 1.7 fvdl } 544 1.7 fvdl 545 1.7 fvdl /* ARGSUSED */ 546 1.7 fvdl int 547 1.28 dsl netbsd32_setcontext(struct lwp *l, const struct netbsd32_setcontext_args *uap, register_t *retval) 548 1.7 fvdl { 549 1.28 dsl /* { 550 1.7 fvdl syscallarg(netbsd32_ucontextp) ucp; 551 1.28 dsl } */ 552 1.7 fvdl ucontext32_t uc; 553 1.7 fvdl int error; 554 1.20 cube struct proc *p = l->l_proc; 555 1.7 fvdl 556 1.23 dsl error = copyin(SCARG_P32(uap, ucp), &uc, sizeof (uc)); 557 1.18 drochner if (error) 558 1.51 simonb return error; 559 1.18 drochner if (!(uc.uc_flags & _UC_CPU)) 560 1.51 simonb return EINVAL; 561 1.29 ad mutex_enter(p->p_lock); 562 1.18 drochner error = setucontext32(l, &uc); 563 1.29 ad mutex_exit(p->p_lock); 564 1.18 drochner if (error) 565 1.51 simonb return error; 566 1.7 fvdl 567 1.51 simonb return EJUSTRETURN; 568 1.1 mrg } 569 1.10 cube 570 1.10 cube static int 571 1.10 cube netbsd32_sigtimedwait_put_info(const void *src, void *dst, size_t size) 572 1.10 cube { 573 1.10 cube const siginfo_t *info = src; 574 1.10 cube siginfo32_t info32; 575 1.10 cube 576 1.10 cube netbsd32_si_to_si32(&info32, info); 577 1.10 cube 578 1.10 cube return copyout(&info32, dst, sizeof(info32)); 579 1.10 cube } 580 1.10 cube 581 1.10 cube static int 582 1.10 cube netbsd32_sigtimedwait_fetch_timeout(const void *src, void *dst, size_t size) 583 1.10 cube { 584 1.10 cube struct timespec *ts = dst; 585 1.10 cube struct netbsd32_timespec ts32; 586 1.10 cube int error; 587 1.10 cube 588 1.10 cube error = copyin(src, &ts32, sizeof(ts32)); 589 1.10 cube if (error) 590 1.10 cube return error; 591 1.10 cube 592 1.10 cube netbsd32_to_timespec(&ts32, ts); 593 1.10 cube return 0; 594 1.10 cube } 595 1.10 cube 596 1.10 cube static int 597 1.10 cube netbsd32_sigtimedwait_put_timeout(const void *src, void *dst, size_t size) 598 1.10 cube { 599 1.10 cube const struct timespec *ts = src; 600 1.10 cube struct netbsd32_timespec ts32; 601 1.10 cube 602 1.10 cube netbsd32_from_timespec(ts, &ts32); 603 1.10 cube 604 1.10 cube return copyout(&ts32, dst, sizeof(ts32)); 605 1.10 cube } 606 1.10 cube 607 1.10 cube int 608 1.32 christos netbsd32_____sigtimedwait50(struct lwp *l, const struct netbsd32_____sigtimedwait50_args *uap, register_t *retval) 609 1.10 cube { 610 1.28 dsl /* { 611 1.10 cube syscallarg(netbsd32_sigsetp_t) set; 612 1.10 cube syscallarg(netbsd32_siginfop_t) info; 613 1.32 christos syscallarg(netbsd32_timespec50p_t) timeout; 614 1.28 dsl } */ 615 1.32 christos struct sys_____sigtimedwait50_args ua; 616 1.10 cube 617 1.10 cube NETBSD32TOP_UAP(set, const sigset_t); 618 1.10 cube NETBSD32TOP_UAP(info, siginfo_t); 619 1.10 cube NETBSD32TOP_UAP(timeout, struct timespec); 620 1.10 cube 621 1.33 pooka return sigtimedwait1(l, &ua, retval, 622 1.36 christos copyin, 623 1.32 christos netbsd32_sigtimedwait_put_info, 624 1.10 cube netbsd32_sigtimedwait_fetch_timeout, 625 1.10 cube netbsd32_sigtimedwait_put_timeout); 626 1.10 cube } 627 1.39 martin 628 1.39 martin int 629 1.39 martin netbsd32_sigqueueinfo(struct lwp *l, 630 1.39 martin const struct netbsd32_sigqueueinfo_args *uap, register_t *retval) 631 1.39 martin { 632 1.39 martin /* { 633 1.39 martin syscallarg(pid_t) pid; 634 1.39 martin syscallarg(const netbsd32_siginfop_t) info; 635 1.39 martin } */ 636 1.39 martin struct __ksiginfo32 ksi32; 637 1.39 martin ksiginfo_t ksi; 638 1.39 martin int error; 639 1.39 martin 640 1.39 martin if ((error = copyin(SCARG_P32(uap, info), &ksi32, 641 1.39 martin sizeof(ksi32))) != 0) 642 1.39 martin return error; 643 1.39 martin 644 1.39 martin KSI_INIT(&ksi); 645 1.39 martin netbsd32_ksi32_to_ksi(&ksi.ksi_info, &ksi32); 646 1.39 martin 647 1.39 martin return kill1(l, SCARG(uap, pid), &ksi, retval); 648 1.39 martin } 649 1.40 martin 650 1.40 martin struct netbsd32_ktr_psig { 651 1.40 martin int signo; 652 1.40 martin netbsd32_pointer_t action; 653 1.40 martin sigset_t mask; 654 1.40 martin int code; 655 1.40 martin /* and optional siginfo_t */ 656 1.40 martin }; 657 1.40 martin 658 1.44 christos #ifdef notyet 659 1.41 christos #ifdef KTRACE 660 1.40 martin void 661 1.40 martin netbsd32_ktrpsig(int sig, sig_t action, const sigset_t *mask, 662 1.40 martin const ksiginfo_t *ksi) 663 1.40 martin { 664 1.40 martin struct ktrace_entry *kte; 665 1.40 martin lwp_t *l = curlwp; 666 1.40 martin struct { 667 1.40 martin struct netbsd32_ktr_psig kp; 668 1.40 martin siginfo32_t si; 669 1.40 martin } *kbuf; 670 1.40 martin 671 1.40 martin if (!KTRPOINT(l->l_proc, KTR_PSIG)) 672 1.40 martin return; 673 1.40 martin 674 1.40 martin if (ktealloc(&kte, (void *)&kbuf, l, KTR_PSIG, sizeof(*kbuf))) 675 1.40 martin return; 676 1.40 martin 677 1.40 martin kbuf->kp.signo = (char)sig; 678 1.40 martin NETBSD32PTR32(kbuf->kp.action, action); 679 1.40 martin kbuf->kp.mask = *mask; 680 1.40 martin 681 1.40 martin if (ksi) { 682 1.40 martin kbuf->kp.code = KSI_TRAPCODE(ksi); 683 1.40 martin (void)memset(&kbuf->si, 0, sizeof(kbuf->si)); 684 1.40 martin netbsd32_ksi_to_ksi32(&kbuf->si._info, &ksi->ksi_info); 685 1.40 martin ktesethdrlen(kte, sizeof(*kbuf)); 686 1.40 martin } else { 687 1.40 martin kbuf->kp.code = 0; 688 1.40 martin ktesethdrlen(kte, sizeof(struct netbsd32_ktr_psig)); 689 1.40 martin } 690 1.40 martin 691 1.40 martin ktraddentry(l, kte, KTA_WAITOK); 692 1.40 martin } 693 1.41 christos #endif 694 1.44 christos #endif 695