diff options
author | davidxu <davidxu@FreeBSD.org> | 2010-08-20 04:28:30 +0000 |
---|---|---|
committer | davidxu <davidxu@FreeBSD.org> | 2010-08-20 04:28:30 +0000 |
commit | 89f466d2b24eb304fba1cca7584fbd61aa0a8c94 (patch) | |
tree | 6e87e70a75d2de5dd44cf0f94627cf1dcafa58e7 | |
parent | 07b66dcf06596326ea9d81d40d460bdef6f50b34 (diff) | |
download | FreeBSD-src-89f466d2b24eb304fba1cca7584fbd61aa0a8c94.zip FreeBSD-src-89f466d2b24eb304fba1cca7584fbd61aa0a8c94.tar.gz |
If thread set a TDP_WAKEUP for itself, clears the flag and returns EINTR
immediately, this is used for implementing reliable pthread cancellation.
-rw-r--r-- | sys/kern/subr_sleepqueue.c | 7 |
1 files changed, 7 insertions, 0 deletions
diff --git a/sys/kern/subr_sleepqueue.c b/sys/kern/subr_sleepqueue.c index c51def6..0d2c65e 100644 --- a/sys/kern/subr_sleepqueue.c +++ b/sys/kern/subr_sleepqueue.c @@ -408,6 +408,12 @@ sleepq_catch_signals(void *wchan, int pri) sc = SC_LOOKUP(wchan); mtx_assert(&sc->sc_lock, MA_OWNED); MPASS(wchan != NULL); + if ((td->td_pflags & TDP_WAKEUP) != 0) { + td->td_pflags &= ~TDP_WAKEUP; + ret = EINTR; + goto out; + } + /* * See if there are any pending signals for this thread. If not * we can switch immediately. Otherwise do the signal processing @@ -453,6 +459,7 @@ sleepq_catch_signals(void *wchan, int pri) sleepq_switch(wchan, pri); return (0); } +out: /* * There were pending signals and this thread is still * on the sleep queue, remove it from the sleep queue. |