X-Git-Url: https://git.saurik.com/apple/libplatform.git/blobdiff_plain/89154bfbfa86dc8977dc06e4201daac587013ec8..HEAD:/src/setjmp/generic/sigtramp.c diff --git a/src/setjmp/generic/sigtramp.c b/src/setjmp/generic/sigtramp.c index 32e31db..ce9f505 100644 --- a/src/setjmp/generic/sigtramp.c +++ b/src/setjmp/generic/sigtramp.c @@ -44,9 +44,9 @@ extern int __sigreturn(ucontext_t *, int, uintptr_t); * Note that the kernel saves/restores all of our register state. */ -/* On i386, i386/sys/_sigtramp.s defines this. There is no in_sigtramp on arm */ -#if defined(__DYNAMIC__) && defined(__x86_64__) -OS_NOEXPORT +/* On i386, i386/sys/_sigtramp.s defines this. */ +#if defined(__DYNAMIC__) && !defined(__i386__) +OS_NOEXPORT int __in_sigtramp; int __in_sigtramp = 0; #endif @@ -72,7 +72,7 @@ _sigunaltstack(int set) { /* sigreturn(uctx, ctxstyle); */ /* syscall (SYS_SIGRETURN, uctx, ctxstyle); */ - __sigreturn (NULL, (set == SS_ONSTACK) ? UC_SET_ALT_STACK : UC_RESET_ALT_STACK, 0); + __sigreturn (NULL, (set & SS_ONSTACK) ? UC_SET_ALT_STACK : UC_RESET_ALT_STACK, 0); } /* On these architectures, _sigtramp is implemented in assembly to @@ -88,21 +88,37 @@ _sigtramp( ucontext_t *uctx, uintptr_t token ) { + __in_sigtramp = sig; int ctxstyle = UC_FLAVOR; - if (sigstyle == UC_TRAD) - sa_handler(sig); - else { + /* Some variants are not supposed to get the last 2 parameters but it's + * easier to pass them along - especially on arm64 whereby the extra fields + * are probably in caller save registers anyways, thereby making no + * difference to callee if we populate them or not. + * + * + * Moreover, sigaction(2)'s man page implies that the following behavior + * should be supported: + * + * If the SA_SIGINFO flag is not set, the handler function should match + * either the ANSI C or traditional BSD prototype and be pointed to by + * the sa_handler member of struct sigaction. In practice, FreeBSD + * always sends the three arguments of the latter and since the ANSI C + * prototype is a subset, both will work. + * + * See bad siginfo struct sent to SIGCHILD signal + * handler in arm64 process + */ #if TARGET_OS_WATCH - // - sa_sigaction(sig, sinfo, NULL); + // + sa_sigaction(sig, sinfo, NULL); #else - sa_sigaction(sig, sinfo, uctx); + sa_sigaction(sig, sinfo, uctx); #endif - } - /* sigreturn(uctx, ctxstyle); */ + /* sigreturn(uctx, ctxstyle); */ /* syscall (SYS_SIGRETURN, uctx, ctxstyle); */ + __in_sigtramp = 0; __sigreturn (uctx, ctxstyle, token); __builtin_trap(); /* __sigreturn returning is a fatal error */ }