/* -*- C++ -*- */ //============================================================================= /** * @file TP_Reactor.h * * $Id$ * * The (aka, Thread Pool Reactor) uses the * Leader/Followers pattern to demultiplex events among a pool of * threads. When using a thread pool reactor, an application * pre-spawns a _fixed_ number of threads. When these threads * invoke the 's method, one thread * will become the leader and wait for an event. The other * follower threads will queue up waiting for their turn to become * the leader. When an event occurs, the leader will pick a * follower to become the leader and go on to handle the event. * The consequence of using is the amortization of * the costs used to creating threads. The context switching cost * will also reduce. More over, the total resources used by * threads are bounded because there are a fixed number of threads. * * * @author Irfan Pyarali * @author Nanbor Wang */ //============================================================================= #ifndef ACE_TP_REACTOR_H #define ACE_TP_REACTOR_H #include "ace/pre.h" #include "ace/Select_Reactor.h" #include "ace/Log_Msg.h" #if !defined (ACE_LACKS_PRAGMA_ONCE) # pragma once #endif /* ACE_LACKS_PRAGMA_ONCE */ /** * @class ACE_EH_Dispatch_Info * * @brief This structure contains information of the activated event * handler. */ class ACE_Export ACE_EH_Dispatch_Info { public: ACE_EH_Dispatch_Info (void); void set (ACE_HANDLE handle, ACE_Event_Handler *event_handler, ACE_Reactor_Mask mask, ACE_EH_PTMF callback); void reset (void); int dispatch (void) const; ACE_HANDLE handle_; ACE_Event_Handler *event_handler_; ACE_Reactor_Mask mask_; ACE_EH_PTMF callback_; int dispatch_; private: ACE_UNIMPLEMENTED_FUNC (ACE_EH_Dispatch_Info (const ACE_EH_Dispatch_Info &)) ACE_UNIMPLEMENTED_FUNC (ACE_EH_Dispatch_Info &operator= (const ACE_EH_Dispatch_Info &)) }; /** * @class ACE_TP_Token_Guard * * @brief A helper class that helps grabbing, releasing and waiting * on tokens for a thread that tries calling handle_events (). * * In short, this class will be owned by one thread by creating on the * stack. This class gives the status of the ownership of the token * and manages the ownership */ class ACE_Export ACE_TP_Token_Guard { public: /// Constructor that will grab the token for us ACE_TP_Token_Guard (ACE_Select_Reactor_Token &token); /// Destructor. This will release the token if it hasnt been /// released till this point ~ACE_TP_Token_Guard (void); /// Release the token .. void release_token (void); /// Returns whether the thread that created this object ownes the /// token or not. int is_owner (void); /// A helper method that grabs the token for us, after which the /// thread that owns that can do some actual work. /// @@todo: Should probably be called acquire_read_token () int grab_token (ACE_Time_Value *max_wait_time = 0); /* A helper method that grabs the token for us, after which the * thread that owns that can do some actual work. This differs from * grab_token () as it uses acquire () to get the token instead of * acquire_read () */ int acquire_token (ACE_Time_Value *max_wait_time = 0); private: /// The Select Reactor token. ACE_Select_Reactor_Token &token_; /// Flag that indicate whether the thread that created this object /// owns the token or not. A value of 0 indicates that this class /// hasnt got the token (and hence the thread) and a value of 1 /// vice-versa. int owner_; private: ACE_UNIMPLEMENTED_FUNC (ACE_TP_Token_Guard (void)) }; /** * @class ACE_TP_Reactor * * @brief Specialization of Select Reactor to support thread-pool based * event dispatching. * * One of the short comings of the Select_Reactor in ACE is that * it did not support a thread pool based event dispatching * model, similar to the one in WFMO_Reactor. In * Select_Reactor, only thread can be blocked in * at any given time. * A new Reactor has been added to ACE that removes this * short-coming. TP_Reactor is a specialization of Select * Reactor to support thread-pool based event dispatching. This * Reactor takes advantage of the fact that events reported by *