Proactor.cpp

Go to the documentation of this file.
00001 // Proactor.cpp,v 4.144 2006/04/19 19:13:09 jwillemsen Exp
00002 
00003 #include "ace/config-lite.h"
00004 #include "ace/Proactor.h"
00005 #if ((defined (ACE_WIN32) && !defined (ACE_HAS_WINCE)) || (defined (ACE_HAS_AIO_CALLS)))
00006 
00007 // This only works on Win32 platforms and on Unix platforms with aio
00008 // calls.
00009 
00010 #include "ace/Auto_Ptr.h"
00011 #include "ace/Proactor_Impl.h"
00012 #include "ace/Object_Manager.h"
00013 #include "ace/Task_T.h"
00014 #if !defined (ACE_HAS_WINCE) && !defined (ACE_LACKS_ACE_SVCCONF)
00015 #    include "ace/Service_Config.h"
00016 #  endif /* !ACE_HAS_WINCE && !ACE_LACKS_ACE_SVCCONF */
00017 
00018 
00019 ACE_RCSID (ace,
00020            Proactor,
00021            "Proactor.cpp,v 4.144 2006/04/19 19:13:09 jwillemsen Exp")
00022 
00023 
00024 #include "ace/Task_T.h"
00025 #include "ace/Log_Msg.h"
00026 #include "ace/Framework_Component.h"
00027 
00028 #if defined (ACE_HAS_AIO_CALLS)
00029 #   include "ace/POSIX_Proactor.h"
00030 #   include "ace/POSIX_CB_Proactor.h"
00031 #else /* !ACE_HAS_AIO_CALLS */
00032 #   include "ace/WIN32_Proactor.h"
00033 #endif /* ACE_HAS_AIO_CALLS */
00034 
00035 #if !defined (__ACE_INLINE__)
00036 #include "ace/Proactor.inl"
00037 #endif /* __ACE_INLINE__ */
00038 
00039 #include "ace/Auto_Event.h"
00040 
00041 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00042 
00043 /// Process-wide ACE_Proactor.
00044 ACE_Proactor *ACE_Proactor::proactor_ = 0;
00045 
00046 /// Controls whether the Proactor is deleted when we shut down (we can
00047 /// only delete it safely if we created it!)
00048 int ACE_Proactor::delete_proactor_ = 0;
00049 
00050 /**
00051  * @class ACE_Proactor_Timer_Handler
00052  *
00053  * @brief A Handler for timer. It helps in the management of timers
00054  * registered with the Proactor.
00055  *
00056  * This object has a thread that will wait on the earliest time
00057  * in a list of timers and an event. When a timer expires, the
00058  * thread will post a completion event on the port and go back
00059  * to waiting on the timer queue and event. If the event is
00060  * signaled, the thread will refresh the time it is currently
00061  * waiting on (in case the earliest time has changed).
00062  */
00063 class ACE_Proactor_Timer_Handler : public ACE_Task<ACE_NULL_SYNCH>
00064 {
00065 
00066   /// Proactor has special privileges
00067   /// Access needed to: timer_event_
00068   friend class ACE_Proactor;
00069 
00070 public:
00071   /// Constructor.
00072   ACE_Proactor_Timer_Handler (ACE_Proactor &proactor);
00073 
00074   /// Destructor.
00075   virtual ~ACE_Proactor_Timer_Handler (void);
00076 
00077   /// Proactor calls this to shut down the timer handler
00078   /// gracefully. Just calling the destructor alone doesnt do what
00079   /// <destroy> does. <destroy> make sure the thread exits properly.
00080   int destroy (void);
00081 
00082 protected:
00083   /// Run by a daemon thread to handle deferred processing. In other
00084   /// words, this method will do the waiting on the earliest timer and
00085   /// event.
00086   virtual int svc (void);
00087 
00088   /// Event to wait on.
00089   ACE_Auto_Event timer_event_;
00090 
00091   /// Proactor.
00092   ACE_Proactor &proactor_;
00093 
00094   /// Flag used to indicate when we are shutting down.
00095   int shutting_down_;
00096 };
00097 
00098 ACE_Proactor_Timer_Handler::ACE_Proactor_Timer_Handler (ACE_Proactor &proactor)
00099   : ACE_Task <ACE_NULL_SYNCH> (&proactor.thr_mgr_),
00100     proactor_ (proactor),
00101     shutting_down_ (0)
00102 {
00103 }
00104 
00105 ACE_Proactor_Timer_Handler::~ACE_Proactor_Timer_Handler (void)
00106 {
00107   // Mark for closing down.
00108   this->shutting_down_ = 1;
00109 
00110   // Signal timer event.
00111   this->timer_event_.signal ();
00112 
00113   // Wait for the Timer Handler thread to exit.
00114   this->thr_mgr ()->wait_grp (this->grp_id ());
00115 }
00116 
00117 int
00118 ACE_Proactor_Timer_Handler::svc (void)
00119 {
00120   ACE_Time_Value absolute_time;
00121   ACE_Time_Value relative_time;
00122   int result = 0;
00123 
00124   while (this->shutting_down_ == 0)
00125     {
00126       // Check whether the timer queue has any items in it.
00127       if (this->proactor_.timer_queue ()->is_empty () == 0)
00128         {
00129           // Get the earliest absolute time.
00130           absolute_time = this->proactor_.timer_queue ()->earliest_time ();
00131 
00132           // Get current time from timer queue since we don't know
00133           // which <gettimeofday> was used.
00134           ACE_Time_Value cur_time = this->proactor_.timer_queue ()->gettimeofday ();
00135 
00136           // Compare absolute time with curent time received from the
00137           // timer queue.
00138           if (absolute_time > cur_time)
00139             relative_time = absolute_time - cur_time;
00140           else
00141             relative_time = ACE_Time_Value::zero;
00142 
00143           // Block for relative time.
00144           result = this->timer_event_.wait (&relative_time, 0);
00145         }
00146       else
00147         // The timer queue has no entries, so wait indefinitely.
00148         result = this->timer_event_.wait ();
00149 
00150       // Check for timer expiries.
00151       if (result == -1)
00152         {
00153           switch (errno)
00154             {
00155             case ETIME:
00156               // timeout: expire timers
00157               this->proactor_.timer_queue ()->expire ();
00158               break;
00159             default:
00160               // Error.
00161               ACE_ERROR_RETURN ((LM_ERROR,
00162                                  ACE_LIB_TEXT ("%N:%l:(%P | %t):%p\n"),
00163                                  ACE_LIB_TEXT ("ACE_Proactor_Timer_Handler::svc:wait failed")),
00164                                 -1);
00165             }
00166         }
00167     }
00168   return 0;
00169 }
00170 
00171 // *********************************************************************
00172 
00173 ACE_Proactor_Handle_Timeout_Upcall::ACE_Proactor_Handle_Timeout_Upcall (void)
00174   : proactor_ (0)
00175 {
00176 }
00177 
00178 int
00179 ACE_Proactor_Handle_Timeout_Upcall::registration (TIMER_QUEUE &,
00180                                                   ACE_Handler *,
00181                                                   const void *)
00182 {
00183   return 0;
00184 }
00185 
00186 int
00187 ACE_Proactor_Handle_Timeout_Upcall::preinvoke (TIMER_QUEUE &,
00188                                                ACE_Handler *,
00189                                                const void *,
00190                                                int,
00191                                                const ACE_Time_Value &,
00192                                                const void *&)
00193 {
00194   return 0;
00195 }
00196 
00197 int
00198 ACE_Proactor_Handle_Timeout_Upcall::postinvoke (TIMER_QUEUE &,
00199                                                 ACE_Handler *,
00200                                                 const void *,
00201                                                 int,
00202                                                 const ACE_Time_Value &,
00203                                                 const void *)
00204 {
00205   return 0;
00206 }
00207 
00208 int
00209 ACE_Proactor_Handle_Timeout_Upcall::timeout (TIMER_QUEUE &,
00210                                              ACE_Handler *handler,
00211                                              const void *act,
00212                                              int,
00213                                              const ACE_Time_Value &time)
00214 {
00215   if (this->proactor_ == 0)
00216     ACE_ERROR_RETURN ((LM_ERROR,
00217                        ACE_LIB_TEXT ("(%t) No Proactor set in ACE_Proactor_Handle_Timeout_Upcall,")
00218                        ACE_LIB_TEXT (" no completion port to post timeout to?!@\n")),
00219                       -1);
00220 
00221   // Create the Asynch_Timer.
00222   ACE_Asynch_Result_Impl *asynch_timer =
00223     this->proactor_->create_asynch_timer (handler->proxy (),
00224                                           act,
00225                                           time,
00226                                           ACE_INVALID_HANDLE,
00227                                           0,
00228                                           -1);
00229 
00230   if (asynch_timer == 0)
00231     ACE_ERROR_RETURN ((LM_ERROR,
00232                        ACE_LIB_TEXT ("%N:%l:(%P | %t):%p\n"),
00233                        ACE_LIB_TEXT ("ACE_Proactor_Handle_Timeout_Upcall::timeout:")
00234                        ACE_LIB_TEXT ("create_asynch_timer failed")),
00235                       -1);
00236 
00237   auto_ptr<ACE_Asynch_Result_Impl> safe_asynch_timer (asynch_timer);
00238 
00239   // Post a completion.
00240   if (-1 == safe_asynch_timer->post_completion
00241       (this->proactor_->implementation ()))
00242     ACE_ERROR_RETURN ((LM_ERROR,
00243                        ACE_LIB_TEXT ("Failure in dealing with timers: ")
00244                        ACE_LIB_TEXT ("PostQueuedCompletionStatus failed\n")),
00245                       -1);
00246 
00247   // The completion has been posted.  The proactor is now responsible
00248   // for managing the asynch_timer memory.
00249   (void) safe_asynch_timer.release ();
00250 
00251   return 0;
00252 }
00253 
00254 int
00255 ACE_Proactor_Handle_Timeout_Upcall::cancel_type (TIMER_QUEUE &,
00256                                                  ACE_Handler *,
00257                                                  int,
00258                                                  int &)
00259 {
00260   // Do nothing
00261   return 0;
00262 }
00263 
00264 int
00265 ACE_Proactor_Handle_Timeout_Upcall::cancel_timer (TIMER_QUEUE &,
00266                                                   ACE_Handler *,
00267                                                   int,
00268                                                   int)
00269 {
00270   // Do nothing
00271   return 0;
00272 }
00273 
00274 int
00275 ACE_Proactor_Handle_Timeout_Upcall::deletion (TIMER_QUEUE &,
00276                                               ACE_Handler *,
00277                                               const void *)
00278 {
00279   // Do nothing
00280   return 0;
00281 }
00282 
00283 int
00284 ACE_Proactor_Handle_Timeout_Upcall::proactor (ACE_Proactor &proactor)
00285 {
00286   if (this->proactor_ == 0)
00287     {
00288       this->proactor_ = &proactor;
00289       return 0;
00290     }
00291   else
00292     ACE_ERROR_RETURN ((LM_ERROR,
00293                        ACE_LIB_TEXT ("ACE_Proactor_Handle_Timeout_Upcall is only suppose")
00294                        ACE_LIB_TEXT (" to be used with ONE (and only one) Proactor\n")),
00295                       -1);
00296 }
00297 
00298 // *********************************************************************
00299 
00300 ACE_Proactor::ACE_Proactor (ACE_Proactor_Impl *implementation,
00301                             int delete_implementation,
00302                             TIMER_QUEUE *tq)
00303   : implementation_ (0),
00304     delete_implementation_ (delete_implementation),
00305     timer_handler_ (0),
00306     timer_queue_ (0),
00307     delete_timer_queue_ (0),
00308     end_event_loop_ (0),
00309     event_loop_thread_count_ (0)
00310 {
00311   this->implementation (implementation);
00312 
00313   if (this->implementation () == 0)
00314     {
00315 #if defined (ACE_HAS_AIO_CALLS)
00316       // POSIX Proactor.
00317 #  if defined (ACE_POSIX_AIOCB_PROACTOR)
00318       ACE_NEW (implementation, ACE_POSIX_AIOCB_Proactor);
00319 #  elif defined (ACE_POSIX_SIG_PROACTOR)
00320       ACE_NEW (implementation, ACE_POSIX_SIG_Proactor);
00321 #  else /* Default order: CB (but not Lynx), SIG, AIOCB */
00322 #    if !defined (__Lynx) && !defined (__FreeBSD__)
00323       ACE_NEW (implementation, ACE_POSIX_CB_Proactor);
00324 #    else
00325 #      if defined(ACE_HAS_POSIX_REALTIME_SIGNALS)
00326       ACE_NEW (implementation, ACE_POSIX_SIG_Proactor);
00327 #      else
00328       ACE_NEW (implementation, ACE_POSIX_AIOCB_Proactor);
00329 #      endif /* ACE_HAS_POSIX_REALTIME_SIGNALS */
00330 #    endif /* !__Lynx && !__FreeBSD__ */
00331 #  endif /* ACE_POSIX_AIOCB_PROACTOR */
00332 #elif (defined (ACE_WIN32) && !defined (ACE_HAS_WINCE))
00333       // WIN_Proactor.
00334       ACE_NEW (implementation,
00335                ACE_WIN32_Proactor);
00336 #endif /* ACE_HAS_AIO_CALLS */
00337       this->implementation (implementation);
00338       this->delete_implementation_ = 1;
00339     }
00340 
00341   // Set the timer queue.
00342   this->timer_queue (tq);
00343 
00344   // Create the timer handler
00345   ACE_NEW (this->timer_handler_,
00346            ACE_Proactor_Timer_Handler (*this));
00347 
00348   // Activate <timer_handler>.
00349   if (this->timer_handler_->activate (THR_NEW_LWP) == -1)
00350     ACE_ERROR ((LM_ERROR,
00351                 ACE_LIB_TEXT ("%N:%l:(%P | %t):%p\n"),
00352                 ACE_LIB_TEXT ("Task::activate:could not create thread\n")));
00353 }
00354 
00355 ACE_Proactor::~ACE_Proactor (void)
00356 {
00357   this->close ();
00358 }
00359 
00360 ACE_Proactor *
00361 ACE_Proactor::instance (size_t /* threads */)
00362 {
00363   ACE_TRACE ("ACE_Proactor::instance");
00364 
00365   if (ACE_Proactor::proactor_ == 0)
00366     {
00367       // Perform Double-Checked Locking Optimization.
00368       ACE_MT (ACE_GUARD_RETURN (ACE_Recursive_Thread_Mutex, ace_mon,
00369                                 *ACE_Static_Object_Lock::instance (),
00370                                 0));
00371 
00372       if (ACE_Proactor::proactor_ == 0)
00373         {
00374           ACE_NEW_RETURN (ACE_Proactor::proactor_,
00375                           ACE_Proactor,
00376                           0);
00377 
00378           ACE_Proactor::delete_proactor_ = 1;
00379           ACE_REGISTER_FRAMEWORK_COMPONENT(ACE_Proactor, ACE_Proactor::proactor_);
00380         }
00381     }
00382   return ACE_Proactor::proactor_;
00383 }
00384 
00385 ACE_Proactor *
00386 ACE_Proactor::instance (ACE_Proactor * r, int delete_proactor)
00387 {
00388   ACE_TRACE ("ACE_Proactor::instance");
00389 
00390   ACE_MT (ACE_GUARD_RETURN (ACE_Recursive_Thread_Mutex, ace_mon,
00391                             *ACE_Static_Object_Lock::instance (), 0));
00392 
00393   ACE_Proactor *t = ACE_Proactor::proactor_;
00394 
00395   ACE_Proactor::delete_proactor_ = delete_proactor;
00396   ACE_Proactor::proactor_ = r;
00397   ACE_REGISTER_FRAMEWORK_COMPONENT(ACE_Proactor, ACE_Proactor::proactor_);
00398 
00399   return t;
00400 }
00401 
00402 void
00403 ACE_Proactor::close_singleton (void)
00404 {
00405   ACE_TRACE ("ACE_Proactor::close_singleton");
00406 
00407   ACE_MT (ACE_GUARD (ACE_Recursive_Thread_Mutex, ace_mon,
00408                      *ACE_Static_Object_Lock::instance ()));
00409 
00410   if (ACE_Proactor::delete_proactor_)
00411     {
00412 
00413       delete ACE_Proactor::proactor_;
00414       ACE_Proactor::proactor_ = 0;
00415       ACE_Proactor::delete_proactor_ = 0;
00416     }
00417 }
00418 
00419 const ACE_TCHAR *
00420 ACE_Proactor::dll_name (void)
00421 {
00422   return ACE_LIB_TEXT ("ACE");
00423 }
00424 
00425 const ACE_TCHAR *
00426 ACE_Proactor::name (void)
00427 {
00428   return ACE_LIB_TEXT ("ACE_Proactor");
00429 }
00430 
00431 int
00432 ACE_Proactor::check_reconfiguration (ACE_Proactor *)
00433 {
00434 #if !defined (ACE_HAS_WINCE)  &&  !defined (ACE_LACKS_ACE_SVCCONF)
00435   if (ACE_Service_Config::reconfig_occurred ())
00436     {
00437       ACE_Service_Config::reconfigure ();
00438       return 1;
00439     }
00440 #endif /* ! ACE_HAS_WINCE || ! ACE_LACKS_ACE_SVCCONF */
00441   return 0;
00442 }
00443 
00444 int
00445 ACE_Proactor::proactor_run_event_loop (PROACTOR_EVENT_HOOK eh)
00446 {
00447   ACE_TRACE ("ACE_Proactor::proactor_run_event_loop");
00448   int result = 0;
00449 
00450   {
00451     ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, mutex_, -1));
00452 
00453     // Early check. It is ok to do this without lock, since we care just
00454     // whether it is zero or non-zero.
00455     if (this->end_event_loop_ != 0)
00456       return 0;
00457 
00458     // First time you are in. Increment the thread count.
00459     this->event_loop_thread_count_ ++;
00460   }
00461 
00462   // Run the event loop.
00463   for (;;)
00464     {
00465       // Check the end loop flag. It is ok to do this without lock,
00466       // since we care just whether it is zero or non-zero.
00467       if (this->end_event_loop_ != 0)
00468         break;
00469 
00470       // <end_event_loop> is not set. Ready to do <handle_events>.
00471       result = this->handle_events ();
00472 
00473       if (eh != 0 && (*eh) (this))
00474         continue;
00475 
00476       if (result == -1)
00477         break;
00478     }
00479 
00480   // Leaving the event loop. Decrement the thread count.
00481 
00482   {
00483     // Obtain the lock in the MT environments.
00484     ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, mutex_, -1));
00485 
00486     // Decrement the thread count.
00487     this->event_loop_thread_count_ --;
00488 
00489     if (this->event_loop_thread_count_ > 0
00490        && this->end_event_loop_ != 0)
00491        this->proactor_post_wakeup_completions (1);
00492   }
00493 
00494   return result;
00495 }
00496 
00497 // Handle events for -tv- time.  handle_events updates -tv- to reflect
00498 // time elapsed, so do not return until -tv- == 0, or an error occurs.
00499 int
00500 ACE_Proactor::proactor_run_event_loop (ACE_Time_Value &tv,
00501                                        PROACTOR_EVENT_HOOK eh)
00502 {
00503   ACE_TRACE ("ACE_Proactor::proactor_run_event_loop");
00504   int result = 0;
00505 
00506   {
00507     ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, mutex_, -1));
00508 
00509     // Early check. It is ok to do this without lock, since we care just
00510     // whether it is zero or non-zero.
00511     if (this->end_event_loop_ != 0
00512        || tv == ACE_Time_Value::zero)
00513       return 0;
00514 
00515     // First time you are in. Increment the thread count.
00516     this->event_loop_thread_count_ ++;
00517   }
00518 
00519   // Run the event loop.
00520   for (;;)
00521     {
00522       // Check the end loop flag. It is ok to do this without lock,
00523       // since we care just whether it is zero or non-zero.
00524       if (this->end_event_loop_ != 0)
00525         break;
00526 
00527       // <end_event_loop> is not set. Ready to do <handle_events>.
00528       result = this->handle_events (tv);
00529 
00530       if (eh != 0 && (*eh) (this))
00531         continue;
00532 
00533       if (result == -1 || result == 0)
00534         break;
00535     }
00536 
00537   // Leaving the event loop. Decrement the thread count.
00538 
00539   {
00540     ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, mutex_, -1));
00541 
00542     // Decrement the thread count.
00543     this->event_loop_thread_count_ --;
00544 
00545     if (this->event_loop_thread_count_ > 0
00546        && this->end_event_loop_ != 0)
00547        this->proactor_post_wakeup_completions (1);
00548   }
00549 
00550   return result;
00551 }
00552 
00553 int
00554 ACE_Proactor::proactor_reset_event_loop(void)
00555 {
00556   ACE_TRACE ("ACE_Proactor::proactor_reset_event_loop");
00557 
00558   // Obtain the lock in the MT environments.
00559   ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, mutex_, -1));
00560 
00561   this->end_event_loop_ = 0;
00562   return 0;
00563 }
00564 
00565 int
00566 ACE_Proactor::proactor_end_event_loop (void)
00567 {
00568   ACE_TRACE ("ACE_Proactor::proactor_end_event_loop");
00569 
00570   int how_many = 0;
00571 
00572   {
00573     // Obtain the lock, set the end flag and post the wakeup
00574     // completions.
00575     ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, mutex_, -1));
00576 
00577     // Set the end flag.
00578     this->end_event_loop_ = 1;
00579 
00580     // Number of completions to post.
00581     how_many = this->event_loop_thread_count_;
00582     if (how_many == 0)
00583       return 0;
00584   }
00585 
00586   // Post completions to all the threads so that they will all wake
00587   // up.
00588   return this->proactor_post_wakeup_completions (how_many);
00589 }
00590 
00591 int
00592 ACE_Proactor::proactor_event_loop_done (void)
00593 {
00594   ACE_TRACE ("ACE_Proactor::proactor_event_loop_done");
00595 
00596   ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, mutex_, -1));
00597 
00598   return this->end_event_loop_ != 0 ? 1 : 0 ;
00599 }
00600 
00601 int
00602 ACE_Proactor::close (void)
00603 {
00604   // Close the implementation.
00605   if (this->implementation ()->close () == -1)
00606     ACE_ERROR_RETURN ((LM_ERROR,
00607                        ACE_LIB_TEXT ("%N:%l:(%P | %t):%p\n"),
00608                        ACE_LIB_TEXT ("ACE_Proactor::close:implementation couldnt be closed")),
00609                       -1);
00610 
00611   // Delete the implementation.
00612   if (this->delete_implementation_)
00613     {
00614       delete this->implementation ();
00615       this->implementation_ = 0;
00616     }
00617 
00618   // Delete the timer handler.
00619   if (this->timer_handler_)
00620     {
00621       delete this->timer_handler_;
00622       this->timer_handler_ = 0;
00623     }
00624 
00625   // Delete the timer queue.
00626   if (this->delete_timer_queue_)
00627     {
00628       delete this->timer_queue_;
00629       this->timer_queue_ = 0;
00630       this->delete_timer_queue_ = 0;
00631     }
00632 
00633   return 0;
00634 }
00635 
00636 int
00637 ACE_Proactor::register_handle (ACE_HANDLE handle,
00638                                const void *completion_key)
00639 {
00640   return this->implementation ()->register_handle (handle,
00641                                                    completion_key);
00642 }
00643 
00644 long
00645 ACE_Proactor::schedule_timer (ACE_Handler &handler,
00646                               const void *act,
00647                               const ACE_Time_Value &time)
00648 {
00649   return this->schedule_timer (handler,
00650                                act,
00651                                time,
00652                                ACE_Time_Value::zero);
00653 }
00654 
00655 long
00656 ACE_Proactor::schedule_repeating_timer (ACE_Handler &handler,
00657                                         const void *act,
00658                                         const ACE_Time_Value &interval)
00659 {
00660   return this->schedule_timer (handler,
00661                                act,
00662                                interval,
00663                                interval);
00664 }
00665 
00666 long
00667 ACE_Proactor::schedule_timer (ACE_Handler &handler,
00668                               const void *act,
00669                               const ACE_Time_Value &time,
00670                               const ACE_Time_Value &interval)
00671 {
00672   // absolute time.
00673   ACE_Time_Value absolute_time =
00674     this->timer_queue_->gettimeofday () + time;
00675 
00676   // Only one guy goes in here at a time
00677   ACE_MT (ACE_GUARD_RETURN (ACE_SYNCH_RECURSIVE_MUTEX,
00678                     ace_mon,
00679                     this->timer_queue_->mutex (),
00680                     -1));
00681 
00682   // Schedule the timer
00683   long result = this->timer_queue_->schedule (&handler,
00684                                               act,
00685                                               absolute_time,
00686                                               interval);
00687   if (result != -1)
00688     {
00689       // no failures: check to see if we are the earliest time
00690       if (this->timer_queue_->earliest_time () == absolute_time)
00691 
00692         // wake up the timer thread
00693         if (this->timer_handler_->timer_event_.signal () == -1)
00694           {
00695             // Cancel timer
00696             this->timer_queue_->cancel (result);
00697             result = -1;
00698           }
00699     }
00700   return result;
00701 }
00702 
00703 int
00704 ACE_Proactor::cancel_timer (long timer_id,
00705                             const void **arg,
00706                             int dont_call_handle_close)
00707 {
00708   // No need to singal timer event here. Even if the cancel timer was
00709   // the earliest, we will have an extra wakeup.
00710   return this->timer_queue_->cancel (timer_id,
00711                                      arg,
00712                                      dont_call_handle_close);
00713 }
00714 
00715 int
00716 ACE_Proactor::cancel_timer (ACE_Handler &handler,
00717                                   int dont_call_handle_close)
00718 {
00719   // No need to signal timer event here. Even if the cancel timer was
00720   // the earliest, we will have an extra wakeup.
00721   return this->timer_queue_->cancel (&handler,
00722                                      dont_call_handle_close);
00723 }
00724 
00725 int
00726 ACE_Proactor::handle_events (ACE_Time_Value &wait_time)
00727 {
00728   return implementation ()->handle_events (wait_time);
00729 }
00730 
00731 int
00732 ACE_Proactor::handle_events (void)
00733 {
00734   return this->implementation ()->handle_events ();
00735 }
00736 
00737 int
00738 ACE_Proactor::wake_up_dispatch_threads (void)
00739 {
00740   return 0;
00741 }
00742 
00743 int
00744 ACE_Proactor::close_dispatch_threads (int)
00745 {
00746   return 0;
00747 }
00748 
00749 size_t
00750 ACE_Proactor::number_of_threads (void) const
00751 {
00752   return this->implementation ()->number_of_threads ();
00753 }
00754 
00755 void
00756 ACE_Proactor::number_of_threads (size_t threads)
00757 {
00758   this->implementation ()->number_of_threads (threads);
00759 }
00760 
00761 ACE_Proactor::TIMER_QUEUE *
00762 ACE_Proactor::timer_queue (void) const
00763 {
00764   return this->timer_queue_;
00765 }
00766 
00767 void
00768 ACE_Proactor::timer_queue (TIMER_QUEUE *tq)
00769 {
00770   // Cleanup old timer queue.
00771   if (this->delete_timer_queue_)
00772     {
00773       delete this->timer_queue_;
00774       this->delete_timer_queue_ = 0;
00775     }
00776 
00777   // New timer queue.
00778   if (tq == 0)
00779     {
00780       ACE_NEW (this->timer_queue_,
00781                TIMER_HEAP);
00782       this->delete_timer_queue_ = 1;
00783     }
00784   else
00785     {
00786       this->timer_queue_ = tq;
00787       this->delete_timer_queue_ = 0;
00788     }
00789 
00790   // Set the proactor in the timer queue's functor
00791   this->timer_queue_->upcall_functor ().proactor (*this);
00792 }
00793 
00794 ACE_HANDLE
00795 ACE_Proactor::get_handle (void) const
00796 {
00797   return this->implementation ()->get_handle ();
00798 }
00799 
00800 ACE_Proactor_Impl *
00801 ACE_Proactor::implementation (void) const
00802 {
00803   return this->implementation_;
00804 }
00805 
00806 
00807 ACE_Asynch_Read_Stream_Impl *
00808 ACE_Proactor::create_asynch_read_stream (void)
00809 {
00810   return this->implementation ()->create_asynch_read_stream ();
00811 }
00812 
00813 ACE_Asynch_Write_Stream_Impl *
00814 ACE_Proactor::create_asynch_write_stream (void)
00815 {
00816   return this->implementation ()->create_asynch_write_stream ();
00817 }
00818 
00819 ACE_Asynch_Read_Dgram_Impl *
00820 ACE_Proactor::create_asynch_read_dgram (void)
00821 {
00822   return this->implementation ()->create_asynch_read_dgram ();
00823 }
00824 
00825 ACE_Asynch_Write_Dgram_Impl *
00826 ACE_Proactor::create_asynch_write_dgram (void)
00827 {
00828   return this->implementation ()->create_asynch_write_dgram ();
00829 }
00830 
00831 ACE_Asynch_Read_File_Impl *
00832 ACE_Proactor::create_asynch_read_file (void)
00833 {
00834   return this->implementation ()->create_asynch_read_file ();
00835 }
00836 
00837 ACE_Asynch_Write_File_Impl *
00838 ACE_Proactor::create_asynch_write_file (void)
00839 {
00840   return this->implementation ()->create_asynch_write_file ();
00841 }
00842 
00843 ACE_Asynch_Accept_Impl *
00844 ACE_Proactor::create_asynch_accept (void)
00845 {
00846   return this->implementation ()->create_asynch_accept ();
00847 }
00848 
00849 ACE_Asynch_Connect_Impl *
00850 ACE_Proactor::create_asynch_connect (void)
00851 {
00852   return this->implementation ()->create_asynch_connect ();
00853 }
00854 
00855 ACE_Asynch_Transmit_File_Impl *
00856 ACE_Proactor::create_asynch_transmit_file (void)
00857 {
00858   return this->implementation ()->create_asynch_transmit_file ();
00859 }
00860 
00861 ACE_Asynch_Read_Stream_Result_Impl *
00862 ACE_Proactor::create_asynch_read_stream_result
00863   (ACE_Handler::Proxy_Ptr &handler_proxy,
00864    ACE_HANDLE handle,
00865    ACE_Message_Block &message_block,
00866    u_long bytes_to_read,
00867    const void* act,
00868    ACE_HANDLE event,
00869    int priority,
00870    int signal_number)
00871 {
00872   return this->implementation ()->create_asynch_read_stream_result
00873     (handler_proxy,
00874      handle,
00875      message_block,
00876      bytes_to_read,
00877      act,
00878      event,
00879      priority,
00880      signal_number);
00881 }
00882 
00883 
00884 ACE_Asynch_Write_Stream_Result_Impl *
00885 ACE_Proactor::create_asynch_write_stream_result
00886   (ACE_Handler::Proxy_Ptr &handler_proxy,
00887    ACE_HANDLE handle,
00888    ACE_Message_Block &message_block,
00889    u_long bytes_to_write,
00890    const void* act,
00891    ACE_HANDLE event,
00892    int priority,
00893    int signal_number)
00894 {
00895   return this->implementation ()->create_asynch_write_stream_result
00896     (handler_proxy,
00897      handle,
00898      message_block,
00899      bytes_to_write,
00900      act,
00901      event,
00902      priority,
00903      signal_number);
00904 }
00905 
00906 ACE_Asynch_Read_File_Result_Impl *
00907 ACE_Proactor::create_asynch_read_file_result
00908   (ACE_Handler::Proxy_Ptr &handler_proxy,
00909    ACE_HANDLE handle,
00910    ACE_Message_Block &message_block,
00911    u_long bytes_to_read,
00912    const void* act,
00913    u_long offset,
00914    u_long offset_high,
00915    ACE_HANDLE event,
00916    int priority,
00917    int signal_number)
00918 {
00919   return this->implementation ()->create_asynch_read_file_result
00920     (handler_proxy,
00921      handle,
00922      message_block,
00923      bytes_to_read,
00924      act,
00925      offset,
00926      offset_high,
00927      event,
00928      priority,
00929      signal_number);
00930 }
00931 
00932 ACE_Asynch_Write_File_Result_Impl *
00933 ACE_Proactor::create_asynch_write_file_result
00934   (ACE_Handler::Proxy_Ptr &handler_proxy,
00935    ACE_HANDLE handle,
00936    ACE_Message_Block &message_block,
00937    u_long bytes_to_write,
00938    const void* act,
00939    u_long offset,
00940    u_long offset_high,
00941    ACE_HANDLE event,
00942    int priority,
00943    int signal_number)
00944 {
00945   return this->implementation ()->create_asynch_write_file_result
00946     (handler_proxy,
00947      handle,
00948      message_block,
00949      bytes_to_write,
00950      act,
00951      offset,
00952      offset_high,
00953      event,
00954      priority,
00955      signal_number);
00956 }
00957 
00958 ACE_Asynch_Read_Dgram_Result_Impl *
00959 ACE_Proactor::create_asynch_read_dgram_result
00960   (ACE_Handler::Proxy_Ptr &handler_proxy,
00961    ACE_HANDLE handle,
00962    ACE_Message_Block *message_block,
00963    size_t bytes_to_read,
00964    int flags,
00965    int protocol_family,
00966    const void* act,
00967    ACE_HANDLE event,
00968    int priority,
00969    int signal_number)
00970 {
00971   return this->implementation()->create_asynch_read_dgram_result
00972     (handler_proxy,
00973      handle,
00974      message_block,
00975      bytes_to_read,
00976      flags,
00977      protocol_family,
00978      act,
00979      event,
00980      priority,
00981      signal_number);
00982 }
00983 
00984 ACE_Asynch_Write_Dgram_Result_Impl *
00985 ACE_Proactor::create_asynch_write_dgram_result
00986   (ACE_Handler::Proxy_Ptr &handler_proxy,
00987    ACE_HANDLE handle,
00988    ACE_Message_Block *message_block,
00989    size_t bytes_to_write,
00990    int flags,
00991    const void* act,
00992    ACE_HANDLE event,
00993    int priority,
00994    int signal_number)
00995 {
00996   return this->implementation()->create_asynch_write_dgram_result
00997     (handler_proxy,
00998      handle,
00999      message_block,
01000      bytes_to_write,
01001      flags,
01002      act,
01003      event,
01004      priority,
01005      signal_number);
01006 }
01007 
01008 ACE_Asynch_Accept_Result_Impl *
01009 ACE_Proactor::create_asynch_accept_result
01010   (ACE_Handler::Proxy_Ptr &handler_proxy,
01011    ACE_HANDLE listen_handle,
01012    ACE_HANDLE accept_handle,
01013    ACE_Message_Block &message_block,
01014    u_long bytes_to_read,
01015    const void* act,
01016    ACE_HANDLE event,
01017    int priority,
01018    int signal_number)
01019 {
01020   return this->implementation ()->create_asynch_accept_result
01021     (handler_proxy,
01022      listen_handle,
01023      accept_handle,
01024      message_block,
01025      bytes_to_read,
01026      act,
01027      event,
01028      priority,
01029      signal_number);
01030 }
01031 
01032 ACE_Asynch_Connect_Result_Impl *
01033 ACE_Proactor::create_asynch_connect_result
01034   (ACE_Handler::Proxy_Ptr &handler_proxy,
01035    ACE_HANDLE  connect_handle,
01036    const void* act,
01037    ACE_HANDLE event,
01038    int priority,
01039    int signal_number)
01040 {
01041   return this->implementation ()->create_asynch_connect_result
01042     (handler_proxy,
01043      connect_handle,
01044      act,
01045      event,
01046      priority,
01047      signal_number);
01048 }
01049 
01050 ACE_Asynch_Transmit_File_Result_Impl *
01051 ACE_Proactor::create_asynch_transmit_file_result
01052   (ACE_Handler::Proxy_Ptr &handler_proxy,
01053    ACE_HANDLE socket,
01054    ACE_HANDLE file,
01055    ACE_Asynch_Transmit_File::Header_And_Trailer *header_and_trailer,
01056    u_long bytes_to_write,
01057    u_long offset,
01058    u_long offset_high,
01059    u_long bytes_per_send,
01060    u_long flags,
01061    const void *act,
01062    ACE_HANDLE event,
01063    int priority,
01064    int signal_number)
01065 {
01066   return this->implementation ()->create_asynch_transmit_file_result
01067     (handler_proxy,
01068      socket,
01069      file,
01070      header_and_trailer,
01071      bytes_to_write,
01072      offset,
01073      offset_high,
01074      bytes_per_send,
01075      flags,
01076      act,
01077      event,
01078      priority,
01079      signal_number);
01080 }
01081 
01082 ACE_Asynch_Result_Impl *
01083 ACE_Proactor::create_asynch_timer
01084   (ACE_Handler::Proxy_Ptr &handler_proxy,
01085    const void *act,
01086    const ACE_Time_Value &tv,
01087    ACE_HANDLE event,
01088    int priority,
01089    int signal_number)
01090 {
01091   return this->implementation ()->create_asynch_timer
01092     (handler_proxy,
01093      act,
01094      tv,
01095      event,
01096      priority,
01097      signal_number);
01098 }
01099 
01100 int
01101 ACE_Proactor::proactor_post_wakeup_completions (int how_many)
01102 {
01103   return this->implementation ()->post_wakeup_completions (how_many);
01104 }
01105 
01106 void
01107 ACE_Proactor::implementation (ACE_Proactor_Impl *implementation)
01108 {
01109   this->implementation_ = implementation;
01110 }
01111 
01112 ACE_END_VERSIONED_NAMESPACE_DECL
01113 
01114 #else /* !ACE_WIN32 || !ACE_HAS_AIO_CALLS */
01115 
01116 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
01117 
01118 ACE_Proactor *
01119 ACE_Proactor::instance (size_t /* threads */)
01120 {
01121   return 0;
01122 }
01123 
01124 ACE_Proactor *
01125 ACE_Proactor::instance (ACE_Proactor *)
01126 {
01127   return 0;
01128 }
01129 
01130 void
01131 ACE_Proactor::close_singleton (void)
01132 {
01133 }
01134 
01135 int
01136 ACE_Proactor::run_event_loop (void)
01137 {
01138   // not implemented
01139   return -1;
01140 }
01141 
01142 int
01143 ACE_Proactor::run_event_loop (ACE_Time_Value &)
01144 {
01145   // not implemented
01146   return -1;
01147 }
01148 
01149 int
01150 ACE_Proactor::end_event_loop (void)
01151 {
01152   // not implemented
01153   return -1;
01154 }
01155 
01156 sig_atomic_t
01157 ACE_Proactor::event_loop_done (void)
01158 {
01159   return sig_atomic_t (1);
01160 }
01161 
01162 ACE_END_VERSIONED_NAMESPACE_DECL
01163 
01164 #endif /* ACE_WIN32 || ACE_HAS_AIO_CALLS*/

Generated on Thu Nov 9 09:41:59 2006 for ACE by doxygen 1.3.6