From 879bb0613c03b10bdf91aa862c2463b7f9f99087 Mon Sep 17 00:00:00 2001 From: rpj Date: Tue, 2 Sep 2003 16:15:05 +0000 Subject: Added cancelation of/from non-POSIX threads; minor fixes; minor changes. --- ptw32_throw.c | 48 +++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 43 insertions(+), 5 deletions(-) (limited to 'ptw32_throw.c') diff --git a/ptw32_throw.c b/ptw32_throw.c index a329e5c..20bfcf5 100644 --- a/ptw32_throw.c +++ b/ptw32_throw.c @@ -38,14 +38,22 @@ #include "pthread.h" #include "implement.h" - +/* + * ptw32_throw + * + * All canceled and explicitly exited POSIX threads go through + * here. This routine knows how to exit both POSIX initiated threads and + * 'implicit' POSIX threads for each of the possible language modes (C, + * C++, and SEH). + */ void ptw32_throw(DWORD exception) { -#ifdef __CLEANUP_C - pthread_t self = pthread_self(); -#endif - + /* + * Don't use pthread_self() to avoid creating an implicit POSIX thread handle + * unnecessarily. + */ + pthread_t self = (pthread_t) pthread_getspecific (ptw32_selfThreadKey); #ifdef __CLEANUP_SEH DWORD exceptionInformation[3]; @@ -58,6 +66,36 @@ ptw32_throw(DWORD exception) exit(1); } + if (NULL == self || self->implicit) + { + /* + * We're inside a non-POSIX initialised Win32 thread + * so there is no point to jump or throw back to. Just do an + * explicit thread exit here after cleaning up POSIX + * residue (i.e. cleanup handlers, POSIX thread handle etc). + */ + unsigned exitCode = 0; + + switch (exception) + { + case PTW32_EPS_CANCEL: + exitCode = (unsigned) PTHREAD_CANCELED; + break; + case PTW32_EPS_EXIT: + exitCode = (unsigned) self->exitStatus;; + break; + } + + pthread_win32_thread_detach_np(); + +#if ! defined (__MINGW32__) || defined (__MSVCRT__) + _endthreadex (exitCode); +#else + _endthread (); +#endif + + } + #ifdef __CLEANUP_SEH -- cgit v1.2.3