1 #include "ace/Reactor.h"
3 #if !defined (ACE_LACKS_ACE_SVCCONF)
4 # include "ace/Service_Config.h"
5 #endif /* !ACE_LACKS_ACE_SVCCONF */
7 // Only include the headers needed to compile.
8 #if !defined (ACE_WIN32) \
9 || !defined (ACE_HAS_WINSOCK2) || (ACE_HAS_WINSOCK2 == 0) \
10 || defined (ACE_USE_SELECT_REACTOR_FOR_REACTOR_IMPL) \
11 || defined (ACE_USE_TP_REACTOR_FOR_REACTOR_IMPL) \
12 || defined (ACE_USE_DEV_POLL_REACTOR_FOR_REACTOR_IMPL)
13 # if defined (ACE_USE_TP_REACTOR_FOR_REACTOR_IMPL)
14 # include "ace/TP_Reactor.h"
16 # if defined (ACE_USE_DEV_POLL_REACTOR_FOR_REACTOR_IMPL)
17 # include "ace/Dev_Poll_Reactor.h"
19 # include "ace/Select_Reactor.h"
20 # endif /* ACE_USE_DEV_POLL_REACTOR_FOR_REACTOR_IMPL */
21 # endif /* ACE_USE_TP_REACTOR_FOR_REACTOR_IMPL */
22 #else /* We are on Win32 and we have winsock and ACE_USE_SELECT_REACTOR_FOR_REACTOR_IMPL is not defined */
23 # if defined (ACE_USE_MSG_WFMO_REACTOR_FOR_REACTOR_IMPL)
24 # include "ace/Msg_WFMO_Reactor.h"
26 # include "ace/WFMO_Reactor.h"
27 # endif /* ACE_USE_MSG_WFMO_REACTOR_FOR_REACTOR_IMPL */
28 #endif /* !defined (ACE_WIN32) || !defined (ACE_HAS_WINSOCK2) || (ACE_HAS_WINSOCK2 == 0) || defined (ACE_USE_SELECT_REACTOR_FOR_REACTOR_IMPL) */
30 #include "ace/Static_Object_Lock.h"
31 #include "ace/Framework_Component.h"
32 #include "ace/Guard_T.h"
33 #include "ace/Recursive_Thread_Mutex.h"
35 #if !defined (__ACE_INLINE__)
36 #include "ace/Reactor.inl"
37 #endif /* __ACE_INLINE__ */
39 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
41 ACE_ALLOC_HOOK_DEFINE(ACE_Reactor
)
43 ACE_Reactor::ACE_Reactor (ACE_Reactor_Impl
*impl
,
44 bool delete_implementation
)
45 : implementation_ (0),
46 delete_implementation_ (delete_implementation
)
48 this->implementation (impl
);
50 if (this->implementation () == 0)
52 #if !defined (ACE_WIN32) \
53 || !defined (ACE_HAS_WINSOCK2) || (ACE_HAS_WINSOCK2 == 0) \
54 || defined (ACE_USE_SELECT_REACTOR_FOR_REACTOR_IMPL) \
55 || defined (ACE_USE_TP_REACTOR_FOR_REACTOR_IMPL) \
56 || defined (ACE_USE_DEV_POLL_REACTOR_FOR_REACTOR_IMPL)
57 # if defined (ACE_USE_TP_REACTOR_FOR_REACTOR_IMPL)
61 # if defined (ACE_USE_DEV_POLL_REACTOR_FOR_REACTOR_IMPL)
63 ACE_Dev_Poll_Reactor
);
67 # endif /* ACE_USE_DEV_POLL_REACTOR_FOR_REACTOR_IMPL */
68 # endif /* ACE_USE_TP_REACTOR_FOR_REACTOR_IMPL */
69 #else /* We are on Win32 and we have winsock and ACE_USE_SELECT_REACTOR_FOR_REACTOR_IMPL is not defined */
70 #if defined (ACE_USE_MSG_WFMO_REACTOR_FOR_REACTOR_IMPL)
72 ACE_Msg_WFMO_Reactor
);
76 #endif /* ACE_USE_MSG_WFMO_REACTOR_FOR_REACTOR_IMPL */
77 #endif /* !defined (ACE_WIN32) || !defined (ACE_HAS_WINSOCK2) || (ACE_HAS_WINSOCK2 == 0) || defined (ACE_USE_SELECT_REACTOR_FOR_REACTOR_IMPL) */
78 this->implementation (impl
);
79 this->delete_implementation_
= true;
83 ACE_Reactor::~ACE_Reactor ()
85 this->implementation ()->close ();
86 if (this->delete_implementation_
)
87 delete this->implementation ();
90 // Process-wide ACE_Reactor.
91 ACE_Reactor
*ACE_Reactor::reactor_
= 0;
93 // Controls whether the Reactor is deleted when we shut down (we can
94 // only delete it safely if we created it!)
95 bool ACE_Reactor::delete_reactor_
= false;
98 ACE_Reactor::instance ()
100 ACE_TRACE ("ACE_Reactor::instance");
102 if (ACE_Reactor::reactor_
== 0)
104 // Perform Double-Checked Locking Optimization.
105 ACE_MT (ACE_GUARD_RETURN (ACE_Recursive_Thread_Mutex
, ace_mon
,
106 *ACE_Static_Object_Lock::instance (), 0));
108 if (ACE_Reactor::reactor_
== 0)
110 ACE_NEW_RETURN (ACE_Reactor::reactor_
,
113 ACE_Reactor::delete_reactor_
= true;
114 ACE_REGISTER_FRAMEWORK_COMPONENT(ACE_Reactor
, ACE_Reactor::reactor_
)
117 return ACE_Reactor::reactor_
;
121 ACE_Reactor::instance (ACE_Reactor
*r
, bool delete_reactor
)
123 ACE_TRACE ("ACE_Reactor::instance");
125 ACE_MT (ACE_GUARD_RETURN (ACE_Recursive_Thread_Mutex
, ace_mon
,
126 *ACE_Static_Object_Lock::instance (), 0));
127 ACE_Reactor
*t
= ACE_Reactor::reactor_
;
128 ACE_Reactor::delete_reactor_
= delete_reactor
;
130 ACE_Reactor::reactor_
= r
;
132 // We can't register the Reactor singleton as a framework component twice.
133 // Therefore we test to see if we had an existing reactor instance, which
134 // if so means it must have already been registered.
136 ACE_REGISTER_FRAMEWORK_COMPONENT(ACE_Reactor
, ACE_Reactor::reactor_
);
142 ACE_Reactor::close_singleton ()
144 ACE_TRACE ("ACE_Reactor::close_singleton");
146 ACE_MT (ACE_GUARD (ACE_Recursive_Thread_Mutex
, ace_mon
,
147 *ACE_Static_Object_Lock::instance ()));
149 if (ACE_Reactor::delete_reactor_
)
151 delete ACE_Reactor::reactor_
;
152 ACE_Reactor::reactor_
= 0;
153 ACE_Reactor::delete_reactor_
= false;
158 ACE_Reactor::dll_name ()
160 return ACE_TEXT ("ACE");
166 return ACE_TEXT ("ACE_Reactor");
170 ACE_Reactor::check_reconfiguration (ACE_Reactor
*)
172 #if !defined (ACE_LACKS_ACE_SVCCONF)
173 if (ACE_Service_Config::reconfig_occurred ())
175 ACE_Service_Config::reconfigure ();
178 #endif /* !ACE_LACKS_ACE_SVCCONF */
183 ACE_Reactor::run_reactor_event_loop (REACTOR_EVENT_HOOK eh
)
185 ACE_TRACE ("ACE_Reactor::run_reactor_event_loop");
187 if (this->reactor_event_loop_done ())
192 int const result
= this->implementation_
->handle_events ();
194 if (eh
!= 0 && (*eh
)(this))
196 else if (result
== -1 && this->implementation_
->deactivated ())
198 else if (result
== -1)
202 ACE_NOTREACHED (return 0;)
206 ACE_Reactor::run_alertable_reactor_event_loop (REACTOR_EVENT_HOOK eh
)
208 ACE_TRACE ("ACE_Reactor::run_alertable_reactor_event_loop");
210 if (this->reactor_event_loop_done ())
215 int const result
= this->implementation_
->alertable_handle_events ();
217 if (eh
!= 0 && (*eh
)(this))
219 else if (result
== -1 && this->implementation_
->deactivated ())
221 else if (result
== -1)
225 ACE_NOTREACHED (return 0;)
229 ACE_Reactor::run_reactor_event_loop (ACE_Time_Value
&tv
,
230 REACTOR_EVENT_HOOK eh
)
232 ACE_TRACE ("ACE_Reactor::run_reactor_event_loop");
234 if (this->reactor_event_loop_done ())
239 int result
= this->implementation_
->handle_events (tv
);
241 if (eh
!= 0 && (*eh
) (this))
243 else if (result
== -1)
245 if (this->implementation_
->deactivated ())
249 else if (result
== 0)
251 // The <handle_events> method timed out without dispatching
252 // anything. Because of rounding and conversion errors and
253 // such, it could be that the wait loop (WFMO, select, etc.)
254 // timed out, but the timer queue said it wasn't quite ready
255 // to expire a timer. In this case, the ACE_Time_Value we
256 // passed into handle_events won't have quite been reduced
257 // to 0, and we need to go around again. If we are all the
258 // way to 0, just return, as the entire time the caller
259 // wanted to wait has been used up.
264 // Else there were some events dispatched; go around again
267 ACE_NOTREACHED (return 0;)
271 ACE_Reactor::run_alertable_reactor_event_loop (ACE_Time_Value
&tv
,
272 REACTOR_EVENT_HOOK eh
)
274 ACE_TRACE ("ACE_Reactor::run_alertable_reactor_event_loop");
276 if (this->reactor_event_loop_done ())
281 int result
= this->implementation_
->alertable_handle_events (tv
);
283 if (eh
!= 0 && (*eh
)(this))
285 else if (result
== -1 && this->implementation_
->deactivated ())
287 else if (result
<= 0)
293 ACE_Reactor::register_handler (ACE_Event_Handler
*event_handler
,
294 ACE_Reactor_Mask mask
)
296 // Remember the old reactor.
297 ACE_Reactor
*old_reactor
= event_handler
->reactor ();
299 // Assign *this* <Reactor> to the <Event_Handler>.
300 event_handler
->reactor (this);
302 int result
= this->implementation ()->register_handler (event_handler
, mask
);
304 // Reset the old reactor in case of failures.
305 event_handler
->reactor (old_reactor
);
311 ACE_Reactor::register_handler (ACE_HANDLE io_handle
,
312 ACE_Event_Handler
*event_handler
,
313 ACE_Reactor_Mask mask
)
315 // Remember the old reactor.
316 ACE_Reactor
*old_reactor
= event_handler
->reactor ();
318 // Assign *this* <Reactor> to the <Event_Handler>.
319 event_handler
->reactor (this);
321 int result
= this->implementation ()->register_handler (io_handle
,
325 // Reset the old reactor in case of failures.
326 event_handler
->reactor (old_reactor
);
331 #if defined (ACE_WIN32)
334 ACE_Reactor::register_handler (ACE_Event_Handler
*event_handler
,
335 ACE_HANDLE event_handle
)
337 // Remember the old reactor.
338 ACE_Reactor
*old_reactor
= event_handler
->reactor ();
340 // Assign *this* <Reactor> to the <Event_Handler>.
341 event_handler
->reactor (this);
343 int result
= this->implementation ()->register_handler (event_handler
,
346 // Reset the old reactor in case of failures.
347 event_handler
->reactor (old_reactor
);
352 #endif /* ACE_WIN32 */
355 ACE_Reactor::register_handler (ACE_HANDLE event_handle
,
356 ACE_HANDLE io_handle
,
357 ACE_Event_Handler
*event_handler
,
358 ACE_Reactor_Mask mask
)
360 // Remember the old reactor.
361 ACE_Reactor
*old_reactor
= event_handler
->reactor ();
363 // Assign *this* <Reactor> to the <Event_Handler>.
364 event_handler
->reactor (this);
366 int result
= this->implementation ()->register_handler (event_handle
,
371 // Reset the old reactor in case of failures.
372 event_handler
->reactor (old_reactor
);
378 ACE_Reactor::register_handler (const ACE_Handle_Set
&handles
,
379 ACE_Event_Handler
*event_handler
,
380 ACE_Reactor_Mask mask
)
382 // Remember the old reactor.
383 ACE_Reactor
*old_reactor
= event_handler
->reactor ();
385 // Assign *this* <Reactor> to the <Event_Handler>.
386 event_handler
->reactor (this);
388 int result
= this->implementation ()->register_handler (handles
,
392 // Reset the old reactor in case of failures.
393 event_handler
->reactor (old_reactor
);
399 ACE_Reactor::schedule_timer (ACE_Event_Handler
*event_handler
,
401 const ACE_Time_Value
&delta
,
402 const ACE_Time_Value
&interval
)
404 // Remember the old reactor.
405 ACE_Reactor
*old_reactor
= event_handler
->reactor ();
407 // Assign *this* <Reactor> to the <Event_Handler>.
408 event_handler
->reactor (this);
410 long result
= this->implementation ()->schedule_timer (event_handler
,
415 // Reset the old reactor in case of failures.
416 event_handler
->reactor (old_reactor
);
422 ACE_Reactor::schedule_wakeup (ACE_Event_Handler
*event_handler
,
423 ACE_Reactor_Mask masks_to_be_added
)
425 // Remember the old reactor.
426 ACE_Reactor
*old_reactor
= event_handler
->reactor ();
428 // Assign *this* <Reactor> to the <Event_Handler>.
429 event_handler
->reactor (this);
431 int result
= this->implementation ()->schedule_wakeup (event_handler
,
434 // Reset the old reactor in case of failures.
435 event_handler
->reactor (old_reactor
);
441 ACE_Reactor::notify (ACE_Event_Handler
*event_handler
,
442 ACE_Reactor_Mask mask
,
445 // First, try to remember this reactor in the event handler, in case
446 // the event handler goes away before the notification is delivered.
447 if (event_handler
!= 0 && event_handler
->reactor () == 0)
449 event_handler
->reactor (this);
451 return this->implementation ()->notify (event_handler
, mask
, tv
);
455 ACE_Reactor::reset_timer_interval
457 const ACE_Time_Value
&interval
)
459 ACE_TRACE ("ACE_Reactor::reset_timer_interval");
461 return this->implementation ()->reset_timer_interval (timer_id
, interval
);
465 ACE_Reactor::cancel_timer (ACE_Event_Handler
*event_handler
,
466 int dont_call_handle_close
)
468 return this->implementation ()->cancel_timer (event_handler
,
469 dont_call_handle_close
);
473 ACE_Reactor::cancel_timer (long timer_id
,
475 int dont_call_handle_close
)
477 return this->implementation ()->cancel_timer (timer_id
,
479 dont_call_handle_close
);
482 ACE_END_VERSIONED_NAMESPACE_DECL