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

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

No CVS admin address has been configured
Powered by
ViewCVS 0.9.2