Don't use the thread_exit vfunc
[platform/upstream/glib.git] / glib / gthread-win32.c
index 81fd7de..f26ff4c 100644 (file)
@@ -99,22 +99,22 @@ g_thread_abort (gint         status,
  */
 typedef struct
 {
-  void     (* CallThisOnThreadExit)        (void);              /* fake */
-
-  void     (* InitializeSRWLock)           (gpointer lock);
-  void     (* DeleteSRWLock)               (gpointer lock);     /* fake */
-  void     (* AcquireSRWLockExclusive)     (gpointer lock);
-  BOOLEAN  (* TryAcquireSRWLockExclusive)  (gpointer lock);
-  void     (* ReleaseSRWLockExclusive)     (gpointer lock);
-
-  void     (* InitializeConditionVariable) (gpointer cond);
-  void     (* DeleteConditionVariable)     (gpointer cond);     /* fake */
-  BOOL     (* SleepConditionVariableSRW)   (gpointer cond,
-                                            gpointer lock,
-                                            DWORD    timeout,
-                                            ULONG    flags);
-  void     (* WakeAllConditionVariable)    (gpointer cond);
-  void     (* WakeConditionVariable)       (gpointer cond);
+  void     (__stdcall * CallThisOnThreadExit)        (void);              /* fake */
+
+  void     (__stdcall * InitializeSRWLock)           (gpointer lock);
+  void     (__stdcall * DeleteSRWLock)               (gpointer lock);     /* fake */
+  void     (__stdcall * AcquireSRWLockExclusive)     (gpointer lock);
+  BOOLEAN  (__stdcall * TryAcquireSRWLockExclusive)  (gpointer lock);
+  void     (__stdcall * ReleaseSRWLockExclusive)     (gpointer lock);
+
+  void     (__stdcall * InitializeConditionVariable) (gpointer cond);
+  void     (__stdcall * DeleteConditionVariable)     (gpointer cond);     /* fake */
+  BOOL     (__stdcall * SleepConditionVariableSRW)   (gpointer cond,
+                                                      gpointer lock,
+                                                      DWORD    timeout,
+                                                      ULONG    flags);
+  void     (__stdcall * WakeAllConditionVariable)    (gpointer cond);
+  void     (__stdcall * WakeConditionVariable)       (gpointer cond);
 } GThreadImplVtable;
 
 static GThreadImplVtable g_thread_impl_vtable;
@@ -245,19 +245,6 @@ struct _GPrivateDestructor
 
 static GPrivateDestructor * volatile g_private_destructors;
 
-GPrivate *
-(g_private_new) (GDestroyNotify notify)
-{
-  GPrivate *key;
-
-  key = malloc (sizeof (GPrivate));
-  if G_UNLIKELY (key == NULL)
-    g_thread_abort (errno, "malloc");
-  g_private_init (key, notify);
-
-  return key;
-}
-
 void
 g_private_init (GPrivate       *key,
                 GDestroyNotify  notify)
@@ -275,18 +262,29 @@ g_private_init (GPrivate       *key,
   do
     destructor->next = g_private_destructors;
   while (InterlockedCompareExchangePointer (&g_private_destructors, destructor->next, destructor) != destructor->next);
+
+  key->ready = TRUE;
 }
 
 gpointer
-(g_private_get) (GPrivate *key)
+g_private_get (GPrivate *key)
 {
+  if (!key->ready)
+    return key->single_value;
+
   return TlsGetValue (key->index);
 }
 
 void
-(g_private_set) (GPrivate *key,
+g_private_set (GPrivate *key,
                gpointer  value)
 {
+  if (!key->ready)
+    {
+      key->single_value = value;
+      return;
+    }
+
   TlsSetValue (key->index, value);
 }
 
@@ -373,8 +371,8 @@ g_thread_self_win32_impl (gpointer thread)
   *(GThreadData **)thread = self;
 }
 
-static void
-g_thread_exit_win32_impl (void)
+void
+g_system_thread_exit (void)
 {
   GThreadData *self = TlsGetValue (g_thread_self_tls);
   gboolean dtors_called;
@@ -433,7 +431,7 @@ g_thread_proxy (gpointer data)
 
   self->func (self->data);
 
-  g_thread_exit_win32_impl ();
+  g_system_thread_exit ();
 
   g_assert_not_reached ();
 
@@ -481,8 +479,8 @@ g_thread_create_win32_impl (GThreadFunc func,
   g_thread_set_priority_win32_impl (thread, priority);
 }
 
-static void
-g_thread_yield_win32_impl (void)
+void
+g_thread_yield (void)
 {
   Sleep(0);
 }
@@ -501,6 +499,13 @@ g_thread_join_win32_impl (gpointer thread)
   g_free (target);
 }
 
+gboolean
+g_system_thread_equal (gpointer thread1,
+                       gpointer thread2)
+{
+   return ((GSystemThread*)thread1)->dummy_pointer == ((GSystemThread*)thread2)->dummy_pointer;
+}
+
 /* {{{1 SRWLock and CONDITION_VARIABLE emulation (for Windows XP) */
 
 static CRITICAL_SECTION g_thread_xp_lock;
@@ -536,7 +541,7 @@ g_thread_xp_waiter_get (void)
   return waiter;
 }
 
