summaryrefslogtreecommitdiffstats
path: root/sys/kern/kern_sig.c
diff options
context:
space:
mode:
Diffstat (limited to 'sys/kern/kern_sig.c')
-rw-r--r--sys/kern/kern_sig.c33
1 files changed, 20 insertions, 13 deletions
diff --git a/sys/kern/kern_sig.c b/sys/kern/kern_sig.c
index 0876245..a72de0e 100644
--- a/sys/kern/kern_sig.c
+++ b/sys/kern/kern_sig.c
@@ -1047,7 +1047,7 @@ psignal(p, sig)
register struct proc *p;
register int sig;
{
- register int s, prop;
+ register int prop;
register sig_t action;
if (sig > _SIG_MAXSIG || sig <= 0) {
@@ -1055,6 +1055,7 @@ psignal(p, sig)
panic("psignal signal number");
}
+ PROC_LOCK(p);
KNOTE(&p->p_klist, NOTE_SIGNAL | sig);
prop = sigprop(sig);
@@ -1074,8 +1075,10 @@ psignal(p, sig)
* and if it is set to SIG_IGN,
* action will be SIG_DFL here.)
*/
- if (SIGISMEMBER(p->p_sigignore, sig) || (p->p_flag & P_WEXIT))
+ if (SIGISMEMBER(p->p_sigignore, sig) || (p->p_flag & P_WEXIT)) {
+ PROC_UNLOCK(p);
return;
+ }
if (SIGISMEMBER(p->p_sigmask, sig))
action = SIG_HOLD;
else if (SIGISMEMBER(p->p_sigcatch, sig))
@@ -1084,9 +1087,11 @@ psignal(p, sig)
action = SIG_DFL;
}
+ mtx_enter(&sched_lock, MTX_SPIN);
if (p->p_nice > NZERO && action == SIG_DFL && (prop & SA_KILL) &&
(p->p_flag & P_TRACED) == 0)
p->p_nice = NZERO;
+ mtx_exit(&sched_lock, MTX_SPIN);
if (prop & SA_CONT)
SIG_STOPSIGMASK(p->p_siglist);
@@ -1099,8 +1104,10 @@ psignal(p, sig)
* and don't clear any pending SIGCONT.
*/
if (prop & SA_TTYSTOP && p->p_pgrp->pg_jobc == 0 &&
- action == SIG_DFL)
+ action == SIG_DFL) {
+ PROC_UNLOCK(p);
return;
+ }
SIG_CONTSIGMASK(p->p_siglist);
}
SIGADDSET(p->p_siglist, sig);
@@ -1112,9 +1119,9 @@ psignal(p, sig)
mtx_enter(&sched_lock, MTX_SPIN);
if (action == SIG_HOLD && (!(prop & SA_CONT) || p->p_stat != SSTOP)) {
mtx_exit(&sched_lock, MTX_SPIN);
+ PROC_UNLOCK(p);
return;
}
- s = splhigh();
switch (p->p_stat) {
case SSLEEP:
@@ -1124,7 +1131,7 @@ psignal(p, sig)
* be noticed when the process returns through
* trap() or syscall().
*/
- if ((p->p_flag & P_SINTR) == 0) {
+ if ((p->p_sflag & PS_SINTR) == 0) {
mtx_exit(&sched_lock, MTX_SPIN);
goto out;
}
@@ -1162,26 +1169,26 @@ psignal(p, sig)
goto out;
SIGDELSET(p->p_siglist, sig);
p->p_xstat = sig;
+ PROC_UNLOCK(p);
PROCTREE_LOCK(PT_SHARED);
if ((p->p_pptr->p_procsig->ps_flag & PS_NOCLDSTOP) == 0)
psignal(p->p_pptr, SIGCHLD);
stop(p);
PROCTREE_LOCK(PT_RELEASE);
+ PROC_LOCK(p);
goto out;
} else
goto runfast;
/* NOTREACHED */
case SSTOP:
+ mtx_exit(&sched_lock, MTX_SPIN);
/*
* If traced process is already stopped,
* then no further action is necessary.
*/
- if (p->p_flag & P_TRACED) {
- mtx_exit(&sched_lock, MTX_SPIN);
+ if (p->p_flag & P_TRACED)
goto out;
- }
- mtx_exit(&sched_lock, MTX_SPIN);
/*
* Kill signal always sets processes running.
@@ -1205,7 +1212,7 @@ psignal(p, sig)
if (action == SIG_CATCH)
goto runfast;
mtx_enter(&sched_lock, MTX_SPIN);
- if (p->p_wchan == 0)
+ if (p->p_wchan == NULL)
goto run;
p->p_stat = SSLEEP;
mtx_exit(&sched_lock, MTX_SPIN);
@@ -1228,8 +1235,8 @@ psignal(p, sig)
* the process runnable, leave it stopped.
*/
mtx_enter(&sched_lock, MTX_SPIN);
- if (p->p_wchan && p->p_flag & P_SINTR) {
- if (p->p_flag & P_CVWAITQ)
+ if (p->p_wchan && p->p_sflag & PS_SINTR) {
+ if (p->p_sflag & PS_CVWAITQ)
cv_waitq_remove(p);
else
unsleep(p);
@@ -1274,7 +1281,7 @@ run:
out:
/* If we jump here, sched_lock should not be owned. */
mtx_assert(&sched_lock, MA_NOTOWNED);
- splx(s);
+ PROC_UNLOCK(p);
}
/*
OpenPOWER on IntegriCloud