diff options
| -rw-r--r-- | ChangeLog | 23 | ||||
| -rw-r--r-- | global.c | 12 | ||||
| -rw-r--r-- | implement.h | 15 | ||||
| -rw-r--r-- | pthread_cond_destroy.c | 12 | ||||
| -rw-r--r-- | pthread_cond_init.c | 6 | ||||
| -rw-r--r-- | pthread_detach.c | 5 | ||||
| -rw-r--r-- | pthread_join.c | 5 | ||||
| -rw-r--r-- | pthread_kill.c | 5 | ||||
| -rw-r--r-- | pthread_mutex_destroy.c | 12 | ||||
| -rw-r--r-- | pthread_rwlock_destroy.c | 5 | ||||
| -rw-r--r-- | pthread_spin_destroy.c | 6 | ||||
| -rw-r--r-- | pthread_timechange_handler_np.c | 5 | ||||
| -rw-r--r-- | ptw32_cond_check_need_init.c | 22 | ||||
| -rw-r--r-- | ptw32_mutex_check_need_init.c | 26 | ||||
| -rw-r--r-- | ptw32_processInitialize.c | 10 | ||||
| -rw-r--r-- | ptw32_processTerminate.c | 15 | ||||
| -rw-r--r-- | ptw32_reuse.c | 10 | ||||
| -rw-r--r-- | ptw32_rwlock_check_need_init.c | 22 | ||||
| -rw-r--r-- | ptw32_spinlock_check_need_init.c | 9 | ||||
| -rwxr-xr-x | tests/SIZES.GC | 2 | ||||
| -rwxr-xr-x | tests/SIZES.VC | 2 | 
21 files changed, 95 insertions, 134 deletions
@@ -1,3 +1,26 @@ +2011-03-09  Ross Johnson <ross.johnson at homemail.com.au>
 +
 +	* implement.h (ptw32_thread_t_): Add process unique sequence number.
 +	* global.c: Replace global Critical Section objects with MCS
 +	queue locks.
 +	* implement.h: Likewise.
 +	* pthread_cond_destroy.c: Likewise.
 +	* pthread_cond_init.c: Likewise.
 +	* pthread_detach.c: Likewise.
 +	* pthread_join.c: Likewise.
 +	* pthread_kill.c: Likewise.
 +	* pthread_mutex_destroy.c: Likewise.
 +	* pthread_rwlock_destroy.c: Likewise.
 +	* pthread_spin_destroy.c: Likewise.
 +	* pthread_timechange_handler_np.c: Likewise.
 +	* ptw32_cond_check_need_init.c: Likewise.
 +	* ptw32_mutex_check_need_init.c: Likewise.
 +	* ptw32_processInitialize.c: Likewise.
 +	* ptw32_processTerminate.c: Likewise.
 +	* ptw32_reuse.c: Likewise.
 +	* ptw32_rwlock_check_need_init.c: Likewise.
 +	* ptw32_spinlock_check_need_init.c: Likewise.
 +
  2011-03-06  Ross Johnson <ross.johnson at homemail.com.au>
  	* several (MINGW64): Cast and call fixups for 64 bit compatibility;
 @@ -62,37 +62,37 @@ DWORD (*ptw32_register_cancelation) (PAPCFUNC, HANDLE, DWORD) = NULL;  /*   * Global lock for managing pthread_t struct reuse.   */ -CRITICAL_SECTION ptw32_thread_reuse_lock; +ptw32_mcs_lock_t ptw32_thread_reuse_lock;  /*   * Global lock for testing internal state of statically declared mutexes.   */ -CRITICAL_SECTION ptw32_mutex_test_init_lock; +ptw32_mcs_lock_t ptw32_mutex_test_init_lock;  /*   * Global lock for testing internal state of PTHREAD_COND_INITIALIZER   * created condition variables.   */ -CRITICAL_SECTION ptw32_cond_test_init_lock; +ptw32_mcs_lock_t ptw32_cond_test_init_lock;  /*   * Global lock for testing internal state of PTHREAD_RWLOCK_INITIALIZER   * created read/write locks.   */ -CRITICAL_SECTION ptw32_rwlock_test_init_lock; +ptw32_mcs_lock_t ptw32_rwlock_test_init_lock;  /*   * Global lock for testing internal state of PTHREAD_SPINLOCK_INITIALIZER   * created spin locks.   */ -CRITICAL_SECTION ptw32_spinlock_test_init_lock; +ptw32_mcs_lock_t ptw32_spinlock_test_init_lock;  /*   * Global lock for condition variable linked list. The list exists   * to wake up CVs when a WM_TIMECHANGE message arrives. See   * w32_TimeChangeHandler.c.   */ -CRITICAL_SECTION ptw32_cond_list_lock; +ptw32_mcs_lock_t ptw32_cond_list_lock;  #ifdef _UWIN  /* diff --git a/implement.h b/implement.h index aaad665..1cd24f2 100644 --- a/implement.h +++ b/implement.h @@ -131,7 +131,8 @@ struct ptw32_thread_t_  #ifdef _UWIN    DWORD dummy[5];  #endif -  DWORD thread; +  UINT64 seqNumber;		/* Process-unique thread sequence number */ +  DWORD thread;			/* Win32 thread ID */    HANDLE threadH;		/* Win32 thread handle - POSIX thread is invalid if threadH == 0 */    pthread_t ptHandle;		/* This thread's permanent pthread_t handle */    ptw32_thread_t * prevReuse;	/* Links threads on reuse stack */ @@ -535,12 +536,12 @@ extern int ptw32_concurrency;  extern int ptw32_features; -extern CRITICAL_SECTION ptw32_thread_reuse_lock; -extern CRITICAL_SECTION ptw32_mutex_test_init_lock; -extern CRITICAL_SECTION ptw32_cond_list_lock; -extern CRITICAL_SECTION ptw32_cond_test_init_lock; -extern CRITICAL_SECTION ptw32_rwlock_test_init_lock; -extern CRITICAL_SECTION ptw32_spinlock_test_init_lock; +extern ptw32_mcs_lock_t ptw32_thread_reuse_lock; +extern ptw32_mcs_lock_t ptw32_mutex_test_init_lock; +extern ptw32_mcs_lock_t ptw32_cond_list_lock; +extern ptw32_mcs_lock_t ptw32_cond_test_init_lock; +extern ptw32_mcs_lock_t ptw32_rwlock_test_init_lock; +extern ptw32_mcs_lock_t ptw32_spinlock_test_init_lock;  #ifdef _UWIN  extern int pthread_count; diff --git a/pthread_cond_destroy.c b/pthread_cond_destroy.c index 53f7a53..40d4a08 100644 --- a/pthread_cond_destroy.c +++ b/pthread_cond_destroy.c @@ -126,7 +126,8 @@ pthread_cond_destroy (pthread_cond_t * cond)    if (*cond != PTHREAD_COND_INITIALIZER)      { -      EnterCriticalSection (&ptw32_cond_list_lock); +      ptw32_mcs_local_node_t node; +      ptw32_mcs_lock_acquire(&ptw32_cond_list_lock, &node);        cv = *cond; @@ -154,7 +155,7 @@ pthread_cond_destroy (pthread_cond_t * cond)        if (result != 0)          { -          LeaveCriticalSection (&ptw32_cond_list_lock); +          ptw32_mcs_lock_release(&node);            return result;          } @@ -213,14 +214,15 @@ pthread_cond_destroy (pthread_cond_t * cond)  	  (void) free (cv);  	} -      LeaveCriticalSection (&ptw32_cond_list_lock); +      ptw32_mcs_lock_release(&node);      }    else      { +      ptw32_mcs_local_node_t node;        /*         * See notes in ptw32_cond_check_need_init() above also.         */ -      EnterCriticalSection (&ptw32_cond_test_init_lock); +      ptw32_mcs_lock_acquire(&ptw32_cond_test_init_lock, &node);        /*         * Check again. @@ -244,7 +246,7 @@ pthread_cond_destroy (pthread_cond_t * cond)  	  result = EBUSY;  	} -      LeaveCriticalSection (&ptw32_cond_test_init_lock); +      ptw32_mcs_lock_release(&node);      }    return ((result != 0) ? result : ((result1 != 0) ? result1 : result2)); diff --git a/pthread_cond_init.c b/pthread_cond_init.c index d2de232..f28fd67 100644 --- a/pthread_cond_init.c +++ b/pthread_cond_init.c @@ -138,7 +138,9 @@ FAIL0:  DONE:    if (0 == result)      { -      EnterCriticalSection (&ptw32_cond_list_lock); +      ptw32_mcs_local_node_t node; + +      ptw32_mcs_lock_acquire(&ptw32_cond_list_lock, &node);        cv->next = NULL;        cv->prev = ptw32_cond_list_tail; @@ -155,7 +157,7 @@ DONE:  	  ptw32_cond_list_head = cv;  	} -      LeaveCriticalSection (&ptw32_cond_list_lock); +      ptw32_mcs_lock_release(&node);      }    *cond = cv; diff --git a/pthread_detach.c b/pthread_detach.c index b110f2b..19bc24d 100644 --- a/pthread_detach.c +++ b/pthread_detach.c @@ -77,8 +77,9 @@ pthread_detach (pthread_t thread)    int result;    BOOL destroyIt = PTW32_FALSE;    ptw32_thread_t * tp = (ptw32_thread_t *) thread.p; +  ptw32_mcs_local_node_t node; -  EnterCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_acquire(&ptw32_thread_reuse_lock, &node);    if (NULL == tp        || thread.x != tp->ptHandle.x) @@ -120,7 +121,7 @@ pthread_detach (pthread_t thread)  	}      } -  LeaveCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_release(&node);    if (result == 0)      { diff --git a/pthread_join.c b/pthread_join.c index 72a3a74..c49484d 100644 --- a/pthread_join.c +++ b/pthread_join.c @@ -85,8 +85,9 @@ pthread_join (pthread_t thread, void **value_ptr)    int result;    pthread_t self;    ptw32_thread_t * tp = (ptw32_thread_t *) thread.p; +  ptw32_mcs_local_node_t node; -  EnterCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_acquire(&ptw32_thread_reuse_lock, &node);    if (NULL == tp        || thread.x != tp->ptHandle.x) @@ -102,7 +103,7 @@ pthread_join (pthread_t thread, void **value_ptr)        result = 0;      } -  LeaveCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_release(&node);    if (result == 0)      { diff --git a/pthread_kill.c b/pthread_kill.c index d360187..21939d8 100644 --- a/pthread_kill.c +++ b/pthread_kill.c @@ -77,8 +77,9 @@ pthread_kill (pthread_t thread, int sig)  {    int result = 0;    ptw32_thread_t * tp; +  ptw32_mcs_local_node_t node; -  EnterCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_acquire(&ptw32_thread_reuse_lock, &node);    tp = (ptw32_thread_t *) thread.p; @@ -89,7 +90,7 @@ pthread_kill (pthread_t thread, int sig)        result = ESRCH;      } -  LeaveCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_release(&node);    if (0 == result && 0 != sig)      { diff --git a/pthread_mutex_destroy.c b/pthread_mutex_destroy.c index 95509b3..c9460dc 100644 --- a/pthread_mutex_destroy.c +++ b/pthread_mutex_destroy.c @@ -71,10 +71,6 @@ pthread_mutex_destroy (pthread_mutex_t * mutex)  	       * be too late invalidating the mutex below since another thread  	       * may already have entered mutex_lock and the check for a valid  	       * *mutex != NULL. -	       * -	       * Note that this would be an unusual situation because it is not -	       * common that mutexes are destroyed while they are still in -	       * use by other threads.  	       */  	      *mutex = NULL; @@ -112,10 +108,13 @@ pthread_mutex_destroy (pthread_mutex_t * mutex)      }    else      { +      ptw32_mcs_local_node_t node; +        /*         * See notes in ptw32_mutex_check_need_init() above also.         */ -      EnterCriticalSection (&ptw32_mutex_test_init_lock); + +      ptw32_mcs_lock_acquire(&ptw32_mutex_test_init_lock, &node);        /*         * Check again. @@ -138,8 +137,7 @@ pthread_mutex_destroy (pthread_mutex_t * mutex)  	   */  	  result = EBUSY;  	} - -      LeaveCriticalSection (&ptw32_mutex_test_init_lock); +      ptw32_mcs_lock_release(&node);      }    return (result); diff --git a/pthread_rwlock_destroy.c b/pthread_rwlock_destroy.c index d14b447..245a892 100644 --- a/pthread_rwlock_destroy.c +++ b/pthread_rwlock_destroy.c @@ -108,10 +108,11 @@ pthread_rwlock_destroy (pthread_rwlock_t * rwlock)      }    else      { +      ptw32_mcs_local_node_t node;        /*         * See notes in ptw32_rwlock_check_need_init() above also.         */ -      EnterCriticalSection (&ptw32_rwlock_test_init_lock); +      ptw32_mcs_lock_acquire(&ptw32_rwlock_test_init_lock, &node);        /*         * Check again. @@ -135,7 +136,7 @@ pthread_rwlock_destroy (pthread_rwlock_t * rwlock)  	  result = EBUSY;  	} -      LeaveCriticalSection (&ptw32_rwlock_test_init_lock); +      ptw32_mcs_lock_release(&node);      }    return ((result != 0) ? result : ((result1 != 0) ? result1 : result2)); diff --git a/pthread_spin_destroy.c b/pthread_spin_destroy.c index c9317d2..2ff1425 100644 --- a/pthread_spin_destroy.c +++ b/pthread_spin_destroy.c @@ -81,7 +81,9 @@ pthread_spin_destroy (pthread_spinlock_t * lock)        /*         * See notes in ptw32_spinlock_check_need_init() above also.         */ -      EnterCriticalSection (&ptw32_spinlock_test_init_lock); +      ptw32_mcs_local_node_t node; + +      ptw32_mcs_lock_acquire(&ptw32_spinlock_test_init_lock, &node);        /*         * Check again. @@ -105,7 +107,7 @@ pthread_spin_destroy (pthread_spinlock_t * lock)  	  result = EBUSY;  	} -      LeaveCriticalSection (&ptw32_spinlock_test_init_lock); +       ptw32_mcs_lock_release(&node);      }    return (result); diff --git a/pthread_timechange_handler_np.c b/pthread_timechange_handler_np.c index 12bd135..0f97e74 100644 --- a/pthread_timechange_handler_np.c +++ b/pthread_timechange_handler_np.c @@ -90,8 +90,9 @@ pthread_timechange_handler_np (void *arg)  {    int result = 0;    pthread_cond_t cv; +  ptw32_mcs_local_node_t node; -  EnterCriticalSection (&ptw32_cond_list_lock); +  ptw32_mcs_lock_acquire(&ptw32_cond_list_lock, &node);    cv = ptw32_cond_list_head; @@ -101,7 +102,7 @@ pthread_timechange_handler_np (void *arg)        cv = cv->next;      } -  LeaveCriticalSection (&ptw32_cond_list_lock); +  ptw32_mcs_lock_release(&node);    return (void *) (size_t) (result != 0 ? EAGAIN : 0);  } diff --git a/ptw32_cond_check_need_init.c b/ptw32_cond_check_need_init.c index 31359ad..ec3e8bb 100644 --- a/ptw32_cond_check_need_init.c +++ b/ptw32_cond_check_need_init.c @@ -43,29 +43,13 @@ INLINE int  ptw32_cond_check_need_init (pthread_cond_t * cond)  {    int result = 0; +  ptw32_mcs_local_node_t node;    /*     * The following guarded test is specifically for statically     * initialised condition variables (via PTHREAD_OBJECT_INITIALIZER). -   * -   * Note that by not providing this synchronisation we risk -   * introducing race conditions into applications which are -   * correctly written. -   * -   * Approach -   * -------- -   * We know that static condition variables will not be PROCESS_SHARED -   * so we can serialise access to internal state using -   * Win32 Critical Sections rather than Win32 Mutexes. -   * -   * If using a single global lock slows applications down too much, -   * multiple global locks could be created and hashed on some random -   * value associated with each mutex, the pointer perhaps. At a guess, -   * a good value for the optimal number of global locks might be -   * the number of processors + 1. -   *     */ -  EnterCriticalSection (&ptw32_cond_test_init_lock); +  ptw32_mcs_lock_acquire(&ptw32_cond_test_init_lock, &node);    /*     * We got here possibly under race @@ -88,7 +72,7 @@ ptw32_cond_check_need_init (pthread_cond_t * cond)        result = EINVAL;      } -  LeaveCriticalSection (&ptw32_cond_test_init_lock); +  ptw32_mcs_lock_release(&node);    return result;  } diff --git a/ptw32_mutex_check_need_init.c b/ptw32_mutex_check_need_init.c index 35ec366..897db3c 100644 --- a/ptw32_mutex_check_need_init.c +++ b/ptw32_mutex_check_need_init.c @@ -50,29 +50,9 @@ ptw32_mutex_check_need_init (pthread_mutex_t * mutex)  {    register int result = 0;    register pthread_mutex_t mtx; +  ptw32_mcs_local_node_t node; -  /* -   * The following guarded test is specifically for statically -   * initialised mutexes (via PTHREAD_MUTEX_INITIALIZER). -   * -   * Note that by not providing this synchronisation we risk -   * introducing race conditions into applications which are -   * correctly written. -   * -   * Approach -   * -------- -   * We know that static mutexes will not be PROCESS_SHARED -   * so we can serialise access to internal state using -   * Win32 Critical Sections rather than Win32 Mutexes. -   * -   * If using a single global lock slows applications down too much, -   * multiple global locks could be created and hashed on some random -   * value associated with each mutex, the pointer perhaps. At a guess, -   * a good value for the optimal number of global locks might be -   * the number of processors + 1. -   * -   */ -  EnterCriticalSection (&ptw32_mutex_test_init_lock); +  ptw32_mcs_lock_acquire(&ptw32_mutex_test_init_lock, &node);    /*     * We got here possibly under race @@ -106,7 +86,7 @@ ptw32_mutex_check_need_init (pthread_mutex_t * mutex)        result = EINVAL;      } -  LeaveCriticalSection (&ptw32_mutex_test_init_lock); +  ptw32_mcs_lock_release(&node);    return (result);  } diff --git a/ptw32_processInitialize.c b/ptw32_processInitialize.c index d13b022..8da3e41 100644 --- a/ptw32_processInitialize.c +++ b/ptw32_processInitialize.c @@ -87,16 +87,6 @@ ptw32_processInitialize (void)        ptw32_processTerminate ();      } -  /*  -   * Set up the global locks. -   */ -  InitializeCriticalSection (&ptw32_thread_reuse_lock); -  InitializeCriticalSection (&ptw32_mutex_test_init_lock); -  InitializeCriticalSection (&ptw32_cond_list_lock); -  InitializeCriticalSection (&ptw32_cond_test_init_lock); -  InitializeCriticalSection (&ptw32_rwlock_test_init_lock); -  InitializeCriticalSection (&ptw32_spinlock_test_init_lock); -    return (ptw32_processInitialized);  }				/* processInitialize */ diff --git a/ptw32_processTerminate.c b/ptw32_processTerminate.c index d2dfa7a..83f0f23 100644 --- a/ptw32_processTerminate.c +++ b/ptw32_processTerminate.c @@ -65,6 +65,7 @@ ptw32_processTerminate (void)    if (ptw32_processInitialized)      {        ptw32_thread_t * tp, * tpNext; +      ptw32_mcs_local_node_t node;        if (ptw32_selfThreadKey != NULL)  	{ @@ -86,7 +87,7 @@ ptw32_processTerminate (void)  	  ptw32_cleanupKey = NULL;  	} -      EnterCriticalSection (&ptw32_thread_reuse_lock); +      ptw32_mcs_lock_acquire(&ptw32_thread_reuse_lock, &node);        tp = ptw32_threadReuseTop;        while (tp != PTW32_THREAD_REUSE_EMPTY) @@ -96,17 +97,7 @@ ptw32_processTerminate (void)  	  tp = tpNext;  	} -      LeaveCriticalSection (&ptw32_thread_reuse_lock); - -      /*  -       * Destroy the global locks and other objects. -       */ -      DeleteCriticalSection (&ptw32_spinlock_test_init_lock); -      DeleteCriticalSection (&ptw32_rwlock_test_init_lock); -      DeleteCriticalSection (&ptw32_cond_test_init_lock); -      DeleteCriticalSection (&ptw32_cond_list_lock); -      DeleteCriticalSection (&ptw32_mutex_test_init_lock); -      DeleteCriticalSection (&ptw32_thread_reuse_lock); +      ptw32_mcs_lock_release(&node);        ptw32_processInitialized = PTW32_FALSE;      } diff --git a/ptw32_reuse.c b/ptw32_reuse.c index 0e86984..79e4dee 100644 --- a/ptw32_reuse.c +++ b/ptw32_reuse.c @@ -76,8 +76,9 @@ pthread_t  ptw32_threadReusePop (void)  {    pthread_t t = {NULL, 0}; +  ptw32_mcs_local_node_t node; -  EnterCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_acquire(&ptw32_thread_reuse_lock, &node);    if (PTW32_THREAD_REUSE_EMPTY != ptw32_threadReuseTop)      { @@ -97,7 +98,7 @@ ptw32_threadReusePop (void)        t = tp->ptHandle;      } -  LeaveCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_release(&node);    return t; @@ -114,8 +115,9 @@ ptw32_threadReusePush (pthread_t thread)  {    ptw32_thread_t * tp = (ptw32_thread_t *) thread.p;    pthread_t t; +  ptw32_mcs_local_node_t node; -  EnterCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_acquire(&ptw32_thread_reuse_lock, &node);    t = tp->ptHandle;    memset(tp, 0, sizeof(ptw32_thread_t)); @@ -143,5 +145,5 @@ ptw32_threadReusePush (pthread_t thread)    ptw32_threadReuseBottom = tp; -  LeaveCriticalSection (&ptw32_thread_reuse_lock); +  ptw32_mcs_lock_release(&node);  } diff --git a/ptw32_rwlock_check_need_init.c b/ptw32_rwlock_check_need_init.c index ea2561e..858ee27 100644 --- a/ptw32_rwlock_check_need_init.c +++ b/ptw32_rwlock_check_need_init.c @@ -41,29 +41,13 @@ INLINE int  ptw32_rwlock_check_need_init (pthread_rwlock_t * rwlock)  {    int result = 0; +  ptw32_mcs_local_node_t node;    /*     * The following guarded test is specifically for statically     * initialised rwlocks (via PTHREAD_RWLOCK_INITIALIZER). -   * -   * Note that by not providing this synchronisation we risk -   * introducing race conditions into applications which are -   * correctly written. -   * -   * Approach -   * -------- -   * We know that static rwlocks will not be PROCESS_SHARED -   * so we can serialise access to internal state using -   * Win32 Critical Sections rather than Win32 Mutexes. -   * -   * If using a single global lock slows applications down too much, -   * multiple global locks could be created and hashed on some random -   * value associated with each mutex, the pointer perhaps. At a guess, -   * a good value for the optimal number of global locks might be -   * the number of processors + 1. -   *     */ -  EnterCriticalSection (&ptw32_rwlock_test_init_lock); +  ptw32_mcs_lock_acquire(&ptw32_rwlock_test_init_lock, &node);    /*     * We got here possibly under race @@ -87,7 +71,7 @@ ptw32_rwlock_check_need_init (pthread_rwlock_t * rwlock)        result = EINVAL;      } -  LeaveCriticalSection (&ptw32_rwlock_test_init_lock); +  ptw32_mcs_lock_release(&node);    return result;  } diff --git a/ptw32_spinlock_check_need_init.c b/ptw32_spinlock_check_need_init.c index bf45bc3..8808454 100644 --- a/ptw32_spinlock_check_need_init.c +++ b/ptw32_spinlock_check_need_init.c @@ -42,16 +42,13 @@ INLINE int  ptw32_spinlock_check_need_init (pthread_spinlock_t * lock)  {    int result = 0; +  ptw32_mcs_local_node_t node;    /*     * The following guarded test is specifically for statically     * initialised spinlocks (via PTHREAD_SPINLOCK_INITIALIZER). -   * -   * Note that by not providing this synchronisation we risk -   * introducing race conditions into applications which are -   * correctly written.     */ -  EnterCriticalSection (&ptw32_spinlock_test_init_lock); +  ptw32_mcs_lock_acquire(&ptw32_spinlock_test_init_lock, &node);    /*     * We got here possibly under race @@ -75,7 +72,7 @@ ptw32_spinlock_check_need_init (pthread_spinlock_t * lock)        result = EINVAL;      } -  LeaveCriticalSection (&ptw32_spinlock_test_init_lock); +  ptw32_mcs_lock_release(&node);    return (result);  } diff --git a/tests/SIZES.GC b/tests/SIZES.GC index 603521b..eddaad7 100755 --- a/tests/SIZES.GC +++ b/tests/SIZES.GC @@ -1,7 +1,7 @@  Sizes of pthreads-win32 structs
  -------------------------------
                       pthread_t    8
 -                ptw32_thread_t  140
 +                ptw32_thread_t  152
                 pthread_attr_t_   28
                          sem_t_   12
                pthread_mutex_t_   24
 diff --git a/tests/SIZES.VC b/tests/SIZES.VC index 603521b..eddaad7 100755 --- a/tests/SIZES.VC +++ b/tests/SIZES.VC @@ -1,7 +1,7 @@  Sizes of pthreads-win32 structs
  -------------------------------
                       pthread_t    8
 -                ptw32_thread_t  140
 +                ptw32_thread_t  152
                 pthread_attr_t_   28
                          sem_t_   12
                pthread_mutex_t_   24
  | 
