diff options
-rw-r--r-- | sys/kern/kern_sig.c | 10 | ||||
-rw-r--r-- | sys/sys/signalvar.h | 23 |
2 files changed, 25 insertions, 8 deletions
diff --git a/sys/kern/kern_sig.c b/sys/kern/kern_sig.c index 8c75985..bfefd24 100644 --- a/sys/kern/kern_sig.c +++ b/sys/kern/kern_sig.c @@ -174,16 +174,10 @@ static int sigproptbl[NSIG] = { int CURSIG(struct proc *p) { - sigset_t tmpset; PROC_LOCK_ASSERT(p, MA_OWNED); - if (SIGISEMPTY(p->p_siglist)) - return (0); - tmpset = p->p_siglist; - SIGSETNAND(tmpset, p->p_sigmask); - if (SIGISEMPTY(tmpset) && (p->p_flag & P_TRACED) == 0) - return (0); - return (issignal(p)); + mtx_assert(&sched_lock, MA_NOTOWNED); + return (SIGPENDING(p) ? issignal(p) : 0); } static __inline int diff --git a/sys/sys/signalvar.h b/sys/sys/signalvar.h index 19abed3..77923c2 100644 --- a/sys/sys/signalvar.h +++ b/sys/sys/signalvar.h @@ -189,6 +189,29 @@ __sigseteq(sigset_t *set1, sigset_t *set2) #ifdef _KERNEL +/* Return nonzero if process p has an unmasked pending signal. */ +#define SIGPENDING(p) \ + (!SIGISEMPTY((p)->p_siglist) && \ + (!sigsetmasked(&(p)->p_siglist, &(p)->p_sigmask) || \ + (p)->p_flag & P_TRACED)) + +/* + * Return the value of the pseudo-expression ((*set & ~*mask) != 0). This + * is an optimized version of SIGISEMPTY() on a temporary variable + * containing SIGSETNAND(*set, *mask). + */ +static __inline int +sigsetmasked(sigset_t *set, sigset_t *mask) +{ + int i; + + for (i = 0; i < _SIG_WORDS; i++) { + if (set->__bits[i] & ~mask->__bits[i]) + return (0); + } + return (1); +} + struct pgrp; struct thread; struct proc; |