Use getcontextx(3) internal API instead of getcontext(2) to provide

the signal handlers with the context information in the deferrred
case.

Only enable the use of getcontextx(3) in the deferred signal delivery
code on amd64 and i386. Sparc64 seems to have some undetermined issues
with interaction of alloca(3) and signal delivery.

Tested by:	flo (who also provided sparc64 harware access for me), pho
Discussed with:	marius
MFC after:	1 month
This commit is contained in:
Konstantin Belousov 2012-01-21 18:06:18 +00:00
parent 2b1de0afd1
commit 10280ca601
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=230430

View File

@ -32,6 +32,7 @@
#include <sys/signalvar.h>
#include <signal.h>
#include <errno.h>
#include <stdlib.h>
#include <string.h>
#include <pthread.h>
#include "un-namespace.h"
@ -314,16 +315,24 @@ check_cancel(struct pthread *curthread, ucontext_t *ucp)
static void
check_deferred_signal(struct pthread *curthread)
{
ucontext_t uc;
ucontext_t *uc;
struct sigaction act;
siginfo_t info;
if (__predict_true(curthread->deferred_siginfo.si_signo == 0))
return;
getcontext(&uc);
#if defined(__amd64__) || defined(__i386__)
uc = alloca(__getcontextx_size());
__fillcontextx((char *)uc);
#else
ucontext_t ucv;
uc = &ucv;
getcontext(uc);
#endif
if (curthread->deferred_siginfo.si_signo != 0) {
act = curthread->deferred_sigact;
uc.uc_sigmask = curthread->deferred_sigmask;
uc->uc_sigmask = curthread->deferred_sigmask;
memcpy(&info, &curthread->deferred_siginfo, sizeof(siginfo_t));
/* remove signal */
curthread->deferred_siginfo.si_signo = 0;
@ -334,7 +343,7 @@ check_deferred_signal(struct pthread *curthread)
tact.sa_handler = SIG_DFL;
_sigaction(info.si_signo, &tact, NULL);
}
handle_signal(&act, info.si_signo, &info, &uc);
handle_signal(&act, info.si_signo, &info, uc);
}
}