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