source: trunk/include/sh_pthread.h@ 318

Last change on this file since 318 was 315, checked in by katerina, 14 years ago

Fix for ticket #236 (blocking on NFS mounts).

File size: 6.0 KB
RevLine 
[130]1#ifndef SH_PTHREAD_H
2#define SH_PTHREAD_H
3
4#ifdef HAVE_PTHREAD
5
6#include <pthread.h>
[138]7
[130]8#define SH_MUTEX(M) pthread_mutex_t M
9#define SH_MUTEX_INIT(M,I) pthread_mutex_t M = I
10#define SH_MUTEX_STATIC(M,I) static pthread_mutex_t M = I
11#define SH_MUTEX_EXTERN(M) extern pthread_mutex_t M
12
[315]13#define SH_SETSIGMASK(A, B, C) sh_pthread_setsigmask(A,B,C)
14
15int sh_pthread_setsigmask(int how, const void *set, void *oldset);
16
[138]17/* pthread_mutex_unlock() has the wrong type (returns int), so
18 * we need to wrap it in this function.
19 */
20extern void sh_pthread_mutex_unlock (void *arg);
21
[130]22#define SH_MUTEX_LOCK(M) \
23 do { \
24 int oldtype; \
25 pthread_setcanceltype(PTHREAD_CANCEL_DEFERRED, &oldtype); \
[138]26 pthread_cleanup_push(sh_pthread_mutex_unlock, (void*)&(M));\
[130]27 pthread_mutex_lock(&(M))
28
29
[138]30#define SH_MUTEX_UNLOCK(M) \
[130]31 pthread_cleanup_pop(1); \
32 pthread_setcanceltype(oldtype, NULL); \
33 } while (0)
34
[132]35#define SH_MUTEX_LOCK_UNSAFE(M) pthread_mutex_lock(&(M))
[214]36#define SH_MUTEX_TRYLOCK_UNSAFE(M) pthread_mutex_trylock(&(M))
[132]37#define SH_MUTEX_UNLOCK_UNSAFE(M) pthread_mutex_unlock(&(M))
[130]38
[138]39
40/*
41 * ---- Recursive mutex ----
42 */
[139]43#if defined(HAVE_PTHREAD_MUTEX_RECURSIVE)
[138]44
45#define SH_MUTEX_RECURSIVE(M) \
46static pthread_mutex_t M; \
47static void M ## _init (void) \
48{ \
49 pthread_mutexattr_t mta; \
[143]50 pthread_mutexattr_init(&mta); \
[138]51 pthread_mutexattr_settype(&mta, PTHREAD_MUTEX_RECURSIVE); \
52 pthread_mutex_init(&(M), &mta); \
53 pthread_mutexattr_destroy(&mta); \
54 return; \
55} \
56static pthread_once_t M ## _initialized = PTHREAD_ONCE_INIT
57
58#define SH_MUTEX_RECURSIVE_INIT(M) \
59(void) pthread_once(&(M ## _initialized), (M ## _init))
60
61#define SH_MUTEX_RECURSIVE_LOCK(M) \
62 do { \
63 int oldtype; \
64 pthread_setcanceltype(PTHREAD_CANCEL_DEFERRED, &oldtype); \
65 pthread_cleanup_push(sh_pthread_mutex_unlock, (void*)&(M));\
66 pthread_mutex_lock(&(M))
67
68#define SH_MUTEX_RECURSIVE_UNLOCK(M) \
69 pthread_cleanup_pop(1); \
70 pthread_setcanceltype(oldtype, NULL); \
71 } while (0)
72
73#else
74/* !defined(PTHREAD_MUTEX_RECURSIVE) */
75 struct sh_RMutex {
76
77 pthread_mutex_t lock;
78 unsigned int held;
79 unsigned int waiters;
80 pthread_t tid;
81 pthread_cond_t cv;
82};
83
84void sh_RMutexLock(struct sh_RMutex * tok);
85void sh_RMutexUnlock(void * arg);
86void sh_InitRMutex(struct sh_RMutex * tok);
87
88#define SH_MUTEX_RECURSIVE(M) \
89static struct sh_RMutex M; \
90static void M ## _init (void) \
91{ \
92 sh_InitRMutex(&(M)); \
93 return; \
94} \
95static pthread_once_t M ## _initialized = PTHREAD_ONCE_INIT
96
97#define SH_MUTEX_RECURSIVE_INIT(M) \
98(void) pthread_once(&(M ## _initialized), (M ## _init))
99
100#define SH_MUTEX_RECURSIVE_LOCK(M) \
101 do { \
102 int oldtype; \
103 pthread_setcanceltype(PTHREAD_CANCEL_DEFERRED, &oldtype); \
104 pthread_cleanup_push(sh_RMutexUnlock, (void*)&(M)); \
105 sh_RMutexLock(&(M))
106
107#define SH_MUTEX_RECURSIVE_UNLOCK(M) \
108 pthread_cleanup_pop(1); \
109 pthread_setcanceltype(oldtype, NULL); \
110 } while (0)
111
112#endif
[133]113/*
114 * ---- Global mutexes ----
115 */
116SH_MUTEX_EXTERN(mutex_skey);
[134]117SH_MUTEX_EXTERN(mutex_resolv);
118SH_MUTEX_EXTERN(mutex_pwent);
[138]119SH_MUTEX_EXTERN(mutex_readdir);
[143]120/* Prevent threads from logging while we are in suspend */
121SH_MUTEX_EXTERN(mutex_thread_nolog);
[133]122
[134]123/*
124 * ---- Initialize thread-specific conversion area ----
125 */
[170]126extern int sh_g_thread(void);
[134]127
[143]128
129/*
130 * ---- Functions for threaded modules ----
131 */
132int sh_pthread_create(void *(*start_routine)(void*), void *arg);
133int sh_pthread_cancel_all(void);
134void sh_threaded_module_reconf(void *arg);
135void * sh_threaded_module_run(void *arg);
136
[130]137#else
138
[315]139#define SH_SETSIGMASK(A, B, C) sh_pthread_setsigmask(A,B,C)
140
141int sh_pthread_setsigmask(int how, const void *set, void *oldset);
142
[140]143#define PTHREAD_MUTEX_INITIALIZER NULL
[130]144#define SH_MUTEX(M) void *SH_MUTEX_DUMMY_ ## M
145#define SH_MUTEX_INIT(M,I) extern void *SH_MUTEX_DUMMY_ ## M
146#define SH_MUTEX_STATIC(M,I) extern void *SH_MUTEX_DUMMY_ ## M
147#define SH_MUTEX_EXTERN(M) extern void *SH_MUTEX_DUMMY_ ## M
148#define SH_MUTEX_LOCK(M) ((void)0)
149#define SH_MUTEX_UNLOCK(M) ((void)0)
[132]150#define SH_MUTEX_LOCK_UNSAFE(M) ((void)0)
[214]151#define SH_MUTEX_TRYLOCK_UNSAFE(M) (0)
[132]152#define SH_MUTEX_UNLOCK_UNSAFE(M) ((void)0)
[130]153
[138]154#define SH_MUTEX_RECURSIVE(M) extern void *SH_MUTEX_DUMMY_ ## M
155#define SH_MUTEX_RECURSIVE_INIT(M) ((void)0)
156#define SH_MUTEX_RECURSIVE_LOCK(M) ((void)0)
157#define SH_MUTEX_RECURSIVE_UNLOCK(M) ((void)0)
158
[130]159/* #ifdef HAVE_PTHREAD */
160#endif
161
162/* #ifndef SH_PTHREAD_H */
163#endif
Note: See TracBrowser for help on using the repository browser.