#include <Connection_Handler.h>
Inheritance diagram for TAO_Connection_Handler:
Public Member Functions | |
TAO_Connection_Handler (void) | |
Constructor. | |
TAO_Connection_Handler (TAO_ORB_Core *orb_core) | |
Constructor. | |
virtual | ~TAO_Connection_Handler (void) |
Destructor. | |
TAO_Transport * | transport (void) |
Return the underlying transport object. | |
void | transport (TAO_Transport *transport) |
Set the underlying transport object. | |
bool | is_closed (void) const |
Is the handler closed or timed out? | |
bool | is_open (void) const |
Is the handler open? | |
bool | is_timeout (void) const |
Closed due to timeout? | |
bool | is_connecting (void) const |
Is the handler in the process of being connected? | |
virtual int | close_connection (void)=0 |
Close the underlying connection. | |
virtual int | handle_input (ACE_HANDLE fd)=0 |
int | svc_i (void) |
virtual int | open_handler (void *)=0 |
A open () hook. | |
virtual int | close_handler (void) |
void | connection_pending (void) |
void | cancel_pending_connection (void) |
virtual int | set_dscp_codepoint (CORBA::Boolean set_network_priority) |
virtual int | set_dscp_codepoint (CORBA::Long dscp_codepoint) |
virtual int | release_os_resources (void) |
Release the OS resources related to this handler. | |
Protected Member Functions | |
TAO_ORB_Core * | orb_core (void) |
Return our TAO_ORB_Core pointer. | |
int | shared_open (void) |
int | set_socket_option (ACE_SOCK &sock, int snd_size, int rcv_size) |
Set options on the socket. | |
Helper methods for Event_Handler-based derived classes. | |
Many (actually all so far) implementations of TAO_Connection_Handler are a mixin of TAO_Connection_Handler and some form of ACE_Event_Handler. The following methods simplify such implementations by capturing the common code in a single place. | |
int | handle_output_eh (ACE_HANDLE h, ACE_Event_Handler *eh) |
Implement the handle_output() callback. | |
int | handle_input_eh (ACE_HANDLE h, ACE_Event_Handler *eh) |
Implement the handle_input() callback. | |
int | handle_input_internal (ACE_HANDLE h, ACE_Event_Handler *eh) |
Implement the handle_output() callback. | |
int | close_connection_eh (ACE_Event_Handler *eh) |
virtual void | pre_io_hook (int &return_value) |
virtual void | pos_io_hook (int &return_value) |
Private Attributes | |
TAO_ORB_Core *const | orb_core_ |
Pointer to the TAO_ORB_Core. | |
TAO_Transport * | transport_ |
Transport object reference. | |
ACE_Lock * | lock_ |
bool | connection_pending_ |
Stores the connection pending state. |
This class is an abstraction for the connection handlers. The connections handler in every protocol can derive from this class as well as the ACE_Svc_Handler specialised for the right protocol. This way, most of the common code for the different protocols would be in this implementation.
Definition at line 56 of file Connection_Handler.h.
|
Constructor.
|
|
Constructor.
Definition at line 26 of file Connection_Handler.cpp. References TAO_Resource_Factory::create_cached_connection_lock(), TAO_ORB_Core::resource_factory(), and TAO_LF_Event::state_changed().
00027 : orb_core_ (orb_core), 00028 transport_ (0), 00029 connection_pending_ (false) 00030 { 00031 // @todo: We need to have a distinct option/ method in the resource 00032 // factory for this and TAO_Transport. 00033 this->lock_ = 00034 this->orb_core_->resource_factory ()->create_cached_connection_lock (); 00035 00036 // Put ourselves in the connection wait state as soon as we get 00037 // created 00038 this->state_changed (TAO_LF_Event::LFS_CONNECTION_WAIT, 00039 this->orb_core_->leader_follower ()); 00040 } |
|
Destructor.
Definition at line 42 of file Connection_Handler.cpp.
00043 { 00044 // @@ TODO Use auto_ptr<> 00045 delete this->lock_; 00046 00047 //@@ CONNECTION_HANDLER_DESTRUCTOR_ADD_HOOK 00048 } |
|
A pending connection may be canceled due to an error detected while the initiating thread is still in the Connector. Definition at line 58 of file Connection_Handler.inl. References connection_pending_, TAO_Transport::remove_reference(), and transport(). Referenced by TAO_IIOP_Connector::complete_connection(), and shared_open().
00059 { 00060 if (this->connection_pending_) 00061 { 00062 this->connection_pending_ = false; 00063 this->transport()->remove_reference(); 00064 } 00065 } |
|
Close the underlying connection. Used by the ORB to actively close connections that are idle, stale or somehow are determined to be broken before the Reactor does.
Implemented in TAO_IIOP_Connection_Handler. Referenced by TAO_Transport::close_connection(), handle_input_eh(), and TAO_Thread_Per_Connection_Handler::~TAO_Thread_Per_Connection_Handler(). |
|
Implement close_connection() for Connection_Handlers that are also Event_Handlers. Definition at line 298 of file Connection_Handler.cpp. References ACE_ASSERT, ACE_DEBUG, ACE_Reactor::cancel_timer(), ACE_Event_Handler::get_handle(), TAO_ORB_Core::has_shutdown(), TAO_Transport::id(), TAO_Wait_Strategy::is_registered(), LM_DEBUG, TAO_Transport::orb_core(), TAO_Transport::pre_close(), TAO_ORB_Core::reactor(), ACE_Event_Handler::reactor(), ACE_Reactor::remove_handler(), TAO_Transport::send_connection_closed_notifications(), TAO_LF_Event::state_changed(), TAO_debug_level, transport(), and TAO_Transport::wait_strategy(). Referenced by TAO_IIOP_Connection_Handler::close_connection().
00299 { 00300 // Save the ID for debugging messages 00301 ACE_HANDLE handle = eh->get_handle (); 00302 00303 size_t const id = this->transport ()->id (); 00304 if (TAO_debug_level) 00305 { 00306 ACE_DEBUG ((LM_DEBUG, 00307 "TAO (%P|%t) - Connection_Handler[%d]::" 00308 "close_connection_eh, purging entry from cache\n", 00309 handle)); 00310 } 00311 00312 this->transport ()->pre_close (); 00313 00314 // @@ This seems silly, but if we have no reason to be in the 00315 // reactor, then we dont remove ourselves. 00316 if (this->transport ()->wait_strategy ()->is_registered ()) 00317 { 00318 ACE_Reactor *eh_reactor = eh->reactor (); 00319 00320 if (this->orb_core_->has_shutdown () == 0) 00321 { 00322 // If the ORB is nil, get the reactor from orb_core which gets it 00323 // from LF. 00324 if (eh_reactor == 0) 00325 eh_reactor = this->transport()->orb_core()->reactor (); 00326 } 00327 00328 // The Reactor must not be null, otherwise something else is 00329 // horribly broken. 00330 ACE_ASSERT (eh_reactor != 0); 00331 00332 if (TAO_debug_level) 00333 { 00334 ACE_DEBUG ((LM_DEBUG, 00335 "TAO (%P|%t) - Connection_Handler[%d]::" 00336 "close_connection_eh, removing from the reactor\n", 00337 handle)); 00338 } 00339 00340 // Use id instead of handle. Why? "handle" may be invalid for RW 00341 // cases when drop_reply_on_shutdown is on, and when the 00342 // orb_core is shutting down. This means that the handler will 00343 // be left behind in the reactor which would create problems 00344 // later. Just forcefully remove them. If none exists reactor 00345 // will make things safer. 00346 ACE_HANDLE tmp_handle = handle; 00347 if (this->orb_core_->has_shutdown ()) 00348 tmp_handle = (ACE_HANDLE) id; 00349 00350 eh_reactor->remove_handler (tmp_handle, 00351 ACE_Event_Handler::ALL_EVENTS_MASK | 00352 ACE_Event_Handler::DONT_CALL); 00353 00354 // Also cancel any timers, we may create those for time-limited 00355 // buffering 00356 if (TAO_debug_level) 00357 { 00358 ACE_DEBUG ((LM_DEBUG, 00359 "TAO (%P|%t) - Connection_Handler[%d]::" 00360 "close_connection_eh, cancel all timers\n", 00361 handle)); 00362 } 00363 00364 eh_reactor->cancel_timer (eh); 00365 00366 // @@ This seems silly, the reactor is a much better authority to 00367 // find out if a handle is registered... 00368 this->transport ()->wait_strategy ()->is_registered (false); 00369 } 00370 00371 // This call should be made only after the cache and reactor are 00372 // cleaned up. This call can make upcalls to the application which 00373 // in turn can make remote calls (Bug 1551 and Bug 1482). The remote 00374 // calls from the application can try to use this handler from the 00375 // cache or from the reactor. So clean them up before this is 00376 // called. 00377 this->transport ()->send_connection_closed_notifications (); 00378 this->state_changed (TAO_LF_Event::LFS_CONNECTION_CLOSED, 00379 this->orb_core_->leader_follower ()); 00380 00381 if (TAO_debug_level) 00382 { 00383 ACE_DEBUG ((LM_DEBUG, 00384 "TAO (%P|%t) - Connection_Handler[%d]::" 00385 "close_connection_eh\n", 00386 id)); 00387 } 00388 00389 return 1; 00390 } |
|
A close() hook, called by the Transport Connector when they want to close this handler Definition at line 432 of file Connection_Handler.cpp. References TAO_Transport::purge_entry(), TAO_Transport::remove_reference(), TAO_LF_Event::state_changed(), and transport(). Referenced by TAO_Connector::check_connection_closure(), and TAO_IIOP_Connection_Handler::close().
00433 { 00434 this->state_changed (TAO_LF_Event::LFS_CONNECTION_CLOSED, 00435 this->orb_core_->leader_follower ()); 00436 this->transport ()->purge_entry(); 00437 this->transport ()->remove_reference (); 00438 00439 // @@ I think that if the connection_pending state is true 00440 // when close_handler is calld, we should probably release 00441 // another reference so that the connector doesn't have to 00442 // worry about it. 00443 00444 return 0; 00445 } |
|
When waiting for an asynchronous connection to complete an additional reference must be maintained, related to bugzilla #2417. However once the connection is successfully established, this reference must be removed. Using connection_pending allows the connection handler to know that it is opening as a result of a delayed asynch connection rather than an immediate synch connection, which has no additional reference needs. Definition at line 48 of file Connection_Handler.inl. References TAO_Transport::add_reference(), connection_pending_, and transport(). Referenced by TAO_IIOP_Connector::complete_connection().
00049 { 00050 if (!this->connection_pending_) 00051 { 00052 this->connection_pending_ = true; 00053 this->transport()->add_reference(); 00054 } 00055 } |
|
The event handler calls, here so that other objects who hold a reference to this object can call the event handler methods. Implemented in TAO_IIOP_Connection_Handler. |
|
Implement the handle_input() callback.
Definition at line 219 of file Connection_Handler.cpp. References ACE_DEBUG, TAO_Wait_Strategy::can_process_upcalls(), close_connection(), handle_input_internal(), LM_DEBUG, TAO_debug_level, transport(), and TAO_Transport::wait_strategy(). Referenced by TAO_IIOP_Connection_Handler::handle_input().
00221 { 00222 // If we can't process upcalls just return 00223 if (!this->transport ()->wait_strategy ()->can_process_upcalls ()) 00224 { 00225 if (TAO_debug_level > 6) 00226 ACE_DEBUG ((LM_DEBUG, 00227 "TAO (%P|%t) - Connection_Handler[%d]::handle_input_eh, " 00228 "not going to handle_input on transport " 00229 "because upcalls temporarily suspended on this thread\n", 00230 this->transport()->id())); 00231 return 0; 00232 } 00233 00234 int const result = this->handle_input_internal (h, eh); 00235 00236 if (result == -1) 00237 { 00238 this->close_connection (); 00239 return 0; 00240 } 00241 00242 return result; 00243 } |
|
Implement the handle_output() callback.
Definition at line 246 of file Connection_Handler.cpp. References ACE_DEBUG, ACE_Event_Handler::get_handle(), TAO_Transport::handle_input(), TAO_Resume_Handle::handle_input_return_value_hook(), TAO_Transport::id(), LM_DEBUG, pos_io_hook(), pre_io_hook(), TAO_Resume_Handle::set_flag(), TAO_debug_level, transport(), and TAO_Transport::update_transport(). Referenced by handle_input_eh().
00248 { 00249 // Let the transport know that it is used 00250 (void) this->transport ()->update_transport (); 00251 00252 // Grab the transport id now and use the cached value for printing 00253 // since the transport could dissappear by the time the thread 00254 // returns. 00255 size_t const t_id = 00256 this->transport ()->id (); 00257 00258 if (TAO_debug_level > 6) 00259 { 00260 ACE_HANDLE handle = eh->get_handle(); 00261 ACE_DEBUG ((LM_DEBUG, 00262 "TAO (%P|%t) - Connection_Handler[%d]::handle_input, " 00263 "handle = %d/%d\n", 00264 t_id, handle, h)); 00265 } 00266 00267 TAO_Resume_Handle resume_handle (this->orb_core (), eh->get_handle ()); 00268 00269 int return_value = 0; 00270 00271 this->pre_io_hook (return_value); 00272 if (return_value != 0) 00273 return return_value; 00274 00275 return_value = this->transport ()->handle_input (resume_handle); 00276 00277 this->pos_io_hook (return_value); 00278 00279 // Bug 1647; might need to change resume_handle's flag or 00280 // change handle_input return value. 00281 resume_handle.handle_input_return_value_hook(return_value); 00282 00283 if (TAO_debug_level > 6) 00284 { 00285 ACE_HANDLE handle = eh->get_handle (); 00286 ACE_DEBUG ((LM_DEBUG, 00287 "TAO (%P|%t) - Connection_Handler[%d]::handle_input, " 00288 "handle = %d/%d, retval = %d\n", 00289 t_id, handle, h, return_value)); 00290 } 00291 00292 if (return_value == -1) 00293 resume_handle.set_flag (TAO_Resume_Handle::TAO_HANDLE_LEAVE_SUSPENDED); 00294 return return_value; 00295 } |
|
Implement the handle_output() callback.
Definition at line 187 of file Connection_Handler.cpp. References ACE_Event_Handler::get_handle(), TAO_Transport::handle_output(), pos_io_hook(), pre_io_hook(), TAO_Resume_Handle::set_flag(), transport(), and TAO_Transport::update_transport(). Referenced by TAO_IIOP_Connection_Handler::handle_output().
00189 { 00190 // Let the transport that it is going to be used 00191 (void) this->transport ()->update_transport (); 00192 00193 // Instantiate the resume handle here.. This will automatically 00194 // resume the handle once data is written.. 00195 TAO_Resume_Handle resume_handle (this->orb_core (), 00196 eh->get_handle ()); 00197 00198 int return_value = 0; 00199 this->pre_io_hook (return_value); 00200 if (return_value != 0) 00201 { 00202 resume_handle.set_flag (TAO_Resume_Handle::TAO_HANDLE_LEAVE_SUSPENDED); 00203 return return_value; 00204 } 00205 00206 return_value = this->transport ()->handle_output (); 00207 00208 this->pos_io_hook (return_value); 00209 00210 if (return_value != 0) 00211 { 00212 resume_handle.set_flag (TAO_Resume_Handle::TAO_HANDLE_LEAVE_SUSPENDED); 00213 } 00214 00215 return return_value; 00216 } |
|
Is the handler closed or timed out?
Definition at line 22 of file Connection_Handler.inl. Referenced by TAO_Connector::check_connection_closure(), and TAO_Connector::wait_for_connection_completion().
00023 { 00024 return (this->state_ == TAO_LF_Event::LFS_CONNECTION_CLOSED || 00025 this->state_ == TAO_LF_Event::LFS_TIMEOUT); 00026 } |
|
Is the handler in the process of being connected?
Definition at line 41 of file Connection_Handler.inl. Referenced by TAO_Connector::check_connection_closure().
00042 { 00043 return this->state_ == TAO_LF_Event::LFS_CONNECTION_WAIT; 00044 } |
|
Is the handler open?
Definition at line 35 of file Connection_Handler.inl. Referenced by TAO_Connector::check_connection_closure(), and TAO_Connector::wait_for_connection_completion().
00036 { 00037 return this->state_ == TAO_LF_Event::LFS_SUCCESS; 00038 } |
|
Closed due to timeout?
Definition at line 29 of file Connection_Handler.inl. Referenced by TAO_Connector::wait_for_connection_completion().
00030 { 00031 return (this->state_ == TAO_LF_Event::LFS_TIMEOUT); 00032 } |
|
A open () hook. See Thread_Per_Connection_Handler for a use case Implemented in TAO_IIOP_Connection_Handler. Referenced by TAO_Thread_Per_Connection_Handler::open(). |
|
Return our TAO_ORB_Core pointer.
Definition at line 10 of file Connection_Handler.inl. Referenced by TAO_IIOP_Connection_Handler::add_transport_to_cache(), TAO_IIOP_Connection_Handler::close_connection(), TAO_IIOP_Connection_Handler::open(), and TAO_IIOP_Connection_Handler::set_dscp_codepoint().
00011 { 00012 return this->orb_core_; 00013 } |
|
See the SSLIOP protocol for an interesting use-case Definition at line 427 of file Connection_Handler.cpp. Referenced by handle_input_internal(), and handle_output_eh().
00428 { 00429 } |
|
See the SSLIOP protocol for an interesting use-case Definition at line 422 of file Connection_Handler.cpp. Referenced by handle_input_internal(), and handle_output_eh().
00423 { 00424 } |
|
Release the OS resources related to this handler.
Reimplemented in TAO_IIOP_Connection_Handler. Definition at line 414 of file Connection_Handler.cpp.
00415 {
00416 return 0;
00417 }
|
|
Reimplemented in TAO_IIOP_Connection_Handler. Definition at line 408 of file Connection_Handler.cpp.
00409 {
00410 return 0;
00411 }
|
|
Set the Diff-Serv codepoint on outgoing packets. Only has effect for remote protocols (e.g., IIOP); no effect for local protocols (UIOP). Default implementation is for local protocols. Remote protocols must overwrite implementation. Reimplemented in TAO_IIOP_Connection_Handler. Definition at line 402 of file Connection_Handler.cpp. Referenced by TAO::Remote_Invocation::send_message().
00403 {
00404 return 0;
00405 }
|
|
Set options on the socket.
Definition at line 64 of file Connection_Handler.cpp. References ACE_CLOEXEC, ACE_IPC_SAP::enable(), ENOTSUP, ACE_SOCK::set_option(), SO_RCVBUF, SO_SNDBUF, and SOL_SOCKET. Referenced by TAO_IIOP_Connection_Handler::open().
00067 { 00068 #if !defined (ACE_LACKS_SOCKET_BUFSIZ) 00069 00070 if (snd_size != 0 00071 && sock.set_option (SOL_SOCKET, 00072 SO_SNDBUF, 00073 (void *) &snd_size, 00074 sizeof (snd_size)) == -1 00075 && errno != ENOTSUP) 00076 { 00077 return -1; 00078 } 00079 00080 if (rcv_size != 0 00081 && sock.set_option (SOL_SOCKET, 00082 SO_RCVBUF, 00083 (void *) &rcv_size, 00084 sizeof (int)) == -1 00085 && errno != ENOTSUP) 00086 { 00087 return -1; 00088 } 00089 #else 00090 ACE_UNUSED_ARG (snd_size); 00091 ACE_UNUSED_ARG (rcv_size); 00092 #endif /* !ACE_LACKS_SOCKET_BUFSIZ */ 00093 00094 // Set the close-on-exec flag for that file descriptor. If the 00095 // operation fails we are out of luck (some platforms do not support 00096 // it and return -1). 00097 (void) sock.enable (ACE_CLOEXEC); 00098 00099 return 0; 00100 } |
|
A common function called at the start of any protocol-specific open. Returns -1 on a failure (although no failure mode is currently defined). Definition at line 51 of file Connection_Handler.cpp. References cancel_pending_connection(). Referenced by TAO_IIOP_Connection_Handler::open().
00052 { 00053 // This reference counting is related to asynch connections. It 00054 // should probably be managed by the ACE_Strategy_Connector, since 00055 // that's really the reference being managed here. also, whether 00056 // open ultimately succeeds or fails, the connection attempted is 00057 // ending, so the reference must be removed in any case. 00058 this->cancel_pending_connection(); 00059 00060 return 0; 00061 } |
|
This method is invoked from the svc () method of the Svc_Handler Object. Definition at line 103 of file Connection_Handler.cpp. References ACE_DEBUG, ACE_TEXT, ETIME, TAO_Transport::handle_input(), TAO_ORB_Core::has_shutdown(), LM_DEBUG, ACE_Time_Value::msec(), TAO_debug_level, TAO_ORB_Core::thread_per_connection_timeout(), transport(), and TAO_Transport::update_transport(). Referenced by TAO_Thread_Per_Connection_Handler::svc().
00104 { 00105 int result = 0; 00106 00107 if (TAO_debug_level > 0) 00108 ACE_DEBUG ((LM_DEBUG, 00109 ACE_TEXT ("TAO (%P|%t) - Connection_Handler::svc_i begin\n"))); 00110 00111 // Here we simply synthesize the "typical" event loop one might find 00112 // in a reactive handler, except that this can simply block waiting 00113 // for input. 00114 00115 ACE_Time_Value *max_wait_time = 0; 00116 ACE_Time_Value timeout; 00117 ACE_Time_Value current_timeout; 00118 00119 if (this->orb_core_->thread_per_connection_timeout (timeout)) 00120 { 00121 current_timeout = timeout; 00122 max_wait_time = ¤t_timeout; 00123 } 00124 00125 TAO_Resume_Handle rh (this->orb_core_, 00126 ACE_INVALID_HANDLE); 00127 00128 // We exit of the loop if 00129 // - If the ORB core is shutdown by another thread 00130 // - Or if the transport is null. This could happen if an error 00131 // occured. 00132 // - Or if during processing a return value of -1 is received. 00133 while (!this->orb_core_->has_shutdown () 00134 && result >= 0) 00135 { 00136 // Let the transport know that it is used 00137 (void) this->transport ()->update_transport (); 00138 00139 result = 00140 this->transport ()->handle_input (rh, 00141 max_wait_time); 00142 00143 if (result == -1 && errno == ETIME) 00144 { 00145 // Ignore timeouts, they are only used to wake up and 00146 // shutdown. 00147 result = 0; 00148 00149 // Reset errno to make sure we don't trip over an old value 00150 // of errno in case it is not reset when the recv() call 00151 // fails if the socket has been closed. 00152 errno = 0; 00153 } 00154 else if (result == -1) 00155 { 00156 // Something went wrong with the socket. Just quit 00157 return result; 00158 } 00159 00160 current_timeout = timeout; 00161 00162 if (TAO_debug_level > 0) 00163 ACE_DEBUG ((LM_DEBUG, 00164 "TAO (%P|%t) - Connection_Handler::svc_i - " 00165 "loop <%d>\n", current_timeout.msec ())); 00166 } 00167 00168 if (TAO_debug_level > 0) 00169 ACE_DEBUG ((LM_DEBUG, 00170 "TAO (%P|%t) - Connection_Handler::svc_i end\n")); 00171 00172 return result; 00173 } |
|
Set the underlying transport object.
Definition at line 176 of file Connection_Handler.cpp. References TAO_Transport::event_handler_i(), and ACE_Event_Handler::reference_counting_policy().
00177 { 00178 this->transport_ = transport; 00179 00180 // Enable reference counting on the event handler. 00181 this->transport_->event_handler_i ()->reference_counting_policy ().value ( 00182 ACE_Event_Handler::Reference_Counting_Policy::ENABLED 00183 ); 00184 } |
|
|
Stores the connection pending state.
Definition at line 212 of file Connection_Handler.h. Referenced by cancel_pending_connection(), and connection_pending(). |
|
Internal state lock, needs to be separate from the reference count / pending upcalls lock because they interleave. Definition at line 209 of file Connection_Handler.h. |
|
Pointer to the TAO_ORB_Core.
Definition at line 202 of file Connection_Handler.h. |
|
Transport object reference.
Definition at line 205 of file Connection_Handler.h. |