00001 #include "ace_pch.h"
00002
00003
00004 #include "ace/XtReactor.h"
00005 #if defined (ACE_HAS_XT)
00006
00007 #include "ace/Synch_T.h"
00008 #include "ace/SOCK_Acceptor.h"
00009 #include "ace/SOCK_Connector.h"
00010
00011 ACE_RCSID(ace, XtReactor, "$Id: XtReactor.cpp,v 1.1.1.4.2.1 2003/03/13 19:44:24 chad Exp $")
00012
00013 ACE_ALLOC_HOOK_DEFINE (ACE_XtReactor)
00014
00015
00016 ACE_XtReactor::ACE_XtReactor (XtAppContext context,
00017 size_t size,
00018 int restart,
00019 ACE_Sig_Handler *h)
00020 : ACE_Select_Reactor (size, restart, h),
00021 context_ (context),
00022 ids_ (0),
00023 timeout_ (0)
00024 {
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036 #if defined (ACE_MT_SAFE) && (ACE_MT_SAFE != 0)
00037 this->notify_handler_->close ();
00038 this->notify_handler_->open (this, 0);
00039 #endif
00040 }
00041
00042 ACE_XtReactor::~ACE_XtReactor (void)
00043 {
00044
00045
00046 while (this->ids_)
00047 {
00048 ACE_XtReactorID *XtID = this->ids_->next_;
00049 delete this->ids_;
00050 this->ids_ = XtID;
00051 }
00052 }
00053
00054
00055
00056
00057 int
00058 ACE_XtReactor::wait_for_multiple_events (ACE_Select_Reactor_Handle_Set &handle_set,
00059 ACE_Time_Value *max_wait_time)
00060 {
00061 ACE_TRACE ("ACE_XtReactor::wait_for_multiple_events");
00062 int nfound;
00063
00064 do
00065 {
00066 max_wait_time = this->timer_queue_->calculate_timeout (max_wait_time);
00067
00068 size_t width = this->handler_rep_.max_handlep1 ();
00069 handle_set.rd_mask_ = this->wait_set_.rd_mask_;
00070 handle_set.wr_mask_ = this->wait_set_.wr_mask_;
00071 handle_set.ex_mask_ = this->wait_set_.ex_mask_;
00072 nfound = XtWaitForMultipleEvents (width,
00073 handle_set,
00074 max_wait_time);
00075
00076 } while (nfound == -1 && this->handle_error () > 0);
00077
00078 if (nfound > 0)
00079 {
00080 #if !defined (ACE_WIN32)
00081 handle_set.rd_mask_.sync (this->handler_rep_.max_handlep1 ());
00082 handle_set.wr_mask_.sync (this->handler_rep_.max_handlep1 ());
00083 handle_set.ex_mask_.sync (this->handler_rep_.max_handlep1 ());
00084 #endif
00085 }
00086 return nfound;
00087 }
00088
00089 void
00090 ACE_XtReactor::TimerCallbackProc (XtPointer closure, XtIntervalId * )
00091 {
00092 ACE_XtReactor *self = (ACE_XtReactor *) closure;
00093 self->timeout_ = 0;
00094
00095
00096 ACE_Select_Reactor_Handle_Set handle_set;
00097 self->dispatch (0, handle_set);
00098 self->reset_timeout ();
00099 }
00100
00101
00102
00103
00104
00105 void
00106 ACE_XtReactor::InputCallbackProc (XtPointer closure,
00107 int *source,
00108 XtInputId *)
00109 {
00110 ACE_XtReactor *self = (ACE_XtReactor *) closure;
00111 ACE_HANDLE handle = (ACE_HANDLE) *source;
00112
00113
00114 ACE_Time_Value zero = ACE_Time_Value::zero;
00115
00116 ACE_Select_Reactor_Handle_Set wait_set;
00117
00118
00119
00120
00121 if (self->wait_set_.rd_mask_.is_set (handle))
00122 wait_set.rd_mask_.set_bit (handle);
00123 if (self->wait_set_.wr_mask_.is_set (handle))
00124 wait_set.wr_mask_.set_bit (handle);
00125 if (self->wait_set_.ex_mask_.is_set (handle))
00126 wait_set.ex_mask_.set_bit (handle);
00127
00128 int result = ACE_OS::select (*source + 1,
00129 wait_set.rd_mask_,
00130 wait_set.wr_mask_,
00131 wait_set.ex_mask_, &zero);
00132
00133 ACE_Select_Reactor_Handle_Set dispatch_set;
00134
00135
00136 if (result > 0)
00137 {
00138 if (wait_set.rd_mask_.is_set (handle))
00139 dispatch_set.rd_mask_.set_bit (handle);
00140 if (wait_set.wr_mask_.is_set (handle))
00141 dispatch_set.wr_mask_.set_bit (handle);
00142 if (wait_set.ex_mask_.is_set (handle))
00143 dispatch_set.ex_mask_.set_bit (handle);
00144
00145 self->dispatch (1, dispatch_set);
00146 }
00147 }
00148
00149 int
00150 ACE_XtReactor::XtWaitForMultipleEvents (int width,
00151 ACE_Select_Reactor_Handle_Set &wait_set,
00152 ACE_Time_Value *)
00153 {
00154
00155 ACE_ASSERT (this->context_ != 0);
00156
00157
00158 ACE_Select_Reactor_Handle_Set temp_set = wait_set;
00159
00160 if (ACE_OS::select (width,
00161 temp_set.rd_mask_,
00162 temp_set.wr_mask_,
00163 temp_set.ex_mask_,
00164 (ACE_Time_Value *) &ACE_Time_Value::zero) == -1)
00165 return -1;
00166
00167
00168
00169
00170
00171 ::XtAppProcessEvent (this->context_, XtIMAll);
00172
00173
00174 width = this->handler_rep_.max_handlep1 ();
00175
00176
00177
00178 return ACE_OS::select (width,
00179 wait_set.rd_mask_,
00180 wait_set.wr_mask_,
00181 wait_set.ex_mask_,
00182 (ACE_Time_Value *) &ACE_Time_Value::zero);
00183 }
00184
00185 XtAppContext
00186 ACE_XtReactor::context (void) const
00187 {
00188 return this->context_;
00189 }
00190
00191 void
00192 ACE_XtReactor::context (XtAppContext context)
00193 {
00194 this->context_ = context;
00195 }
00196
00197 int
00198 ACE_XtReactor::register_handler_i (ACE_HANDLE handle,
00199 ACE_Event_Handler *handler,
00200 ACE_Reactor_Mask mask)
00201 {
00202 ACE_TRACE ("ACE_XtReactor::register_handler_i");
00203
00204
00205 ACE_ASSERT (this->context_ != 0);
00206
00207 int result = ACE_Select_Reactor::register_handler_i (handle,
00208 handler, mask);
00209 if (result == -1)
00210 return -1;
00211
00212 int condition = 0;
00213
00214 #if !defined ACE_WIN32
00215 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::READ_MASK))
00216 ACE_SET_BITS (condition, XtInputReadMask);
00217 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::WRITE_MASK))
00218 ACE_SET_BITS (condition, XtInputWriteMask);
00219 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::EXCEPT_MASK))
00220 ACE_SET_BITS (condition, XtInputExceptMask);
00221 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::ACCEPT_MASK))
00222 ACE_SET_BITS (condition, XtInputReadMask);
00223 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::CONNECT_MASK)){
00224 ACE_SET_BITS (condition, XtInputWriteMask);
00225 ACE_SET_BITS (condition, XtInputReadMask);
00226 }
00227 #else
00228 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::READ_MASK))
00229 ACE_SET_BITS (condition, XtInputReadWinsock);
00230 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::WRITE_MASK))
00231 ACE_SET_BITS (condition, XtInputWriteWinsock);
00232 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::EXCEPT_MASK))
00233 ACE_NOTSUP_RETURN(-1);
00234 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::ACCEPT_MASK))
00235 ACE_SET_BITS (condition, XtInputReadWinsock);
00236 if (ACE_BIT_ENABLED (mask, ACE_Event_Handler::CONNECT_MASK)){
00237 ACE_SET_BITS (condition, XtInputWriteWinsock);
00238 ACE_SET_BITS (condition, XtInputReadWinsock);
00239 }
00240 #endif
00241
00242 if (condition != 0)
00243 {
00244 ACE_XtReactorID *XtID = this->ids_;
00245
00246 while(XtID)
00247 {
00248 if (XtID->handle_ == handle)
00249 {
00250 ::XtRemoveInput (XtID->id_);
00251
00252 XtID->id_ = ::XtAppAddInput (this->context_,
00253 (int) handle,
00254 (XtPointer) condition,
00255 InputCallbackProc,
00256 (XtPointer) this);
00257 return 0;
00258 }
00259 else
00260 XtID = XtID->next_;
00261 }
00262
00263 ACE_NEW_RETURN (XtID,
00264 ACE_XtReactorID,
00265 -1);
00266 XtID->next_ = this->ids_;
00267 XtID->handle_ = handle;
00268 XtID->id_ = ::XtAppAddInput (this->context_,
00269 (int) handle,
00270 (XtPointer) condition,
00271 InputCallbackProc,
00272 (XtPointer) this);
00273 this->ids_ = XtID;
00274 }
00275 return 0;
00276 }
00277
00278 int
00279 ACE_XtReactor::register_handler_i (const ACE_Handle_Set &handles,
00280 ACE_Event_Handler *handler,
00281 ACE_Reactor_Mask mask)
00282 {
00283 return ACE_Select_Reactor::register_handler_i (handles,
00284 handler,
00285 mask);
00286 }
00287
00288 int
00289 ACE_XtReactor::remove_handler_i (ACE_HANDLE handle,
00290 ACE_Reactor_Mask mask)
00291 {
00292 ACE_TRACE ("ACE_XtReactor::remove_handler_i");
00293
00294
00295
00296
00297
00298
00299 this->remove_XtInput (handle);
00300
00301
00302 return ACE_Select_Reactor::remove_handler_i (handle,
00303 mask);
00304 }
00305
00306 void
00307 ACE_XtReactor::remove_XtInput (ACE_HANDLE handle)
00308 {
00309 ACE_TRACE ("ACE_XtReactor::remove_XtInput");
00310
00311 ACE_XtReactorID *XtID = this->ids_;
00312
00313 if (XtID)
00314 {
00315 if (XtID->handle_ == handle)
00316 {
00317 ::XtRemoveInput (XtID->id_);
00318 this->ids_ = XtID->next_;
00319 delete XtID;
00320 return;
00321 }
00322
00323 ACE_XtReactorID *NextID = XtID->next_;
00324
00325 while (NextID)
00326 {
00327 if (NextID->handle_ == handle)
00328 {
00329 ::XtRemoveInput(NextID->id_);
00330 XtID->next_ = NextID->next_;
00331 delete NextID;
00332 return;
00333 }
00334 else
00335 {
00336 XtID = NextID;
00337 NextID = NextID->next_;
00338 }
00339 }
00340 }
00341 }
00342
00343 int
00344 ACE_XtReactor::remove_handler_i (const ACE_Handle_Set &handles,
00345 ACE_Reactor_Mask mask)
00346 {
00347 return ACE_Select_Reactor::remove_handler_i (handles,
00348 mask);
00349 }
00350
00351
00352
00353
00354 void
00355 ACE_XtReactor::reset_timeout (void)
00356 {
00357
00358 ACE_ASSERT (this->context_ != 0);
00359
00360 if (timeout_)
00361 ::XtRemoveTimeOut (timeout_);
00362 timeout_ = 0;
00363
00364 ACE_Time_Value *max_wait_time =
00365 this->timer_queue_->calculate_timeout (0);
00366
00367 if (max_wait_time)
00368 timeout_ = ::XtAppAddTimeOut (this->context_,
00369 max_wait_time->msec (),
00370 TimerCallbackProc,
00371 (XtPointer) this);
00372 }
00373
00374 int
00375 ACE_XtReactor::reset_timer_interval
00376 (long timer_id,
00377 const ACE_Time_Value &interval)
00378 {
00379 ACE_TRACE ("ACE_XtReactor::reset_timer_interval");
00380 ACE_MT (ACE_GUARD_RETURN (ACE_Select_Reactor_Token, ace_mon, this->token_, -1));
00381
00382 int result = ACE_Select_Reactor::timer_queue_->reset_interval
00383 (timer_id,
00384 interval);
00385
00386 if (result == -1)
00387 return -1;
00388 else
00389 {
00390 this->reset_timeout ();
00391 return result;
00392 }
00393 }
00394
00395 long
00396 ACE_XtReactor::schedule_timer (ACE_Event_Handler *event_handler,
00397 const void *arg,
00398 const ACE_Time_Value &delay,
00399 const ACE_Time_Value &interval)
00400 {
00401 ACE_TRACE ("ACE_XtReactor::schedule_timer");
00402 ACE_MT (ACE_GUARD_RETURN (ACE_Select_Reactor_Token, ace_mon, this->token_, -1));
00403
00404 long result = ACE_Select_Reactor::schedule_timer (event_handler,
00405 arg,
00406 delay,
00407 interval);
00408 if (result == -1)
00409 return -1;
00410 else
00411 {
00412 this->reset_timeout ();
00413 return result;
00414 }
00415 }
00416
00417 int
00418 ACE_XtReactor::cancel_timer (ACE_Event_Handler *handler,
00419 int dont_call_handle_close)
00420 {
00421 ACE_TRACE ("ACE_XtReactor::cancel_timer");
00422
00423 if (ACE_Select_Reactor::cancel_timer (handler,
00424 dont_call_handle_close) == -1)
00425 return -1;
00426 else
00427 {
00428 this->reset_timeout ();
00429 return 0;
00430 }
00431 }
00432
00433 int
00434 ACE_XtReactor::cancel_timer (long timer_id,
00435 const void **arg,
00436 int dont_call_handle_close)
00437 {
00438 ACE_TRACE ("ACE_XtReactor::cancel_timer");
00439
00440 if (ACE_Select_Reactor::cancel_timer (timer_id,
00441 arg,
00442 dont_call_handle_close) == -1)
00443 return -1;
00444 else
00445 {
00446 this->reset_timeout ();
00447 return 0;
00448 }
00449 }
00450
00451 #endif