diff options
author | Keith Whitwell <[email protected]> | 2008-09-11 18:32:05 +0100 |
---|---|---|
committer | Keith Whitwell <[email protected]> | 2008-09-11 18:32:05 +0100 |
commit | cc7dd4fc1b3c765ca1ecd943d189bb156dae529d (patch) | |
tree | 1a3560eb6df8a443c4f0e5af0a916f190b1542f6 /src/gallium/include/pipe | |
parent | 685248bea1fef5fd6335982570e34d0f6672030d (diff) | |
parent | d50d68a1c940ed9c8d8c65e8e33667fa90d5baa1 (diff) |
Merge commit 'origin/gallium-0.1' into gallium-0.2
Conflicts:
Makefile
progs/demos/Makefile
progs/glsl/Makefile
progs/redbook/Makefile
progs/samples/Makefile
progs/tests/Makefile
progs/trivial/Makefile
progs/xdemos/Makefile
src/gallium/Makefile
src/mesa/main/attrib.c
src/mesa/main/bufferobj.c
src/mesa/vbo/vbo_exec_draw.c
Diffstat (limited to 'src/gallium/include/pipe')
-rw-r--r-- | src/gallium/include/pipe/p_debug.h | 3 | ||||
-rw-r--r-- | src/gallium/include/pipe/p_format.h | 29 | ||||
-rw-r--r-- | src/gallium/include/pipe/p_inlines.h | 28 | ||||
-rw-r--r-- | src/gallium/include/pipe/p_pointer.h | 95 | ||||
-rw-r--r-- | src/gallium/include/pipe/p_state.h | 14 | ||||
-rw-r--r-- | src/gallium/include/pipe/p_thread.h | 403 |
6 files changed, 227 insertions, 345 deletions
diff --git a/src/gallium/include/pipe/p_debug.h b/src/gallium/include/pipe/p_debug.h index 6478ae2f08e..cb6196aa9fb 100644 --- a/src/gallium/include/pipe/p_debug.h +++ b/src/gallium/include/pipe/p_debug.h @@ -340,9 +340,12 @@ void debug_dump_image(const char *prefix, const void *data); void debug_dump_surface(const char *prefix, struct pipe_surface *surface); +void debug_dump_surface_bmp(const char *filename, + struct pipe_surface *surface); #else #define debug_dump_image(prefix, format, cpp, width, height, stride, data) ((void)0) #define debug_dump_surface(prefix, surface) ((void)0) +#define debug_dump_surface_bmp(filename, surface) ((void)0) #endif diff --git a/src/gallium/include/pipe/p_format.h b/src/gallium/include/pipe/p_format.h index d9aa5792a44..97a4c8c510b 100644 --- a/src/gallium/include/pipe/p_format.h +++ b/src/gallium/include/pipe/p_format.h @@ -531,6 +531,35 @@ pf_is_ycbcr( enum pipe_format format ) return pf_layout(format) == PIPE_FORMAT_LAYOUT_YCBCR ? TRUE : FALSE; } +static INLINE boolean +pf_has_alpha( enum pipe_format format ) +{ + switch (pf_layout(format)) { + case PIPE_FORMAT_LAYOUT_RGBAZS: + case PIPE_FORMAT_LAYOUT_MIXED: + /* FIXME: pf_get_component_bits( PIPE_FORMAT_A8L8_UNORM, PIPE_FORMAT_COMP_A ) should not return 0 right? */ + if(format == PIPE_FORMAT_A8_UNORM || + format == PIPE_FORMAT_A8L8_UNORM || + format == PIPE_FORMAT_A8_L8_SRGB) + return TRUE; + return pf_get_component_bits( format, PIPE_FORMAT_COMP_A ) ? TRUE : FALSE; + case PIPE_FORMAT_LAYOUT_YCBCR: + return FALSE; + case PIPE_FORMAT_LAYOUT_DXT: + switch (format) { + case PIPE_FORMAT_DXT1_RGBA: + case PIPE_FORMAT_DXT3_RGBA: + case PIPE_FORMAT_DXT5_RGBA: + return TRUE; + default: + return FALSE; + } + default: + assert( 0 ); + return FALSE; + } +} + #ifdef __cplusplus } #endif diff --git a/src/gallium/include/pipe/p_inlines.h b/src/gallium/include/pipe/p_inlines.h index 1e4b98edb48..d70de8e3011 100644 --- a/src/gallium/include/pipe/p_inlines.h +++ b/src/gallium/include/pipe/p_inlines.h @@ -109,7 +109,7 @@ pipe_surface_reference(struct pipe_surface **ptr, struct pipe_surface *surf) /* XXX: thread safety issues! */ static INLINE void -pipe_buffer_reference(struct pipe_winsys *winsys, +winsys_buffer_reference(struct pipe_winsys *winsys, struct pipe_buffer **ptr, struct pipe_buffer *buf) { @@ -164,48 +164,48 @@ pipe_texture_release(struct pipe_texture **ptr) */ static INLINE struct pipe_buffer * -pipe_buffer_create( struct pipe_context *pipe, +pipe_buffer_create( struct pipe_screen *screen, unsigned alignment, unsigned usage, unsigned size ) { - return pipe->winsys->buffer_create(pipe->winsys, alignment, usage, size); + return screen->winsys->buffer_create(screen->winsys, alignment, usage, size); } static INLINE struct pipe_buffer * -pipe_user_buffer_create( struct pipe_context *pipe, void *ptr, unsigned size ) +pipe_user_buffer_create( struct pipe_screen *screen, void *ptr, unsigned size ) { - return pipe->winsys->user_buffer_create(pipe->winsys, ptr, size); + return screen->winsys->user_buffer_create(screen->winsys, ptr, size); } static INLINE void -pipe_buffer_destroy( struct pipe_context *pipe, struct pipe_buffer *buf ) +pipe_buffer_destroy( struct pipe_screen *screen, struct pipe_buffer *buf ) { - pipe->winsys->buffer_destroy(pipe->winsys, buf); + screen->winsys->buffer_destroy(screen->winsys, buf); } static INLINE void * -pipe_buffer_map(struct pipe_context *pipe, +pipe_buffer_map(struct pipe_screen *screen, struct pipe_buffer *buf, unsigned usage) { - return pipe->winsys->buffer_map(pipe->winsys, buf, usage); + return screen->winsys->buffer_map(screen->winsys, buf, usage); } static INLINE void -pipe_buffer_unmap(struct pipe_context *pipe, +pipe_buffer_unmap(struct pipe_screen *screen, struct pipe_buffer *buf) { - pipe->winsys->buffer_unmap(pipe->winsys, buf); + screen->winsys->buffer_unmap(screen->winsys, buf); } /* XXX when we're using this everywhere, get rid of - * pipe_buffer_reference() above. + * winsys_buffer_reference() above. */ static INLINE void -pipe_reference_buffer(struct pipe_context *pipe, +pipe_buffer_reference(struct pipe_screen *screen, struct pipe_buffer **ptr, struct pipe_buffer *buf) { - pipe_buffer_reference(pipe->winsys, ptr, buf); + winsys_buffer_reference(screen->winsys, ptr, buf); } diff --git a/src/gallium/include/pipe/p_pointer.h b/src/gallium/include/pipe/p_pointer.h deleted file mode 100644 index 3a1e6be88e7..00000000000 --- a/src/gallium/include/pipe/p_pointer.h +++ /dev/null @@ -1,95 +0,0 @@ -/************************************************************************** - * - * Copyright 2007-2008 Tungsten Graphics, Inc., Cedar Park, Texas. - * All Rights Reserved. - * - * Permission is hereby granted, free of charge, to any person obtaining a - * copy of this software and associated documentation files (the - * "Software"), to deal in the Software without restriction, including - * without limitation the rights to use, copy, modify, merge, publish, - * distribute, sub license, and/or sell copies of the Software, and to - * permit persons to whom the Software is furnished to do so, subject to - * the following conditions: - * - * The above copyright notice and this permission notice (including the - * next paragraph) shall be included in all copies or substantial portions - * of the Software. - * - * 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 NON-INFRINGEMENT. - * IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS 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. - * - **************************************************************************/ - -#ifndef P_POINTER_H -#define P_POINTER_H - -#include "p_compiler.h" - -#ifdef __cplusplus -extern "C" { -#endif - -static INLINE intptr_t -pointer_to_intptr( const void *p ) -{ - union { - const void *p; - intptr_t i; - } pi; - pi.p = p; - return pi.i; -} - -static INLINE void * -intptr_to_pointer( intptr_t i ) -{ - union { - void *p; - intptr_t i; - } pi; - pi.i = i; - return pi.p; -} - -static INLINE uintptr_t -pointer_to_uintptr( const void *ptr ) -{ - union { - const void *p; - uintptr_t u; - } pu; - pu.p = ptr; - return pu.u; -} - -static INLINE void * -uintptr_to_pointer( uintptr_t u ) -{ - union { - void *p; - uintptr_t u; - } pu; - pu.u = u; - return pu.p; -} - -/** - * Return a pointer aligned to next multiple of N bytes. - */ -static INLINE void * -align_pointer( const void *unaligned, uintptr_t alignment ) -{ - uintptr_t aligned = (pointer_to_uintptr( unaligned ) + alignment - 1) & ~(alignment - 1); - return uintptr_to_pointer( aligned ); -} - -#ifdef __cplusplus -} -#endif - -#endif /* P_POINTER_H */ diff --git a/src/gallium/include/pipe/p_state.h b/src/gallium/include/pipe/p_state.h index 4d0f3597e60..da783389dae 100644 --- a/src/gallium/include/pipe/p_state.h +++ b/src/gallium/include/pipe/p_state.h @@ -276,12 +276,12 @@ struct pipe_surface enum pipe_format format; /**< PIPE_FORMAT_x */ unsigned status; /**< PIPE_SURFACE_STATUS_x */ unsigned clear_value; /**< XXX may be temporary */ - unsigned width; - unsigned height; + unsigned width; /**< logical width in pixels */ + unsigned height; /**< logical height in pixels */ struct pipe_format_block block; - unsigned nblocksx; - unsigned nblocksy; - unsigned stride; /**< in bytes */ + unsigned nblocksx; /**< allocated width in blocks */ + unsigned nblocksy; /**< allocated height in blocks */ + unsigned stride; /**< stride in bytes between rows of blocks */ unsigned layout; /**< PIPE_SURFACE_LAYOUT_x */ unsigned offset; /**< offset from start of buffer, in bytes */ unsigned refcount; @@ -309,8 +309,8 @@ struct pipe_texture unsigned depth[PIPE_MAX_TEXTURE_LEVELS]; struct pipe_format_block block; - unsigned nblocksx[PIPE_MAX_TEXTURE_LEVELS]; - unsigned nblocksy[PIPE_MAX_TEXTURE_LEVELS]; + unsigned nblocksx[PIPE_MAX_TEXTURE_LEVELS]; /**< allocated width in blocks */ + unsigned nblocksy[PIPE_MAX_TEXTURE_LEVELS]; /**< allocated height in blocks */ unsigned last_level:8; /**< Index of last mipmap level present/defined */ unsigned compressed:1; diff --git a/src/gallium/include/pipe/p_thread.h b/src/gallium/include/pipe/p_thread.h index 6e526b7aa8b..e01d5a602b8 100644 --- a/src/gallium/include/pipe/p_thread.h +++ b/src/gallium/include/pipe/p_thread.h @@ -23,307 +23,252 @@ * **************************************************************************/ + /** - * @file - * Thread - * - * Initial version by John Stone ([email protected]) ([email protected]) - * and Christoph Poliwoda ([email protected]) - * Revised by Keith Whitwell - * Adapted for new gl dispatcher by Brian Paul - * - * - * - * DOCUMENTATION - * - * This thread module exports the following types: - * _glthread_TSD Thread-specific data area - * _glthread_Thread Thread datatype - * _glthread_Mutex Mutual exclusion lock - * - * Macros: - * _glthread_DECLARE_STATIC_MUTEX(name) Declare a non-local mutex - * _glthread_INIT_MUTEX(name) Initialize a mutex - * _glthread_LOCK_MUTEX(name) Lock a mutex - * _glthread_UNLOCK_MUTEX(name) Unlock a mutex - * - * Functions: - * _glthread_GetID(v) Get integer thread ID - * _glthread_InitTSD() Initialize thread-specific data - * _glthread_GetTSD() Get thread-specific data - * _glthread_SetTSD() Set thread-specific data - * - * If this file is accidentally included by a non-threaded build, - * it should not cause the build to fail, or otherwise cause problems. - * In general, it should only be included when needed however. + * Thread, mutex, condition var and thread-specific data functions. */ -#ifndef _P_THREAD_H_ -#define _P_THREAD_H_ +#ifndef _P_THREAD2_H_ +#define _P_THREAD2_H_ -#if (defined(PTHREADS) || defined(SOLARIS_THREADS) ||\ - defined(WIN32_THREADS) || defined(USE_XTHREADS) || defined(BEOS_THREADS)) \ - && !defined(THREADS) -# define THREADS -#endif -#ifdef VMS -#include <GL/vms_x_fix.h> -#endif +#include "pipe/p_compiler.h" + + +#if defined(PIPE_OS_LINUX) -/* - * POSIX threads. This should be your choice in the Unix world - * whenever possible. When building with POSIX threads, be sure - * to enable any compiler flags which will cause the MT-safe - * libc (if one exists) to be used when linking, as well as any - * header macros for MT-safe errno, etc. For Solaris, this is the -mt - * compiler flag. On Solaris with gcc, use -D_REENTRANT to enable - * proper compiling for MT-safe libc etc. - */ -#if defined(PTHREADS) #include <pthread.h> /* POSIX threads headers */ +#include <stdio.h> /* for perror() */ -typedef struct { - pthread_key_t key; - int initMagic; -} _glthread_TSD; +typedef pthread_t pipe_thread; + +#define PIPE_THREAD_ROUTINE( name, param ) \ + void *name( void *param ) -typedef pthread_t _glthread_Thread; +static INLINE pipe_thread pipe_thread_create( void *(* routine)( void *), void *param ) +{ + pipe_thread thread; + if (pthread_create( &thread, NULL, routine, param )) + return 0; + return thread; +} -typedef pthread_mutex_t _glthread_Mutex; +static INLINE int pipe_thread_wait( pipe_thread thread ) +{ + return pthread_join( thread, NULL ); +} -#define _glthread_DECLARE_STATIC_MUTEX(name) \ - static _glthread_Mutex name = PTHREAD_MUTEX_INITIALIZER +static INLINE int pipe_thread_destroy( pipe_thread thread ) +{ + return pthread_detach( thread ); +} -#define _glthread_INIT_MUTEX(name) \ - pthread_mutex_init(&(name), NULL) +typedef pthread_mutex_t pipe_mutex; +typedef pthread_cond_t pipe_condvar; -#define _glthread_DESTROY_MUTEX(name) \ - pthread_mutex_destroy(&(name)) +#define pipe_static_mutex(mutex) \ + static pipe_mutex mutex = PTHREAD_MUTEX_INITIALIZER -#define _glthread_LOCK_MUTEX(name) \ - (void) pthread_mutex_lock(&(name)) +#define pipe_mutex_init(mutex) \ + pthread_mutex_init(&(mutex), NULL) -#define _glthread_UNLOCK_MUTEX(name) \ - (void) pthread_mutex_unlock(&(name)) +#define pipe_mutex_destroy(mutex) \ + pthread_mutex_destroy(&(mutex)) -typedef pthread_cond_t _glthread_Cond; +#define pipe_mutex_lock(mutex) \ + (void) pthread_mutex_lock(&(mutex)) -#define _glthread_DECLARE_STATIC_COND(name) \ - static _glthread_Cond name = PTHREAD_COND_INITIALIZER +#define pipe_mutex_unlock(mutex) \ + (void) pthread_mutex_unlock(&(mutex)) -#define _glthread_INIT_COND(cond) \ +#define pipe_static_condvar(mutex) \ + static pipe_condvar mutex = PTHREAD_COND_INITIALIZER + +#define pipe_condvar_init(cond) \ pthread_cond_init(&(cond), NULL) -#define _glthread_DESTROY_COND(name) \ - pthread_cond_destroy(&(name)) +#define pipe_condvar_destroy(cond) \ + pthread_cond_destroy(&(cond)) -#define _glthread_COND_WAIT(cond, mutex) \ +#define pipe_condvar_wait(cond, mutex) \ pthread_cond_wait(&(cond), &(mutex)) -#define _glthread_COND_SIGNAL(cond) \ +#define pipe_condvar_signal(cond) \ pthread_cond_signal(&(cond)) -#define _glthread_COND_BROADCAST(cond) \ +#define pipe_condvar_broadcast(cond) \ pthread_cond_broadcast(&(cond)) -#endif /* PTHREADS */ - +#elif defined(PIPE_SUBSYSTEM_WINDOWS_USER) - -/* - * Solaris threads. Use only up to Solaris 2.4. - * Solaris 2.5 and higher provide POSIX threads. - * Be sure to compile with -mt on the Solaris compilers, or - * use -D_REENTRANT if using gcc. - */ -#ifdef SOLARIS_THREADS -#include <thread.h> - -typedef struct { - thread_key_t key; - mutex_t keylock; - int initMagic; -} _glthread_TSD; - -typedef thread_t _glthread_Thread; - -typedef mutex_t _glthread_Mutex; - -/* XXX need to really implement mutex-related macros */ -#define _glthread_DECLARE_STATIC_MUTEX(name) static _glthread_Mutex name = 0 -#define _glthread_INIT_MUTEX(name) (void) name -#define _glthread_DESTROY_MUTEX(name) (void) name -#define _glthread_LOCK_MUTEX(name) (void) name -#define _glthread_UNLOCK_MUTEX(name) (void) name - -#endif /* SOLARIS_THREADS */ - - - - -/* - * Windows threads. Should work with Windows NT and 95. - * IMPORTANT: Link with multithreaded runtime library when THREADS are - * used! - */ -#ifdef WIN32_THREADS #include <windows.h> -typedef struct { - DWORD key; - int initMagic; -} _glthread_TSD; +typedef HANDLE pipe_thread; -typedef HANDLE _glthread_Thread; +#define PIPE_THREAD_ROUTINE( name, param ) \ + void * WINAPI name( void *param ) -typedef CRITICAL_SECTION _glthread_Mutex; +static INLINE pipe_thread pipe_thread_create( void *(WINAPI * routine)( void *), void *param ) +{ + DWORD id; + return CreateThread( NULL, 0, (LPTHREAD_START_ROUTINE) routine, param, 0, &id ); +} -#define _glthread_DECLARE_STATIC_MUTEX(name) /*static*/ _glthread_Mutex name = {0,0,0,0,0,0} -#define _glthread_INIT_MUTEX(name) InitializeCriticalSection(&name) -#define _glthread_DESTROY_MUTEX(name) DeleteCriticalSection(&name) -#define _glthread_LOCK_MUTEX(name) EnterCriticalSection(&name) -#define _glthread_UNLOCK_MUTEX(name) LeaveCriticalSection(&name) +static INLINE int pipe_thread_wait( pipe_thread thread ) +{ + if (WaitForSingleObject( thread, INFINITE ) == WAIT_OBJECT_0) + return 0; + return -1; +} -#endif /* WIN32_THREADS */ +static INLINE int pipe_thread_destroy( pipe_thread thread ) +{ + if (CloseHandle( thread )) + return 0; + return -1; +} +typedef CRITICAL_SECTION pipe_mutex; +#define pipe_static_mutex(name) \ + /*static*/ pipe_mutex name = {0,0,0,0,0,0} +#define pipe_mutex_init(name) \ + InitializeCriticalSection(&name) -/* - * XFree86 has its own thread wrapper, Xthreads.h - * We wrap it again for GL. - */ -#ifdef USE_XTHREADS -#include <X11/Xthreads.h> +#define pipe_mutex_destroy(name) \ + DeleteCriticalSection(&name) -typedef struct { - xthread_key_t key; - int initMagic; -} _glthread_TSD; - -typedef xthread_t _glthread_Thread; - -typedef xmutex_rec _glthread_Mutex; - -#ifdef XMUTEX_INITIALIZER -#define _glthread_DECLARE_STATIC_MUTEX(name) \ - static _glthread_Mutex name = XMUTEX_INITIALIZER -#else -#define _glthread_DECLARE_STATIC_MUTEX(name) \ - static _glthread_Mutex name -#endif - -#define _glthread_INIT_MUTEX(name) \ - xmutex_init(&(name)) - -#define _glthread_DESTROY_MUTEX(name) \ - xmutex_clear(&(name)) - -#define _glthread_LOCK_MUTEX(name) \ - (void) xmutex_lock(&(name)) - -#define _glthread_UNLOCK_MUTEX(name) \ - (void) xmutex_unlock(&(name)) - -#endif /* USE_XTHREADS */ - - - -/* - * BeOS threads. R5.x required. - */ -#ifdef BEOS_THREADS - -#include <kernel/OS.h> -#include <support/TLS.h> - -typedef struct { - int32 key; - int initMagic; -} _glthread_TSD; - -typedef thread_id _glthread_Thread; - -/* Use Benaphore, aka speeder semaphore */ -typedef struct { - int32 lock; - sem_id sem; -} benaphore; -typedef benaphore _glthread_Mutex; - -#define _glthread_DECLARE_STATIC_MUTEX(name) static _glthread_Mutex name = { 0, 0 } -#define _glthread_INIT_MUTEX(name) name.sem = create_sem(0, #name"_benaphore"), name.lock = 0 -#define _glthread_DESTROY_MUTEX(name) delete_sem(name.sem), name.lock = 0 -#define _glthread_LOCK_MUTEX(name) if (name.sem == 0) _glthread_INIT_MUTEX(name); \ - if (atomic_add(&(name.lock), 1) >= 1) acquire_sem(name.sem) -#define _glthread_UNLOCK_MUTEX(name) if (atomic_add(&(name.lock), -1) > 1) release_sem(name.sem) +#define pipe_mutex_lock(name) \ + EnterCriticalSection(&name) -#endif /* BEOS_THREADS */ +#define pipe_mutex_unlock(name) \ + LeaveCriticalSection(&name) +/* XXX: dummy definitions, make it compile */ +typedef unsigned pipe_condvar; -#ifndef THREADS +#define pipe_condvar_init(condvar) \ + (void) condvar -/* - * THREADS not defined - */ +#define pipe_condvar_broadcast(condvar) \ + (void) condvar -typedef unsigned _glthread_TSD; +#else -typedef unsigned _glthread_Thread; +/** Dummy definitions */ -typedef unsigned _glthread_Mutex; +typedef unsigned pipe_thread; +typedef unsigned pipe_mutex; +typedef unsigned pipe_condvar; -#define _glthread_DECLARE_STATIC_MUTEX(name) static _glthread_Mutex name = 0 +#define pipe_static_mutex(mutex) \ + static pipe_mutex mutex = 0 -#define _glthread_INIT_MUTEX(name) (void) name +#define pipe_mutex_init(mutex) \ + (void) mutex -#define _glthread_DESTROY_MUTEX(name) (void) name +#define pipe_mutex_destroy(mutex) \ + (void) mutex -#define _glthread_LOCK_MUTEX(name) (void) name +#define pipe_mutex_lock(mutex) \ + (void) mutex -#define _glthread_UNLOCK_MUTEX(name) (void) name +#define pipe_mutex_unlock(mutex) \ + (void) mutex -typedef unsigned _glthread_Cond; +#define pipe_static_condvar(condvar) \ + static unsigned condvar = 0 -#define _glthread_DECLARE_STATIC_COND(name) static _glthread_Cond name = 0 +#define pipe_condvar_init(condvar) \ + (void) condvar -#define _glthread_INIT_COND(name) (void) name +#define pipe_condvar_destroy(condvar) \ + (void) condvar -#define _glthread_DESTROY_COND(name) (void) name +#define pipe_condvar_wait(condvar, mutex) \ + (void) condvar -#define _glthread_COND_WAIT(name, mutex) (void) name +#define pipe_condvar_signal(condvar) \ + (void) condvar -#define _glthread_COND_SIGNAL(name) (void) name +#define pipe_condvar_broadcast(condvar) \ + (void) condvar -#define _glthread_COND_BROADCAST(name) (void) name -#endif /* THREADS */ +#endif /* PIPE_OS_? */ /* - * Platform independent thread specific data API. + * Thread-specific data. */ -extern unsigned long -_glthread_GetID(void); - - -extern void -_glthread_InitTSD(_glthread_TSD *); +typedef struct { +#if defined(PIPE_OS_LINUX) + pthread_key_t key; +#elif defined(PIPE_SUBSYSTEM_WINDOWS_USER) + DWORD key; +#endif + int initMagic; +} pipe_tsd; -extern void * -_glthread_GetTSD(_glthread_TSD *); +#define PIPE_TSD_INIT_MAGIC 0xff8adc98 -extern void -_glthread_SetTSD(_glthread_TSD *, void *); +static INLINE void +pipe_tsd_init(pipe_tsd *tsd) +{ +#if defined(PIPE_OS_LINUX) + if (pthread_key_create(&tsd->key, NULL/*free*/) != 0) { + perror("pthread_key_create(): failed to allocate key for thread specific data"); + exit(-1); + } +#elif defined(PIPE_SUBSYSTEM_WINDOWS_USER) + assert(0); +#endif + tsd->initMagic = PIPE_TSD_INIT_MAGIC; +} + +static INLINE void * +pipe_tsd_get(pipe_tsd *tsd) +{ + if (tsd->initMagic != (int) PIPE_TSD_INIT_MAGIC) { + pipe_tsd_init(tsd); + } +#if defined(PIPE_OS_LINUX) + return pthread_getspecific(tsd->key); +#elif defined(PIPE_SUBSYSTEM_WINDOWS_USER) + assert(0); + return NULL; +#else + assert(0); + return NULL; +#endif +} + +static INLINE void +pipe_tsd_set(pipe_tsd *tsd, void *value) +{ + if (tsd->initMagic != (int) PIPE_TSD_INIT_MAGIC) { + pipe_tsd_init(tsd); + } +#if defined(PIPE_OS_LINUX) + if (pthread_setspecific(tsd->key, value) != 0) { + perror("pthread_set_specific() failed"); + exit(-1); + } +#elif defined(PIPE_SUBSYSTEM_WINDOWS_USER) + assert(0); +#else + assert(0); +#endif +} -#endif /* _P_THREAD_H_ */ +#endif /* _P_THREAD2_H_ */ |