Added few more stubs so that control reaches to DestroyDevice().
[mesa.git] / src / mapi / u_current.c
index ba13fe9653b838c08a41bfe461e867d8630854bf..554c974047745b80a63adaa54809cde149d9d8f3 100644 (file)
@@ -1,6 +1,5 @@
 /*
  * Mesa 3-D graphics library
- * Version:  7.1
  *
  * Copyright (C) 1999-2008  Brian Paul   All Rights Reserved.
  *
  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
- * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+ * OTHER DEALINGS IN THE SOFTWARE.
  */
 
 
@@ -48,8 +48,8 @@
  *                 drivers!  No changes to the public glapi interface.
  */
 
+#include "c11/threads.h"
 #include "u_current.h"
-#include "u_thread.h"
 
 #ifndef MAPI_MODE_UTIL
 
@@ -97,54 +97,89 @@ extern void (*__glapi_noop_table[])(void);
  * between TLS enabled loaders and non-TLS DRI drivers.
  */
 /*@{*/
-#if defined(GLX_USE_TLS)
+#if defined(USE_ELF_TLS)
 
-__thread struct mapi_table *u_current_table
+__thread struct _glapi_table *u_current_table
     __attribute__((tls_model("initial-exec")))
-    = (struct mapi_table *) table_noop_array;
+    = (struct _glapi_table *) table_noop_array;
 
-__thread void *u_current_user
+__thread void *u_current_context
     __attribute__((tls_model("initial-exec")));
 
 #else
 
-struct mapi_table *u_current_table =
-   (struct mapi_table *) table_noop_array;
-void *u_current_user;
+struct _glapi_table *u_current_table =
+   (struct _glapi_table *) table_noop_array;
+void *u_current_context;
 
-#ifdef THREADS
-struct u_tsd u_current_table_tsd;
-static struct u_tsd u_current_user_tsd;
+tss_t u_current_table_tsd;
+static tss_t u_current_context_tsd;
 static int ThreadSafe;
-#endif /* THREADS */
 
-#endif /* defined(GLX_USE_TLS) */
+#endif /* defined(USE_ELF_TLS) */
 /*@}*/
 
 
 void
 u_current_destroy(void)
 {
-#if defined(THREADS) && defined(_WIN32)
-   u_tsd_destroy(&u_current_table_tsd);
-   u_tsd_destroy(&u_current_user_tsd);
+#if !defined(USE_ELF_TLS)
+   tss_delete(u_current_table_tsd);
+   tss_delete(u_current_context_tsd);
 #endif
 }
 
 
-#if defined(THREADS) && !defined(GLX_USE_TLS)
+#if !defined(USE_ELF_TLS)
 
 static void
 u_current_init_tsd(void)
 {
-   u_tsd_init(&u_current_table_tsd);
-   u_tsd_init(&u_current_user_tsd);
+   tss_create(&u_current_table_tsd, NULL);
+   tss_create(&u_current_context_tsd, NULL);
 }
 
 /**
  * Mutex for multithread check.
  */
-u_mutex_declare_static(ThreadCheckMutex);
+static mtx_t ThreadCheckMutex = _MTX_INITIALIZER_NP;
+
+
+#ifdef _WIN32
+typedef DWORD thread_id;
+#else
+typedef thrd_t thread_id;
+#endif
+
+
+static inline thread_id
+get_thread_id(void)
+{
+   /*
+    * XXX: Callers of of this function assume it is a lightweight function.
+    * But unfortunately C11's thrd_current() gives no such guarantees.  In
+    * fact, it's pretty hard to have a compliant implementation of
+    * thrd_current() on Windows with such characteristics.  So for now, we
+    * side-step this mess and use Windows thread primitives directly here.
+    */
+#ifdef _WIN32
+   return GetCurrentThreadId();
+#else
+   return thrd_current();
+#endif
+}
+
+
+static inline int
+thread_id_equal(thread_id t1, thread_id t2)
+{
+#ifdef _WIN32
+   return t1 == t2;
+#else
+   return thrd_equal(t1, t2);
+#endif
+}
+
 
 /**
  * We should call this periodically from a function such as glXMakeCurrent
@@ -153,25 +188,25 @@ u_mutex_declare_static(ThreadCheckMutex);
 void
 u_current_init(void)
 {
-   static unsigned long knownID;
+   static thread_id knownID;
    static int firstCall = 1;
 
    if (ThreadSafe)
       return;
 
-   u_mutex_lock(ThreadCheckMutex);
+   mtx_lock(&ThreadCheckMutex);
    if (firstCall) {
       u_current_init_tsd();
 
-      knownID = u_thread_self();
+      knownID = get_thread_id();
       firstCall = 0;
    }
-   else if (knownID != u_thread_self()) {
+   else if (!thread_id_equal(knownID, get_thread_id())) {
       ThreadSafe = 1;
-      u_current_set(NULL);
-      u_current_set_user(NULL);
+      u_current_set_table(NULL);
+      u_current_set_context(NULL);
    }
-   u_mutex_unlock(ThreadCheckMutex);
+   mtx_unlock(&ThreadCheckMutex);
 }
 
 #else
@@ -191,17 +226,15 @@ u_current_init(void)
  * void from the real context pointer type.
  */
 void
