aboutsummaryrefslogtreecommitdiff
path: root/lib/libthr/thread/thr_cancel.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/libthr/thread/thr_cancel.c')
-rw-r--r--lib/libthr/thread/thr_cancel.c26
1 files changed, 12 insertions, 14 deletions
diff --git a/lib/libthr/thread/thr_cancel.c b/lib/libthr/thread/thr_cancel.c
index 86632e41449b..4189a2640d14 100644
--- a/lib/libthr/thread/thr_cancel.c
+++ b/lib/libthr/thread/thr_cancel.c
@@ -26,7 +26,6 @@
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#include <sys/cdefs.h>
#include "namespace.h"
#include <pthread.h>
#include "un-namespace.h"
@@ -84,25 +83,25 @@ int
_thr_setcancelstate(int state, int *oldstate)
{
struct pthread *curthread = _get_curthread();
- int oldval;
+ int oldval, val;
- oldval = curthread->cancel_enable;
switch (state) {
case PTHREAD_CANCEL_DISABLE:
- curthread->cancel_enable = 0;
+ val = 0;
break;
case PTHREAD_CANCEL_ENABLE:
- curthread->cancel_enable = 1;
- if (curthread->cancel_async)
- testcancel(curthread);
+ val = 1;
break;
default:
return (EINVAL);
}
- if (oldstate) {
+ oldval = atomic_swap_int(&curthread->cancel_enable, val);
+ if (state == PTHREAD_CANCEL_ENABLE && curthread->cancel_async)
+ testcancel(curthread);
+ if (oldstate != NULL) {
*oldstate = oldval ? PTHREAD_CANCEL_ENABLE :
- PTHREAD_CANCEL_DISABLE;
+ PTHREAD_CANCEL_DISABLE;
}
return (0);
}
@@ -126,9 +125,9 @@ _thr_setcanceltype(int type, int *oldtype)
return (EINVAL);
}
- if (oldtype) {
+ if (oldtype != NULL) {
*oldtype = oldval ? PTHREAD_CANCEL_ASYNCHRONOUS :
- PTHREAD_CANCEL_DEFERRED;
+ PTHREAD_CANCEL_DEFERRED;
}
return (0);
}
@@ -167,9 +166,8 @@ void
_thr_cancel_leave(struct pthread *curthread, int maycancel)
{
curthread->cancel_point = 0;
- if (__predict_false(SHOULD_CANCEL(curthread) &&
- !THR_IN_CRITICAL(curthread) && maycancel))
- _pthread_exit(PTHREAD_CANCELED);
+ if (maycancel)
+ testcancel(curthread);
}
void