NAME
ACE_Reactor -
An object oriented event demultiplexor and event handler
dispatcher.
SYNOPSIS
#include <ace/Reactor.h>
class ACE_Reactor
{
public:
enum { DEFAULT_SIZE = ACE_DEFAULT_REACTOR_SIZE,
GET_MASK = 1,
SET_MASK = 2,
ADD_MASK = 3,
CLR_MASK = 4 };
ACE_Reactor (ACE_Sig_Handler * = 0);
ACE_Reactor (size_t size, int restart = 0, ACE_Sig_Handler * = 0);
virtual int open (
size_t size = DEFAULT_SIZE,
int restart = 0,
ACE_Sig_Handler * = 0
);
virtual void close (void);
virtual ~ACE_Reactor (void);
virtual int schedule_timer (
ACE_Event_Handler *,
const void *arg,
const ACE_Time_Value &delta,
const ACE_Time_Value &interval = ACE_Time_Value::zero
);
virtual int cancel_timer (ACE_Event_Handler *event_handler);
virtual int cancel_timer (int timer_id, const void **arg = 0);
virtual int handle_events (ACE_Time_Value *how_long = 0);
virtual int handle_events (ACE_Time_Value &how_long);
virtual int register_handler (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
virtual int register_handler (
ACE_HANDLE handle,
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
virtual int register_handler (
const ACE_Handle_Set &handles,
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
virtual int register_handler (
int signum,
ACE_Event_Handler *new_sh,
ACE_Sig_Action *new_disp = 0,
ACE_Event_Handler **old_sh = 0,
ACE_Sig_Action *old_disp = 0
);
virtual int register_handler (
const ACE_Sig_Set &sigset,
ACE_Event_Handler *new_sh,
ACE_Sig_Action *new_disp = 0
);
virtual int remove_handler (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
virtual int remove_handler (ACE_HANDLE handle, ACE_Reactor_Mask);
virtual int remove_handler (
const ACE_Handle_Set &handle_set,
ACE_Reactor_Mask
);
virtual int remove_handler (
int signum,
ACE_Sig_Action *new_disp,
ACE_Sig_Action *old_disp = 0,
int sigkey = -1
);
virtual int remove_handler (const ACE_Sig_Set &sigset);
virtual int suspend_handler (ACE_Event_Handler *eh);
virtual int suspend_handler (ACE_HANDLE handle);
virtual int resume_handler (ACE_Event_Handler *eh);
virtual int resume_handler (ACE_HANDLE handle);
virtual int suspend_handlers (void);
virtual int resume_handlers (void);
virtual int handler (
ACE_HANDLE handle,
ACE_Reactor_Mask mask,
ACE_Event_Handler **eh = 0
);
virtual int handler (int signum, ACE_Event_Handler ** = 0);
virtual int schedule_wakeup (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
virtual int schedule_wakeup (
ACE_HANDLE handle,
ACE_Reactor_Mask mask
);
virtual int cancel_wakeup (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
virtual int cancel_wakeup (
ACE_HANDLE handle,
ACE_Reactor_Mask mask
);
virtual int mask_ops (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask,
int ops
);
virtual int mask_ops (
ACE_HANDLE handle,
ACE_Reactor_Mask mask,
int ops
);
virtual int ready_ops (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask,
int ops
);
virtual int ready_ops (
ACE_HANDLE handle,
ACE_Reactor_Mask,
int ops
);
virtual int notify (
ACE_Event_Handler * = 0,
ACE_Reactor_Mask = ACE_Event_Handler::EXCEPT_MASK
);
void requeue_position (int);
int requeue_position (void);
void owner (ACE_thread_t n_id, ACE_thread_t *o_id = 0);
int owner (ACE_thread_t *);
void dump (void) const;
ACE_ALLOC_HOOK_DECLARE;
protected:
virtual int attach (
ACE_HANDLE handle,
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
virtual int detach (ACE_HANDLE handle, ACE_Reactor_Mask);
virtual int suspend (ACE_HANDLE handle);
virtual int resume (ACE_HANDLE handle);
virtual int remove_handlers (
const ACE_Handle_Set &handles,
ACE_Reactor_Mask
);
virtual int register_handlers (
const ACE_Handle_Set &handles,
ACE_Event_Handler *handler,
ACE_Reactor_Mask mask
);
virtual int handler_i (
ACE_HANDLE handle,
ACE_Reactor_Mask,
ACE_Event_Handler ** = 0
);
virtual int handler_i (int signum, ACE_Event_Handler ** = 0);
virtual int any_ready (void) const;
virtual int handle_error (void);
virtual int check_handles (void);
virtual int bit_ops (
ACE_HANDLE handle,
ACE_Reactor_Mask mask,
ACE_Handle_Set &rd,
ACE_Handle_Set &wr,
ACE_Handle_Set &ex,
int ops
);
virtual int fill_in_ready (
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Handle_Set &
);
virtual int wait_for_multiple_events (
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Time_Value *
);
virtual void dispatch (
int,
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Handle_Set &
);
virtual void notify_handle (
ACE_HANDLE handle,
ACE_Reactor_Mask mask,
ACE_Handle_Set &,
ACE_Event_Handler *eh,
ACE_EH_PTMF callback
);
ACE_Timer_Queue *timer_queue_;
ACE_Handler_Repository handler_rep_;
ACE_Sig_Handler *signal_handler_;
int delete_signal_handler_;
ACE_Handle_Set rd_handle_mask_;
ACE_Handle_Set wr_handle_mask_;
ACE_Handle_Set ex_handle_mask_;
ACE_Handle_Set rd_handle_mask_ready_;
ACE_Handle_Set wr_handle_mask_ready_;
ACE_Handle_Set ex_handle_mask_ready_;
int restart_;
int requeue_position_;
int initialized_;
ACE_thread_t owner_;
ACE_Notification_Handler notification_handler_;
ACE_Reactor_Token token_;
void renew (void);
friend class ACE_Notification_Handler;
friend class ACE_Handler_Repository;
pollfd *handle_sets_to_poll_fds (ACE_HANDLE &width);
void poll_fds_to_handle_sets (
ACE_HANDLE width,
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Handle_Set &,
int nfound
);
pollfd *poll_h_;
private:
ACE_Time_Value timer_skew_;
ACE_Reactor (const ACE_Reactor &);
ACE_Reactor &operator = (const ACE_Reactor &);
};
DESCRIPTION
The ACE_Reactor is an object-oriented event demultiplexor
and event handler dispatcher. The sources of events that the
ACE_Reactor waits for and dispatches includes I/O events,
signals, and timer events.
Initialization and termination methods.
ACE_Reactor (ACE_Sig_Handler * = 0);
Initialize the new ACE_Reactor with the default size.
ACE_Reactor (size_t size, int restart = 0, ACE_Sig_Handler * = 0);
Initialize the new ACE_Reactor of size size.
virtual int open (
size_t size = DEFAULT_SIZE,
int restart = 0,
ACE_Sig_Handler * = 0
);
Initialize the new ACE_Reactor of size size.
virtual void close (void);
Close down the reactor and release all of its resources.
virtual ~ACE_Reactor (void);
Close down the reactor and release all of its resources.
Timer management.
virtual int schedule_timer (
ACE_Event_Handler *,
const void *arg,
const ACE_Time_Value &delta,
const ACE_Time_Value &interval = ACE_Time_Value::zero
);
Schedule an event_handler that will expire after delay amount
of time. If it expires then arg is passed in as the value to
the event_handler's handle_timeout callback method. If
interval is != to ACE_Time_Value::zero then it is used to
reschedule the event_handler automatically. This method
returns a timer handle that uniquely identifies the
event_handler in an internal list. This timer handle can be
used to cancel an event_handler before it expires. The
cancellation ensures that timer_ids are unique up to values of
greater than 2 billion timers. As long as timers don't stay
around longer than this there should be no problems with
accidentally deleting the wrong timer.
virtual int cancel_timer (ACE_Event_Handler *event_handler);
Cancel all event_handlers that match the address of
event_handler.
virtual int cancel_timer (int timer_id, const void **arg = 0);
Cancel the single ACE_Event_Handler that matches the timer_id
value (which was returned from the schedule method). If arg is
non-NULL then it will be set to point to the ``magic cookie''
argument passed in when the Event_Handler was registered. This
makes it possible to free up the memory and avoid memory leaks.
Event loop drivers.
virtual int handle_events (ACE_Time_Value *how_long = 0);
Main event loop driver that blocks for how_long before
returning (will return earlier if I/O or signal events occur).
Note that how_long can be 0, in which case this method blocks
until I/O events or signals occur.
virtual int handle_events (ACE_Time_Value &how_long);
Main event loop driver that blocks for how_long before
returning (will return earlier if I/O or signal events occur).
Register and remove Handlers.
virtual int register_handler (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
Register an Event_Handler eh with a particular mask. Note
that the Reactor will call eh-get_handle() to extract the
underlying I/O handle).
virtual int register_handler (
ACE_HANDLE handle,
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
Register an Event_Handler eh with a particular mask. Note
that since the handle is given the Reactor will *not* call
eh-get_handle() to extract the underlying I/O handle).
virtual int register_handler (
const ACE_Handle_Set &handles,
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
Register eh with all the handles in the Handle_Set.
virtual int register_handler (
int signum,
ACE_Event_Handler *new_sh,
ACE_Sig_Action *new_disp = 0,
ACE_Event_Handler **old_sh = 0,
ACE_Sig_Action *old_disp = 0
);
Register new_sh to handle the signal signum using the
new_disp. Returns the old_sh that was previously registered
(if any), along with the old_disp of the signal handler.
virtual int register_handler (
const ACE_Sig_Set &sigset,
ACE_Event_Handler *new_sh,
ACE_Sig_Action *new_disp = 0
);
Registers new_sh to handle a set of signals sigset using the
new_disp.
virtual int remove_handler (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
Removes the mask binding of eh from the Reactor. If there
are no more bindings for this eh then it is removed from the
Reactor. Note that the Reactor will call eh-get_handle() to
extract the underlying I/O handle.
virtual int remove_handler (ACE_HANDLE handle, ACE_Reactor_Mask);
Removes the mask bind of Event_Handler whose handle is
handle from the Reactor. If there are no more bindings for
this eh then it is removed from the Reactor.
virtual int remove_handler (
const ACE_Handle_Set &handle_set,
ACE_Reactor_Mask
);
Removes all the mask bindings for handles in the handle_set
bind of Event_Handler. If there are no more bindings for any
of these handlers then they are removed from the Reactor.
virtual int remove_handler (
int signum,
ACE_Sig_Action *new_disp,
ACE_Sig_Action *old_disp = 0,
int sigkey = -1
);
Remove the ACE_Event_Handler currently associated with signum.
sigkey is ignored in this implementation since there is only
one instance of a signal handler. Install the new disposition
(if given) and return the previous disposition (if desired by the
caller). Returns 0 on success and -1 if signum is invalid.
virtual int remove_handler (const ACE_Sig_Set &sigset);
Calls remove_handler for every signal in sigset.
Suspend and resume Handlers.
virtual int suspend_handler (ACE_Event_Handler *eh);
Temporarily suspend the Event_Handler associated with eh.
virtual int suspend_handler (ACE_HANDLE handle);
Temporarily suspend the Event_Handler associated with handle.
virtual int resume_handler (ACE_Event_Handler *eh);
Resume a temporarily suspend Event_Handler associated with
eh.
virtual int resume_handler (ACE_HANDLE handle);
Resume a temporarily suspended Event_Handler associated with
handle.
virtual int suspend_handlers (void);
Suspend all the Event_Handlers in the Reactor.
virtual int resume_handlers (void);
Resume all the Event_Handlers in the Reactor.
Misc. Handler operations.
virtual int handler (
ACE_HANDLE handle,
ACE_Reactor_Mask mask,
ACE_Event_Handler **eh = 0
);
Check to see if handle is associated with a valid Event_Handler
bound to mask. Return the eh associated with this handler
if eh != 0.
virtual int handler (int signum, ACE_Event_Handler ** = 0);
Check to see if signum is associated with a valid Event_Handler
bound to a signal. Return the eh associated with this
handler if eh != 0.
High-level Event_Handler scheduling operations
virtual int schedule_wakeup (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
ADD the dispatch MASK "bit" bound with the eh and the mask.
virtual int schedule_wakeup (
ACE_HANDLE handle,
ACE_Reactor_Mask mask
);
ADD the dispatch MASK "bit" bound with the handle and the mask.
virtual int cancel_wakeup (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
CLR the dispatch MASK "bit" bound with the eh and the mask.
virtual int cancel_wakeup (ACE_HANDLE handle, ACE_Reactor_Mask mask);
CLR the dispatch MASK "bit" bound with the handle and the mask.
Low-level dispatch mask manipulation methods.
virtual int mask_ops (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask,
int ops
);
GET/SET/ADD/CLR the dispatch MASK "bit" bound with the eh and
mask.
virtual int mask_ops (
ACE_HANDLE handle,
ACE_Reactor_Mask mask,
int ops
);
GET/SET/ADD/CLR the dispatch MASK "bit" bound with the handle
and mask.
Ready bit manipulation methods.
virtual int ready_ops (
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask,
int ops
);
GET/SET/ADD/CLR the ready "bit" bound with the eh and mask.
virtual int ready_ops (ACE_HANDLE handle, ACE_Reactor_Mask, int ops);
GET/SET/ADD/CLR the ready "bit" bound with the handle and mask.
virtual int notify (
ACE_Event_Handler * = 0,
ACE_Reactor_Mask = ACE_Event_Handler::EXCEPT_MASK
);
Wakeup ACE_Reactor if currently blocked in select()/poll(). Pass
over both the Event_Handler *and* the mask in order to allow the
caller to dictate which Event_Handler method the receiver
invokes.
Get/set position that the main ACE_Reactor thread is requeued
in the list of waiters during a notify() callback.
void requeue_position (int);
int requeue_position (void);
Get/set the current
owner" of the thread (i.e., the only"
thread that can perform a handle_events()).
void owner (ACE_thread_t n_id, ACE_thread_t *o_id = 0);
Set the new owner of the thread and return the old owner.
int owner (ACE_thread_t *);
Return the current owner of the thread.
void dump (void) const;
Dump the state of an object.
ACE_ALLOC_HOOK_DECLARE;
Declare the dynamic allocation hooks.
Internal methods that do the actual work (most of these
assume that locks are held).
virtual int attach (
ACE_HANDLE handle,
ACE_Event_Handler *eh,
ACE_Reactor_Mask mask
);
Do the work of actually binding the handle and eh with the
mask.
virtual int detach (ACE_HANDLE handle, ACE_Reactor_Mask);
Do the work of actually unbinding the handle and eh with the
mask.
virtual int suspend (ACE_HANDLE handle);
Suspend the Event_Handler associated with handle
virtual int resume (ACE_HANDLE handle);
Resume the Event_Handler associated with handle
virtual int remove_handlers (
const ACE_Handle_Set &handles,
ACE_Reactor_Mask
);
virtual int register_handlers (
const ACE_Handle_Set &handles,
ACE_Event_Handler *handler,
ACE_Reactor_Mask mask
);
Register a set of handles.
virtual int handler_i (
ACE_HANDLE handle,
ACE_Reactor_Mask,
ACE_Event_Handler ** = 0
);
Implement the public handler method.
virtual int handler_i (int signum, ACE_Event_Handler ** = 0);
Implement the public handler method.
virtual int any_ready (void) const;
virtual int handle_error (void);
Take corrective action when errors occur.
virtual int check_handles (void);
Make sure the handles are all valid.
virtual int bit_ops (
ACE_HANDLE handle,
ACE_Reactor_Mask mask,
ACE_Handle_Set &rd,
ACE_Handle_Set &wr,
ACE_Handle_Set &ex,
int ops
);
Allow manipulation of the dispatch mask and ready ops mask.
virtual int fill_in_ready (
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Handle_Set &
);
Check if there are any bits enabled in the ready_ops set.
virtual int wait_for_multiple_events (
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Time_Value *
);
Wait for events to occur.
virtual void dispatch (
int,
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Handle_Set &
);
Dispatch timers and I/O event handlers once events have occurred.
virtual void notify_handle (
ACE_HANDLE handle,
ACE_Reactor_Mask mask,
ACE_Handle_Set &,
ACE_Event_Handler *eh,
ACE_EH_PTMF callback
);
Notify the appropriate callback in the context of the eh
associated with handle that a particular event has occurred.
ACE_Timer_Queue *timer_queue_;
Defined as a pointer to allow overriding by derived classes...
ACE_Handler_Repository handler_rep_;
Pointer to an array of ACE_Event_Handler *s used to keep track
of the user-defined callbacks.
ACE_Sig_Handler *signal_handler_;
Handle signals without requiring global/static variables.
int delete_signal_handler_;
Keeps track of whether we should delete the signal handler.
Track which handles we are interested
for various types of (reading, writing, and exception) events.
The following three Handle_Sets are waited for by poll() or
select().
ACE_Handle_Set rd_handle_mask_;
ACE_Handle_Set wr_handle_mask_;
ACE_Handle_Set ex_handle_mask_;
Keep track of events that we'd like to have dispatched
*without* requiring poll() or select() to wait...
ACE_Handle_Set rd_handle_mask_ready_;
ACE_Handle_Set wr_handle_mask_ready_;
ACE_Handle_Set ex_handle_mask_ready_;
int restart_;
Restart automatically when interrupted
int requeue_position_;
Position that the main ACE_Reactor thread is requeued in the list
of waiters during a notify() callback. If this value == -1 we
are requeued at the end of the list. Else if it's 0 then we are
requeued at the front of the list. Else if it's 1 then that
indicates the number of waiters to skip over.
int initialized_;
True if we've been initialized yet...
ACE_thread_t owner_;
The original thread that created this Reactor.
ACE_Notification_Handler notification_handler_;
Callback object that unblocks the ACE_Reactor if it's sleeping.
ACE_Reactor_Token token_;
Synchronization token for the MT_SAFE ACE_Reactor.
void renew (void);
Enqueue ourselves into the list of waiting threads at the
appropriate point specified by requeue_position_.
friend class ACE_Notification_Handler;
friend class ACE_Handler_Repository;
Convert to and from the select() to poll() types.
pollfd *handle_sets_to_poll_fds (ACE_HANDLE &width);
void poll_fds_to_handle_sets (
ACE_HANDLE width,
ACE_Handle_Set &,
ACE_Handle_Set &,
ACE_Handle_Set &,
int nfound
);
pollfd *poll_h_;
Pointer to the array of pollfd handles for poll() version.
AUTHOR
Doug Schmidt
LIBRARY
ace