00001 #include "ace_pch.h"
00002
00003
00004 #ifndef ACE_SVC_HANDLER_C
00005 #define ACE_SVC_HANDLER_C
00006
00007 #include "ace/Svc_Handler.h"
00008
00009 #if !defined (ACE_LACKS_PRAGMA_ONCE)
00010 # pragma once
00011 #endif
00012
00013 #include "ace/Object_Manager.h"
00014 #include "ace/Connection_Recycling_Strategy.h"
00015
00016 #include "ace/Dynamic.h"
00017
00018 ACE_RCSID(ace, Svc_Handler, "$Id: Svc_Handler.cpp,v 1.1.1.4.2.1 2003/03/13 19:44:22 chad Exp $")
00019
00020 #define PR_ST_1 ACE_PEER_STREAM_1
00021 #define PR_ST_2 ACE_PEER_STREAM_2
00022
00023 template <PR_ST_1, ACE_SYNCH_DECL> void *
00024 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator new (size_t,
00025 void *p)
00026 {
00027 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator new (NOOP, 2 parameters)");
00028 return p;
00029 }
00030
00031 #if !defined (ACE_LACKS_PLACEMENT_OPERATOR_DELETE)
00032 template <PR_ST_1, ACE_SYNCH_DECL> void
00033 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator delete (void *,
00034 void *)
00035 {
00036 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator delete (NOOP, 2 parameters)");
00037 return;
00038 }
00039 #endif
00040
00041 template <PR_ST_1, ACE_SYNCH_DECL> void *
00042 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator new (size_t n)
00043 {
00044 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator new");
00045
00046 ACE_Dynamic *const dynamic_instance = ACE_Dynamic::instance ();
00047
00048 if (dynamic_instance == 0)
00049 {
00050
00051
00052
00053 ACE_ASSERT (dynamic_instance != 0);
00054
00055 ACE_throw_bad_alloc;
00056 }
00057 else
00058 {
00059
00060
00061 dynamic_instance->set ();
00062
00063 return ::new char[n];
00064 }
00065 }
00066
00067 #if defined (ACE_HAS_NEW_NOTHROW)
00068 template <PR_ST_1, ACE_SYNCH_DECL> void *
00069 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator new (size_t n,
00070 const ACE_nothrow_t&)
00071 {
00072 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator new(nothrow)");
00073
00074 ACE_Dynamic *const dynamic_instance = ACE_Dynamic::instance ();
00075
00076 if (dynamic_instance == 0)
00077 {
00078
00079
00080
00081 ACE_ASSERT (dynamic_instance != 0);
00082
00083 return 0;
00084 }
00085 else
00086 {
00087
00088
00089 dynamic_instance->set ();
00090
00091 return ::new(ACE_nothrow) char[n];
00092 }
00093 }
00094 #endif
00095
00096 template <PR_ST_1, ACE_SYNCH_DECL> void
00097 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::destroy (void)
00098 {
00099 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::destroy");
00100
00101
00102
00103 if (this->mod_ == 0 && this->dynamic_ && this->closing_ == 0)
00104
00105
00106
00107
00108 delete this;
00109 }
00110
00111 template <PR_ST_1, ACE_SYNCH_DECL> void
00112 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator delete (void *obj)
00113 {
00114 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::operator delete");
00115
00116
00117
00118 char *tmp = (char *) obj;
00119 ::delete [] tmp;
00120 }
00121
00122
00123
00124 template <PR_ST_1, ACE_SYNCH_DECL>
00125 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::ACE_Svc_Handler (ACE_Thread_Manager *tm,
00126 ACE_Message_Queue<ACE_SYNCH_USE> *mq,
00127 ACE_Reactor *reactor)
00128 : ACE_Task<ACE_SYNCH_USE> (tm, mq),
00129 closing_ (0),
00130 recycler_ (0),
00131 recycling_act_ (0)
00132 {
00133 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::ACE_Svc_Handler");
00134
00135 this->reactor (reactor);
00136
00137
00138
00139
00140
00141
00142
00143
00144 this->dynamic_ = ACE_Dynamic::instance ()->is_dynamic ();
00145
00146 if (this->dynamic_ != 0)
00147
00148 ACE_Dynamic::instance ()->reset ();
00149 }
00150
00151
00152
00153
00154 template <PR_ST_1, ACE_SYNCH_DECL> int
00155 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::open (void *)
00156 {
00157 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::open");
00158 #if defined (ACE_DEBUGGING)
00159 ACE_TCHAR buf[BUFSIZ];
00160 ACE_PEER_STREAM_ADDR client_addr;
00161
00162 if (this->peer_.get_remote_addr (client_addr) == -1)
00163 ACE_ERROR_RETURN ((LM_ERROR,
00164 ACE_LIB_TEXT ("%p\n"),
00165 ACE_LIB_TEXT ("get_remote_addr")),
00166 -1);
00167 else if (client_addr.addr_to_string (buf, sizeof buf) == -1)
00168 ACE_ERROR_RETURN ((LM_ERROR,
00169 ACE_LIB_TEXT ("%p\n"),
00170 ACE_LIB_TEXT ("can't obtain peer's address")),
00171 -1);
00172 ACE_DEBUG ((LM_DEBUG,
00173 ACE_LIB_TEXT ("connected to %s on fd %d\n"),
00174 buf,
00175 this->peer_.get_handle ()));
00176 #endif
00177 if (this->reactor ()
00178 && this->reactor ()->register_handler
00179 (this,
00180 ACE_Event_Handler::READ_MASK) == -1)
00181 ACE_ERROR_RETURN ((LM_ERROR,
00182 ACE_LIB_TEXT ("%p\n"),
00183 ACE_LIB_TEXT ("unable to register client handler")),
00184 -1);
00185 return 0;
00186 }
00187
00188
00189
00190 template <PR_ST_1, ACE_SYNCH_DECL> void
00191 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::shutdown (void)
00192 {
00193 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::shutdown");
00194
00195
00196 if (this->reactor ())
00197 {
00198 ACE_Reactor_Mask mask = ACE_Event_Handler::ALL_EVENTS_MASK |
00199 ACE_Event_Handler::DONT_CALL;
00200
00201
00202 this->reactor ()->cancel_timer (this);
00203
00204 if (this->peer ().get_handle () != ACE_INVALID_HANDLE)
00205
00206 this->reactor ()->remove_handler (this, mask);
00207 }
00208
00209
00210 if (this->recycler ())
00211 this->recycler ()->purge (this->recycling_act_);
00212
00213 this->peer ().close ();
00214 }
00215
00216 template <PR_ST_1, ACE_SYNCH_DECL> void
00217 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::cleanup_hint (void **act_holder)
00218 {
00219 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::cleanup_hint");
00220
00221
00222 if (this->recycler ())
00223 this->recycler ()->cleanup_hint (this->recycling_act_,
00224 act_holder);
00225 }
00226
00227 template <PR_ST_1, ACE_SYNCH_DECL> void
00228 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::dump (void) const
00229 {
00230 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::dump");
00231
00232 this->peer_.dump ();
00233 ACE_DEBUG ((LM_DEBUG,
00234 "dynamic_ = %d\n",
00235 this->dynamic_));
00236 ACE_DEBUG ((LM_DEBUG,
00237 "closing_ = %d\n",
00238 this->closing_));
00239 ACE_DEBUG ((LM_DEBUG,
00240 "recycler_ = %d\n",
00241 this->recycler_));
00242 ACE_DEBUG ((LM_DEBUG,
00243 "recycling_act_ = %d\n",
00244 this->recycling_act_));
00245 }
00246
00247 template <PR_ST_1, ACE_SYNCH_DECL> ACE_PEER_STREAM &
00248 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::peer (void) const
00249 {
00250 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::peer");
00251 return (ACE_PEER_STREAM &) this->peer_;
00252 }
00253
00254
00255
00256 template <PR_ST_1, ACE_SYNCH_DECL> ACE_HANDLE
00257 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::get_handle (void) const
00258 {
00259 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::get_handle");
00260 return this->peer_.get_handle ();
00261 }
00262
00263
00264
00265 template <PR_ST_1, ACE_SYNCH_DECL> void
00266 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::set_handle (ACE_HANDLE h)
00267 {
00268 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::set_handle");
00269 this->peer_.set_handle (h);
00270 }
00271
00272 template <PR_ST_1, ACE_SYNCH_DECL>
00273 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::~ACE_Svc_Handler (void)
00274 {
00275 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::~ACE_Svc_Handler");
00276
00277 if (this->closing_ == 0)
00278 {
00279
00280
00281
00282 this->closing_ = 1;
00283
00284 this->shutdown ();
00285 }
00286 }
00287
00288 template <PR_ST_1, ACE_SYNCH_DECL> int
00289 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::handle_close (ACE_HANDLE,
00290 ACE_Reactor_Mask)
00291 {
00292 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::handle_close");
00293
00294 this->destroy ();
00295 return 0;
00296 }
00297
00298 template <PR_ST_1, ACE_SYNCH_DECL> int
00299 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::handle_timeout (const ACE_Time_Value &,
00300 const void *)
00301 {
00302 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::handle_timeout");
00303 return this->handle_close ();
00304 }
00305
00306 template <PR_ST_1, ACE_SYNCH_DECL> int
00307 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::close (u_long)
00308 {
00309 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::close");
00310 return this->handle_close ();
00311 }
00312
00313 template <PR_ST_1, ACE_SYNCH_DECL> int
00314 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::init (int argc, ACE_TCHAR *argv[])
00315 {
00316 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::init");
00317 ACE_UNUSED_ARG (argc);
00318 ACE_UNUSED_ARG (argv);
00319 return -1;
00320 }
00321
00322 template <PR_ST_1, ACE_SYNCH_DECL> int
00323 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::fini (void)
00324 {
00325 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::fini");
00326 return -1;
00327 }
00328
00329 template <PR_ST_1, ACE_SYNCH_DECL> int
00330 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::info (ACE_TCHAR **, size_t) const
00331 {
00332 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::info");
00333 return -1;
00334 }
00335
00336 template <PR_ST_1, ACE_SYNCH_DECL> int
00337 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::idle (u_long flags)
00338 {
00339 if (this->recycler ())
00340 return this->recycler ()->cache (this->recycling_act_);
00341 else
00342 return this->close (flags);
00343 }
00344
00345 template <PR_ST_1, ACE_SYNCH_DECL> int
00346 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycle_state (ACE_Recyclable_State new_state)
00347 {
00348 if (this->recycler ())
00349 return this->recycler ()->recycle_state (this->recycling_act_,
00350 new_state);
00351
00352 return 0;
00353 }
00354
00355 template <PR_ST_1, ACE_SYNCH_DECL> ACE_Recyclable_State
00356 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycle_state (void) const
00357 {
00358 if (this->recycler ())
00359 return this->recycler ()->recycle_state (this->recycling_act_);
00360
00361 return ACE_RECYCLABLE_UNKNOWN;
00362 }
00363
00364 template <PR_ST_1, ACE_SYNCH_DECL> void
00365 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycler (ACE_Connection_Recycling_Strategy *recycler,
00366 const void *recycling_act)
00367 {
00368 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycler");
00369 this->recycler_ = recycler;
00370 this->recycling_act_ = recycling_act;
00371 }
00372
00373 template <PR_ST_1, ACE_SYNCH_DECL> ACE_Connection_Recycling_Strategy *
00374 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycler (void) const
00375 {
00376 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycler");
00377 return this->recycler_;
00378 }
00379
00380 template <PR_ST_1, ACE_SYNCH_DECL> const void *
00381 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycling_act (void) const
00382 {
00383 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycling_act");
00384 return this->recycling_act_;
00385 }
00386
00387 template <PR_ST_1, ACE_SYNCH_DECL> int
00388 ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycle (void *)
00389 {
00390 ACE_TRACE ("ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::recycle");
00391
00392 return 0;
00393 }
00394
00395 template <PR_ST_1, ACE_SYNCH_DECL>
00396 ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::~ACE_Buffered_Svc_Handler (void)
00397 {
00398 this->flush ();
00399 }
00400
00401 template <PR_ST_1, ACE_SYNCH_DECL>
00402 ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::ACE_Buffered_Svc_Handler (ACE_Thread_Manager *tm,
00403 ACE_Message_Queue<ACE_SYNCH_USE> *mq,
00404 ACE_Reactor *reactor,
00405 size_t maximum_buffer_size,
00406 ACE_Time_Value *timeout)
00407 : ACE_Svc_Handler<PR_ST_2, ACE_SYNCH_USE> (tm, mq, reactor),
00408 maximum_buffer_size_ (maximum_buffer_size),
00409 current_buffer_size_ (0),
00410 timeoutp_ (timeout)
00411 {
00412 ACE_TRACE ("ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::ACE_Buffered_Svc_Handler");
00413
00414 if (this->timeoutp_ != 0)
00415 {
00416 this->interval_ = *timeout;
00417 this->next_timeout_ = ACE_OS::gettimeofday () + this->interval_;
00418 }
00419 }
00420
00421 template <PR_ST_1, ACE_SYNCH_DECL> int
00422 ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::put (ACE_Message_Block *mb,
00423 ACE_Time_Value *tv)
00424 {
00425 ACE_GUARD_RETURN (ACE_SYNCH_MUTEX_T, m, this->msg_queue ()->lock (), -1);
00426
00427
00428 if (this->putq (mb, tv) == -1)
00429 return -1;
00430 else
00431 {
00432
00433 this->current_buffer_size_ += mb->total_size ();
00434
00435
00436
00437 if (this->current_buffer_size_ >= this->maximum_buffer_size_
00438 || (this->timeoutp_ != 0
00439 && this->next_timeout_ <= ACE_OS::gettimeofday ()))
00440 return this->flush_i ();
00441 else
00442 return 0;
00443 }
00444 }
00445
00446
00447
00448 template <PR_ST_1, ACE_SYNCH_DECL> int
00449 ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::flush (void)
00450 {
00451 ACE_GUARD_RETURN (ACE_SYNCH_MUTEX_T, m, this->msg_queue ()->lock (), -1);
00452
00453 return this->flush_i ();
00454 }
00455
00456 template <PR_ST_1, ACE_SYNCH_DECL> int
00457 ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::flush_i (void)
00458 {
00459 ACE_Message_Queue_Iterator<ACE_SYNCH_USE> iterator (*this->msg_queue ());
00460 ACE_Message_Block *mblk;
00461 int result = 0;
00462
00463
00464
00465 if (iterator.next (mblk) != 0)
00466 result = this->peer ().send_n (mblk);
00467
00468
00469 if (result != -1)
00470 this->msg_queue ()->flush_i ();
00471
00472 if (this->timeoutp_ != 0)
00473
00474 this->next_timeout_ += this->interval_;
00475
00476 this->current_buffer_size_ = 0;
00477
00478 return result;
00479 }
00480
00481 template <PR_ST_1, ACE_SYNCH_DECL> void
00482 ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::dump (void) const
00483 {
00484 ACE_TRACE ("ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::dump");
00485
00486 ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::dump ();
00487 ACE_DEBUG ((LM_DEBUG,
00488 "maximum_buffer_size_ = %d\n",
00489 this->maximum_buffer_size_));
00490 ACE_DEBUG ((LM_DEBUG,
00491 "current_buffer_size_ = %d\n",
00492 this->current_buffer_size_));
00493 if (this->timeoutp_ != 0)
00494 ACE_DEBUG ((LM_DEBUG,
00495 "next_timeout_.sec = %d, next_timeout_.usec = %d\n",
00496 this->next_timeout_.sec (),
00497 this->next_timeout_.usec ()));
00498 }
00499
00500 template <PR_ST_1, ACE_SYNCH_DECL> int
00501 ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::handle_timeout (const ACE_Time_Value &,
00502 const void *)
00503 {
00504 ACE_TRACE ("ACE_Buffered_Svc_Handler<PR_ST_2, ACE_SYNCH_USE>::handle_timeout");
00505 return 0;
00506 }
00507
00508 #undef PR_ST_1
00509 #undef PR_ST_2
00510 #endif