(file) Return to Threads.h CVS log (file) (dir) Up to [Pegasus] / pegasus / src / Pegasus / Common

  1 mike  1.2 //%2006////////////////////////////////////////////////////////////////////////
  2           //
  3           // Copyright (c) 2000, 2001, 2002 BMC Software; Hewlett-Packard Development
  4           // Company, L.P.; IBM Corp.; The Open Group; Tivoli Systems.
  5           // Copyright (c) 2003 BMC Software; Hewlett-Packard Development Company, L.P.;
  6           // IBM Corp.; EMC Corporation, The Open Group.
  7           // Copyright (c) 2004 BMC Software; Hewlett-Packard Development Company, L.P.;
  8           // IBM Corp.; EMC Corporation; VERITAS Software Corporation; The Open Group.
  9           // Copyright (c) 2005 Hewlett-Packard Development Company, L.P.; IBM Corp.;
 10           // EMC Corporation; VERITAS Software Corporation; The Open Group.
 11           // Copyright (c) 2006 Hewlett-Packard Development Company, L.P.; IBM Corp.;
 12           // EMC Corporation; Symantec Corporation; The Open Group.
 13           //
 14           // Permission is hereby granted, free of charge, to any person obtaining a copy
 15           // of this software and associated documentation files (the "Software"), to
 16           // deal in the Software without restriction, including without limitation the
 17           // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
 18           // sell copies of the Software, and to permit persons to whom the Software is
 19           // furnished to do so, subject to the following conditions:
 20           // 
 21           // THE ABOVE COPYRIGHT NOTICE AND THIS PERMISSION NOTICE SHALL BE INCLUDED IN
 22 mike  1.2 // ALL COPIES OR SUBSTANTIAL PORTIONS OF THE SOFTWARE. THE SOFTWARE IS PROVIDED
 23           // "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT
 24           // LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
 25           // PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
 26           // HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
 27           // ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
 28           // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 29           //
 30           //==============================================================================
 31           //
 32           // Author: Mike Brasher (m.brasher@inovadevelopment.com)
 33           //
 34           //%/////////////////////////////////////////////////////////////////////////////
 35           
 36           #ifndef Pegasus_Threads_h
 37           #define Pegasus_Threads_h
 38           
 39           #include <cstring>
 40 mike  1.5 #include <cstdio>
 41           #include <cstring>
 42 mike  1.2 #include <Pegasus/Common/Config.h>
 43           #include <Pegasus/Common/Linkage.h>
 44           
 45           // ATTN: can we consolidate these someplace?
 46           
 47           #if defined(PEGASUS_HAVE_PTHREADS)
 48           # if defined(PEGASUS_PLATFORM_OS400_ISERIES_IBM)
 49           # define _MULTI_THREADED // Is this really necessary?
 50           # endif
 51           # include <pthread.h>
 52           # include <errno.h>
 53           # include <sys/time.h>
 54           #elif defined(PEGASUS_HAVE_WINDOWS_THREADS)
 55           # include <windows.h>
 56           # include <process.h>
 57           #else
 58           # error "<Pegasus/Common/Threads.h>: not implemented"
 59           #endif
 60           
 61           PEGASUS_NAMESPACE_BEGIN
 62           
 63 mike  1.2 //==============================================================================
 64           //
 65           // PEGASUS_THREAD_CDECL
 66           //
 67           //==============================================================================
 68           
 69           #if defined(PEGASUS_PLATFORM_WIN32_IX86_MSVC)
 70           # define PEGASUS_THREAD_CDECL __stdcall
 71           #else
 72           # define PEGASUS_THREAD_CDECL /* empty */
 73           #endif
 74           
 75           //==============================================================================
 76           //
 77 mike  1.4 // ThreadId
 78           //
 79           //==============================================================================
 80           
 81           struct ThreadId
 82           {
 83               // The character representation of a uint64 requires 22 bytes including the 
 84               // null terminator.
 85               char buffer[22];
 86           };
 87           
 88           //==============================================================================
 89           //
 90 mike  1.2 // ThreadType
 91           //
 92           //==============================================================================
 93           
 94           #if defined(PEGASUS_HAVE_PTHREADS)
 95           struct ThreadType
 96           {
 97               ThreadType()
 98               {
 99 mike  1.3         memset(&thread, 0, sizeof(thread));
100 mike  1.2     }
101           
102 mike  1.3     ThreadType(pthread_t thread_) : thread(thread_)
103 mike  1.2     {
104               }
105           
106 mike  1.3     pthread_t thread;
107           };
108 mike  1.2 #endif /* PEGASUS_HAVE_PTHREADS */
109           
110           #if defined(PEGASUS_HAVE_WINDOWS_THREADS)
111           struct ThreadType
112           {
113 mike  1.3     ThreadType() : handle(NULL) 
114               { 
115               }
116           
117 mike  1.2     HANDLE handle;
118           };
119           #endif /* PEGASUS_HAVE_WINDOWS_THREADS */
120           
121           //==============================================================================
122           //
123           // ThreadReturnType
124           //
125           //==============================================================================
126           
127           #if defined(PEGASUS_HAVE_PTHREADS)
128           typedef void* ThreadReturnType;
129           #endif
130           
131           #if defined(PEGASUS_HAVE_WINDOWS_THREADS)
132           typedef unsigned ThreadReturnType;
133           #endif
134           
135           //==============================================================================
136           //
137           // ThreadHandle
138 mike  1.2 //
139           //==============================================================================
140           
141           #if defined(PEGASUS_HAVE_PTHREADS)
142           struct ThreadHandle
143           {
144               ThreadType thid;
145           };
146           #elif defined(PEGASUS_HAVE_WINDOWS_THREADS)
147           struct ThreadHandle
148           {
149               ThreadType thid;
150           };
151           #endif
152           
153           //==============================================================================
154           //
155           // Threads
156           //
157           //==============================================================================
158           
159 mike  1.2 class PEGASUS_COMMON_LINKAGE Threads
160           {
161           public:
162           
163               enum Type { DETACHED, JOINABLE };
164           
165               static int create(
166                   ThreadType& thread, 
167                   Type type,
168                   void* (*start)(void*), 
169                   void* arg);
170           
171               static ThreadType self();
172           
173               static bool equal(ThreadType x, ThreadType y);
174           
175               static void exit(ThreadReturnType rc);
176           
177               static void cancel(ThreadType th, ThreadReturnType rc);
178           
179               static void yield();
180 mike  1.2 
181               static void sleep(int msec);
182           
183               static void cleanup_push(void (*start)(void*), void* arg);
184           
185               static void cleanup_pop(int execute);
186           
187 mike  1.3     static ThreadId id(const ThreadType& x = Threads::self());
188           
189               static bool null(const ThreadType& x = Threads::self());
190 mike  1.2 
191               static void clear(ThreadType& x);
192           };
193           
194           //==============================================================================
195           //
196           // POSIX Threads Implementation
197           //
198           //==============================================================================
199           
200           #if defined(PEGASUS_HAVE_PTHREADS)
201           
202           inline bool Threads::equal(ThreadType x, ThreadType y) 
203           { 
204 mike  1.3     return pthread_equal(x.thread, y.thread);
205 mike  1.2 }
206           
207           inline void Threads::exit(ThreadReturnType rc)
208           {
209               pthread_exit(rc);
210           }
211           
212           inline void Threads::cancel(ThreadType th, ThreadReturnType rc)
213           {
214 mike  1.3     pthread_cancel(th.thread);
215 mike  1.2 }
216           
217           inline void Threads::yield()
218           {
219           #if defined(PEGASUS_PLATFORM_AIX_RS_IBMCXX) || \
220               defined(PEGASUS_PLATFORM_HPUX_ACC) || \
221               defined(PEGASUS_PLATFORM_OS400_ISERIES_IBM) || \
222               defined(PEGASUS_PLATFORM_TRU64_ALPHA_DECCXX) || \
223               defined(PEGASUS_OS_VMS) || \
224               defined(PEGASUS_OS_ZOS)
225               sched_yield();
226           #else
227               pthread_yield();
228           #endif
229           }
230           
231           inline void Threads::cleanup_push(void (*func)(void*), void* arg)
232           {
233               // ATTN: it is doubtful whether cleanup handlers ever really worked.
234               //       They are only used in two places and not used in many other
235               //       places where mutexes are obtained. Further, they are only
236 mike  1.2     //       implemented correctly on one or two platforms. For now, we
237               //       will defer their implementation until we can find a way to
238               //       implement them on all platforms (using thread local storage).
239           }
240           
241           inline void Threads::cleanup_pop(int execute)
242           {
243               // ATTN: not implemented.
244           }
245           
246 mike  1.3 inline ThreadId Threads::id(const ThreadType& x)
247 mike  1.2 {
248 mike  1.3     ThreadId tid;
249           
250           #if defined(PEGASUS_PLATFORM_ZOS_ZSERIES_IBM)
251               const char* s = x.thread.__;
252               sprintf(tid.buffer, "%X%X%X%X%X%X%X%X", 
253                   s[0], s[1], s[2], s[3], s[4], s[5], s[6], s[7]);
254           #else
255               sprintf(tid.buffer, "%" PEGASUS_64BIT_CONVERSION_WIDTH "u", 
256 mike  1.6         Uint64(x.thread));
257 mike  1.3 #endif
258           
259               return tid;
260           }
261           
262           inline bool Threads::null(const ThreadType& x)
263           {
264           #if defined(PEGASUS_PLATFORM_ZOS_ZSERIES_IBM)
265               Uint64 tmp;
266 marek 1.7     memcpy(&tmp, x.thread.__, sizeof(Uint64));
267 mike  1.3     return tmp == 0;
268           #else
269               return x.thread == 0;
270           #endif
271 mike  1.2 }
272           
273           inline void Threads::clear(ThreadType& x)
274           {
275               memset(&x, 0, sizeof(x));
276           }
277           
278           #endif /* defined(PEGASUS_HAVE_PTHREADS) */
279           
280           //==============================================================================
281           //
282           // Windows Threads Implementation
283           //
284           //==============================================================================
285           
286           #if defined(PEGASUS_HAVE_WINDOWS_THREADS)
287           
288           inline ThreadType Threads::self() 
289           {
290               ThreadType tt;
291 mike  1.5     tt.handle = GetCurrentThread();
292 mike  1.2     return tt;
293           }
294           
295           inline bool Threads::equal(ThreadType x, ThreadType y) 
296           {
297               return x.handle == y.handle;
298           }
299           
300           inline void Threads::exit(ThreadReturnType rc)
301           {
302               _endthreadex(rc);
303           }
304           
305           inline void Threads::cancel(ThreadType th, ThreadReturnType rc)
306           {
307               TerminateThread(th.handle, rc);
308           }
309           
310           inline void Threads::yield()
311           {
312               Sleep(0);
313 mike  1.2 }
314           
315           inline void Threads::cleanup_push(void (*func)(void*), void* arg)
316           {
317               // ATTN: Not implemented on Windows.
318           }
319           
320           inline void Threads::cleanup_pop(int execute)
321           {
322               // ATTN: Not implemented on Windows.
323           }
324           
325 mike  1.3 inline ThreadId Threads::id(const ThreadType& x)
326           {
327               ThreadId tmp;
328           
329               sprintf(tmp.buffer, "%" PEGASUS_64BIT_CONVERSION_WIDTH "u", 
330 mike  1.5         Uint64(x.handle));
331 mike  1.3 
332               return tmp;
333           }
334           
335           inline bool Threads::null(const ThreadType& x)
336 mike  1.2 {
337 mike  1.3     return x.handle == NULL;
338 mike  1.2 }
339           
340           inline void Threads::clear(ThreadType& x)
341           {
342               x.handle = NULL;
343           }
344           
345           #endif /* defined(PEGASUS_HAVE_WINDOWS_THREADS) */
346           
347           PEGASUS_NAMESPACE_END
348           
349           #endif /* Pegasus_Threads_h */

No CVS admin address has been configured
Powered by
ViewCVS 0.9.2