OS_NS_Thread.h

Go to the documentation of this file.
00001 // -*- C++ -*-
00002 
00003 //=============================================================================
00004 /**
00005  *  @file   OS_NS_Thread.h
00006  *
00007  *  $Id: OS_NS_Thread.h 79637 2007-09-13 15:39:21Z wilsond $
00008  *
00009  *  @author Douglas C. Schmidt <schmidt@cs.wustl.edu>
00010  *  @author Jesper S. M|ller<stophph@diku.dk>
00011  *  @author and a cast of thousands...
00012  *
00013  *  Originally in OS.h.
00014  */
00015 //=============================================================================
00016 
00017 #ifndef ACE_OS_NS_THREAD_H
00018 # define ACE_OS_NS_THREAD_H
00019 
00020 # include /**/ "ace/pre.h"
00021 
00022 # include "ace/config-all.h"
00023 
00024 # if !defined (ACE_LACKS_PRAGMA_ONCE)
00025 #  pragma once
00026 # endif /* ACE_LACKS_PRAGMA_ONCE */
00027 
00028 # include "ace/Global_Macros.h"
00029 # include "ace/Basic_Types.h"
00030 # include "ace/Default_Constants.h"
00031 # include "ace/os_include/os_pthread.h"
00032 # include "ace/os_include/os_sched.h"
00033 # include "ace/Base_Thread_Adapter.h"
00034 # include "ace/os_include/sys/os_sem.h"
00035 # include "ace/os_include/os_semaphore.h"
00036 # include "ace/OS_Memory.h"
00037 # include "ace/OS_NS_signal.h"
00038 # include "ace/ACE_export.h"
00039 # include "ace/Object_Manager_Base.h"
00040 
00041 # if defined (ACE_EXPORT_MACRO)
00042 #   undef ACE_EXPORT_MACRO
00043 # endif
00044 # define ACE_EXPORT_MACRO ACE_Export
00045 
00046 # if defined (ACE_HAS_PRIOCNTL)
00047   // Need to #include thread.h before #defining THR_BOUND, etc.,
00048   // when building without threads on SunOS 5.x.
00049 #   if defined (sun)
00050 #     include /**/ <thread.h>
00051 #   endif /* sun */
00052 
00053   // Need to #include these before #defining USYNC_PROCESS on SunOS 5.x.
00054 #   include /**/ <sys/rtpriocntl.h>
00055 #   include /**/ <sys/tspriocntl.h>
00056 # endif /* ACE_HAS_PRIOCNTL */
00057 
00058 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00059 
00060 # if defined (ACE_WIN32)
00061 typedef DWORD ACE_thread_t;
00062 typedef HANDLE ACE_hthread_t;
00063 // Native TSS key type
00064 typedef DWORD ACE_OS_thread_key_t;
00065 // Application TSS key type (use this type except in TSS Emulation)
00066 #   if defined (ACE_HAS_TSS_EMULATION)
00067       typedef u_int ACE_thread_key_t;
00068 #   else  /* ! ACE_HAS_TSS_EMULATION */
00069       typedef ACE_OS_thread_key_t ACE_thread_key_t;
00070 #   endif /* ! ACE_HAS_TSS_EMULATION */
00071 # endif /* ACE_WIN32 */
00072 
00073 ACE_END_VERSIONED_NAMESPACE_DECL
00074 
00075 # if !defined (ACE_HAS_POSIX_SEM) && defined (ACE_USES_FIFO_SEM)
00076 
00077 extern "C" {
00078   typedef struct
00079   {
00080     char* name_;
00081     ACE_HANDLE fd_[2];
00082   } ACE_sema_t;
00083 }
00084 
00085 #endif /* !ACE_HAS_POSIX_SEM && ACE_USES_FIFO_SEM */
00086 
00087 # if defined (ACE_HAS_THREADS)
00088 
00089 #   if defined (ACE_HAS_STHREADS)
00090 #     include /**/ <synch.h>
00091 #     include /**/ <thread.h>
00092 #     define ACE_SCOPE_PROCESS P_PID
00093 #     define ACE_SCOPE_LWP P_LWPID
00094 #     define ACE_SCOPE_THREAD (ACE_SCOPE_LWP + 1)
00095 #   else
00096 #     define ACE_SCOPE_PROCESS 0
00097 #     define ACE_SCOPE_LWP 1
00098 #     define ACE_SCOPE_THREAD 2
00099 #   endif /* ACE_HAS_STHREADS */
00100 
00101 #   if !defined (ACE_HAS_PTHREADS)
00102 #     define ACE_SCHED_OTHER 0
00103 #     define ACE_SCHED_FIFO 1
00104 #     define ACE_SCHED_RR 2
00105 #   endif /* ! ACE_HAS_PTHREADS */
00106 
00107 #   if defined (ACE_HAS_PTHREADS)
00108 // moved to pthread.h
00109 #   elif defined (ACE_HAS_STHREADS)
00110 
00111 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00112 
00113 // Solaris threads, without PTHREADS.
00114 // Typedefs to help compatibility with Windows NT and Pthreads.
00115 typedef thread_t ACE_thread_t;
00116 // Native TSS key type (not for general use)
00117 typedef thread_key_t ACE_OS_thread_key_t;
00118 // Application TSS key type (use this type except in TSS Emulation)
00119 #   if defined (ACE_HAS_TSS_EMULATION)
00120       typedef u_int ACE_thread_key_t;
00121 #   else  /* ! ACE_HAS_TSS_EMULATION */
00122       typedef ACE_OS_thread_key_t ACE_thread_key_t;
00123 #   endif /* ! ACE_HAS_TSS_EMULATION */
00124 typedef mutex_t ACE_mutex_t;
00125 #     if !defined (ACE_LACKS_RWLOCK_T)
00126 typedef rwlock_t ACE_rwlock_t;
00127 #     endif /* !ACE_LACKS_RWLOCK_T */
00128 #     if !defined (ACE_HAS_POSIX_SEM) && !defined (ACE_USES_FIFO_SEM)
00129 typedef sema_t ACE_sema_t;
00130 #     endif /* !ACE_HAS_POSIX_SEM */
00131 
00132 typedef cond_t ACE_cond_t;
00133 struct ACE_Export ACE_condattr_t
00134 {
00135   int type;
00136 };
00137 struct ACE_Export ACE_mutexattr_t
00138 {
00139   int type;
00140 };
00141 typedef ACE_thread_t ACE_hthread_t;
00142 typedef ACE_mutex_t ACE_thread_mutex_t;
00143 
00144 ACE_END_VERSIONED_NAMESPACE_DECL
00145 
00146 #     define THR_CANCEL_DISABLE      0
00147 #     define THR_CANCEL_ENABLE       0
00148 #     define THR_CANCEL_DEFERRED     0
00149 #     define THR_CANCEL_ASYNCHRONOUS 0
00150 #     define THR_JOINABLE            0
00151 #     define THR_SCHED_FIFO          0
00152 #     define THR_SCHED_RR            0
00153 #     define THR_SCHED_DEFAULT       0
00154 #     define THR_INHERIT_SCHED       0
00155 #     define THR_SCOPE_PROCESS       0
00156 
00157 #   elif defined (ACE_VXWORKS)
00158 #     include /**/ <sysLib.h> // for sysClkRateGet()
00159 #     if !defined (__RTP__)
00160 #       include /**/ <taskLib.h>
00161 #       include /**/ <taskHookLib.h>
00162 #     endif
00163 
00164 // make sure these are included for VXWORKS.
00165 // @todo move these to a common place, perhaps the top of the file.
00166 #     include "ace/os_include/os_fcntl.h"
00167 #     include "ace/os_include/os_netdb.h"
00168 #     include "ace/os_include/os_semaphore.h"
00169 #     include "ace/os_include/os_signal.h"
00170 #     include "ace/os_include/os_stdio.h"
00171 #     include "ace/os_include/os_stdlib.h"
00172 #     include "ace/os_include/os_stropts.h"
00173 #     include "ace/os_include/os_unistd.h"
00174 #     include "ace/os_include/arpa/os_inet.h"
00175 #     include "ace/os_include/sys/os_select.h"
00176 #     include "ace/os_include/sys/os_socket.h"
00177 
00178 // task options:  the other options are either obsolete, internal, or for
00179 // Fortran or Ada support
00180 #     define VX_UNBREAKABLE        0x0002  /* breakpoints ignored */
00181 #     if !defined (VX_FP_TASK)
00182 #       define VX_FP_TASK            0x0008  /* floating point coprocessor */
00183 #     endif
00184 #     define VX_PRIVATE_ENV        0x0080  /* private environment support */
00185 #     define VX_NO_STACK_FILL      0x0100  /* do not stack fill for
00186                                               checkstack () */
00187 
00188 #     define THR_CANCEL_DISABLE      0
00189 #     define THR_CANCEL_ENABLE       0
00190 #     define THR_CANCEL_DEFERRED     0
00191 #     define THR_CANCEL_ASYNCHRONOUS 0
00192 #     define THR_BOUND               0
00193 #     define THR_NEW_LWP             0
00194 #     define THR_DETACHED            0
00195 #     define THR_SUSPENDED           0
00196 #     define THR_DAEMON              0
00197 #     define THR_JOINABLE            0
00198 #     define THR_SCHED_FIFO          0
00199 #     define THR_SCHED_RR            0
00200 #     define THR_SCHED_DEFAULT       0
00201 #     define THR_INHERIT_SCHED       0
00202 #     define THR_EXPLICIT_SCHED      0
00203 #     define THR_SCHED_IO            0
00204 #     define THR_SCOPE_SYSTEM        0
00205 #     define THR_SCOPE_PROCESS       0
00206 #     define USYNC_THREAD            0
00207 #     define USYNC_PROCESS           1 /* It's all global on VxWorks
00208                                           (without MMU option). */
00209 
00210 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00211 
00212 typedef SEM_ID ACE_mutex_t;
00213 // Implement ACE_thread_mutex_t with ACE_mutex_t because there's just
00214 // one process . . .
00215 typedef ACE_mutex_t ACE_thread_mutex_t;
00216 #     if !defined (ACE_HAS_POSIX_SEM)
00217 // Use VxWorks semaphores, wrapped ...
00218 typedef struct
00219 {
00220   /// Semaphore handle.  This is allocated by VxWorks.
00221   SEM_ID sema_;
00222 
00223   /// Name of the semaphore:  always NULL with VxWorks.
00224   char *name_;
00225 } ACE_sema_t;
00226 #     endif /* !ACE_HAS_POSIX_SEM */
00227 typedef char * ACE_thread_t;
00228 typedef int ACE_hthread_t;
00229 // Key type: the ACE TSS emulation requires the key type be unsigned,
00230 // for efficiency.  (Current POSIX and Solaris TSS implementations also
00231 // use u_int, so the ACE TSS emulation is compatible with them.)
00232 // Native TSS key type
00233 typedef u_int ACE_OS_thread_key_t;
00234 // Application TSS key type (use this type except in TSS Emulation)
00235 #   if defined (ACE_HAS_TSS_EMULATION)
00236       typedef u_int ACE_thread_key_t;
00237 #   else  /* ! ACE_HAS_TSS_EMULATION */
00238       typedef ACE_OS_thread_key_t ACE_thread_key_t;
00239 #   endif /* ! ACE_HAS_TSS_EMULATION */
00240 
00241 ACE_END_VERSIONED_NAMESPACE_DECL
00242 
00243       // Marker for ACE_Thread_Manager to indicate that it allocated
00244       // an ACE_thread_t.  It is placed at the beginning of the ID.
00245 #     define ACE_THR_ID_ALLOCATED '\022'
00246 
00247 #   elif defined (ACE_HAS_WTHREADS)
00248 
00249 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00250 
00251 typedef CRITICAL_SECTION ACE_thread_mutex_t;
00252 
00253 typedef struct
00254 {
00255   /// Either USYNC_THREAD or USYNC_PROCESS
00256   int type_;
00257   union
00258   {
00259     HANDLE proc_mutex_;
00260     CRITICAL_SECTION thr_mutex_;
00261   };
00262 } ACE_mutex_t;
00263 
00264 // Wrapper for NT Events.
00265 typedef HANDLE ACE_event_t;
00266 
00267 #     if defined (ACE_WIN32)
00268 //@@ ACE_USES_WINCE_SEMA_SIMULATION is used to debug
00269 //   semaphore simulation on WinNT.  It should be
00270 //   changed to ACE_USES_HAS_WINCE at some later point.
00271 #       if !defined (ACE_USES_WINCE_SEMA_SIMULATION)
00272 typedef HANDLE ACE_sema_t;
00273 #       else
00274 /**
00275  * @class ACE_sema_t
00276  *
00277  * @brief Semaphore simulation for Windows CE.
00278  */
00279 class ACE_Export ACE_sema_t
00280 {
00281 public:
00282   /// Serializes access to @c count_.
00283   ACE_thread_mutex_t lock_;
00284 
00285   /// This event is signaled whenever the count becomes non-zero.
00286   ACE_event_t count_nonzero_;
00287 
00288   /// Current count of the semaphore.
00289   u_int count_;
00290 };
00291 
00292 #       endif /* ACE_USES_WINCE_SEMA_SIMULATION */
00293 #     endif /* defined (ACE_WIN32) */
00294 
00295 ACE_END_VERSIONED_NAMESPACE_DECL
00296 
00297 // These need to be different values, neither of which can be 0...
00298 #     define USYNC_THREAD 1
00299 #     define USYNC_PROCESS 2
00300 
00301 #     define THR_CANCEL_DISABLE      0
00302 #     define THR_CANCEL_ENABLE       0
00303 #     define THR_CANCEL_DEFERRED     0
00304 #     define THR_CANCEL_ASYNCHRONOUS 0
00305 #     define THR_DETACHED            0x02000000 /* ignore in most places */
00306 #     define THR_BOUND               0          /* ignore in most places */
00307 #     define THR_NEW_LWP             0          /* ignore in most places */
00308 #     define THR_DAEMON              0          /* ignore in most places */
00309 #     define THR_JOINABLE            0          /* ignore in most places */
00310 #     define THR_SUSPENDED   CREATE_SUSPENDED
00311 #     define THR_USE_AFX             0x01000000
00312 #     define THR_SCHED_FIFO          0
00313 #     define THR_SCHED_RR            0
00314 #     define THR_SCHED_DEFAULT       0
00315 #     define THR_INHERIT_SCHED       0
00316 #     define THR_EXPLICIT_SCHED      0
00317 #     define THR_SCOPE_PROCESS       0
00318 #     define THR_SCOPE_SYSTEM        0
00319 #   endif /* ACE_HAS_PTHREADS / STHREADS / VXWORKS / WTHREADS **********/
00320 
00321 // If we're using PACE then we don't want this class (since PACE
00322 // takes care of it) unless we're on Windows. Win32 mutexes, semaphores,
00323 // and condition variables are not yet supported in PACE.
00324 #   if defined (ACE_LACKS_COND_T)
00325 
00326 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00327 
00328 /**
00329  * @class ACE_cond_t
00330  *
00331  * @brief This structure is used to implement condition variables on
00332  * platforms that lack it natively, such as VxWorks, and Win32.
00333  *
00334  * At the current time, this stuff only works for threads
00335  * within the same process.
00336  */
00337 class ACE_Export ACE_cond_t
00338 {
00339 public:
00340 
00341   /// Returns the number of waiters.
00342   long waiters (void) const;
00343 
00344 //protected:
00345   /// Number of waiting threads.
00346   long waiters_;
00347 
00348   /// Serialize access to the waiters count.
00349   ACE_thread_mutex_t waiters_lock_;
00350 
00351   /// Queue up threads waiting for the condition to become signaled.
00352   ACE_sema_t sema_;
00353 
00354 #     if defined (ACE_VXWORKS)
00355   /**
00356    * A semaphore used by the broadcast/signal thread to wait for all
00357    * the waiting thread(s) to wake up and be released from the
00358    * semaphore.
00359    */
00360   ACE_sema_t waiters_done_;
00361 #     elif defined (ACE_WIN32)
00362   /**
00363    * An auto reset event used by the broadcast/signal thread to wait
00364    * for the waiting thread(s) to wake up and get a chance at the
00365    * semaphore.
00366    */
00367   HANDLE waiters_done_;
00368 #     else
00369 #       error "Please implement this feature or check your config.h file!"
00370 #     endif /* ACE_VXWORKS */
00371 
00372   /// Keeps track of whether we were broadcasting or just signaling.
00373   size_t was_broadcast_;
00374 };
00375 
00376 struct ACE_Export ACE_condattr_t
00377 {
00378   int type;
00379 };
00380 
00381 struct ACE_Export ACE_mutexattr_t
00382 {
00383   int type;
00384 };
00385 
00386 ACE_END_VERSIONED_NAMESPACE_DECL
00387 
00388 #   endif /* ACE_LACKS_COND_T */
00389 
00390 #   if defined (ACE_LACKS_RWLOCK_T) && !defined (ACE_HAS_PTHREADS_UNIX98_EXT)
00391 
00392 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00393 
00394 /**
00395  * @class ACE_rwlock_t
00396  *
00397  * @brief This is used to implement readers/writer locks on NT,
00398  *     VxWorks, and POSIX pthreads.
00399  *
00400  *     At the current time, this stuff only works for threads
00401  *     within the same process.
00402  */
00403 struct ACE_Export ACE_rwlock_t
00404 {
00405 public:
00406 //protected:
00407 
00408   /// Serialize access to internal state.
00409   ACE_mutex_t lock_;
00410 
00411   /// Reader threads waiting to acquire the lock.
00412   ACE_cond_t waiting_readers_;
00413 
00414   /// Number of waiting readers.
00415   int num_waiting_readers_;
00416 
00417   /// Writer threads waiting to acquire the lock.
00418   ACE_cond_t waiting_writers_;
00419 
00420   /// Number of waiting writers.
00421   int num_waiting_writers_;
00422 
00423   /// Value is -1 if writer has the lock, else this keeps track of the
00424   /// number of readers holding the lock.
00425   int ref_count_;
00426 
00427   /// Indicate that a reader is trying to upgrade
00428   int important_writer_;
00429 
00430   /// Condition for the upgrading reader
00431   ACE_cond_t waiting_important_writer_;
00432 };
00433 
00434 ACE_END_VERSIONED_NAMESPACE_DECL
00435 
00436 #   elif defined (ACE_HAS_PTHREADS_UNIX98_EXT)
00437 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00438 typedef pthread_rwlock_t ACE_rwlock_t;
00439 ACE_END_VERSIONED_NAMESPACE_DECL
00440 #   elif defined (ACE_HAS_STHREADS)
00441 #     include /**/ <synch.h>
00442 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00443 typedef rwlock_t ACE_rwlock_t;
00444 ACE_END_VERSIONED_NAMESPACE_DECL
00445 #   endif /* ACE_LACKS_RWLOCK_T */
00446 
00447 // Define some default thread priorities on all threaded platforms, if
00448 // not defined above or in the individual platform config file.
00449 // ACE_THR_PRI_FIFO_DEF should be used by applications for default
00450 // real-time thread priority.  ACE_THR_PRI_OTHER_DEF should be used
00451 // for non-real-time priority.
00452 #   if !defined(ACE_THR_PRI_FIFO_DEF)
00453 #     if defined (ACE_WTHREADS)
00454       // It would be more in spirit to use THREAD_PRIORITY_NORMAL.  But,
00455       // using THREAD_PRIORITY_ABOVE_NORMAL should give preference to the
00456       // threads in this process, even if the process is not in the
00457       // REALTIME_PRIORITY_CLASS.
00458 #       define ACE_THR_PRI_FIFO_DEF THREAD_PRIORITY_ABOVE_NORMAL
00459 #     else  /* ! ACE_WTHREADS */
00460 #       define ACE_THR_PRI_FIFO_DEF 0
00461 #     endif /* ! ACE_WTHREADS */
00462 #   endif /* ! ACE_THR_PRI_FIFO_DEF */
00463 
00464 #   if !defined(ACE_THR_PRI_OTHER_DEF)
00465 #     if defined (ACE_WTHREADS)
00466       // It would be more in spirit to use THREAD_PRIORITY_NORMAL.  But,
00467       // using THREAD_PRIORITY_ABOVE_NORMAL should give preference to the
00468       // threads in this process, even if the process is not in the
00469       // REALTIME_PRIORITY_CLASS.
00470 #       define ACE_THR_PRI_OTHER_DEF THREAD_PRIORITY_NORMAL
00471 #     else  /* ! ACE_WTHREADS */
00472 #       define ACE_THR_PRI_OTHER_DEF 0
00473 #     endif /* ! ACE_WTHREADS */
00474 #   endif /* ! ACE_THR_PRI_OTHER_DEF */
00475 
00476 // Recursive mutex support.
00477 //
00478 // There are two parts to this:
00479 // 1. The mutex type itself. This is based on whether or not the
00480 //    platform supports recursive mutexes natively or they're emulated.
00481 // 2. Support for using the recursive mutex with a condition variable.
00482 //    When a thread waits on a condition variable, it has to relinquish
00483 //    the lock and wait atomically, then reacquire it after the condition
00484 //    variable is signaled. In non-recursive mutexes, the platform
00485 //    handles this automatically. But in recursive mutexes, especially
00486 //    when emulated, the recursion count needs to be maintained across
00487 //    the wait. Since another thread needs to be able to acquire the
00488 //    lock, it needs to appear free, even if the waiting thread had done
00489 //    multiple acquires. Thus, there's another structure to hold this
00490 //    information, and is used with the recursive_mutex_cond_unlock()
00491 //    and recursive_mutex_cond_relock() methods to maintain the expected
00492 //    state when the wait finishes.
00493 #   if defined (ACE_HAS_RECURSIVE_MUTEXES)
00494 
00495 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00496 
00497 typedef ACE_thread_mutex_t ACE_recursive_thread_mutex_t;
00498 #     if defined (ACE_WIN32)
00499 // Windows has recursive mutexes, but doesn't have condition variables,
00500 // so there's no built-in support for this. Thus, the condition-related
00501 // unlock/relock is augmented in ACE.
00502 struct ACE_recursive_mutex_state
00503 {
00504   // On Windows the augmented processing is simply unlocking/relocking
00505   // the recursive locks - the condition handles a single lock ok.
00506   LONG relock_count_;
00507 };
00508 #     else
00509 // No need for special handling; just need a type for method signatures.
00510 typedef int ACE_recursive_mutex_state;
00511 #     endif /* ACE_WIN32 */
00512 
00513 ACE_END_VERSIONED_NAMESPACE_DECL
00514 
00515 #   else
00516 
00517 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00518 
00519 /**
00520  * @class ACE_recursive_thread_mutex_t
00521  *
00522  * @brief Implement a thin C++ wrapper that allows nested acquisition
00523  * and release of a mutex that occurs in the same thread.
00524  *
00525  * This implementation is based on an algorithm sketched by Dave
00526  * Butenhof <butenhof@zko.dec.com>.  Naturally, I take the
00527  * credit for any mistakes ;-)
00528  */
00529 class ACE_recursive_thread_mutex_t
00530 {
00531 public:
00532   /// Guards the state of the nesting level and thread id.
00533   ACE_thread_mutex_t nesting_mutex_;
00534 
00535   /// This condition variable suspends other waiting threads until the
00536   /// mutex is available.
00537   ACE_cond_t lock_available_;
00538 
00539   /// Current nesting level of the recursion.
00540   int nesting_level_;
00541 
00542   /// Current owner of the lock.
00543   ACE_thread_t owner_id_;
00544 };
00545 
00546 // Since recursive mutex is emulated, the state saving needs to be handled
00547 // in ACE as well. These members save those from ACE_recursive_thread_mutex_t.
00548 struct ACE_recursive_mutex_state
00549 {
00550   int nesting_level_;
00551   ACE_thread_t owner_id_;
00552 };
00553 
00554 ACE_END_VERSIONED_NAMESPACE_DECL
00555 
00556 #   endif /* ACE_HAS_RECURSIVE_MUTEXES */
00557 
00558 # else /* !ACE_HAS_THREADS, i.e., the OS/platform doesn't support threading. */
00559 
00560 // Give these things some reasonable value...
00561 #   define ACE_SCOPE_PROCESS 0
00562 #   define ACE_SCOPE_LWP 1
00563 #   define ACE_SCOPE_THREAD 2
00564 #   define ACE_SCHED_OTHER 0
00565 #   define ACE_SCHED_FIFO 1
00566 #   define ACE_SCHED_RR 2
00567 #   if !defined (THR_CANCEL_DISABLE)
00568 #     define THR_CANCEL_DISABLE      0
00569 #   endif /* ! THR_CANCEL_DISABLE */
00570 #   if !defined (THR_CANCEL_ENABLE)
00571 #     define THR_CANCEL_ENABLE       0
00572 #   endif /* ! THR_CANCEL_ENABLE */
00573 #   if !defined (THR_CANCEL_DEFERRED)
00574 #     define THR_CANCEL_DEFERRED     0
00575 #   endif /* ! THR_CANCEL_DEFERRED */
00576 #   if !defined (THR_CANCEL_ASYNCHRONOUS)
00577 #     define THR_CANCEL_ASYNCHRONOUS 0
00578 #   endif /* ! THR_CANCEL_ASYNCHRONOUS */
00579 #   if !defined (THR_JOINABLE)
00580 #     define THR_JOINABLE    0     /* ignore in most places */
00581 #   endif /* ! THR_JOINABLE */
00582 #   if !defined (THR_DETACHED)
00583 #     define THR_DETACHED    0     /* ignore in most places */
00584 #   endif /* ! THR_DETACHED */
00585 #   if !defined (THR_DAEMON)
00586 #     define THR_DAEMON      0     /* ignore in most places */
00587 #   endif /* ! THR_DAEMON */
00588 #   if !defined (THR_BOUND)
00589 #     define THR_BOUND       0     /* ignore in most places */
00590 #   endif /* ! THR_BOUND */
00591 #   if !defined (THR_NEW_LWP)
00592 #     define THR_NEW_LWP     0     /* ignore in most places */
00593 #   endif /* ! THR_NEW_LWP */
00594 #   if !defined (THR_SUSPENDED)
00595 #     define THR_SUSPENDED   0     /* ignore in most places */
00596 #   endif /* ! THR_SUSPENDED */
00597 #   if !defined (THR_SCHED_FIFO)
00598 #     define THR_SCHED_FIFO 0
00599 #   endif /* ! THR_SCHED_FIFO */
00600 #   if !defined (THR_SCHED_RR)
00601 #     define THR_SCHED_RR 0
00602 #   endif /* ! THR_SCHED_RR */
00603 #   if !defined (THR_SCHED_DEFAULT)
00604 #     define THR_SCHED_DEFAULT 0
00605 #   endif /* ! THR_SCHED_DEFAULT */
00606 #   if !defined (THR_INHERIT_SCHED)
00607 #     define THR_INHERIT_SCHED 0
00608 #   endif /* ! THR_INHERIT_SCHED */
00609 #   if !defined (USYNC_THREAD)
00610 #     define USYNC_THREAD 0
00611 #   endif /* ! USYNC_THREAD */
00612 #   if !defined (USYNC_PROCESS)
00613 #     define USYNC_PROCESS 0
00614 #   endif /* ! USYNC_PROCESS */
00615 #   if !defined (THR_SCOPE_PROCESS)
00616 #     define THR_SCOPE_PROCESS 0
00617 #   endif /* ! THR_SCOPE_PROCESS */
00618 #   if !defined (THR_SCOPE_SYSTEM)
00619 #     define THR_SCOPE_SYSTEM 0
00620 #   endif /* ! THR_SCOPE_SYSTEM */
00621 
00622 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00623 
00624 // These are dummies needed for class OS.h
00625 typedef int ACE_cond_t;
00626 struct ACE_Export ACE_condattr_t
00627 {
00628   int type;
00629 };
00630 struct ACE_Export ACE_mutexattr_t
00631 {
00632   int type;
00633 };
00634 typedef int ACE_mutex_t;
00635 typedef int ACE_thread_mutex_t;
00636 typedef int ACE_recursive_thread_mutex_t;
00637 typedef int ACE_recursive_mutex_state;
00638 #   if !defined (ACE_HAS_POSIX_SEM) && !defined (ACE_USES_FIFO_SEM)
00639 typedef int ACE_sema_t;
00640 #   endif /* !ACE_HAS_POSIX_SEM && !ACE_USES_FIFO_SEM */
00641 typedef int ACE_rwlock_t;
00642 typedef int ACE_thread_t;
00643 typedef int ACE_hthread_t;
00644 // Native TSS key type
00645 typedef unsigned int ACE_OS_thread_key_t;
00646 // Application TSS key type (use this type except in TSS Emulation)
00647 #   if defined (ACE_HAS_TSS_EMULATION)
00648       typedef u_int ACE_thread_key_t;
00649 #   else  /* ! ACE_HAS_TSS_EMULATION */
00650       typedef ACE_OS_thread_key_t ACE_thread_key_t;
00651 #   endif /* ! ACE_HAS_TSS_EMULATION */
00652 
00653 ACE_END_VERSIONED_NAMESPACE_DECL
00654 
00655 // Ensure that ACE_THR_PRI_FIFO_DEF and ACE_THR_PRI_OTHER_DEF are
00656 // defined on non-threaded platforms, to support application source
00657 // code compatibility.  ACE_THR_PRI_FIFO_DEF should be used by
00658 // applications for default real-time thread priority.
00659 // ACE_THR_PRI_OTHER_DEF should be used for non-real-time priority.
00660 #   if !defined(ACE_THR_PRI_FIFO_DEF)
00661 #     define ACE_THR_PRI_FIFO_DEF 0
00662 #   endif /* ! ACE_THR_PRI_FIFO_DEF */
00663 #   if !defined(ACE_THR_PRI_OTHER_DEF)
00664 #     define ACE_THR_PRI_OTHER_DEF 0
00665 #   endif /* ! ACE_THR_PRI_OTHER_DEF */
00666 
00667 # endif /* ACE_HAS_THREADS ***********************************************/
00668 
00669 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00670 
00671 /**
00672  * @class ACE_Thread_ID
00673  *
00674  * @brief Defines a platform-independent thread ID class.  Note that
00675  *  this class should be defined within the scope of a thread, rather
00676  *  than at global scope!
00677  */
00678 class ACE_Export ACE_Thread_ID
00679 {
00680 public:
00681   /// Initialize the object using the thread id and thread handle
00682   /// passed as parameters.
00683   ACE_Thread_ID (ACE_thread_t thr_id,
00684                  ACE_hthread_t thr_handle);
00685 
00686   /// Initialize the object using calls to ACE_OS::thr_self().
00687   ACE_Thread_ID (void);
00688 
00689   /// Copy constructor.
00690   ACE_Thread_ID (const ACE_Thread_ID &rhs);
00691 
00692   /// Get the thread id.
00693   ACE_thread_t id (void) const;
00694 
00695   /// Set the thread id.
00696   void id (ACE_thread_t);
00697 
00698   /// Get the thread handle.
00699   ACE_hthread_t handle (void) const;
00700 
00701   /// Set the thread handle.
00702   void handle (ACE_hthread_t);
00703 
00704   // Create a string representation of the thread id.
00705   void to_string (char *thr_string) const;
00706 
00707   /// Equality operator.
00708   bool operator== (const ACE_Thread_ID &) const;
00709 
00710   /// Inequality operator.
00711   bool operator!= (const ACE_Thread_ID &) const;
00712 
00713 private:
00714   /// Identify the thread.
00715   ACE_thread_t thread_id_;
00716 
00717   /// Handle to the thread (typically used to "wait" on Win32).
00718   ACE_hthread_t thread_handle_;
00719 };
00720 
00721 // = The ACE_Sched_Priority type should be used for platform-
00722 //   independent thread and process priorities, by convention.
00723 //   int should be used for OS-specific priorities.
00724 typedef int ACE_Sched_Priority;
00725 
00726 # if !defined (ACE_DEFAULT_SYNCH_TYPE)
00727 #   if defined (ACE_VXWORKS)
00728       // Types include these options: SEM_Q_PRIORITY, SEM_Q_FIFO,
00729       // SEM_DELETE_SAFE, and SEM_INVERSION_SAFE.  SEM_Q_FIFO is
00730       // used as the default because that is VxWorks' default.
00731 #     define ACE_DEFAULT_SYNCH_TYPE SEM_Q_FIFO
00732 #   else
00733 #     define ACE_DEFAULT_SYNCH_TYPE USYNC_THREAD
00734 #   endif /* ACE_VXWORKS */
00735 #endif /* ! ACE_DEFAULT_SYNCH_TYPE */
00736 
00737 // forward declaration
00738 class ACE_Sched_Params;
00739 class ACE_Time_Value;
00740 
00741 #if defined (ACE_WIN32)
00742 typedef int ACE_idtype_t;
00743 typedef DWORD ACE_id_t;
00744 typedef int ACE_pri_t;
00745 #   define ACE_SELF (0)
00746 #else /* !defined (ACE_WIN32) */
00747 #   if defined (ACE_HAS_IDTYPE_T)
00748   typedef idtype_t ACE_idtype_t;
00749 #   else
00750   typedef int ACE_idtype_t;
00751 #   endif /* ACE_HAS_IDTYPE_T */
00752 #   if defined (ACE_HAS_STHREADS) || defined (DIGITAL_UNIX)
00753 #     if defined (ACE_LACKS_PRI_T)
00754     typedef int pri_t;
00755 #     endif /* ACE_LACKS_PRI_T */
00756   typedef id_t ACE_id_t;
00757 #     define ACE_SELF P_MYID
00758   typedef pri_t ACE_pri_t;
00759 #   else  /* ! ACE_HAS_STHREADS && ! DIGITAL_UNIX */
00760   typedef long ACE_id_t;
00761 #     define ACE_SELF (-1)
00762   typedef short ACE_pri_t;
00763 #   endif /* ! ACE_HAS_STHREADS && ! DIGITAL_UNIX */
00764 #endif /* !defined (ACE_WIN32) */
00765 
00766 # if defined (ACE_HAS_TSS_EMULATION)
00767     // Allow config.h to set the default number of thread keys.
00768 #   if !defined (ACE_DEFAULT_THREAD_KEYS)
00769 #     define ACE_DEFAULT_THREAD_KEYS 64
00770 #   endif /* ! ACE_DEFAULT_THREAD_KEYS */
00771 
00772 // forward declaration
00773 class ACE_TSS_Keys;
00774 
00775 /**
00776  * @class ACE_TSS_Emulation
00777  *
00778  * @brief Thread-specific storage emulation.
00779  *
00780  * This provides a thread-specific storage implementation.
00781  * It is intended for use on platforms that don't have a
00782  * native TSS, or have a TSS with limitations such as the
00783  * number of keys or lack of support for removing keys.
00784  */
00785 class ACE_Export ACE_TSS_Emulation
00786 {
00787 public:
00788   typedef void (*ACE_TSS_DESTRUCTOR)(void *value) /* throw () */;
00789 
00790   /// Maximum number of TSS keys allowed over the life of the program.
00791   enum { ACE_TSS_THREAD_KEYS_MAX = ACE_DEFAULT_THREAD_KEYS };
00792 
00793   /// Returns the total number of keys allocated so far.
00794   static u_int total_keys ();
00795 
00796   /// Sets the argument to the next available key.  Returns 0 on success,
00797   /// -1 if no keys are available.
00798   static int next_key (ACE_thread_key_t &key);
00799 
00800   /// Release a key that was used. This way the key can be given out in a
00801   /// new request. Returns 0 on success, 1 if the key was not reserved.
00802   static int release_key (ACE_thread_key_t key);
00803 
00804   /// Check a key for validity.
00805   static int is_key (ACE_thread_key_t key);
00806 
00807   /// Returns the exit hook associated with the key.  Does _not_ check
00808   /// for a valid key.
00809   static ACE_TSS_DESTRUCTOR tss_destructor (const ACE_thread_key_t key);
00810 
00811   /// Associates the TSS destructor with the key.  Does _not_ check
00812   /// for a valid key.
00813   static void tss_destructor (const ACE_thread_key_t key,
00814                               ACE_TSS_DESTRUCTOR destructor);
00815 
00816   /// Accesses the object referenced by key in the current thread's TSS array.
00817   /// Does _not_ check for a valid key.
00818   static void *&ts_object (const ACE_thread_key_t key);
00819 
00820   /**
00821    * Setup an array to be used for local TSS.  Returns the array
00822    * address on success.  Returns 0 if local TSS had already been
00823    * setup for this thread.  There is no corresponding tss_close ()
00824    * because it is not needed.
00825    * @note tss_open () is called by ACE for threads that it spawns.
00826    * If your application spawns threads without using ACE, and it uses
00827    * ACE's TSS emulation, each of those threads should call tss_open
00828    * ().  See the ace_thread_adapter () implementation for an example.
00829    */
00830   static void *tss_open (void *ts_storage[ACE_TSS_THREAD_KEYS_MAX]);
00831 
00832   /// Shutdown TSS emulation.  For use only by ACE_OS::cleanup_tss ().
00833   static void tss_close ();
00834 
00835 private:
00836   // Global TSS structures.
00837   /// Contains the possible value of the next key to be allocated. Which key
00838   /// is actually allocated is based on the tss_keys_used
00839   static u_int total_keys_;
00840 
00841   /// Array of thread exit hooks (TSS destructors) that are called for each
00842   /// key (that has one) when the thread exits.
00843   static ACE_TSS_DESTRUCTOR tss_destructor_ [ACE_TSS_THREAD_KEYS_MAX];
00844 
00845   /// TSS_Keys instance to administrate whether a specific key is in used
00846   /// or not.
00847   /// or not.
00848   // Static construction in VxWorks 5.4 and later is slightly broken.
00849   // If the static object is more complex than an integral type, static
00850   // construction will occur twice.  The tss_keys_used_ object is
00851   // statically constructed and then modified by ACE_Log_Msg::instance()
00852   // when two keys are created and TSS data is stored.  However, at
00853   // the end of static construction the tss_keys_used_ object is again
00854   // initialized and therefore it will appear to next_key() that no
00855   // TSS keys have been handed out.  That is all true unless the
00856   // tss_keys_used object is a static pointer instead of a static object.
00857   static ACE_TSS_Keys* tss_keys_used_;
00858 
00859 #   if defined (ACE_HAS_THREAD_SPECIFIC_STORAGE)
00860   /// Location of current thread's TSS array.
00861   static void **tss_base (void* ts_storage[] = 0, u_int *ts_created = 0);
00862 #   else  /* ! ACE_HAS_THREAD_SPECIFIC_STORAGE */
00863   /// Location of current thread's TSS array.
00864   static void **&tss_base ();
00865 #   endif /* ! ACE_HAS_THREAD_SPECIFIC_STORAGE */
00866 
00867 #   if defined (ACE_HAS_THREAD_SPECIFIC_STORAGE)
00868   // Rely on native thread specific storage for the implementation,
00869   // but just use one key.
00870   static ACE_OS_thread_key_t native_tss_key_;
00871 
00872   // Used to indicate if native tss key has been allocated
00873   static int key_created_;
00874 #   endif /* ACE_HAS_THREAD_SPECIFIC_STORAGE */
00875 };
00876 
00877 # else   /* ! ACE_HAS_TSS_EMULATION */
00878 #   if !defined (ACE_DEFAULT_THREAD_KEYS)
00879       // This should have been defined in config-win32-common.h
00880 #     define ACE_DEFAULT_THREAD_KEYS 1088
00881 #   endif /* TSL_MINIMUM_AVAILABLE */
00882 
00883 # endif /* ACE_HAS_TSS_EMULATION */
00884 
00885 // moved ACE_TSS_Ref, ACE_TSS_Info, and ACE_TSS_Keys class
00886 // declarations from OS.cpp so they are visible to the single
00887 // file of template instantiations.
00888 # if defined (ACE_WIN32) || defined (ACE_HAS_TSS_EMULATION)
00889 /**
00890  * @class ACE_TSS_Ref
00891  *
00892  * @brief "Reference count" for thread-specific storage keys.
00893  *
00894  * Since the <ACE_Unbounded_Stack> doesn't allow duplicates, the
00895  * "reference count" is the identify of the thread_id.
00896  */
00897 class ACE_TSS_Ref
00898 {
00899 public:
00900   /// Constructor
00901   ACE_TSS_Ref (ACE_thread_t id);
00902 
00903   /// Default constructor
00904   ACE_TSS_Ref (void);
00905 
00906   /// Check for equality.
00907   bool operator== (const ACE_TSS_Ref &) const;
00908 
00909   /// Check for inequality.
00910   bool operator!= (const ACE_TSS_Ref &) const;
00911 
00912 // private:
00913 
00914   /// ID of thread using a specific key.
00915   ACE_thread_t tid_;
00916 };
00917 
00918 /**
00919  * @class ACE_TSS_Info
00920  *
00921  * @brief Thread Specific Key management.
00922  *
00923  * This class maps a key to a "destructor."
00924  */
00925 class ACE_TSS_Info
00926 {
00927 public:
00928   /// Declare pointer to function to destroy tss object.
00929   typedef void (*Destructor)(void *);
00930 
00931   /// Constructor
00932   ACE_TSS_Info (ACE_thread_key_t key,
00933                 Destructor dest = 0);
00934 
00935   /// Default constructor
00936   ACE_TSS_Info (void);
00937 
00938   /// Returns 1 if the key is in use, 0 if not.
00939   int key_in_use (void) const { return thread_count_ != -1; }
00940 
00941   /// Mark the key as being in use if the flag is non-zero, or
00942   /// not in use if the flag is 0.
00943   void key_in_use (int flag) { thread_count_ = flag == 0  ?  -1  :  1; }
00944 
00945   /// Check for equality.
00946   bool operator== (const ACE_TSS_Info &) const;
00947 
00948   /// Check for inequality.
00949   bool operator!= (const ACE_TSS_Info &) const;
00950 
00951   /// Dump the state.
00952   void dump (void);
00953 
00954 private:
00955   /// Key to the thread-specific storage item.
00956   ACE_thread_key_t key_;
00957 
00958   /// "Destructor" that gets called when the item is finally released.
00959   Destructor destructor_;
00960 
00961   /// Count of threads that are using this key.  Contains -1 when the
00962   /// key is not in use.
00963   int thread_count_;
00964 
00965   friend class ACE_TSS_Cleanup;
00966 };
00967 
00968 /**
00969  * @class ACE_TSS_Keys
00970  *
00971  * @brief Collection of in-use flags for a thread's TSS keys.
00972  * For internal use only by ACE_TSS_Cleanup; it is public because
00973  * some compilers can't use nested classes for template instantiation
00974  * parameters.
00975  *
00976  * Wrapper around array of whether each key is in use.  A simple
00977  * typedef doesn't work with Sun C++ 4.2.
00978  */
00979 class ACE_TSS_Keys
00980 {
00981 public:
00982   /// Default constructor, to initialize all bits to zero (unused).
00983   ACE_TSS_Keys (void);
00984 
00985   /// Mark the specified key as being in use, if it was not already so marked.
00986   /// Returns 1 if the had already been marked, 0 if not.
00987   int test_and_set (const ACE_thread_key_t key);
00988 
00989   /// Mark the specified key as not being in use, if it was not already so
00990   /// cleared.  Returns 1 if the key had already been cleared, 0 if not.
00991   int test_and_clear (const ACE_thread_key_t key);
00992 
00993   /// Return whether the specific key is marked as in use.
00994   /// Returns 1 if the key is been marked, 0 if not.
00995   int is_set (const ACE_thread_key_t key) const;
00996 
00997 private:
00998   /// For a given key, find the word and bit number that represent it.
00999   static void find (const u_int key, u_int &word, u_int &bit);
01000 
01001   enum
01002     {
01003 #   if ACE_SIZEOF_LONG == 8
01004       ACE_BITS_PER_WORD = 64,
01005 #   elif ACE_SIZEOF_LONG == 4
01006       ACE_BITS_PER_WORD = 32,
01007 #   else
01008 #     error ACE_TSS_Keys only supports 32 or 64 bit longs.
01009 #   endif /* ACE_SIZEOF_LONG == 8 */
01010       ACE_WORDS = (ACE_DEFAULT_THREAD_KEYS - 1) / ACE_BITS_PER_WORD + 1
01011     };
01012 
01013   /// Bit flag collection.  A bit value of 1 indicates that the key is in
01014   /// use by this thread.
01015   u_long key_bit_words_[ACE_WORDS];
01016 };
01017 
01018 # endif /* defined (ACE_WIN32) || defined (ACE_HAS_TSS_EMULATION) */
01019 
01020 // Support non-scalar thread keys, such as with some POSIX
01021 // implementations, e.g., MVS.
01022 # if defined (ACE_HAS_NONSCALAR_THREAD_KEY_T)
01023 #   define ACE_KEY_INDEX(OBJ,KEY) \
01024   u_int OBJ; \
01025   ACE_OS::memcpy (&OBJ, &KEY, sizeof (u_int))
01026 # else
01027 #   define ACE_KEY_INDEX(OBJ,KEY) u_int OBJ = KEY
01028 # endif /* ACE_HAS_NONSCALAR_THREAD_KEY_T */
01029 
01030 ACE_END_VERSIONED_NAMESPACE_DECL
01031 
01032 #if (defined (ACE_HAS_VERSIONED_NAMESPACE) && ACE_HAS_VERSIONED_NAMESPACE == 1)
01033 # define ACE_MUTEX_LOCK_CLEANUP_ADAPTER_NAME ACE_PREPROC_CONCATENATE(ACE_VERSIONED_NAMESPACE_NAME, _ace_mutex_lock_cleanup_adapter)
01034 #endif  /* ACE_HAS_VERSIONED_NAMESPACE == 1 */
01035 
01036 
01037 # if defined (ACE_HAS_THR_C_FUNC)
01038 // This is necessary to work around nasty problems with MVS C++.
01039 extern "C" ACE_Export void ACE_MUTEX_LOCK_CLEANUP_ADAPTER_NAME (void *args);
01040 #   define ACE_PTHREAD_CLEANUP_PUSH(A) pthread_cleanup_push (ACE_MUTEX_LOCK_CLEANUP_ADAPTER_NAME, (void *) A);
01041 #   define ACE_PTHREAD_CLEANUP_POP(A) pthread_cleanup_pop(A)
01042 # elif defined (ACE_HAS_PTHREADS) && !defined (ACE_LACKS_PTHREAD_CLEANUP)
01043 // Though we are defining a extern "C" function to match the prototype of
01044 // pthread_cleanup_push, it is undone by the Solaris header file
01045 // /usr/include/pthread.h. So this macro generates a warning under Solaris
01046 // with SunCC. This is a bug in the Solaris header file.
01047 extern "C" ACE_Export void ACE_MUTEX_LOCK_CLEANUP_ADAPTER_NAME (void *args);
01048 #   define ACE_PTHREAD_CLEANUP_PUSH(A) pthread_cleanup_push (ACE_MUTEX_LOCK_CLEANUP_ADAPTER_NAME, (void *) A);
01049 #   define ACE_PTHREAD_CLEANUP_POP(A) pthread_cleanup_pop(A)
01050 # else
01051 #   define ACE_PTHREAD_CLEANUP_PUSH(A)
01052 #   define ACE_PTHREAD_CLEANUP_POP(A)
01053 # endif /* ACE_HAS_THR_C_FUNC */
01054 
01055 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
01056 
01057 # if !defined (ACE_WIN32)
01058 // forward decl's
01059 class ACE_event_t;
01060 # endif
01061 
01062 class ACE_Base_Thread_Adapter;
01063 
01064 namespace ACE_OS {
01065   //@{ @name A set of wrappers for threads
01066 
01067   /// This is necessary to deal with POSIX pthreads and their use of
01068   /// structures for thread ids.
01069   extern ACE_Export ACE_thread_t NULL_thread;
01070 
01071   /// This is necessary to deal with POSIX pthreads and their use of
01072   /// structures for thread handles.
01073   extern ACE_Export ACE_hthread_t NULL_hthread;
01074 
01075   /// This is necessary to deal with POSIX pthreads and their use of
01076   /// structures for TSS keys.
01077   extern ACE_Export ACE_thread_key_t NULL_key;
01078   //@}
01079 
01080   /**
01081    * Call TSS destructors for the current thread.  If the current
01082    * thread is the main thread, then the argument must be 1.
01083    * For private use of ACE_Object_Manager and ACE_Thread_Adapter only.
01084    */
01085   extern ACE_Export
01086   void cleanup_tss (const u_int main_thread);
01087 
01088   //@{ @name A set of wrappers for condition variables.
01089 #if defined (ACE_LACKS_COND_T)
01090   extern ACE_Export
01091 #else
01092   ACE_NAMESPACE_INLINE_FUNCTION
01093 #endif /* ACE_LACKS_COND_T */
01094   int condattr_init (ACE_condattr_t &attributes,
01095                      int type = ACE_DEFAULT_SYNCH_TYPE);
01096 
01097 #if defined (ACE_LACKS_COND_T)
01098   extern ACE_Export
01099 #else
01100   ACE_NAMESPACE_INLINE_FUNCTION
01101 #endif /* ACE_LACKS_COND_T */
01102   int condattr_destroy (ACE_condattr_t &attributes);
01103 
01104 #if defined (ACE_LACKS_COND_T)
01105   extern ACE_Export
01106 #else
01107   ACE_NAMESPACE_INLINE_FUNCTION
01108 #endif /* ACE_LACKS_COND_T */
01109   int cond_broadcast (ACE_cond_t *cv);
01110 
01111 #if defined (ACE_LACKS_COND_T)
01112   extern ACE_Export
01113 #else
01114   ACE_NAMESPACE_INLINE_FUNCTION
01115 #endif /* ACE_LACKS_COND_T */
01116   int cond_destroy (ACE_cond_t *cv);
01117 
01118   extern ACE_Export
01119   int cond_init (ACE_cond_t *cv,
01120                  short type = ACE_DEFAULT_SYNCH_TYPE,
01121                  const char *name = 0,
01122                  void *arg = 0);
01123 
01124 #if defined (ACE_LACKS_COND_T)
01125   extern ACE_Export
01126 #else
01127   ACE_NAMESPACE_INLINE_FUNCTION
01128 #endif /* ACE_LACKS_COND_T */
01129   int cond_init (ACE_cond_t *cv,
01130                  ACE_condattr_t &attributes,
01131                  const char *name = 0,
01132                  void *arg = 0);
01133 
01134 # if defined (ACE_HAS_WCHAR)
01135 #   if defined (ACE_LACKS_COND_T)
01136   extern ACE_Export
01137 #   else
01138   ACE_NAMESPACE_INLINE_FUNCTION
01139 #   endif /* ACE_LACKS_COND_T */
01140   int cond_init (ACE_cond_t *cv,
01141                  short type,
01142                  const wchar_t *name,
01143                  void *arg = 0);
01144 
01145 #   if defined (ACE_LACKS_COND_T)
01146   extern ACE_Export
01147 #   else
01148   ACE_NAMESPACE_INLINE_FUNCTION
01149 #   endif /* ACE_LACKS_COND_T */
01150   int cond_init (ACE_cond_t *cv,
01151                  ACE_condattr_t &attributes,
01152                  const wchar_t *name,
01153                  void *arg = 0);
01154 # endif /* ACE_HAS_WCHAR */
01155 
01156 #if defined (ACE_LACKS_COND_T)
01157   extern ACE_Export
01158 #else
01159   ACE_NAMESPACE_INLINE_FUNCTION
01160 #endif /* ACE_LACKS_COND_T */
01161   int cond_signal (ACE_cond_t *cv);
01162 
01163 #if defined (ACE_LACKS_COND_T)
01164   extern ACE_Export
01165 #else
01166   ACE_NAMESPACE_INLINE_FUNCTION
01167 #endif /* ACE_LACKS_COND_T */
01168   int cond_timedwait (ACE_cond_t *cv,
01169                       ACE_mutex_t *m,
01170                       ACE_Time_Value *);
01171 
01172 #if defined (ACE_LACKS_COND_T)
01173   extern ACE_Export
01174 #else
01175   ACE_NAMESPACE_INLINE_FUNCTION
01176 #endif /* ACE_LACKS_COND_T */
01177   int cond_wait (ACE_cond_t *cv,
01178                  ACE_mutex_t *m);
01179 
01180 # if defined (ACE_WIN32) && defined (ACE_HAS_WTHREADS)
01181 #   if defined (ACE_LACKS_COND_T)
01182   extern ACE_Export
01183 #   else
01184   ACE_NAMESPACE_INLINE_FUNCTION
01185 #   endif /* ACE_LACKS_COND_T */
01186   int cond_timedwait (ACE_cond_t *cv,
01187                       ACE_thread_mutex_t *m,
01188                       ACE_Time_Value *);
01189 
01190 #   if defined (ACE_LACKS_COND_T)
01191   extern ACE_Export
01192 #   else
01193   ACE_NAMESPACE_INLINE_FUNCTION
01194 #   endif /* ACE_LACKS_COND_T */
01195   int cond_wait (ACE_cond_t *cv,
01196                  ACE_thread_mutex_t *m);
01197 # endif /* ACE_WIN32 && ACE_HAS_WTHREADS */
01198 
01199   //@{ @name A set of wrappers for auto-reset and manual events.
01200 
01201   extern ACE_Export
01202   int event_destroy (ACE_event_t *event);
01203 
01204   extern ACE_Export
01205   int event_init (ACE_event_t *event,
01206                   int manual_reset = 0,
01207                   int initial_state = 0,
01208                   int type = ACE_DEFAULT_SYNCH_TYPE,
01209                   const char *name = 0,
01210                   void *arg = 0,
01211                   LPSECURITY_ATTRIBUTES sa = 0);
01212 
01213 # if defined (ACE_HAS_WCHAR)
01214   ACE_NAMESPACE_INLINE_FUNCTION
01215   int event_init (ACE_event_t *event,
01216                   int manual_reset,
01217                   int initial_state,
01218                   int type,
01219                   const wchar_t *name,
01220                   void *arg = 0,
01221                   LPSECURITY_ATTRIBUTES sa = 0);
01222 # endif /* ACE_HAS_WCHAR */
01223 
01224   extern ACE_Export
01225   int event_pulse (ACE_event_t *event);
01226 
01227   extern ACE_Export
01228   int event_reset (ACE_event_t *event);
01229 
01230   extern ACE_Export
01231   int event_signal (ACE_event_t *event);
01232 
01233   extern ACE_Export
01234   int event_timedwait (ACE_event_t *event,
01235                        ACE_Time_Value *timeout,
01236                        int use_absolute_time = 1);
01237 
01238   extern ACE_Export
01239   int event_wait (ACE_event_t *event);
01240 
01241   //@}
01242 
01243   extern ACE_Export
01244   int lwp_getparams (ACE_Sched_Params &);
01245 
01246   extern ACE_Export
01247   int lwp_setparams (const ACE_Sched_Params &);
01248 
01249 
01250   //@{ @name A set of wrappers for mutex locks.
01251 
01252   extern ACE_Export
01253   int mutex_destroy (ACE_mutex_t *m);
01254 
01255   extern ACE_Export
01256   int mutex_init (ACE_mutex_t *m,
01257                   int lock_scope = ACE_DEFAULT_SYNCH_TYPE,
01258                   const char *name = 0,
01259                   ACE_mutexattr_t *arg = 0,
01260                   LPSECURITY_ATTRIBUTES sa = 0,
01261                   int lock_type = 0);
01262 
01263 #if defined (ACE_HAS_WCHAR)
01264   extern ACE_Export
01265   int mutex_init (ACE_mutex_t *m,
01266                   int lock_scope,
01267                   const wchar_t *name,
01268                   ACE_mutexattr_t *arg = 0,
01269                   LPSECURITY_ATTRIBUTES sa = 0,
01270                   int lock_type = 0);
01271 #endif /* ACE_HAS_WCHAR */
01272 
01273   /// Win32 note: Abandoned mutexes are not treated differently. 0 is
01274   /// returned since the calling thread does get the ownership.
01275   extern ACE_Export
01276   int mutex_lock (ACE_mutex_t *m);
01277 
01278   /// This method is only implemented for Win32.  For abandoned
01279   /// mutexes, @a abandoned is set to 1 and 0 is returned.
01280   extern ACE_Export
01281   int mutex_lock (ACE_mutex_t *m,
01282                   int &abandoned);
01283 
01284   /**
01285    * This method attempts to acquire a lock, but gives up if the lock
01286    * has not been acquired by the given time.  If the lock is not
01287    * acquired within the given amount of time, then this method
01288    * returns -1 with an @c ETIME errno on platforms that actually
01289    * support timed mutexes.  The timeout should be an absolute time.
01290    * Note that the mutex should not be a recursive one, i.e., it
01291    * should only be a standard mutex or an error checking mutex since
01292    * some implementations of this method don't support recursive
01293    * mutexes.  If you want to use a recursive mutex see the methods
01294    * below.
01295    */
01296   extern ACE_Export
01297   int mutex_lock (ACE_mutex_t *m,
01298                   const ACE_Time_Value &timeout);
01299 
01300   /**
01301    * If <timeout> == 0, calls <ACE_OS::mutex_lock(m)>.  Otherwise,
01302    * this method attempts to acquire a lock, but gives up if the lock
01303    * has not been acquired by the given time, in which case it returns
01304    * -1 with an @c ETIME errno on platforms that actually support timed
01305    * mutexes.  The timeout should be an absolute time.  Note that the
01306    * mutex should not be a recursive one, i.e., it should only be a
01307    * standard mutex or an error checking mutex since some
01308    * implementations of this method don't support recursive mutexes.
01309    * If you want to use a recursive mutex see the methods below.
01310    */
01311   ACE_NAMESPACE_INLINE_FUNCTION
01312   int mutex_lock (ACE_mutex_t *m,
01313                   const ACE_Time_Value *timeout);
01314 
01315   /// Handle asynchronous thread cancellation cleanup.
01316   extern ACE_Export
01317   void mutex_lock_cleanup (void *mutex);
01318 
01319   /// Win32 note: Abandoned mutexes are not treated differently. 0 is
01320   /// returned since the calling thread does get the ownership.
01321   extern ACE_Export
01322   int mutex_trylock (ACE_mutex_t *m);
01323 
01324   /// This method is only implemented for Win32.  For abandoned
01325   /// mutexes, <abandoned> is set to 1 and 0 is returned.
01326   extern ACE_Export
01327   int mutex_trylock (ACE_mutex_t *m,
01328                      int &abandoned);
01329 
01330   extern ACE_Export
01331   int mutex_unlock (ACE_mutex_t *m);
01332 
01333   //@}
01334 
01335   /// Low-level interface to <priocntl>(2).
01336   /**
01337    * Can't call the following priocntl, because that's a macro on
01338    * Solaris.
01339    */
01340   ACE_NAMESPACE_INLINE_FUNCTION
01341   long priority_control (ACE_idtype_t, ACE_id_t, int, void *);
01342 
01343   //@{ @name A set of wrappers for recursive mutex locks.
01344 
01345   // These two methods are primarily in support of
01346   // ACE_Condition<ACE_Recursive_Thread_Mutex> and should probably not
01347   // be called outside that context.
01348   ACE_NAMESPACE_INLINE_FUNCTION
01349   int recursive_mutex_cond_unlock (ACE_recursive_thread_mutex_t *m,
01350                                    ACE_recursive_mutex_state &state);
01351 
01352   ACE_NAMESPACE_INLINE_FUNCTION
01353   void recursive_mutex_cond_relock (ACE_recursive_thread_mutex_t *m,
01354                                     ACE_recursive_mutex_state &state);
01355 
01356   ACE_NAMESPACE_INLINE_FUNCTION
01357   int recursive_mutex_destroy (ACE_recursive_thread_mutex_t *m);
01358 
01359   ACE_NAMESPACE_INLINE_FUNCTION
01360   int recursive_mutex_init (ACE_recursive_thread_mutex_t *m,
01361                             const ACE_TCHAR *name = 0,
01362                             ACE_mutexattr_t *arg = 0,
01363                             LPSECURITY_ATTRIBUTES sa = 0);
01364 
01365   ACE_NAMESPACE_INLINE_FUNCTION
01366   int recursive_mutex_lock (ACE_recursive_thread_mutex_t *m);
01367 
01368   ACE_NAMESPACE_INLINE_FUNCTION
01369   int recursive_mutex_lock (ACE_recursive_thread_mutex_t *m,
01370                             const ACE_Time_Value &timeout);
01371 
01372   ACE_NAMESPACE_INLINE_FUNCTION
01373   int recursive_mutex_lock (ACE_recursive_thread_mutex_t *m,
01374                             const ACE_Time_Value *timeout);
01375 
01376   ACE_NAMESPACE_INLINE_FUNCTION
01377   int recursive_mutex_trylock (ACE_recursive_thread_mutex_t *m);
01378 
01379   ACE_NAMESPACE_INLINE_FUNCTION
01380   int recursive_mutex_unlock (ACE_recursive_thread_mutex_t *m);
01381 
01382   //@}
01383 
01384 
01385   //@{ @name A set of wrappers for readers/writer locks.
01386 
01387   ACE_NAMESPACE_INLINE_FUNCTION
01388   int rw_rdlock (ACE_rwlock_t *rw);
01389 
01390   ACE_NAMESPACE_INLINE_FUNCTION
01391   int rw_tryrdlock (ACE_rwlock_t *rw);
01392 
01393   ACE_NAMESPACE_INLINE_FUNCTION
01394   int rw_trywrlock (ACE_rwlock_t *rw);
01395 
01396   ACE_NAMESPACE_INLINE_FUNCTION
01397   int rw_trywrlock_upgrade (ACE_rwlock_t *rw);
01398 
01399   ACE_NAMESPACE_INLINE_FUNCTION
01400   int rw_unlock (ACE_rwlock_t *rw);
01401 
01402   ACE_NAMESPACE_INLINE_FUNCTION
01403   int rw_wrlock (ACE_rwlock_t *rw);
01404 
01405   ACE_NAMESPACE_INLINE_FUNCTION
01406   int rwlock_destroy (ACE_rwlock_t *rw);
01407 
01408   extern ACE_Export
01409   int rwlock_init (ACE_rwlock_t *rw,
01410                    int type = ACE_DEFAULT_SYNCH_TYPE,
01411                    const ACE_TCHAR *name = 0,
01412                    void *arg = 0);
01413 
01414   //@}
01415 
01416   //@{ @name Thread scheduler interface.
01417   /// Set scheduling parameters.  An id of ACE_SELF indicates, e.g.,
01418   /// set the parameters on the calling thread.
01419   extern ACE_Export
01420   int sched_params (const ACE_Sched_Params &, ACE_id_t id = ACE_SELF);
01421   //@}
01422 
01423   /// Find the schedling class ID that corresponds to the class name.
01424   extern ACE_Export
01425   int scheduling_class (const char *class_name, ACE_id_t &);
01426 
01427   //@{ @name A set of wrappers for semaphores.
01428 
01429   ACE_NAMESPACE_INLINE_FUNCTION
01430   int sema_destroy (ACE_sema_t *s);
01431 
01432   ACE_NAMESPACE_INLINE_FUNCTION
01433   int sema_init (ACE_sema_t *s,
01434                  u_int count,
01435                  int type = ACE_DEFAULT_SYNCH_TYPE,
01436                  const char *name = 0,
01437                  void *arg = 0,
01438                  int max = 0x7fffffff,
01439                  LPSECURITY_ATTRIBUTES sa = 0);
01440 
01441 # if defined (ACE_HAS_WCHAR)
01442   ACE_NAMESPACE_INLINE_FUNCTION
01443   int sema_init (ACE_sema_t *s,
01444                  u_int count,
01445                  int type,
01446                  const wchar_t *name,
01447                  void *arg = 0,
01448                  int max = 0x7fffffff,
01449                  LPSECURITY_ATTRIBUTES sa = 0);
01450 # endif /* ACE_HAS_WCHAR */
01451 
01452   ACE_NAMESPACE_INLINE_FUNCTION
01453   int sema_post (ACE_sema_t *s);
01454 
01455   ACE_NAMESPACE_INLINE_FUNCTION
01456   int sema_post (ACE_sema_t *s,
01457                  u_int release_count);
01458 
01459   ACE_NAMESPACE_INLINE_FUNCTION
01460   int sema_trywait (ACE_sema_t *s);
01461 
01462   ACE_NAMESPACE_INLINE_FUNCTION
01463   int sema_wait (ACE_sema_t *s);
01464 
01465   ACE_NAMESPACE_INLINE_FUNCTION
01466   int sema_wait (ACE_sema_t *s,
01467                  ACE_Time_Value &tv);
01468 
01469   ACE_NAMESPACE_INLINE_FUNCTION
01470   int sema_wait (ACE_sema_t *s,
01471                  ACE_Time_Value *tv);
01472 
01473   //@}
01474 
01475   //@{ @name A set of wrappers for System V semaphores.
01476   ACE_NAMESPACE_INLINE_FUNCTION
01477   int semctl (int int_id,
01478               int semnum,
01479               int cmd,
01480               semun);
01481 
01482   ACE_NAMESPACE_INLINE_FUNCTION
01483   int semget (key_t key,
01484               int nsems,
01485               int flags);
01486 
01487   ACE_NAMESPACE_INLINE_FUNCTION
01488   int semop (int int_id,
01489              struct sembuf *sops,
01490              size_t nsops);
01491   //@}
01492 
01493   /// Friendly interface to <priocntl>(2).
01494   extern ACE_Export
01495   int set_scheduling_params (const ACE_Sched_Params &,
01496                              ACE_id_t id = ACE_SELF);
01497 
01498   ACE_NAMESPACE_INLINE_FUNCTION
01499   int sigtimedwait (const sigset_t *set,
01500                     siginfo_t *info,
01501                     const ACE_Time_Value *timeout);
01502 
01503   ACE_NAMESPACE_INLINE_FUNCTION
01504   int sigwait (sigset_t *set,
01505                int *sig = 0);
01506 
01507   ACE_NAMESPACE_INLINE_FUNCTION
01508   int sigwaitinfo (const sigset_t *set,
01509                    siginfo_t *info);
01510 
01511   ACE_NAMESPACE_INLINE_FUNCTION
01512   int thr_cancel (ACE_thread_t t_id);
01513 
01514   ACE_NAMESPACE_INLINE_FUNCTION
01515   int thr_cmp (ACE_hthread_t t1,
01516                ACE_hthread_t t2);
01517 
01518   // These are non-portable since they use ACE_thread_t and
01519   // ACE_hthread_t and will go away in a future release.
01520   ACE_NAMESPACE_INLINE_FUNCTION
01521   int thr_continue (ACE_hthread_t target_thread);
01522 
01523   /*
01524    * Creates a new thread having <flags> attributes and running <func>
01525    * with <args> (if <thread_adapter> is non-0 then <func> and <args>
01526    * are ignored and are obtained from <thread_adapter>).  <thr_id>
01527    * and <t_handle> are set to the thread's ID and handle (?),
01528    * respectively.  The thread runs at <priority> priority (see
01529    * below).
01530    *
01531    * The <flags> are a bitwise-OR of the following:
01532    * = BEGIN<INDENT>
01533    * THR_CANCEL_DISABLE, THR_CANCEL_ENABLE, THR_CANCEL_DEFERRED,
01534    * THR_CANCEL_ASYNCHRONOUS, THR_BOUND, THR_NEW_LWP, THR_DETACHED,
01535    * THR_SUSPENDED, THR_DAEMON, THR_JOINABLE, THR_SCHED_FIFO,
01536    * THR_SCHED_RR, THR_SCHED_DEFAULT, THR_EXPLICIT_SCHED,
01537    * THR_SCOPE_SYSTEM, THR_SCOPE_PROCESS
01538    * = END<INDENT>
01539    *
01540    * By default, or if <priority> is set to
01541    * ACE_DEFAULT_THREAD_PRIORITY, an "appropriate" priority value for
01542    * the given scheduling policy (specified in <flags}>, e.g.,
01543    * <THR_SCHED_DEFAULT>) is used.  This value is calculated
01544    * dynamically, and is the median value between the minimum and
01545    * maximum priority values for the given policy.  If an explicit
01546    * value is given, it is used.  Note that actual priority values are
01547    * EXTREMEMLY implementation-dependent, and are probably best
01548    * avoided.
01549    *
01550    * Note that <thread_adapter> is always deleted by <thr_create>,
01551    * therefore it must be allocated with global operator new.
01552    */
01553   extern ACE_Export
01554   int thr_create (ACE_THR_FUNC func,
01555                   void *args,
01556                   long flags,
01557                   ACE_thread_t *thr_id,
01558                   ACE_hthread_t *t_handle = 0,
01559                   long priority = ACE_DEFAULT_THREAD_PRIORITY,
01560                   void *stack = 0,
01561                   size_t stacksize = ACE_DEFAULT_THREAD_STACKSIZE,
01562                   ACE_Base_Thread_Adapter *thread_adapter = 0);
01563 
01564   ACE_NAMESPACE_INLINE_FUNCTION
01565   int thr_equal (ACE_thread_t t1,
01566                  ACE_thread_t t2);
01567 
01568   extern ACE_Export
01569   void thr_exit (ACE_THR_FUNC_RETURN status = 0);
01570 
01571   ACE_NAMESPACE_INLINE_FUNCTION
01572   int thr_getconcurrency (void);
01573 
01574   ACE_NAMESPACE_INLINE_FUNCTION
01575   int thr_getprio (ACE_hthread_t id,
01576                    int &priority);
01577 
01578   ACE_NAMESPACE_INLINE_FUNCTION
01579   int thr_getprio (ACE_hthread_t id,
01580                    int &priority,
01581                    int &policy);
01582 
01583 # if defined (ACE_HAS_THREAD_SPECIFIC_STORAGE)
01584   ACE_NAMESPACE_INLINE_FUNCTION
01585   /// for internal use only.  Applications should call thr_getspecific
01586   int thr_getspecific_native (ACE_OS_thread_key_t key,
01587                        void **data);
01588 # endif /* ACE_HAS_THREAD_SPECIFIC_STORAGE */
01589 
01590   ACE_NAMESPACE_INLINE_FUNCTION
01591   int thr_getspecific (ACE_thread_key_t key,
01592                        void **data);
01593 
01594 #if defined (ACE_VXWORKS)
01595   extern ACE_Export
01596 #else
01597   ACE_NAMESPACE_INLINE_FUNCTION
01598 #endif /* ACE_VXWORKS */
01599   int thr_join (ACE_hthread_t waiter_id,
01600                 ACE_THR_FUNC_RETURN *status);
01601 
01602 #if defined (ACE_VXWORKS)
01603   extern ACE_Export
01604 #else
01605   ACE_NAMESPACE_INLINE_FUNCTION
01606 #endif /* ACE_VXWORKS */
01607   int thr_join (ACE_thread_t waiter_id,
01608                 ACE_thread_t *thr_id,
01609                 ACE_THR_FUNC_RETURN *status);
01610 
01611   /**
01612    * Get the thread affinity
01613    *
01614    * @param thr_id For NPTL-threads, when ACE_HAS_PTHREAD_SETAFFINITY_NP
01615    * defined, this is the thread-id. For linux-threads, when
01616    * ACE_HAS_SCHED_SETAFFINITY defined, it expects a process-id. Since for
01617    * linux-threads a thread is seen as a process, it does the job.
01618    * @param cpu_set_size The size of the cpu_mask
01619    * @param cpu_mask Is a bitmask of CPUs to bind to, e.g value 1 binds the
01620    * thread to the "CPU 0", etc
01621    */
01622   extern ACE_Export
01623   int thr_get_affinity (ACE_hthread_t thr_id,
01624                         size_t cpu_set_size,
01625                         cpu_set_t * cpu_mask);
01626 
01627 
01628   /**
01629    * Set the thread affinity
01630    *
01631    * @param thr_id For NPTL-threads, when ACE_HAS_PTHREAD_SETAFFINITY_NP
01632    * defined, this is the thread-id. For linux-threads, when
01633    * ACE_HAS_SCHED_SETAFFINITY defined, it expects a process-id. Since for
01634    * linux-threads a thread is seen as a process, it does the job.
01635    * @param cpu_set_size The size of the cpu_mask
01636    * @param cpu_mask Is a bitmask of CPUs to bind to, e.g value 1 binds the
01637    * thread to the "CPU 0", etc
01638    */
01639   extern ACE_Export
01640   int thr_set_affinity (ACE_hthread_t thr_id,
01641                         size_t cpu_set_size,
01642                         const cpu_set_t * cpu_mask);
01643 
01644   /**
01645    * @note the "inst" arg is deprecated.  It will be ignored.
01646    */
01647   extern ACE_Export
01648   int thr_key_detach (ACE_thread_key_t key, void * inst);
01649 
01650   extern ACE_Export
01651   int thr_key_used (ACE_thread_key_t key);
01652 
01653 # if defined (ACE_HAS_THR_C_DEST)
01654 #   if defined (ACE_HAS_THREAD_SPECIFIC_STORAGE)
01655   /// @internal Applications should call thr_keycreate
01656   extern ACE_Export
01657   int thr_keycreate_native (ACE_OS_thread_key_t *key,
01658                      ACE_THR_C_DEST);
01659 #   endif /* ACE_HAS_THREAD_SPECIFIC_STORAGE */
01660 
01661   /**
01662    * @note the "inst" arge is deprecated.  It will be ignored.
01663    */
01664   extern ACE_Export
01665   int thr_keycreate (ACE_thread_key_t *key,
01666                      ACE_THR_C_DEST,
01667                      void *inst = 0);
01668 # else
01669 #   if defined (ACE_HAS_THREAD_SPECIFIC_STORAGE)
01670   /// @internal Applications should call thr_keycreate instead
01671   extern ACE_Export
01672   int thr_keycreate_native (ACE_OS_thread_key_t *key,
01673                      ACE_THR_DEST);
01674 #   endif /* ACE_HAS_THREAD_SPECIFIC_STORAGE */
01675   /**
01676    * @note the "inst" arge is deprecated.  It will be ignored.
01677    */
01678   extern ACE_Export
01679   int thr_keycreate (ACE_thread_key_t *key,
01680                      ACE_THR_DEST,
01681                      void *inst = 0);
01682 
01683 # endif /* ACE_HAS_THR_C_DEST */
01684 
01685 # if defined (ACE_HAS_THREAD_SPECIFIC_STORAGE)
01686   /// @internal  applications should call thr_keyfree instead
01687   extern ACE_Export
01688   int thr_keyfree_native (ACE_OS_thread_key_t key);
01689 # endif /* ACE_HAS_THREAD_SPECIFIC_STORAGE */
01690 
01691   extern ACE_Export
01692   int thr_keyfree (ACE_thread_key_t key);
01693 
01694   ACE_NAMESPACE_INLINE_FUNCTION
01695   int thr_kill (ACE_thread_t thr_id,
01696                 int signum);
01697 
01698   ACE_NAMESPACE_INLINE_FUNCTION
01699   size_t thr_min_stack (void);
01700 
01701   ACE_NAMESPACE_INLINE_FUNCTION
01702   ACE_thread_t thr_self (void);
01703 
01704   ACE_NAMESPACE_INLINE_FUNCTION
01705   void thr_self (ACE_hthread_t &);
01706 
01707   ACE_NAMESPACE_INLINE_FUNCTION
01708   int thr_setcancelstate (int new_state,
01709                           int *old_state);
01710 
01711   ACE_NAMESPACE_INLINE_FUNCTION
01712   int thr_setcanceltype (int new_type,
01713                          int *old_type);
01714 
01715   ACE_NAMESPACE_INLINE_FUNCTION
01716   int thr_setconcurrency (int hint);
01717 
01718   ACE_NAMESPACE_INLINE_FUNCTION
01719   int thr_setprio (ACE_hthread_t ht_id,
01720                    int priority,
01721                    int policy = -1);
01722 
01723   extern ACE_Export
01724   int thr_setprio (const ACE_Sched_Priority prio);
01725 
01726 # if defined (ACE_HAS_THREAD_SPECIFIC_STORAGE)
01727   /// @internal Applications should call thr_setspecific
01728   extern ACE_Export
01729   int thr_setspecific_native (ACE_OS_thread_key_t key,
01730                               void *data);
01731 # endif /* ACE_HAS_THREAD_SPECIFIC_STORAGE */
01732 
01733   extern ACE_Export
01734   int thr_setspecific (ACE_thread_key_t key,
01735                        void *data);
01736 
01737   ACE_NAMESPACE_INLINE_FUNCTION
01738   int thr_sigsetmask (int how,
01739                       const sigset_t *nsm,
01740                       sigset_t *osm);
01741 
01742   ACE_NAMESPACE_INLINE_FUNCTION
01743   int thr_suspend (ACE_hthread_t target_thread);
01744 
01745   ACE_NAMESPACE_INLINE_FUNCTION
01746   void thr_testcancel (void);
01747 
01748   ACE_NAMESPACE_INLINE_FUNCTION
01749   void thr_yield (void);
01750 
01751   //@{ @name A set of wrappers for mutex locks that only work within a single process.
01752 
01753   ACE_NAMESPACE_INLINE_FUNCTION
01754   int thread_mutex_destroy (ACE_thread_mutex_t *m);
01755 
01756   ACE_NAMESPACE_INLINE_FUNCTION
01757   int thread_mutex_init (ACE_thread_mutex_t *m,
01758                          int lock_type = 0,
01759                          const char *name = 0,
01760                          ACE_mutexattr_t *arg = 0);
01761 
01762 #if defined (ACE_HAS_WCHAR)
01763   ACE_NAMESPACE_INLINE_FUNCTION
01764   int thread_mutex_init (ACE_thread_mutex_t *m,
01765                          int lock_type,
01766                          const wchar_t *name,
01767                          ACE_mutexattr_t *arg = 0);
01768 #endif /* ACE_HAS_WCHAR */
01769 
01770   ACE_NAMESPACE_INLINE_FUNCTION
01771   int thread_mutex_lock (ACE_thread_mutex_t *m);
01772 
01773   ACE_NAMESPACE_INLINE_FUNCTION
01774   int thread_mutex_lock (ACE_thread_mutex_t *m,
01775                          const ACE_Time_Value &timeout);
01776 
01777   ACE_NAMESPACE_INLINE_FUNCTION
01778   int thread_mutex_lock (ACE_thread_mutex_t *m,
01779                          const ACE_Time_Value *timeout);
01780 
01781   ACE_NAMESPACE_INLINE_FUNCTION
01782   int thread_mutex_trylock (ACE_thread_mutex_t *m);
01783 
01784   ACE_NAMESPACE_INLINE_FUNCTION
01785   int thread_mutex_unlock (ACE_thread_mutex_t *m);
01786 
01787   //@}
01788 
01789   /**
01790    * This method uses process id and object pointer to come up with a
01791    * machine wide unique name.  The process ID will provide uniqueness
01792    * between processes on the same machine. The "this" pointer of the
01793    * <object> will provide uniqueness between other "live" objects in
01794    * the same process. The uniqueness of this name is therefore only
01795    * valid for the life of <object>.
01796    */
01797   extern ACE_Export
01798   void unique_name (const void *object,
01799                     char *name,
01800                     size_t length);
01801 #if defined (ACE_USES_WCHAR)
01802   extern ACE_Export
01803   void unique_name (const void *object,
01804                     wchar_t *name,
01805                     size_t length);
01806 #endif /* ACE_USES_WCHAR */
01807 } /* namespace ACE_OS */
01808 
01809 ACE_END_VERSIONED_NAMESPACE_DECL
01810 
01811 #if !defined (ACE_WIN32)
01812 
01813 extern "C"
01814 {
01815   typedef struct
01816   {
01817 #if (defined (ACE_HAS_PTHREADS) && defined (_POSIX_THREAD_PROCESS_SHARED) && !defined (ACE_LACKS_CONDATTR_PSHARED)) || \
01818     (!defined (ACE_USES_FIFO_SEM) && \
01819       (!defined (ACE_HAS_POSIX_SEM) || !defined (ACE_HAS_POSIX_SEM_TIMEOUT) || defined (ACE_LACKS_NAMED_POSIX_SEM)))
01820     /// Protect critical section.
01821     ACE_mutex_t lock_;
01822     /// Keeps track of waiters.
01823     ACE_cond_t condition_;
01824 #else
01825 # if (defined (ACE_HAS_PTHREADS) && defined (_POSIX_THREAD_PROCESS_SHARED) && !defined (ACE_LACKS_MUTEXATTR_PSHARED)) || \
01826      (!defined (ACE_USES_FIFO_SEM) && (!defined (ACE_HAS_POSIX_SEM) || defined (ACE_LACKS_NAMED_POSIX_SEM)))
01827     /// Protect critical section.
01828     ACE_mutex_t lock_;
01829 # endif
01830 #endif
01831 
01832     /// Object type.
01833     int type_;
01834 
01835     /// Specifies if this is an auto- or manual-reset event.
01836     int manual_reset_;
01837 
01838     /// "True" if signaled.
01839     int is_signaled_;
01840 
01841     /// Special bool for auto_events alone
01842     /**
01843      * The semantics of auto events forces us to introduce this extra
01844      * variable to ensure that the thread is not woken up
01845      * spuriously. Please see event_wait and event_timedwait () to see
01846      * how this is used for auto_events.
01847      * @todo This is a hack that needs revisiting after x.4
01848      */
01849     bool auto_event_signaled_;
01850 
01851     /// Number of waiting threads.
01852     unsigned long waiting_threads_;
01853 
01854     /// Signal count
01855     unsigned long signal_count_;
01856   } ACE_eventdata_t;
01857 }
01858 
01859 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
01860 
01861 /**
01862  * @class ACE_event_t
01863  *
01864  * @brief Wrapper for NT events on UNIX.
01865  */
01866 class ACE_Export ACE_event_t
01867 {
01868   friend int ACE_OS::event_init(ACE_event_t*, int, int, int, const char*, void*,int);
01869   friend int ACE_OS::event_destroy(ACE_event_t*);
01870   friend int ACE_OS::event_wait(ACE_event_t*);
01871   friend int ACE_OS::event_timedwait(ACE_event_t*, ACE_Time_Value*, int);
01872   friend int ACE_OS::event_signal(ACE_event_t*);
01873   friend int ACE_OS::event_pulse(ACE_event_t*);
01874   friend int ACE_OS::event_reset(ACE_event_t*);
01875 protected:
01876 
01877   /// Event name if process shared.
01878   char* name_;
01879 
01880   /// Event data
01881   ACE_eventdata_t* eventdata_;
01882 
01883 #if (!defined (ACE_HAS_PTHREADS) || !defined (_POSIX_THREAD_PROCESS_SHARED) || defined (ACE_LACKS_CONDATTR_PSHARED)) && \
01884   (defined (ACE_USES_FIFO_SEM) || \
01885     (defined (ACE_HAS_POSIX_SEM) && defined (ACE_HAS_POSIX_SEM_TIMEOUT) && !defined (ACE_LACKS_NAMED_POSIX_SEM)))
01886   /// Keeps track of waiters.
01887   ACE_sema_t semaphore_;
01888 
01889 # if (!defined (ACE_HAS_PTHREADS) || !defined (_POSIX_THREAD_PROCESS_SHARED) || defined (ACE_LACKS_MUTEXATTR_PSHARED)) && \
01890      (defined (ACE_USES_FIFO_SEM) || (defined (ACE_HAS_POSIX_SEM) && !defined (ACE_LACKS_NAMED_POSIX_SEM)))
01891     /// Protect critical section.
01892   ACE_sema_t lock_;
01893 # endif
01894 #endif
01895 };
01896 
01897 ACE_END_VERSIONED_NAMESPACE_DECL
01898 
01899 #endif /* ACE_WIN32 */
01900 
01901 #if defined (ACE_MT_SAFE) && (ACE_MT_SAFE != 0)
01902 
01903 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
01904 
01905 /**
01906  * @class ACE_OS_Thread_Mutex_Guard
01907  *
01908  * This data structure is meant to be used within an ACE_OS
01909  * function.  It performs automatic aquisition and release of
01910  * an ACE_thread_mutex_t.
01911  *
01912  * If an object of this class is instantiated before ACE_Object_Manager is
01913  * initialized, it will not do anything. This is because this class is
01914  * used only with the ACE_OS_GUARD macro which is passing a reference to
01915  * one of the preallocated Object Manager locks. If the object manager
01916  * hasn't been initialized yet, the lock reference is bogus. This is an
01917  * acceptable tradeoff since in cases where the lock reference is bogus,
01918  * there isn't multithreaded access. Please see detailed comments in
01919  * Object_Manager.h for further information.
01920  *
01921  * For internal use only by ACE_OS.
01922  */
01923 class ACE_OS_Thread_Mutex_Guard
01924 {
01925 public:
01926   /// Implicitly and automatically acquire the lock.
01927   ACE_OS_Thread_Mutex_Guard (ACE_thread_mutex_t &m);
01928 
01929   /// Implicitly release the lock.
01930   ~ACE_OS_Thread_Mutex_Guard (void);
01931 
01932   /// Explicitly acquire the lock.
01933   int acquire (void);
01934 
01935   /// Explicitly release the lock.
01936   int release (void);
01937 
01938 protected:
01939   /// Reference to the mutex.
01940   ACE_thread_mutex_t &lock_;
01941 
01942   /// Keeps track of whether we acquired the lock or failed.
01943   int owner_;
01944 
01945   // = Prevent assignment and initialization.
01946   ACE_OS_Thread_Mutex_Guard &operator= (const ACE_OS_Thread_Mutex_Guard &);
01947   ACE_OS_Thread_Mutex_Guard (const ACE_OS_Thread_Mutex_Guard &);
01948 };
01949 
01950 /**
01951  * @class ACE_OS_Recursive_Thread_Mutex_Guard
01952  *
01953  * @brief For internal use only by ACE_OS.
01954  *
01955  * This data structure is meant to be used within an ACE_OS
01956  * function.  It performs automatic aquisition and release of
01957  * an ACE_recursive_thread_mutex_t.
01958  *
01959  * If an object of this class is instantiated before ACE_Object_Manager is
01960  * initialized, it will not do anything. This is because this class is
01961  * used only with the ACE_TSS_GUARD macro which is passing a reference to
01962  * one of the preallocated Object Manager locks. If the object manager
01963  * hasn't been initialized yet, the lock reference is bogus. This is an
01964  * acceptable tradeoff since in cases where the lock reference is bogus,
01965  * there isn't multithreaded access. Please see detailed comments in
01966  * Object_Manager.h for further information.
01967  */
01968 class ACE_OS_Recursive_Thread_Mutex_Guard
01969 {
01970 public:
01971   /// Implicitly and automatically acquire the lock.
01972   ACE_OS_Recursive_Thread_Mutex_Guard (ACE_recursive_thread_mutex_t &m);
01973 
01974   /// Implicitly release the lock.
01975   ~ACE_OS_Recursive_Thread_Mutex_Guard (void);
01976 
01977   /// Explicitly acquire the lock.
01978   int acquire (void);
01979 
01980   /// Explicitly release the lock.
01981   int release (void);
01982 
01983 protected:
01984   /// Reference to the mutex.
01985   ACE_recursive_thread_mutex_t &lock_;
01986 
01987   /// Keeps track of whether we acquired the lock or failed.
01988   int owner_;
01989 
01990   // = Prevent assignment and initialization.
01991   ACE_OS_Recursive_Thread_Mutex_Guard &operator= (
01992     const ACE_OS_Recursive_Thread_Mutex_Guard &);
01993   ACE_OS_Recursive_Thread_Mutex_Guard (
01994     const ACE_OS_Recursive_Thread_Mutex_Guard &);
01995 };
01996 
01997 ACE_END_VERSIONED_NAMESPACE_DECL
01998 
01999 // used in time and unistd
02000 # define ACE_OS_GUARD \
02001   ACE_OS_Thread_Mutex_Guard ace_os_guard__ (*(ACE_thread_mutex_t *) \
02002     ACE_OS_Object_Manager::preallocated_object[ \
02003       ACE_OS_Object_Manager::ACE_OS_MONITOR_LOCK]);
02004 
02005 // used in Thread
02006 # define ACE_TSS_CLEANUP_GUARD \
02007   ACE_OS_Recursive_Thread_Mutex_Guard ace_tss_cleanup_guard__ (*(ACE_recursive_thread_mutex_t *) \
02008     ACE_OS_Object_Manager::preallocated_object[ \
02009       ACE_OS_Object_Manager::ACE_TSS_CLEANUP_LOCK]);
02010 
02011 // used in Thread
02012 # define ACE_TSS_BASE_GUARD \
02013   ACE_OS_Recursive_Thread_Mutex_Guard ace_tss_base_guard__ (*(ACE_recursive_thread_mutex_t *) \
02014     ACE_OS_Object_Manager::preallocated_object[ \
02015       ACE_OS_Object_Manager::ACE_TSS_BASE_LOCK]);
02016 
02017 #else  /* ! ACE_MT_SAFE */
02018 # define ACE_OS_GUARD
02019 # define ACE_TSS_CLEANUP_GUARD
02020 # define ACE_TSS_BASE_GUARD
02021 #endif /* ! ACE_MT_SAFE */
02022 
02023 # if defined (ACE_HAS_INLINED_OSCALLS)
02024 #   if defined (ACE_INLINE)
02025 #     undef ACE_INLINE
02026 #   endif /* ACE_INLINE */
02027 #   define ACE_INLINE inline
02028 #   include "ace/OS_NS_Thread.inl"
02029 # endif /* ACE_HAS_INLINED_OSCALLS */
02030 
02031 # include /**/ "ace/post.h"
02032 #endif /* ACE_OS_NS_THREAD_H */

Generated on Sun Jan 27 12:05:33 2008 for ACE by doxygen 1.3.6