3 // =========================================================================
5 * @file Dev_Poll_Reactor.h
7 * @c /dev/poll (or Linux @c sys_epoll) based Reactor implementation.
9 * @author Ossama Othman <ossama@dre.vanderbilt.edu>
11 // =========================================================================
14 #ifndef ACE_DEV_POLL_REACTOR_H
15 #define ACE_DEV_POLL_REACTOR_H
17 #include /**/ "ace/pre.h"
19 #include /**/ "ace/ACE_export.h"
21 #if !defined (ACE_LACKS_PRAGMA_ONCE)
23 #endif /* ACE_LACKS_PRAGMA_ONCE */
25 #if defined (ACE_HAS_EVENT_POLL) && defined (ACE_HAS_DEV_POLL)
26 # error ACE_HAS_EVENT_POLL and ACE_HAS_DEV_POLL are mutually exclusive.
27 #endif /* ACE_HAS_EVENT_POLL && defined ACE_HAS_DEV_POLL */
29 #if defined (ACE_HAS_EVENT_POLL) || defined (ACE_HAS_DEV_POLL)
32 #include "ace/Lock_Adapter_T.h"
33 #include "ace/Reactor_Impl.h"
34 #include "ace/Reactor_Token_T.h"
35 #include "ace/Token.h"
37 #if defined (ACE_HAS_REACTOR_NOTIFICATION_QUEUE)
38 # include "ace/Notification_Queue.h"
39 #endif /* ACE_HAS_REACTOR_NOTIFICATION_QUEUE */
41 #if defined (ACE_HAS_DEV_POLL)
43 #elif defined (ACE_HAS_EVENT_POLL)
44 # include "ace/Array_Map.h"
45 # include /**/ <sys/epoll.h>
48 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
50 // Forward declarations
51 class ACE_Sig_Handler
;
52 class ACE_Dev_Poll_Reactor
;
54 // ---------------------------------------------------------------------
57 * @class ACE_Dev_Poll_Reactor_Notify
59 * @brief Event handler used for unblocking the ACE_Dev_Poll_Reactor
60 * from its event loop.
62 * This event handler is used internally by the ACE_Dev_Poll_Reactor
63 * as a means to allow a thread other then the one running the event
64 * loop to unblock the event loop.
66 class ACE_Dev_Poll_Reactor_Notify
: public ACE_Reactor_Notify
70 ACE_Dev_Poll_Reactor_Notify ();
73 * @name Initialization and Termination Methods
75 * Methods called when initializing and terminating this event
78 virtual int open (ACE_Reactor_Impl
*,
79 ACE_Timer_Queue
*timer_queue
= 0,
80 int disable_notify
= 0);
84 * Called by a thread when it wants to unblock the Reactor_Impl.
85 * This wakes up the Reactor_Impl if currently blocked. Pass over
86 * both the Event_Handler and the mask to allow the caller to
87 * dictate which Event_Handler method the Reactor_Impl will
88 * invoke. The ACE_Time_Value indicates how long to block
89 * trying to notify the Reactor_Impl. If timeout == 0, the
90 * caller will block until action is possible, else will wait until
91 * the relative time specified in *timeout elapses).
93 virtual int notify (ACE_Event_Handler
*eh
= 0,
94 ACE_Reactor_Mask mask
= ACE_Event_Handler::EXCEPT_MASK
,
95 ACE_Time_Value
*timeout
= 0);
97 /// Unimplemented method required by pure virtual method in abstract
100 * This method's interface is not very compatible with this
101 * Reactor's design. It's not clear why this method is pure virtual
104 virtual int dispatch_notifications (int &number_of_active_handles
,
105 ACE_Handle_Set
&rd_mask
);
107 /// Returns the ACE_HANDLE of the notify pipe on which the reactor
108 /// is listening for notifications so that other threads can unblock
109 /// the Reactor_Impl.
110 virtual ACE_HANDLE
notify_handle ();
112 /// Verify whether the buffer has dispatchable info or not.
113 virtual int is_dispatchable (ACE_Notification_Buffer
&buffer
);
115 /// Handle one notify call represented in @a buffer. This could be
116 /// because of a thread trying to unblock the Reactor_Impl.
117 virtual int dispatch_notify (ACE_Notification_Buffer
&buffer
);
119 /// Read one notify call on the handle into @a buffer.
120 /// This could be because of a thread trying to unblock the Reactor_Impl.
121 virtual int read_notify_pipe (ACE_HANDLE handle
,
122 ACE_Notification_Buffer
&buffer
);
124 /// Called back by the ACE_Dev_Poll_Reactor when a thread wants to
126 virtual int handle_input (ACE_HANDLE handle
);
129 * Set the maximum number of times that the handle_input method
130 * will iterate and dispatch the ACE_Event_Handlers that are
131 * passed in via the notify queue before breaking out of the event
132 * loop. By default, this is set to -1, which means "iterate until
133 * the queue is empty." Setting this to a value like "1 or 2" will
134 * increase "fairness" (and thus prevent starvation) at the expense
135 * of slightly higher dispatching overhead.
137 virtual void max_notify_iterations (int);
140 * Get the maximum number of times that the handle_input method
141 * will iterate and dispatch the ACE_Event_Handlers that are
142 * passed in via the notify queue before breaking out of its event
145 virtual int max_notify_iterations ();
148 * Purge any notifications pending in this reactor for the specified
149 * ACE_Event_Handler object. Returns the number of notifications
150 * purged. Returns -1 on error.
152 virtual int purge_pending_notifications (
153 ACE_Event_Handler
* = 0,
154 ACE_Reactor_Mask
= ACE_Event_Handler::ALL_EVENTS_MASK
);
156 /// Dump the state of an object.
157 virtual void dump () const;
159 /// Method called by ACE_Dev_Poll_Reactor to obtain one notification.
160 /// THIS METHOD MUST BE CALLED WITH THE REACTOR TOKEN HELD!
162 /// @return -1 on error, else 0 and @arg nb has the notify to
163 /// dispatch. Note that the contained event handler may be
164 /// 0 if there were only wake-ups (no handlers to dispatch).
165 int dequeue_one (ACE_Notification_Buffer
&nb
);
167 ACE_ALLOC_HOOK_DECLARE
;
171 * Keep a back pointer to the ACE_Dev_Poll_Reactor. If this value
172 * if NULL then the ACE_Dev_Poll_Reactor has been initialized with
173 * disable_notify_pipe.
175 ACE_Dev_Poll_Reactor
*dp_reactor_
;
178 * Contains the ACE_HANDLE the ACE_Dev_Poll_Reactor is listening
179 * on, as well as the ACE_HANDLE that threads wanting the attention
180 * of the ACE_Dev_Poll_Reactor will write to.
182 ACE_Pipe notification_pipe_
;
185 * Keeps track of the maximum number of times that the
186 * ACE_Dev_Poll_Reactor_Notify::handle_input method will iterate and
187 * dispatch the ACE_Event_Handlers that are passed in via the
188 * notify pipe before breaking out of its recv loop. By default,
189 * this is set to -1, which means "iterate until the pipe is empty."
191 int max_notify_iterations_
;
193 #if defined (ACE_HAS_REACTOR_NOTIFICATION_QUEUE)
195 * @brief A user-space queue to store the notifications.
197 * The notification pipe has OS-specific size restrictions. That
198 * is, no more than a certain number of bytes may be stored in the
199 * pipe without blocking. This limit may be too small for certain
200 * applications. In this case, ACE can be configured to store all
201 * the events in user-space. The pipe is still needed to wake up
202 * the reactor thread, but only one event is sent through the pipe
205 ACE_Notification_Queue notification_queue_
;
206 #endif /* ACE_HAS_REACTOR_NOTIFICATION_QUEUE */
209 // ---------------------------------------------------------------------
212 * @class ACE_Dev_Poll_Reactor
214 * @brief A `/dev/poll' or `/dev/epoll' based Reactor implemenatation.
216 * @attention The Linux epoll implementation works quite well and is
217 * fully supported; however, the /dev/poll implementation is @em experimental.
219 * The ACE_Dev_Poll_Reactor uses the `/dev/poll' or '/dev/epoll'
220 * character devices to demultiplex events on a given set of file
221 * descriptors. Unlike @c select(), `/dev/poll' and `/dev/epoll' have
222 * no hard-coded limit on the number of file descriptors that may be
223 * handled at any given time. As such, the ACE_Dev_Poll_Reactor can
224 * generally handle a much larger number of file descriptors than
225 * @c select() -based reactors. Furthermore, since `/dev/poll' and
226 * `/dev/epoll' both return a set of file descriptors that are active,
227 * there is no need to "walk" the set of file descriptors to determine
228 * which ones are active, such as what is done with the @c select() and
229 * @c poll() system calls. All returned file descriptors are active.
230 * This makes event dispatching very efficient.
232 * @note In general, this reactor may only be used to demultiplex
233 * events on sockets. Demultiplexing events on pipes, for
234 * example may not work. This is due to a limitation in the
235 * underlying `/dev/poll' device driver.
237 * @note It is only possible to achieve millisecond timeout
238 * resolutions with the @c ACE_Dev_Poll_Reactor. However, the
239 * timeout resolution for timers is independent of the reactors
240 * timeout resolution. As such, it may be possible to achieve
241 * sub-millisecond timeout resolutions for timers but that is
242 * entirely platform dependent.
245 #if defined (ACE_MT_SAFE) && (ACE_MT_SAFE != 0)
246 typedef ACE_Token ACE_DEV_POLL_TOKEN
;
248 typedef ACE_Noop_Token ACE_DEV_POLL_TOKEN
;
249 #endif /* ACE_MT_SAFE && ACE_MT_SAFE != 0 */
250 typedef ACE_Reactor_Token_T
<ACE_DEV_POLL_TOKEN
> ACE_Dev_Poll_Reactor_Token
;
252 class ACE_Export ACE_Dev_Poll_Reactor
: public ACE_Reactor_Impl
255 * @struct Event_Tuple
257 * @brief Struct that collects event registration information for a handle.
259 * @internal Internal use only
261 * This struct merely provides a means to associate an event mask
262 * with an event handler. Such an association is needed since it is
263 * not possible to retrieve the event mask from the "interest set"
264 * stored in the `/dev/poll' or `/dev/epoll' driver. Without this
265 * external association, it would not be possible keep track of the
266 * event mask for a given event handler when suspending it or resuming
269 * @note An ACE_Handle_Set is not used since the number of handles may
270 * exceed its capacity (ACE_DEFAULT_SELECT_REACTOR_SIZE).
274 /// Constructor to set up defaults.
275 Event_Tuple (ACE_Event_Handler
*eh
= 0,
276 ACE_Reactor_Mask m
= ACE_Event_Handler::NULL_MASK
,
277 bool is_suspended
= false,
278 bool is_controlled
= false);
280 /// The event handler.
281 ACE_Event_Handler
*event_handler
;
283 /// The event mask for the above event handler.
284 ACE_Reactor_Mask mask
;
286 /// Flag that states whether or not the event handler is suspended.
289 /// Flag to say whether or not this handle is registered with epoll.
292 ACE_ALLOC_HOOK_DECLARE
;
296 // ---------------------------------------------------------------------
299 * @class Handler_Repository
303 * @brief Used to map ACE_HANDLEs onto the appropriate Event_Tuple.
305 * This class is simply a container that maps a handle to its
306 * corresponding event tuple. It is not meant for use outside of
307 * the Dev_Poll_Reactor.
309 * @note Calls to any method in this class, and any modification to a
310 * Event_Tuple returned from this class's methods, must be made
311 * while holding the repository lock.
313 class Handler_Repository
317 Handler_Repository ();
319 /// Initialize a repository that can map handles up to the value @a size.
320 /// Since the event tuples are accessed directly using the handle as
321 /// an index, @a size sets the maximum handle value, minus 1.
322 int open (size_t size
);
324 /// Close down the repository.
328 * @name Repository Manipulation Operations
330 * Methods used to search and modify the handler repository.
333 /// Return a pointer to the Event_Tuple associated with @a handle.
334 /// If there is none associated, returns 0 and sets errno.
335 Event_Tuple
*find (ACE_HANDLE handle
);
338 /// Bind the ACE_Event_Handler to the @c ACE_HANDLE with the
339 /// appropriate ACE_Reactor_Mask settings.
340 int bind (ACE_HANDLE handle
,
341 ACE_Event_Handler
*handler
,
342 ACE_Reactor_Mask mask
);
344 /// Remove the binding for @a handle; optionally decrement the associated
345 /// handler's reference count.
346 int unbind (ACE_HANDLE handle
, bool decr_refcnt
= true);
348 /// Remove all the registered tuples.
354 * @name Sanity Checking
356 * Methods used to prevent "out-of-range" errors when indexing the
357 * underlying handler array.
360 // Check the @a handle to make sure it's a valid @c ACE_HANDLE that
361 // within the range of legal handles (i.e., greater than or equal to
362 // zero and less than @c max_size_).
363 bool invalid_handle (ACE_HANDLE handle
) const;
365 // Check the handle to make sure it's a valid @c ACE_HANDLE that is
366 // within the range of currently registered handles (i.e., greater
367 // than or equal to zero and less than @c max_handlep1_).
368 bool handle_in_range (ACE_HANDLE handle
) const;
372 /// Returns the current table size.
373 size_t size () const;
375 /// Returns the maximum table size.
376 size_t max_size () const;
378 /// Dump the state of an object.
381 /// Declare the dynamic allocation hooks.
382 ACE_ALLOC_HOOK_DECLARE
;
385 /// Current number of handles.
388 /// Maximum number of handles.
391 /// The underlying array of event handlers.
393 * The array of event handlers is directly indexed directly using
394 * an @c ACE_HANDLE value. This is Unix-specific.
396 Event_Tuple
*handlers_
;
400 /// Initialize @c ACE_Dev_Poll_Reactor with the default size.
402 * The default size for the @c ACE_Dev_Poll_Reactor is the maximum
403 * number of open file descriptors for the process.
405 ACE_Dev_Poll_Reactor (ACE_Sig_Handler
* = 0,
406 ACE_Timer_Queue
* = 0,
407 int disable_notify_pipe
= 0,
408 ACE_Reactor_Notify
*notify
= 0,
409 int mask_signals
= 1,
410 int s_queue
= ACE_DEV_POLL_TOKEN::FIFO
);
412 /// Initialize ACE_Dev_Poll_Reactor with size @a size.
414 * @note On Unix platforms, the @a size parameter should be as large
415 * as the maximum number of file descriptors allowed for a
416 * given process. This is necessary since a file descriptor
417 * is used to directly index the array of event handlers
418 * maintained by the Reactor's handler repository. Direct
419 * indexing is used for efficiency reasons. If the size
420 * parameter is less than the process maximum, the process
421 * maximum will be decreased in order to prevent potential
424 ACE_Dev_Poll_Reactor (size_t size
,
425 bool restart
= false,
426 ACE_Sig_Handler
* = 0,
427 ACE_Timer_Queue
* = 0,
428 int disable_notify_pipe
= 0,
429 ACE_Reactor_Notify
*notify
= 0,
430 int mask_signals
= 1,
431 int s_queue
= ACE_DEV_POLL_TOKEN::FIFO
);
433 /// Close down and release all resources.
434 virtual ~ACE_Dev_Poll_Reactor ();
437 virtual int open (size_t size
,
438 bool restart
= false,
439 ACE_Sig_Handler
* = 0,
440 ACE_Timer_Queue
* = 0,
441 int disable_notify_pipe
= 0,
442 ACE_Reactor_Notify
* = 0);
445 * @param handle allows the reactor to check if the caller is
448 * @return 0 if the size of the current message has been put in
451 virtual int current_info (ACE_HANDLE handle
, size_t & /* size */);
453 /// Use a user specified signal handler instead.
454 virtual int set_sig_handler (ACE_Sig_Handler
*signal_handler
);
456 /// Set a user-specified timer queue.
457 virtual int timer_queue (ACE_Timer_Queue
*tq
);
459 /// Get the timer queue
460 /// @return The current @c ACE_Timer_Queue.
461 virtual ACE_Timer_Queue
*timer_queue () const;
463 /// Close down and release all resources.
464 virtual int close ();
466 // = Event loop drivers.
468 * Returns non-zero if there are I/O events "ready" for dispatching,
469 * but does not actually dispatch the event handlers. By default,
470 * don't block while checking this, i.e., "poll".
472 * @note It is only possible to achieve millisecond timeout
473 * resolutions with the @c ACE_Dev_Poll_Reactor.
475 virtual int work_pending (
476 const ACE_Time_Value
&max_wait_time
= ACE_Time_Value::zero
);
479 * This event loop driver blocks for up to @a max_wait_time before
480 * returning. It will return earlier if events occur. Note that
481 * @a max_wait_time can be 0, in which case this method blocks
482 * indefinitely until events occur.
484 * @a max_wait_time is decremented to reflect how much time this
485 * call took. For instance, if a time value of 3 seconds is passed
486 * to @c handle_events() and an event occurs after 2 seconds,
487 * @a max_wait_time will equal 1 second. This can be used if an
488 * application wishes to handle events for some fixed amount of
491 * The only difference between @c alertable_handle_events() and
492 * handle_events() is that in the alertable case, the event loop
493 * will return when the system queues an I/O completion routine or
494 * an Asynchronous Procedure Call.
496 * @return The total number of @c ACE_Event_Handlers that were
497 * dispatched, 0 if the @a max_wait_time elapsed without
498 * dispatching any handlers, or -1 if an error occurs.
500 * @note It is only possible to achieve millisecond timeout
501 * resolutions with the @c ACE_Dev_Poll_Reactor.
503 virtual int handle_events (ACE_Time_Value
*max_wait_time
= 0);
504 virtual int alertable_handle_events (ACE_Time_Value
*max_wait_time
= 0);
507 * This method is just like the one above, except the
508 * @a max_wait_time value is a reference and can therefore never be
511 * @note It is only possible to achieve millisecond timeout
512 * resolutions with the @c ACE_Dev_Poll_Reactor.
514 virtual int handle_events (ACE_Time_Value
&max_wait_time
);
515 virtual int alertable_handle_events (ACE_Time_Value
&max_wait_time
);
517 // = Event handling control.
520 * @return The status of Reactor. If this function returns 0, the
521 * reactor is actively handling events. If it returns
522 * non-zero, @c handle_events() and
523 * @c handle_alertable_events() return -1 immediately.
525 virtual int deactivated ();
528 * Control whether the Reactor will handle any more incoming events
529 * or not. If @a do_stop == 1, the Reactor will be disabled. By
530 * default, a reactor is in active state and can be
531 * deactivated/reactived as desired.
533 virtual void deactivate (int do_stop
);
535 // = Register and remove Handlers.
537 /// Register @a event_handler with @a mask. The I/O handle will
538 /// always come from get_handle on the event_handler.
539 virtual int register_handler (ACE_Event_Handler
*event_handler
,
540 ACE_Reactor_Mask mask
);
542 /// Register @a event_handler with @a mask. The I/O handle is
543 /// provided through the @a io_handle parameter.
544 virtual int register_handler (ACE_HANDLE io_handle
,
545 ACE_Event_Handler
*event_handler
,
546 ACE_Reactor_Mask mask
);
549 * Register an @a event_handler that will be notified when
550 * @a event_handle is signaled. @a mask specifies the network
551 * events that the @a event_handler is interested in.
553 virtual int register_handler (ACE_HANDLE event_handle
,
554 ACE_HANDLE io_handle
,
555 ACE_Event_Handler
*event_handler
,
556 ACE_Reactor_Mask mask
);
558 /// Register @a event_handler with all the @a handles in the @c
560 virtual int register_handler (const ACE_Handle_Set
&handles
,
561 ACE_Event_Handler
*event_handler
,
562 ACE_Reactor_Mask mask
);
565 * Register @a new_sh to handle the signal @a signum using the
566 * @a new_disp. Returns the @a old_sh that was previously
567 * registered (if any), along with the @a old_disp of the signal
570 virtual int register_handler (int signum
,
571 ACE_Event_Handler
*new_sh
,
572 ACE_Sig_Action
*new_disp
= 0,
573 ACE_Event_Handler
**old_sh
= 0,
574 ACE_Sig_Action
*old_disp
= 0);
576 /// Registers @a new_sh to handle a set of signals @a sigset using the
578 virtual int register_handler (const ACE_Sig_Set
&sigset
,
579 ACE_Event_Handler
*new_sh
,
580 ACE_Sig_Action
*new_disp
= 0);
582 /// Removes @a event_handler.
584 * @note The I/O handle will be obtained using @c get_handle()
585 * method of @a event_handler . If @a mask ==
586 * @c ACE_Event_Handler::DONT_CALL then the @c handle_close()
587 * method of the @a event_handler is not invoked.
589 virtual int remove_handler (ACE_Event_Handler
*event_handler
,
590 ACE_Reactor_Mask mask
);
593 * Removes @a handle. If @a mask == ACE_Event_Handler::DONT_CALL
594 * then the <handle_close> method of the associated <event_handler>
597 virtual int remove_handler (ACE_HANDLE handle
,
598 ACE_Reactor_Mask mask
);
601 * Removes all handles in @a handle_set. If @a mask ==
602 * ACE_Event_Handler::DONT_CALL then the <handle_close> method of
603 * the associated <event_handler>s is not invoked.
605 virtual int remove_handler (const ACE_Handle_Set
&handle_set
,
606 ACE_Reactor_Mask mask
);
609 * Remove the ACE_Event_Handler currently associated with @a signum.
610 * Install the new disposition (if given) and return the previous
611 * disposition (if desired by the caller). Returns 0 on success and
612 * -1 if @a signum is invalid.
614 virtual int remove_handler (int signum
,
615 ACE_Sig_Action
*new_disp
,
616 ACE_Sig_Action
*old_disp
= 0,
619 /// Calls <remove_handler> for every signal in @a sigset.
620 virtual int remove_handler (const ACE_Sig_Set
&sigset
);
622 // = Suspend and resume Handlers.
624 /// Suspend event_handler temporarily. Use
625 /// ACE_Event_Handler::get_handle() to get the handle.
626 virtual int suspend_handler (ACE_Event_Handler
*event_handler
);
628 /// Suspend handle temporarily.
629 virtual int suspend_handler (ACE_HANDLE handle
);
631 /// Suspend all handles in handle set temporarily.
632 virtual int suspend_handler (const ACE_Handle_Set
&handles
);
634 /// Suspend all handles temporarily.
635 virtual int suspend_handlers ();
637 /// Resume event_handler. Use ACE_Event_Handler::get_handle() to
639 virtual int resume_handler (ACE_Event_Handler
*event_handler
);
642 virtual int resume_handler (ACE_HANDLE handle
);
644 /// Resume all handles in handle set.
645 virtual int resume_handler (const ACE_Handle_Set
&handles
);
647 /// Resume all handles.
648 virtual int resume_handlers ();
650 /// Does the reactor allow the application to resume the handle on
651 /// its own, i.e., can it pass on the control of handle resumption to
653 virtual int resumable_handler ();
655 /// Return true if we any event associations were made by the reactor
656 /// for the handles that it waits on, false otherwise.
657 virtual bool uses_event_associations ();
659 // = Timer management.
662 * Schedule an ACE_Event_Handler that will expire after an amount
663 * of time. The return value of this method, a timer_id value,
664 * uniquely identifies the event_handler in the ACE_Reactor's
665 * internal list of timers.
666 * This timer_id value can be used to cancel the timer
667 * with the cancel_timer() call.
669 * @see cancel_timer()
670 * @see reset_timer_interval()
672 * @param event_handler event handler to schedule on reactor
673 * @param arg argument passed to the handle_timeout() method of
675 * @param delay time interval after which the timer will expire.
676 * @param interval time interval for which the timer will be
677 * automatically rescheduled.
678 * @return -1 on failure, a timer_id value on success
680 virtual long schedule_timer (ACE_Event_Handler
*event_handler
,
682 const ACE_Time_Value
&delay
,
683 const ACE_Time_Value
&interval
= ACE_Time_Value::zero
);
686 * Resets the interval of the timer represented by @a timer_id to
687 * @a interval, which is specified in relative time to the current
688 * <gettimeofday>. If @a interval is equal to
689 * ACE_Time_Value::zero, the timer will become a non-rescheduling
690 * timer. Returns 0 if successful, -1 if not.
692 virtual int reset_timer_interval (long timer_id
,
693 const ACE_Time_Value
&interval
);
695 /// Cancel all Event_Handlers that match the address of
696 /// @a event_handler. Returns number of handlers cancelled.
697 virtual int cancel_timer (ACE_Event_Handler
*event_handler
,
698 int dont_call_handle_close
= 1);
701 * Cancel the single event handler that matches the @a timer_id value
702 * (which was returned from the schedule method). If @a arg is
703 * non-NULL then it will be set to point to the ``magic cookie''
704 * argument passed in when the event handler was registered. This
705 * makes it possible to free up the memory and avoid memory leaks.
706 * Returns 1 if cancellation succeeded and 0 if the @a timer_id
709 virtual int cancel_timer (long timer_id
,
710 const void **arg
= 0,
711 int dont_call_handle_close
= 1);
713 // = High-level event handler scheduling operations
715 /// Add @a masks_to_be_added to the @a event_handler's entry.
716 /// @a event_handler must already have been registered.
717 virtual int schedule_wakeup (ACE_Event_Handler
*event_handler
,
718 ACE_Reactor_Mask masks_to_be_added
);
720 /// Add @a masks_to_be_added to the @a handle's entry. <event_handler>
721 /// associated with @a handle must already have been registered.
722 virtual int schedule_wakeup (ACE_HANDLE handle
,
723 ACE_Reactor_Mask masks_to_be_added
);
725 /// Clear @a masks_to_be_cleared from the @a event_handler's entry.
726 virtual int cancel_wakeup (ACE_Event_Handler
*event_handler
,
727 ACE_Reactor_Mask masks_to_be_cleared
);
729 /// Clear @a masks_to_be_cleared from the @a handle's entry.
730 virtual int cancel_wakeup (ACE_HANDLE handle
,
731 ACE_Reactor_Mask masks_to_be_cleared
);
733 // = Notification methods.
736 * Notify @a event_handler of @a mask event. The ACE_Time_Value
737 * indicates how long to blocking trying to notify. If @a timeout ==
738 * 0, the caller will block until action is possible, else will wait
739 * until the relative time specified in @a timeout elapses).
741 virtual int notify (ACE_Event_Handler
*event_handler
= 0,
742 ACE_Reactor_Mask mask
= ACE_Event_Handler::EXCEPT_MASK
,
743 ACE_Time_Value
* = 0);
746 * Set the maximum number of times that ACE_Reactor_Impl will
747 * iterate and dispatch the ACE_Event_Handlers that are passed in
748 * via the notify queue before breaking out of its
749 * ACE_Message_Queue::dequeue() loop. By default, this is set to
750 * -1, which means "iterate until the queue is empty." Setting this
751 * to a value like "1 or 2" will increase "fairness" (and thus
752 * prevent starvation) at the expense of slightly higher dispatching
755 virtual void max_notify_iterations (int);
758 * Get the maximum number of times that the ACE_Reactor_Impl will
759 * iterate and dispatch the ACE_Event_Handlers that are passed in
760 * via the notify queue before breaking out of its
761 * ACE_Message_Queue::dequeue() loop.
763 virtual int max_notify_iterations ();
766 * Purge any notifications pending in this reactor for the specified
767 * ACE_Event_Handler object. Returns the number of notifications
768 * purged. Returns -1 on error.
770 virtual int purge_pending_notifications (ACE_Event_Handler
* = 0,
771 ACE_Reactor_Mask
= ACE_Event_Handler::ALL_EVENTS_MASK
);
774 * Return the Event_Handler associated with @a handle. Return 0 if
775 * @a handle is not registered.
777 virtual ACE_Event_Handler
*find_handler (ACE_HANDLE handle
);
780 * Check to see if @a handle is associated with a valid Event_Handler
781 * bound to @a mask. Return the @a event_handler associated with this
782 * @c handler if @a event_handler != 0.
784 virtual int handler (ACE_HANDLE handle
,
785 ACE_Reactor_Mask mask
,
786 ACE_Event_Handler
**event_handler
= 0);
789 * Check to see if @a signum is associated with a valid Event_Handler
790 * bound to a signal. Return the @a event_handler associated with
791 * this @c handler if @a event_handler != 0.
793 virtual int handler (int signum
,
794 ACE_Event_Handler
** = 0);
796 /// Returns true if Reactor has been successfully initialized, else
798 virtual bool initialized ();
800 /// Returns the current size of the Reactor's internal descriptor
802 virtual size_t size () const;
804 /// Returns a reference to the Reactor's internal repository lock.
805 virtual ACE_Lock
&lock ();
807 /// Wake up all threads waiting in the event loop.
808 virtual void wakeup_all_threads ();
810 /// Transfers ownership of Reactor_Impl to the @a new_owner.
812 * @note There is no need to set the owner of the event loop for the
813 * ACE_Dev_Poll_Reactor. Multiple threads may invoke the
814 * event loop simulataneously. As such, this method is a
817 virtual int owner (ACE_thread_t new_owner
, ACE_thread_t
*old_owner
= 0);
819 /// Return the ID of the "owner" thread.
821 * @note There is no need to set the owner of the event loop for the
822 * ACE_Dev_Poll_Reactor. Multiple threads may invoke the
823 * event loop simultaneously. As such, this method is a
826 virtual int owner (ACE_thread_t
*owner
);
828 /// Get the existing restart value.
829 virtual bool restart ();
831 /// Set a new value for restart and return the original value.
833 * @param r If zero, then the event loop will not be automatically
834 * restarted if the underlying poll is interrupted via the
835 * INTR (interrupt) signal.
837 * @return Returns the previous "restart" value.
839 virtual bool restart (bool r
);
841 /// Set position of the owner thread.
843 * @note This is currently a no-op.
845 virtual void requeue_position (int);
847 /// Get position of the owner thread.
849 * @note This is currently a no-op.
851 virtual int requeue_position ();
854 * @name Low-level wait_set mask manipulation methods
856 * Low-level methods to manipulate the event/reactor mask associated
857 * with a handle and event handler when polling for events.
859 * The "interest set," i.e. the wait set, can be directly
860 * manipulated with these methods.
863 /// GET/SET/ADD/CLR the dispatch mask "bit" bound with the
864 /// event_handler and mask.
866 * @return Old mask on success, -1 on error.
868 virtual int mask_ops (ACE_Event_Handler
*event_handler
,
869 ACE_Reactor_Mask mask
,
872 /// GET/SET/ADD/CLR the dispatch MASK "bit" bound with the handle
875 * @return Old mask on success, -1 on error.
877 virtual int mask_ops (ACE_HANDLE handle
,
878 ACE_Reactor_Mask mask
,
884 * @name Low-level ready_set mask manipulation methods
886 * These methods are unimplemented.
889 /// GET/SET/ADD/CLR the ready "bit" bound with the event_handler
891 virtual int ready_ops (ACE_Event_Handler
*event_handler
,
892 ACE_Reactor_Mask mask
,
895 /// GET/SET/ADD/CLR the ready "bit" bound with the handle and mask.
896 virtual int ready_ops (ACE_HANDLE handle
,
902 /// Dump the state of an object.
903 virtual void dump () const;
905 /// Declare the dynamic allocation hooks.
906 ACE_ALLOC_HOOK_DECLARE
;
911 /// Non-locking version of wait_pending().
913 * Returns non-zero if there are I/O events "ready" for dispatching,
914 * but does not actually dispatch the event handlers. By default,
915 * don't block while checking this, i.e., "poll".
917 * @note It is only possible to achieve millisecond timeout
918 * resolutions with the ACE_Dev_Poll_Reactor.
920 int work_pending_i (ACE_Time_Value
*max_wait_time
);
922 /// Poll for events and return the number of event handlers that
925 * This is a helper method called by all handle_events() methods.
927 int handle_events_i (ACE_Time_Value
*max_wait_time
, Token_Guard
&guard
);
929 /// Perform the upcall with the given event handler method.
930 int upcall (ACE_Event_Handler
*event_handler
,
931 int (ACE_Event_Handler::*callback
)(ACE_HANDLE
),
935 * Dispatch ACE_Event_Handlers for time events, I/O events, and
936 * signal events. Returns the total number of ACE_Event_Handlers
937 * that were dispatched or -1 if something goes wrong.
939 int dispatch (Token_Guard
&guard
);
941 /// Dispatch a single timer, if ready.
942 /// Returns: 0 if no timers ready (token still held),
943 /// 1 if a timer was expired (token released),
944 /// -1 on error (token still held).
945 int dispatch_timer_handler (Token_Guard
&guard
);
947 /// Dispatch an IO event to the corresponding event handler. Returns
948 /// Returns: 0 if no events ready (token still held),
949 /// 1 if an event was expired (token released),
950 /// -1 on error (token still held).
951 int dispatch_io_event (Token_Guard
&guard
);
953 /// Register the given event handler with the reactor.
954 int register_handler_i (ACE_HANDLE handle
,
955 ACE_Event_Handler
*eh
,
956 ACE_Reactor_Mask mask
);
958 /// Remove the event handler associated with the given handle and
959 /// event mask from the "interest set." If @a eh is supplied, only do the
960 /// remove if @eh matches the event handler that's registered for @a handle.
961 /// The caller is expected to be holding the repo token on entry and have
962 /// @repo_guard referencing that token. It will be temporarily released
963 /// during a handle_close() callback if needed; if it is released for the
964 //// callback it will be reacquired before return.
965 // FUZZ: disable check_for_ACE_Guard
966 int remove_handler_i (ACE_HANDLE handle
,
967 ACE_Reactor_Mask mask
,
968 ACE_Guard
<ACE_SYNCH_MUTEX
> &repo_guard
,
969 ACE_Event_Handler
*eh
= 0);
970 // FUZZ: enable check_for_ACE_Guard
972 /// Temporarily remove the given handle from the "interest set."
973 int suspend_handler_i (ACE_HANDLE handle
);
975 /// Place the given handle that was temporarily removed from the
976 /// "interest set," i.e that was suspended, back in to the interest
977 /// set. The given handle will once again be polled for events.
978 int resume_handler_i (ACE_HANDLE handle
);
980 /// GET/SET/ADD/CLR the dispatch MASK "bit" bound with the handle
981 /// and mask. This internal helper method acquires no lock.
983 * @return Old mask on success, -1 on error.
985 int mask_ops_i (ACE_HANDLE handle
,
986 ACE_Reactor_Mask mask
,
989 /// Convert a reactor mask to its corresponding poll() event mask.
990 short reactor_mask_to_poll_event (ACE_Reactor_Mask mask
);
993 /// Has the reactor been initialized.
996 /// The file descriptor associated with the open `/dev/poll' or
997 /// `/dev/epoll' device.
999 * All interactions with the `/dev/poll' or `/dev/epoll' device are
1000 * done through this file descriptor.
1002 ACE_HANDLE poll_fd_
;
1004 #if defined (ACE_HAS_EVENT_POLL)
1005 /// Event structure to be filled by epoll_wait. epoll_wait() only gets
1006 /// one event at a time and we rely on it's internals for fairness.
1007 /// If this struct's fd is ACE_INVALID_HANDLE, the rest is indeterminate.
1008 /// If the fd is good, the event is one that's been retrieved by
1009 /// epoll_wait() but not yet processed.
1010 struct epoll_event event_
;
1013 /// The pollfd array that `/dev/poll' will feed its results to.
1014 struct pollfd
*dp_fds_
;
1017 /// Pointer to the next pollfd array element that contains the next
1018 /// event to be dispatched.
1019 struct pollfd
*start_pfds_
;
1021 /// The last element in the pollfd array plus one.
1023 * The loop that dispatches IO events stops when this->start_pfds ==
1026 struct pollfd
*end_pfds_
;
1027 #endif /* ACE_HAS_EVENT_POLL */
1029 /// Token serializing event waiter threads.
1030 ACE_Dev_Poll_Reactor_Token token_
;
1032 /// Adapter used to return internal lock to outside world.
1033 ACE_Lock_Adapter
<ACE_Dev_Poll_Reactor_Token
> lock_adapter_
;
1035 /// This flag is used to keep track of whether we are actively handling
1037 sig_atomic_t deactivated_
;
1039 /// Token used to protect manipulation of the handler repository.
1040 /// No need to hold the waiter token to change the repo.
1041 // ACE_DEV_POLL_TOKEN repo_token_;
1042 ACE_SYNCH_MUTEX repo_lock_
;
1044 /// The repository that contains all registered event handlers.
1045 Handler_Repository handler_rep_
;
1047 /// Defined as a pointer to allow overriding by derived classes...
1048 ACE_Timer_Queue
*timer_queue_
;
1050 /// Keeps track of whether we should delete the timer queue (if we
1051 /// didn't create it, then we don't delete it).
1052 bool delete_timer_queue_
;
1054 /// Handle signals without requiring global/static variables.
1055 ACE_Sig_Handler
*signal_handler_
;
1057 /// Keeps track of whether we should delete the signal handler (if we
1058 /// didn't create it, then we don't delete it).
1059 bool delete_signal_handler_
;
1061 /// Callback object that unblocks the <ACE_Select_Reactor> if it's
1063 ACE_Reactor_Notify
*notify_handler_
;
1065 /// Keeps track of whether we need to delete the notify handler (if
1066 /// we didn't create it, then we don't delete it).
1067 bool delete_notify_handler_
;
1069 /// Flag that determines if signals are masked during event
1072 * If 0 then the Reactor will not mask the signals during the event
1073 * dispatching. This is useful for applications that do not
1074 * register any signal handlers and want to reduce the overhead
1075 * introduce by the kernel level locks required to change the mask.
1079 /// Restart the handle_events event loop method automatically when
1080 /// polling function in use (ioctl() in this case) is interrupted
1081 /// via an EINTR signal.
1086 * @class Token_Guard
1088 * @brief A helper class that helps grabbing, releasing and waiting
1089 * on tokens for a thread that needs access to the reactor's token.
1091 class ACE_Export Token_Guard
1094 /// Constructor that will grab the token for us
1095 Token_Guard (ACE_Dev_Poll_Reactor_Token
&token
);
1097 /// Destructor. This will release the token if it hasn't been
1098 /// released till this point
1101 /// Release the token ..
1102 void release_token ();
1104 /// Returns whether the thread that created this object owns the
1108 /// A helper method that acquires the token 1) at a low priority, and
1109 /// 2) wait quietly for the token, not waking another thread. This
1110 /// is appropriate for cases where a thread wants to wait for and
1111 /// dispatch an event, not causing an existing waiter to relinquish the
1113 int acquire_quietly (ACE_Time_Value
*max_wait
= 0);
1115 /// A helper method that acquires the token at a high priority, and
1116 /// does wake the current token holder.
1117 int acquire (ACE_Time_Value
*max_wait
= 0);
1123 /// The Reactor token.
1124 ACE_Dev_Poll_Reactor_Token
&token_
;
1126 /// Flag that indicate whether the thread that created this object
1127 /// owns the token or not. A value of false indicates that this class
1128 /// hasn't got the token (and hence the thread) and a value of true
1136 * @class ACE_Dev_Poll_Handler_Guard
1138 * @brief Class used to make event handler reference count
1139 * manipulation exception-safe.
1141 * This class makes the reference count manipulation that occurs
1142 * during an upcall exception-safe. Prior to dispatching the event
1143 * handler, the reference count is increased. Once the upcall for the
1144 * given event handler is complete, its reference count will be decreased.
1146 class ACE_Dev_Poll_Handler_Guard
1151 * The constructor checks to see if @a eh is a reference-counted handler and
1152 * remember that for later. If @a eh is reference counted, its reference
1153 * count is incremented unless @a do_incr is false.
1154 * @a do_incr should be false if the reference count was incremented
1155 * independently of this guard, for example, on a notify handler since
1156 * the reference count is incremented when the notify is queued.
1158 ACE_Dev_Poll_Handler_Guard (ACE_Event_Handler
*eh
, bool do_incr
= true);
1162 * The destructor decrements the reference count on the event
1163 * handler corresponding to the given handle.
1165 ~ACE_Dev_Poll_Handler_Guard ();
1167 /// Release the event handler from this guard; when the destructor is
1168 /// called, the handler's reference count will not be decremented.
1172 /// The event handler being managed.
1173 ACE_Event_Handler
*eh_
;
1175 /// true if eh_ is a reference-counted handler.
1179 ACE_END_VERSIONED_NAMESPACE_DECL
1181 #if defined (__ACE_INLINE__)
1182 # include "ace/Dev_Poll_Reactor.inl"
1183 #endif /* __ACE_INLINE__ */
1185 #endif /* ACE_HAS_EVENT_POLL || ACE_HAS_DEV_POLL */
1187 #include /**/ "ace/post.h"
1189 #endif /* ACE_DEV_POLL_REACTOR_H */