-u_current_set_user(const void *ptr)
+u_current_set_context(const void *ptr)
 {
    u_current_init();
 
-#if defined(GLX_USE_TLS)
-   u_current_user = (void *) ptr;
-#elif defined(THREADS)
-   u_tsd_set(&u_current_user_tsd, (void *) ptr);
-   u_current_user = (ThreadSafe) ? NULL : (void *) ptr;
+#if defined(USE_ELF_TLS)
+   u_current_context = (void *) ptr;
 #else
-   u_current_user = (void *) ptr;
+   tss_set(u_current_context_tsd, (void *) ptr);
+   u_current_context = (ThreadSafe) ? NULL : (void *) ptr;
 #endif
 }
 
@@ -211,16 +244,12 @@ u_current_set_user(const void *ptr)
  * void to the real context pointer type.
  */
 void *
-u_current_get_user_internal(void)
+u_current_get_context_internal(void)
 {
-#if defined(GLX_USE_TLS)
-   return u_current_user;
-#elif defined(THREADS)
-   return (ThreadSafe)
-      ? u_tsd_get(&u_current_user_tsd)
-      : u_current_user;
+#if defined(USE_ELF_TLS)
+   return u_current_context;
 #else
-   return u_current_user;
+   return ThreadSafe ? tss_get(u_current_context_tsd) : u_current_context;
 #endif
 }
 
@@ -230,37 +259,35 @@ u_current_get_user_internal(void)
  * table (__glapi_noop_table).
  */
 void
-u_current_set(const struct mapi_table *tbl)
+u_current_set_table(const struct _glapi_table *tbl)
 {
    u_current_init();
 
    stub_init_once();
 
    if (!tbl)
-      tbl = (const struct mapi_table *) table_noop_array;
+      tbl = (const struct _glapi_table *) table_noop_array;
 
-#if defined(GLX_USE_TLS)
-   u_current_table = (struct mapi_table *) tbl;
-#elif defined(THREADS)
-   u_tsd_set(&u_current_table_tsd, (void *) tbl);
-   u_current_table = (ThreadSafe) ? NULL : (void *) tbl;
+#if defined(USE_ELF_TLS)
+   u_current_table = (struct _glapi_table *) tbl;
 #else
-   u_current_table = (struct mapi_table *) tbl;
+   tss_set(u_current_table_tsd, (void *) tbl);
+   u_current_table = (ThreadSafe) ? NULL : (void *) tbl;
 #endif
 }
 
 /**
  * Return pointer to current dispatch table for calling thread.
  */
-struct mapi_table *
-u_current_get_internal(void)
+struct _glapi_table *
+u_current_get_table_internal(void)
 {
-#if defined(GLX_USE_TLS)
+#if defined(USE_ELF_TLS)
    return u_current_table;
-#elif defined(THREADS)
-   return (struct mapi_table *) ((ThreadSafe) ?
-         u_tsd_get(&u_current_table_tsd) : (void *) u_current_table);
 #else
-   return u_current_table;
+   if (ThreadSafe)
+      return (struct _glapi_table *) tss_get(u_current_table_tsd);
+   else
+      return (struct _glapi_table *) u_current_table;
 #endif
 }