summaryrefslogtreecommitdiffstats
path: root/sys/kern/subr_sleepqueue.c
diff options
context:
space:
mode:
authordavidxu <davidxu@FreeBSD.org>2008-11-05 03:01:23 +0000
committerdavidxu <davidxu@FreeBSD.org>2008-11-05 03:01:23 +0000
commit1ebf3ee9a3db9492efa600f6c7614a1851e8c357 (patch)
tree50003b0f3882d55b6d31a3135664f3a2abd73c56 /sys/kern/subr_sleepqueue.c
parente07ee09f61c3fc9b2a221bb67f0bb35f0da0ce63 (diff)
downloadFreeBSD-src-1ebf3ee9a3db9492efa600f6c7614a1851e8c357.zip
FreeBSD-src-1ebf3ee9a3db9492efa600f6c7614a1851e8c357.tar.gz
Revert rev 184216 and 184199, due to the way the thread_lock works,
it may cause a lockup. Noticed by: peter, jhb
Diffstat (limited to 'sys/kern/subr_sleepqueue.c')
-rw-r--r--sys/kern/subr_sleepqueue.c16
1 files changed, 8 insertions, 8 deletions
diff --git a/sys/kern/subr_sleepqueue.c b/sys/kern/subr_sleepqueue.c
index 97511e0..8ce6c0a 100644
--- a/sys/kern/subr_sleepqueue.c
+++ b/sys/kern/subr_sleepqueue.c
@@ -395,7 +395,6 @@ sleepq_catch_signals(void *wchan, int pri)
sleepq_switch(wchan, pri);
return (0);
}
-
thread_unlock(td);
mtx_unlock_spin(&sc->sc_lock);
CTR3(KTR_PROC, "sleepq catching signals: thread %p (pid %ld, %s)",
@@ -415,15 +414,16 @@ sleepq_catch_signals(void *wchan, int pri)
ret = ERESTART;
mtx_unlock(&ps->ps_mtx);
}
-
+ /*
+ * Lock the per-process spinlock prior to dropping the PROC_LOCK
+ * to avoid a signal delivery race. PROC_LOCK, PROC_SLOCK, and
+ * thread_lock() are currently held in tdsignal().
+ */
+ PROC_SLOCK(p);
mtx_lock_spin(&sc->sc_lock);
- thread_lock(td);
PROC_UNLOCK(p);
- if (ret == 0) {
- sleepq_switch(wchan, pri);
- return (0);
- }
-
+ thread_lock(td);
+ PROC_SUNLOCK(p);
/*
* There were pending signals and this thread is still
* on the sleep queue, remove it from the sleep queue.
OpenPOWER on IntegriCloud