-static void
+static void __stdcall
 g_thread_xp_CallThisOnThreadExit (void)
 {
   GThreadXpWaiter *waiter;
@@ -557,13 +562,13 @@ typedef struct
   CRITICAL_SECTION critical_section;
 } GThreadSRWLock;
 
-static void
+static void __stdcall
 g_thread_xp_InitializeSRWLock (gpointer mutex)
 {
   *(GThreadSRWLock * volatile *) mutex = NULL;
 }
 
-static void
+static void __stdcall
 g_thread_xp_DeleteSRWLock (gpointer mutex)
 {
   GThreadSRWLock *lock = *(GThreadSRWLock * volatile *) mutex;
@@ -575,7 +580,7 @@ g_thread_xp_DeleteSRWLock (gpointer mutex)
     }
 }
 
-static GThreadSRWLock *
+static GThreadSRWLock * __stdcall
 g_thread_xp_get_srwlock (GThreadSRWLock * volatile *lock)
 {
   GThreadSRWLock *result;
@@ -605,7 +610,7 @@ g_thread_xp_get_srwlock (GThreadSRWLock * volatile *lock)
   return result;
 }
 
-static void
+static void __stdcall
 g_thread_xp_AcquireSRWLockExclusive (gpointer mutex)
 {
   GThreadSRWLock *lock = g_thread_xp_get_srwlock (mutex);
@@ -613,7 +618,7 @@ g_thread_xp_AcquireSRWLockExclusive (gpointer mutex)
   EnterCriticalSection (&lock->critical_section);
 }
 
-static BOOLEAN
+static BOOLEAN __stdcall
 g_thread_xp_TryAcquireSRWLockExclusive (gpointer mutex)
 {
   GThreadSRWLock *lock = g_thread_xp_get_srwlock (mutex);
@@ -621,7 +626,7 @@ g_thread_xp_TryAcquireSRWLockExclusive (gpointer mutex)
   return TryEnterCriticalSection (&lock->critical_section);
 }
 
-static void
+static void __stdcall
 g_thread_xp_ReleaseSRWLockExclusive (gpointer mutex)
 {
   GThreadSRWLock *lock = *(GThreadSRWLock * volatile *) mutex;
@@ -640,13 +645,13 @@ typedef struct
   volatile GThreadXpWaiter **last_ptr;
 } GThreadXpCONDITION_VARIABLE;
 
-static void
+static void __stdcall
 g_thread_xp_InitializeConditionVariable (gpointer cond)
 {
   *(GThreadXpCONDITION_VARIABLE * volatile *) cond = NULL;
 }
 
-static void
+static void __stdcall
 g_thread_xp_DeleteConditionVariable (gpointer cond)
 {
   GThreadXpCONDITION_VARIABLE *cv = *(GThreadXpCONDITION_VARIABLE * volatile *) cond;
@@ -655,7 +660,7 @@ g_thread_xp_DeleteConditionVariable (gpointer cond)
     free (cv);
 }
 
-static GThreadXpCONDITION_VARIABLE *
+static GThreadXpCONDITION_VARIABLE * __stdcall
 g_thread_xp_get_condition_variable (GThreadXpCONDITION_VARIABLE * volatile *cond)
 {
   GThreadXpCONDITION_VARIABLE *result;
@@ -687,7 +692,7 @@ g_thread_xp_get_condition_variable (GThreadXpCONDITION_VARIABLE * volatile *cond
   return result;
 }
 
-static BOOL
+static BOOL __stdcall
 g_thread_xp_SleepConditionVariableSRW (gpointer cond,
                                        gpointer mutex,
                                        DWORD    timeout,
@@ -715,7 +720,7 @@ g_thread_xp_SleepConditionVariableSRW (gpointer cond,
   return status == WAIT_OBJECT_0;
 }
 
-static void
+static void __stdcall
 g_thread_xp_WakeConditionVariable (gpointer cond)
 {
   GThreadXpCONDITION_VARIABLE *cv = g_thread_xp_get_condition_variable (cond);
@@ -735,7 +740,7 @@ g_thread_xp_WakeConditionVariable (gpointer cond)
     SetEvent (waiter->event);
 }
 
-static void
+static void __stdcall
 g_thread_xp_WakeAllConditionVariable (gpointer cond)
 {
   GThreadXpCONDITION_VARIABLE *cv = g_thread_xp_get_condition_variable (cond);
@@ -800,12 +805,12 @@ GThreadFunctions g_thread_functions_for_glib_use =
   g_private_get,
   g_private_set,
   g_thread_create_win32_impl,       /* thread */
-  g_thread_yield_win32_impl,
+  g_thread_yield,
   g_thread_join_win32_impl,
-  g_thread_exit_win32_impl,
+  g_system_thread_exit,
   g_thread_set_priority_win32_impl,
   g_thread_self_win32_impl,
-  NULL                             /* no equal function necessary */
+  g_system_thread_equal
 };
 
 void
@@ -856,12 +861,9 @@ g_thread_lookup_native_funcs (void)
 G_GNUC_INTERNAL void
 g_thread_DllMain (void)
 {
-  /* XXX This is broken right now for some unknown reason...
-
   if (g_thread_lookup_native_funcs ())
     fprintf (stderr, "(debug) GThread using native mode\n");
   else
-*/
     {
       fprintf (stderr, "(debug) GThread using Windows XP mode\n");
       g_thread_xp_init ();