Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenglthread.c
Go to the documentation of this file.
00001 /* 00002 * Mesa 3-D graphics library 00003 * Version: 6.5.1 00004 * 00005 * Copyright (C) 1999-2006 Brian Paul All Rights Reserved. 00006 * 00007 * Permission is hereby granted, free of charge, to any person obtaining a 00008 * copy of this software and associated documentation files (the "Software"), 00009 * to deal in the Software without restriction, including without limitation 00010 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 00011 * and/or sell copies of the Software, and to permit persons to whom the 00012 * Software is furnished to do so, subject to the following conditions: 00013 * 00014 * The above copyright notice and this permission notice shall be included 00015 * in all copies or substantial portions of the Software. 00016 * 00017 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 00018 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 00019 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 00020 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN 00021 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 00022 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 00023 */ 00024 00025 00026 /* 00027 * XXX There's probably some work to do in order to make this file 00028 * truly reusable outside of Mesa. 00029 */ 00030 00031 00032 #ifdef HAVE_DIX_CONFIG_H 00033 #include <dix-config.h> 00034 #endif 00035 00036 #include <stdlib.h> 00037 #include <stdio.h> 00038 #include "glthread.h" 00039 00040 00041 /* 00042 * This file should still compile even when THREADS is not defined. 00043 * This is to make things easier to deal with on the makefile scene.. 00044 */ 00045 #ifdef THREADS 00046 #include <errno.h> 00047 00048 /* 00049 * Error messages 00050 */ 00051 #define INIT_TSD_ERROR "_glthread_: failed to allocate key for thread specific data" 00052 #define GET_TSD_ERROR "_glthread_: failed to get thread specific data" 00053 #define SET_TSD_ERROR "_glthread_: thread failed to set thread specific data" 00054 00055 00056 /* 00057 * Magic number to determine if a TSD object has been initialized. 00058 * Kind of a hack but there doesn't appear to be a better cross-platform 00059 * solution. 00060 */ 00061 #define INIT_MAGIC 0xff8adc98 00062 00063 00064 00065 /* 00066 * POSIX Threads -- The best way to go if your platform supports them. 00067 * Solaris >= 2.5 have POSIX threads, IRIX >= 6.4 reportedly 00068 * has them, and many of the free Unixes now have them. 00069 * Be sure to use appropriate -mt or -D_REENTRANT type 00070 * compile flags when building. 00071 */ 00072 #ifdef PTHREADS 00073 00074 unsigned long 00075 _glthread_GetID(void) 00076 { 00077 return (unsigned long) pthread_self(); 00078 } 00079 00080 00081 void 00082 _glthread_InitTSD(_glthread_TSD *tsd) 00083 { 00084 if (pthread_key_create(&tsd->key, NULL/*free*/) != 0) { 00085 perror(INIT_TSD_ERROR); 00086 exit(-1); 00087 } 00088 tsd->initMagic = INIT_MAGIC; 00089 } 00090 00091 00092 void * 00093 _glthread_GetTSD(_glthread_TSD *tsd) 00094 { 00095 if (tsd->initMagic != (int) INIT_MAGIC) { 00096 _glthread_InitTSD(tsd); 00097 } 00098 return pthread_getspecific(tsd->key); 00099 } 00100 00101 00102 void 00103 _glthread_SetTSD(_glthread_TSD *tsd, void *ptr) 00104 { 00105 if (tsd->initMagic != (int) INIT_MAGIC) { 00106 _glthread_InitTSD(tsd); 00107 } 00108 if (pthread_setspecific(tsd->key, ptr) != 0) { 00109 perror(SET_TSD_ERROR); 00110 exit(-1); 00111 } 00112 } 00113 00114 #endif /* PTHREADS */ 00115 00116 00117 00118 /* 00119 * Solaris/Unix International Threads -- Use only if POSIX threads 00120 * aren't available on your Unix platform. Solaris 2.[34] are examples 00121 * of platforms where this is the case. Be sure to use -mt and/or 00122 * -D_REENTRANT when compiling. 00123 */ 00124 #ifdef SOLARIS_THREADS 00125 #define USE_LOCK_FOR_KEY /* undef this to try a version without 00126 lock for the global key... */ 00127 00128 unsigned long 00129 _glthread_GetID(void) 00130 { 00131 abort(); /* XXX not implemented yet */ 00132 return (unsigned long) 0; 00133 } 00134 00135 00136 void 00137 _glthread_InitTSD(_glthread_TSD *tsd) 00138 { 00139 if ((errno = mutex_init(&tsd->keylock, 0, NULL)) != 0 || 00140 (errno = thr_keycreate(&(tsd->key), free)) != 0) { 00141 perror(INIT_TSD_ERROR); 00142 exit(-1); 00143 } 00144 tsd->initMagic = INIT_MAGIC; 00145 } 00146 00147 00148 void * 00149 _glthread_GetTSD(_glthread_TSD *tsd) 00150 { 00151 void* ret; 00152 if (tsd->initMagic != INIT_MAGIC) { 00153 _glthread_InitTSD(tsd); 00154 } 00155 #ifdef USE_LOCK_FOR_KEY 00156 mutex_lock(&tsd->keylock); 00157 thr_getspecific(tsd->key, &ret); 00158 mutex_unlock(&tsd->keylock); 00159 #else 00160 if ((errno = thr_getspecific(tsd->key, &ret)) != 0) { 00161 perror(GET_TSD_ERROR); 00162 exit(-1); 00163 } 00164 #endif 00165 return ret; 00166 } 00167 00168 00169 void 00170 _glthread_SetTSD(_glthread_TSD *tsd, void *ptr) 00171 { 00172 if (tsd->initMagic != INIT_MAGIC) { 00173 _glthread_InitTSD(tsd); 00174 } 00175 if ((errno = thr_setspecific(tsd->key, ptr)) != 0) { 00176 perror(SET_TSD_ERROR); 00177 exit(-1); 00178 } 00179 } 00180 00181 #undef USE_LOCK_FOR_KEY 00182 #endif /* SOLARIS_THREADS */ 00183 00184 00185 00186 /* 00187 * Win32 Threads. The only available option for Windows 95/NT. 00188 * Be sure that you compile using the Multithreaded runtime, otherwise 00189 * bad things will happen. 00190 */ 00191 #ifdef WIN32_THREADS 00192 00193 void FreeTSD(_glthread_TSD *p) 00194 { 00195 if (p->initMagic==INIT_MAGIC) { 00196 TlsFree(p->key); 00197 p->initMagic=0; 00198 } 00199 } 00200 00201 void InsteadOf_exit(int nCode) 00202 { 00203 DWORD dwErr=GetLastError(); 00204 } 00205 00206 unsigned long 00207 _glthread_GetID(void) 00208 { 00209 return GetCurrentThreadId(); 00210 } 00211 00212 00213 void 00214 _glthread_InitTSD(_glthread_TSD *tsd) 00215 { 00216 tsd->key = TlsAlloc(); 00217 if (tsd->key == TLS_OUT_OF_INDEXES) { 00218 perror("Mesa:_glthread_InitTSD"); 00219 InsteadOf_exit(-1); 00220 } 00221 tsd->initMagic = INIT_MAGIC; 00222 } 00223 00224 00225 void * 00226 _glthread_GetTSD(_glthread_TSD *tsd) 00227 { 00228 if (tsd->initMagic != INIT_MAGIC) { 00229 _glthread_InitTSD(tsd); 00230 } 00231 return TlsGetValue(tsd->key); 00232 } 00233 00234 00235 void 00236 _glthread_SetTSD(_glthread_TSD *tsd, void *ptr) 00237 { 00238 /* the following code assumes that the _glthread_TSD has been initialized 00239 to zero at creation */ 00240 if (tsd->initMagic != INIT_MAGIC) { 00241 _glthread_InitTSD(tsd); 00242 } 00243 if (TlsSetValue(tsd->key, ptr) == 0) { 00244 perror("Mesa:_glthread_SetTSD"); 00245 InsteadOf_exit(-1); 00246 } 00247 } 00248 00249 #endif /* WIN32_THREADS */ 00250 00251 00252 00253 /* 00254 * XFree86 has its own thread wrapper, Xthreads.h 00255 * We wrap it again for GL. 00256 */ 00257 #ifdef USE_XTHREADS 00258 00259 unsigned long 00260 _glthread_GetID(void) 00261 { 00262 return (unsigned long) xthread_self(); 00263 } 00264 00265 00266 void 00267 _glthread_InitTSD(_glthread_TSD *tsd) 00268 { 00269 if (xthread_key_create(&tsd->key, NULL) != 0) { 00270 perror(INIT_TSD_ERROR); 00271 exit(-1); 00272 } 00273 tsd->initMagic = INIT_MAGIC; 00274 } 00275 00276 00277 void * 00278 _glthread_GetTSD(_glthread_TSD *tsd) 00279 { 00280 void *ptr; 00281 if (tsd->initMagic != INIT_MAGIC) { 00282 _glthread_InitTSD(tsd); 00283 } 00284 xthread_get_specific(tsd->key, &ptr); 00285 return ptr; 00286 } 00287 00288 00289 void 00290 _glthread_SetTSD(_glthread_TSD *tsd, void *ptr) 00291 { 00292 if (tsd->initMagic != INIT_MAGIC) { 00293 _glthread_InitTSD(tsd); 00294 } 00295 xthread_set_specific(tsd->key, ptr); 00296 } 00297 00298 #endif /* XTHREAD */ 00299 00300 00301 00302 /* 00303 * BeOS threads 00304 */ 00305 #ifdef BEOS_THREADS 00306 00307 unsigned long 00308 _glthread_GetID(void) 00309 { 00310 return (unsigned long) find_thread(NULL); 00311 } 00312 00313 void 00314 _glthread_InitTSD(_glthread_TSD *tsd) 00315 { 00316 tsd->key = tls_allocate(); 00317 tsd->initMagic = INIT_MAGIC; 00318 } 00319 00320 void * 00321 _glthread_GetTSD(_glthread_TSD *tsd) 00322 { 00323 if (tsd->initMagic != (int) INIT_MAGIC) { 00324 _glthread_InitTSD(tsd); 00325 } 00326 return tls_get(tsd->key); 00327 } 00328 00329 void 00330 _glthread_SetTSD(_glthread_TSD *tsd, void *ptr) 00331 { 00332 if (tsd->initMagic != (int) INIT_MAGIC) { 00333 _glthread_InitTSD(tsd); 00334 } 00335 tls_set(tsd->key, ptr); 00336 } 00337 00338 #endif /* BEOS_THREADS */ 00339 00340 00341 00342 #else /* THREADS */ 00343 00344 00345 /* 00346 * no-op functions 00347 */ 00348 00349 unsigned long 00350 _glthread_GetID(void) 00351 { 00352 return 0; 00353 } 00354 00355 00356 void 00357 _glthread_InitTSD(_glthread_TSD *tsd) 00358 { 00359 (void) tsd; 00360 } 00361 00362 00363 void * 00364 _glthread_GetTSD(_glthread_TSD *tsd) 00365 { 00366 (void) tsd; 00367 return NULL; 00368 } 00369 00370 00371 void 00372 _glthread_SetTSD(_glthread_TSD *tsd, void *ptr) 00373 { 00374 (void) tsd; 00375 (void) ptr; 00376 } 00377 00378 00379 #endif /* THREADS */ Generated on Sat May 26 2012 04:18:56 for ReactOS by
1.7.6.1
|