TAO_IIOP_Connector Class Reference

IIOP-specific Connector bridge for pluggable protocols. More...

#include <IIOP_Connector.h>

Inheritance diagram for TAO_IIOP_Connector:

Inheritance graph
[legend]
Collaboration diagram for TAO_IIOP_Connector:

Collaboration graph
[legend]
List of all members.

Public Types

typedef TAO_Connect_Concurrency_Strategy<
TAO_IIOP_Connection_Handler
TAO_IIOP_CONNECT_CONCURRENCY_STRATEGY
typedef TAO_Connect_Creation_Strategy<
TAO_IIOP_Connection_Handler
TAO_IIOP_CONNECT_CREATION_STRATEGY
typedef ACE_Connect_Strategy<
TAO_IIOP_Connection_Handler,
ACE_SOCK_CONNECTOR
TAO_IIOP_CONNECT_STRATEGY
typedef ACE_Strategy_Connector<
TAO_IIOP_Connection_Handler,
ACE_SOCK_CONNECTOR
TAO_IIOP_BASE_CONNECTOR

Public Member Functions

 TAO_IIOP_Connector (void)
 Constructor.
 ~TAO_IIOP_Connector (void)
 Destructor.
int open (TAO_ORB_Core *orb_core)
 Initialize object and register with reactor.
int close (void)
 Shutdown Connector bridge and concrete Connector.
TAO_Profilecreate_profile (TAO_InputCDR &cdr)
virtual int check_prefix (const char *endpoint)
virtual char object_key_delimiter (void) const
 Return the object key delimiter to use or expect.

Protected Member Functions

virtual int supports_parallel_connects (void) const
int set_validate_endpoint (TAO_Endpoint *ep)
virtual TAO_Transportmake_connection (TAO::Profile_Transport_Resolver *r, TAO_Transport_Descriptor_Interface &desc, ACE_Time_Value *timeout=0)
 Make a connection.
virtual TAO_Transportmake_parallel_connection (TAO::Profile_Transport_Resolver *r, TAO_Transport_Descriptor_Interface &desc, ACE_Time_Value *timeout=0)
virtual TAO_Profilemake_profile (void)
virtual int cancel_svc_handler (TAO_Connection_Handler *svc_handler)
 Cancel the passed cvs handler from the connector.

Private Member Functions

int begin_connection (TAO_IIOP_Connection_Handler *&svc_handler, TAO::Profile_Transport_Resolver *r, TAO_IIOP_Endpoint *endpoint, ACE_Time_Value *timeout=0)
TAO_Transportcomplete_connection (int result, TAO_Transport_Descriptor_Interface &desc, TAO_IIOP_Connection_Handler **&sh_list, TAO_IIOP_Endpoint **ep_list, unsigned count, TAO::Profile_Transport_Resolver *r, TAO_LF_Multi_Event *mev, ACE_Time_Value *timeout=0)
TAO_IIOP_Endpointremote_endpoint (TAO_Endpoint *ep)
 Return the remote endpoint, a helper function.

Private Attributes

TAO_IIOP_CONNECT_STRATEGY connect_strategy_
 Our connect strategy.
TAO_IIOP_BASE_CONNECTOR base_connector_
 The connector initiating connection requests for IIOP.

Detailed Description

IIOP-specific Connector bridge for pluggable protocols.

Concrete instance of the TAO_Connector class. Responsible for establishing a connection with a server and is called from the Connector_Registory.

Definition at line 53 of file IIOP_Connector.h.


Member Typedef Documentation

typedef ACE_Strategy_Connector<TAO_IIOP_Connection_Handler, ACE_SOCK_CONNECTOR> TAO_IIOP_Connector::TAO_IIOP_BASE_CONNECTOR

Definition at line 89 of file IIOP_Connector.h.

typedef TAO_Connect_Concurrency_Strategy<TAO_IIOP_Connection_Handler> TAO_IIOP_Connector::TAO_IIOP_CONNECT_CONCURRENCY_STRATEGY

Definition at line 78 of file IIOP_Connector.h.

typedef TAO_Connect_Creation_Strategy<TAO_IIOP_Connection_Handler> TAO_IIOP_Connector::TAO_IIOP_CONNECT_CREATION_STRATEGY

Definition at line 81 of file IIOP_Connector.h.

typedef ACE_Connect_Strategy<TAO_IIOP_Connection_Handler, ACE_SOCK_CONNECTOR> TAO_IIOP_Connector::TAO_IIOP_CONNECT_STRATEGY

Definition at line 85 of file IIOP_Connector.h.


Constructor & Destructor Documentation

TAO_IIOP_Connector::TAO_IIOP_Connector ( void   ) 

Constructor.

Definition at line 89 of file IIOP_Connector.cpp.

00090   : TAO_Connector (IOP::TAG_INTERNET_IOP)
00091   , connect_strategy_ ()
00092   , base_connector_ ()
00093 {
00094 }

TAO_IIOP_Connector::~TAO_IIOP_Connector ( void   ) 

Destructor.

Definition at line 84 of file IIOP_Connector.cpp.

00085 {
00086 }


Member Function Documentation

int TAO_IIOP_Connector::begin_connection ( TAO_IIOP_Connection_Handler *&  svc_handler,
TAO::Profile_Transport_Resolver *  r,
TAO_IIOP_Endpoint endpoint,
ACE_Time_Value timeout = 0 
) [private]

This is the first half of making a connection. Both make_connection and make_parallel_connection will start out using begin_connection.

Definition at line 317 of file IIOP_Connector.cpp.

References ACE_DEBUG, ACE_TEXT, ACE_TEXT_CHAR_TO_TCHAR, TAO_Connector::active_connect_strategy_, base_connector_, ACE_Connector< SVC_HANDLER, >::connect(), ACE_Addr::get_type(), TAO_IIOP_Endpoint::host(), INADDR_ANY, TAO_IIOP_Endpoint::is_preferred_network(), LM_DEBUG, TAO_IIOP_Endpoint::object_addr(), TAO_IIOP_Endpoint::port(), TAO_IIOP_Endpoint::preferred_network(), ACE_INET_Addr::set(), TAO_Connect_Strategy::synch_options(), and TAO_debug_level.

Referenced by make_connection(), and make_parallel_connection().

00321 {
00322   const ACE_INET_Addr &remote_address =
00323     iiop_endpoint->object_addr ();
00324 
00325   u_short port = 0;
00326   const ACE_UINT32 ia_any = INADDR_ANY;
00327   ACE_INET_Addr local_addr(port, ia_any);
00328 
00329   if (iiop_endpoint->is_preferred_network ())
00330     local_addr.set (port,
00331                     iiop_endpoint->preferred_network ());
00332 #if defined (ACE_HAS_IPV6)
00333   else if (remote_address.get_type () == AF_INET6)
00334     local_addr.set (port,
00335                     ACE_IPV6_ANY);
00336 #endif /* ACE_HAS_IPV6 */
00337 
00338   if (TAO_debug_level > 2)
00339     ACE_DEBUG ((LM_DEBUG,
00340                 ACE_TEXT ("TAO (%P|%t) - IIOP_Connector::begin_connection, ")
00341                 ACE_TEXT ("to <%s:%d> which should %s\n"),
00342                 ACE_TEXT_CHAR_TO_TCHAR(iiop_endpoint->host()),
00343                 iiop_endpoint->port(),
00344                 r->blocked_connect () ? ACE_TEXT("block") : ACE_TEXT("nonblock")));
00345 
00346   // Get the right synch options
00347   ACE_Synch_Options synch_options;
00348 
00349   this->active_connect_strategy_->synch_options (timeout,
00350                                                  synch_options);
00351 
00352   // The code used to set the timeout to zero, with the intent of
00353   // polling the reactor for connection completion. However, the side-effect
00354   // was to cause the connection to timeout immediately.
00355 
00356   svc_handler = 0;
00357 
00358   int result =
00359     this->base_connector_.connect (svc_handler,
00360                                    remote_address,
00361                                    synch_options,
00362                                    local_addr);
00363 
00364   // The connect() method creates the service handler and bumps the
00365   // #REFCOUNT# up one extra.  There are four possibilities from
00366   // calling connect(): (a) connection succeeds immediately - in this
00367   // case, the #REFCOUNT# on the handler is two; (b) connection
00368   // completion is pending - in this case, the #REFCOUNT# on the
00369   // handler is also two; (c) connection fails immediately - in this
00370   // case, the #REFCOUNT# on the handler is one since close() gets
00371   // called on the handler; (d) the connect immediately returns when we
00372   // have specified that it shouldn't block.
00373   //
00374   // The extra reference count in
00375   // TAO_Connect_Creation_Strategy::make_svc_handler() is needed in
00376   // the case when connection completion is pending and we are going
00377   // to wait on a variable in the handler to changes, signifying
00378   // success or failure.  Note, that this increment cannot be done
00379   // once the connect() returns since this might be too late if
00380   // another thread pick up the completion and potentially deletes the
00381   // handler before we get a chance to increment the reference count.
00382   return result;
00383 }

int TAO_IIOP_Connector::cancel_svc_handler ( TAO_Connection_Handler svc_handler  )  [protected, virtual]

Cancel the passed cvs handler from the connector.

Implements TAO_Connector.

Definition at line 726 of file IIOP_Connector.cpp.

References TAO_IIOP_Connection_Handler::abort(), base_connector_, and ACE_Connector< SVC_HANDLER, >::cancel().

00728 {
00729   TAO_IIOP_Connection_Handler* handler=
00730     dynamic_cast<TAO_IIOP_Connection_Handler*>(svc_handler);
00731 
00732   // Cancel from the connector
00733   if (handler)
00734     {
00735       handler->abort();
00736       return this->base_connector_.cancel (handler);
00737     }
00738 
00739   return -1;
00740 }

int TAO_IIOP_Connector::check_prefix ( const char *  endpoint  )  [virtual]

Check that the prefix of the provided endpoint is valid for use with a given pluggable protocol.

Implements TAO_Connector.

Definition at line 677 of file IIOP_Connector.cpp.

References ACE_OS::strchr(), ACE_OS::strlen(), and ACE_OS::strncasecmp().

00678 {
00679   // Check for a valid string
00680   if (!endpoint || !*endpoint)
00681     return -1;  // Failure
00682 
00683   static const char *protocol[] = { "iiop", "iioploc" };
00684 
00685   size_t const slot = ACE_OS::strchr (endpoint, ':') - endpoint;
00686   if (slot == 0) // an empty string is valid for corbaloc.
00687     return 0;
00688 
00689   size_t const len0 = ACE_OS::strlen (protocol[0]);
00690   size_t const len1 = ACE_OS::strlen (protocol[1]);
00691 
00692   // Check for the proper prefix in the IOR.  If the proper prefix
00693   // isn't in the IOR then it is not an IOR we can use.
00694   if (slot == len0 && ACE_OS::strncasecmp (endpoint, protocol[0], len0) == 0)
00695     return 0;
00696   else if (slot == len1 && ACE_OS::strncasecmp (endpoint, protocol[1], len1) == 0)
00697     return 0;
00698 
00699   return -1;
00700   // Failure: not an IIOP IOR
00701   // DO NOT throw an exception here.
00702 }

int TAO_IIOP_Connector::close ( void   )  [virtual]

Shutdown Connector bridge and concrete Connector.

Implements TAO_Connector.

Definition at line 133 of file IIOP_Connector.cpp.

References base_connector_, ACE_Strategy_Connector< SVC_HANDLER, >::close(), ACE_Strategy_Connector< SVC_HANDLER, >::concurrency_strategy(), and ACE_Strategy_Connector< SVC_HANDLER, >::creation_strategy().

00134 {
00135   delete this->base_connector_.concurrency_strategy ();
00136   delete this->base_connector_.creation_strategy ();
00137   return this->base_connector_.close ();
00138 }

TAO_Transport * TAO_IIOP_Connector::complete_connection ( int  result,
TAO_Transport_Descriptor_Interface desc,
TAO_IIOP_Connection_Handler **&  sh_list,
TAO_IIOP_Endpoint **  ep_list,
unsigned  count,
TAO::Profile_Transport_Resolver *  r,
TAO_LF_Multi_Event mev,
ACE_Time_Value timeout = 0 
) [private]

This is the second half of making a connection when several endpoints are involved. This works with modified wait strategies to wait for one of many transports, and when once completes it will cancel the rest. The winning transport is returned.

Definition at line 386 of file IIOP_Connector.cpp.

References ACE_DEBUG, ACE_ERROR, ACE_NEW_RETURN, ACE_TEXT, ACE_TEXT_CHAR_TO_TCHAR, TAO_Connection_Handler::cancel_pending_connection(), TAO_IIOP_Connection_Handler::close(), TAO_Transport::close_connection(), TAO_Transport::connection_handler(), TAO_Connection_Handler::connection_pending(), TAO_LF_CH_Event::error_detected(), TAO_IIOP_Endpoint::host(), TAO_Transport::id(), TAO_Transport::is_connected(), TAO_LF_Event::keep_waiting(), LM_DEBUG, LM_ERROR, ACE_OS::nanosleep(), TAO_IIOP_Endpoint::port(), TAO_Transport::purge_entry(), TAO_Wait_Strategy::register_handler(), TAO_Transport_Descriptor_Interface::reset_endpoint(), TAO_debug_level, and TAO_Transport::wait_strategy().

Referenced by make_connection(), and make_parallel_connection().

00394 {
00395   // Make sure that we always do a remove_reference for every member
00396   // of the list
00397   TAO_IIOP_Connection_Handler_Array_Guard svc_handler_auto_ptr (sh_list,count);
00398   TAO_Transport *transport  = 0;
00399   TAO_Transport **tlist = 0;
00400   ACE_NEW_RETURN (tlist,TAO_Transport*[count],0);
00401 
00402   //  populate the transport list
00403   for (unsigned i = 0; i < count; i++)
00404     tlist[i] = sh_list[i]->transport();
00405 
00406   if (result != -1)
00407     {
00408       // We received a compeleted connection and 0 or more pending.
00409       // the winner is the last member of the list, because the
00410       // iterator stopped on a successful connect.
00411       transport = tlist[count-1];
00412     }
00413   else
00414     {
00415       if (count == 1)
00416         {
00417           transport = tlist[0];
00418           if (!this->wait_for_connection_completion (r,
00419                                                      transport,
00420                                                      timeout))
00421             {
00422               if (TAO_debug_level > 2)
00423                 ACE_ERROR ((LM_ERROR,
00424                             ACE_TEXT ("TAO (%P|%t) - IIOP_Connector::")
00425                             ACE_TEXT ("complete_connection, wait for completion ")
00426                             ACE_TEXT ("failed for 1 pending connect\n")));
00427             }
00428         }
00429       else
00430         {
00431           if (!this->wait_for_connection_completion (r,
00432                                                      transport,
00433                                                      tlist,
00434                                                      count,
00435                                                      mev,
00436                                                      timeout))
00437             {
00438               if (TAO_debug_level > 2)
00439                 ACE_ERROR ((LM_ERROR,
00440                             ACE_TEXT ("TAO (%P|%t) - IIOP_Connector::")
00441                             ACE_TEXT ("complete_connection, wait for completion ")
00442                             ACE_TEXT ("failed for %d pending connects\n"),
00443                             count));
00444             }
00445         }
00446     }
00447 
00448 #if defined (INDUCE_BUG_2654_A)
00449   // This is where the fatal error would occur. A pending asynch
00450   // connection would fail, the failure handled by another thread,
00451   // closing the connection.  However the remainder of this method
00452   // only checked to see if the keep_waiting status was true, and bump
00453   // the refcount then. However if the status was really
00454   // error_detected, then no bump in refcount occured allowing the
00455   // connection_handler's close_handler method to effectively steal
00456   // the reference to be handed back to the caller. That would then
00457   // trigger an abort as the profile_transport_resolver (our caller)
00458   // to delete the transport while it is still cached.
00459   ACE_Time_Value udelay(0,600);
00460   struct timespec ts = udelay;
00461   ACE_OS::nanosleep (&ts);
00462 #endif // INDUCE_BUG_2654_A
00463 
00464   int retval = -1;
00465 
00466   // At this point, the connection has been successfully created
00467   // connected or not connected, but we have a connection.
00468   TAO_IIOP_Connection_Handler *svc_handler = 0;
00469   TAO_IIOP_Endpoint *iiop_endpoint = 0;
00470 
00471   if (transport != 0)
00472     {
00473       if (count == 1)
00474         {
00475           svc_handler = sh_list[0];
00476           iiop_endpoint = ep_list[0];
00477         }
00478       else
00479         {
00480           for (unsigned i = 0; i < count; i++)
00481             {
00482               if (transport == tlist[i])
00483                 {
00484                   svc_handler = sh_list[i];
00485                   iiop_endpoint = ep_list[i];
00486                   break;
00487                 }
00488             }
00489         }
00490     }
00491 
00492 
00493   // Done with the transport list. It was a temporary that did not
00494   // affect the reference count.
00495   delete [] tlist;
00496 
00497   // In case of errors transport is zero
00498   if (transport == 0)
00499     {
00500       // Give users a clue to the problem.
00501       if (TAO_debug_level > 3)
00502         {
00503           for (unsigned i = 0; i < count; i++)
00504             {
00505               ACE_ERROR ((LM_ERROR,
00506                           ACE_TEXT ("TAO (%P|%t) - IIOP_Connector::complete_connection,")
00507                           ACE_TEXT (" connection to <%s:%d> failed (%p)\n"),
00508                           ACE_TEXT_CHAR_TO_TCHAR (ep_list[i]->host ()),
00509                           ep_list[i]->port (),
00510                           ACE_TEXT("errno")));
00511             }
00512         }
00513       return 0;
00514     }
00515 
00516   if (svc_handler->keep_waiting())
00517     {
00518       svc_handler->connection_pending();
00519     }
00520 
00521 #if defined (INDUCE_BUG_2654_B)
00522   // It is possible for the connection failure to be processed after bumping
00523   // the reference count and before we plan to cache the connection. Prior to
00524   // fixing bug 2654, this would lead to a failed connection in the cache.
00525   // Though not a fatal condition, it was certainly wasteful of resources.
00526   ACE_Time_Value udelay(0,600);
00527   struct timespec ts = udelay;
00528   ACE_OS::nanosleep (&ts);
00529 #endif // INDUCE_BUG_2654_B
00530 
00531   // Fix for bug 2654.
00532   if (transport->connection_handler()->error_detected())
00533     {
00534       if (TAO_debug_level > 0)
00535         ACE_DEBUG((LM_DEBUG,
00536                    ACE_TEXT("TAO (%P|%t) - IIOP_Connector::make_connection, ")
00537                    ACE_TEXT("transport in error before cache! \n")));
00538       transport->connection_handler()->cancel_pending_connection();
00539       return 0;
00540     }
00541 
00542   if (TAO_debug_level > 2)
00543     {
00544     ACE_DEBUG ((LM_DEBUG,
00545                   ACE_TEXT ("TAO (%P|%t) - IIOP_Connector::make_connection, ")
00546                   ACE_TEXT ("new %s connection to <%s:%d> on Transport[%d]\n"),
00547                   transport->is_connected() ?
00548                   ACE_TEXT("connected") : ACE_TEXT("not connected"),
00549                   ACE_TEXT_CHAR_TO_TCHAR (iiop_endpoint->host ()),
00550                 iiop_endpoint->port (),
00551                 svc_handler->peer ().get_handle ()));
00552     }
00553 
00554 #if defined (INDUCE_BUG_2654_C)
00555   // This sets up the possibility that a failed connection is detected after we
00556   // checked the connection status but before we cached the connection. This
00557   // will allow a failed connection to be cached
00558   ACE_Time_Value udelay(0,600);
00559   struct timespec ts = udelay;
00560   ACE_OS::nanosleep (&ts);
00561 #endif // INDUCE_BUG_2654_C
00562 
00563 
00564   // Add the handler to Cache
00565   if (count == 1 || desc.reset_endpoint(iiop_endpoint))
00566     {
00567       retval = this->orb_core ()->
00568         lane_resources ().transport_cache ().cache_transport (&desc,
00569                                                               transport);
00570     }
00571 
00572   // Failure in adding to cache
00573   if (retval != 0)
00574     {
00575       // Close the handler.
00576       svc_handler->close ();
00577 
00578       if (TAO_debug_level > 0)
00579         {
00580           ACE_ERROR ((LM_ERROR,
00581                       ACE_TEXT ("TAO (%P|%t) IIOP_Connector::make_connection, ")
00582                       ACE_TEXT ("could not add new connection to cache\n")));
00583         }
00584 
00585       return 0;
00586     }
00587 
00588   // Other part of fix for bug 2654.
00589   // It is possible that after checking for a connection failure but
00590   // before caching, the connection really failed, thus an invalid
00591   // connection is put into the cache. Thus we do one last status
00592   // check before handing the connection back to the caller.
00593   if (svc_handler->error_detected())
00594     {
00595       if (TAO_debug_level > 0)
00596         ACE_DEBUG((LM_DEBUG,
00597                    ACE_TEXT("TAO (%P|%t) - IIOP_Connector::make_connection, ")
00598                    ACE_TEXT("transport in error after cache! \n")));
00599       svc_handler->cancel_pending_connection();
00600       transport->purge_entry();
00601       return 0;
00602     }
00603 
00604 
00605 #if defined (INDUCE_BUG_2654_D)
00606   // at this point the connection handler's close connection will manage
00607   // purging the entry from the cache so we are fine there.
00608   ACE_Time_Value udelay(0,600);
00609   struct timespec ts = udelay;
00610   ACE_OS::nanosleep (&ts);
00611 #endif // INDUCE_BUG_2654_D
00612 
00613   if (transport->is_connected () &&
00614       transport->wait_strategy ()->register_handler () != 0)
00615     {
00616       // Registration failures.
00617 
00618       // Purge from the connection cache, if we are not in the cache, this
00619       // just does nothing.
00620       (void) transport->purge_entry ();
00621 
00622       // Close the handler.
00623       (void) transport->close_connection ();
00624 
00625       if (TAO_debug_level > 0)
00626         ACE_ERROR ((LM_ERROR,
00627                     ACE_TEXT ("TAO (%P|%t) IIOP_Connector [%d]::make_connection, ")
00628                     ACE_TEXT ("could not register the transport ")
00629                     ACE_TEXT ("in the reactor.\n"),
00630                     transport->id ()));
00631 
00632       return 0;
00633     }
00634 
00635   return transport;
00636 }

TAO_Profile * TAO_IIOP_Connector::create_profile ( TAO_InputCDR cdr  )  [virtual]

Create a profile for this protocol and initialize it based on the encapsulation in cdr

Implements TAO_Connector.

Definition at line 639 of file IIOP_Connector.cpp.

References TAO_Profile::_decr_refcnt(), ACE_NEW_RETURN, and TAO_Profile::decode().

00640 {
00641   TAO_Profile *pfile = 0;
00642   ACE_NEW_RETURN (pfile,
00643                   TAO_IIOP_Profile (this->orb_core ()),
00644                   0);
00645 
00646   const int r = pfile->decode (cdr);
00647   if (r == -1)
00648     {
00649       pfile->_decr_refcnt ();
00650       pfile = 0;
00651     }
00652 
00653   return pfile;
00654 }

TAO_Transport * TAO_IIOP_Connector::make_connection ( TAO::Profile_Transport_Resolver *  r,
TAO_Transport_Descriptor_Interface desc,
ACE_Time_Value timeout = 0 
) [protected, virtual]

Make a connection.

Implements TAO_Connector.

Definition at line 184 of file IIOP_Connector.cpp.

References ACE_ERROR, ACE_TEXT, ACE_TEXT_CHAR_TO_TCHAR, TAO_LF_Multi_Event::add_event(), begin_connection(), complete_connection(), TAO_Transport_Descriptor_Interface::endpoint(), TAO_IIOP_Endpoint::host(), LM_ERROR, TAO_IIOP_Endpoint::port(), remote_endpoint(), and TAO_debug_level.

00187 {
00188   TAO_IIOP_Connection_Handler *svc_handler = 0;
00189   TAO_IIOP_Endpoint *iiop_endpoint =
00190     this->remote_endpoint (desc.endpoint());
00191   int result = -1;
00192   if (iiop_endpoint == 0)
00193     return 0;
00194 
00195   result = this->begin_connection (svc_handler, r, iiop_endpoint, timeout);
00196 
00197   if (result == -1 && errno != EWOULDBLOCK)
00198     {
00199       // connect completed unsuccessfully
00200       svc_handler->remove_reference();
00201        // Give users a clue to the problem.
00202       if (TAO_debug_level > 1)
00203         {
00204           ACE_ERROR ((LM_ERROR,
00205                       ACE_TEXT ("TAO (%P|%t) IIOP_Connector::make_connection, ")
00206                       ACE_TEXT("connection to <%s:%d> failed (%p)\n"),
00207                       ACE_TEXT_CHAR_TO_TCHAR (iiop_endpoint->host ()),
00208                       iiop_endpoint->port (),
00209                       ACE_TEXT("errno")));
00210         }
00211     return 0;
00212     }
00213   TAO_IIOP_Connection_Handler **sh_ptr = &svc_handler;
00214   TAO_IIOP_Endpoint **ep_ptr = &iiop_endpoint;
00215   TAO_LF_Multi_Event mev;
00216   mev.add_event (svc_handler);
00217 
00218   return this->complete_connection (result,
00219                                     desc,
00220                                     sh_ptr,
00221                                     ep_ptr,
00222                                     1U,
00223                                     r,
00224                                     &mev,
00225                                     timeout);
00226 }

TAO_Transport * TAO_IIOP_Connector::make_parallel_connection ( TAO::Profile_Transport_Resolver *  r,
TAO_Transport_Descriptor_Interface desc,
ACE_Time_Value timeout = 0 
) [protected, virtual]

Make a connection using - not a pure virtual since not all protocols support this.

Reimplemented from TAO_Connector.

Definition at line 229 of file IIOP_Connector.cpp.

References ACE_DEBUG, ACE_NEW_RETURN, ACE_TEXT, TAO_Connector::active_connect_strategy_, TAO_LF_Multi_Event::add_event(), begin_connection(), complete_connection(), TAO_Transport_Descriptor_Interface::endpoint(), LM_DEBUG, ACE_OS::nanosleep(), TAO_Endpoint::next_filtered(), TAO_Connector::orb_core(), TAO_ORB_Core::orb_params(), TAO_ORB_Parameters::parallel_connect_delay(), TAO_Connect_Strategy::poll(), remote_endpoint(), and TAO_debug_level.

00233 {
00234   TAO_Endpoint *root_ep = desc.endpoint();
00235   unsigned max_count = 1;
00236   unsigned long ns_stagger =
00237     this->orb_core ()->orb_params ()->parallel_connect_delay ();
00238   unsigned long sec_stagger = ns_stagger/1000;
00239   ns_stagger = (ns_stagger % 1000) * 1000000;
00240   for (TAO_Endpoint *ep = root_ep->next_filtered (this->orb_core(), 0);
00241        ep != 0;
00242        ep = ep->next_filtered (this->orb_core(), root_ep))
00243     ++max_count;
00244 
00245   if (TAO_debug_level > 2)
00246     ACE_DEBUG ((LM_DEBUG,
00247                 ACE_TEXT ("TAO (%P|%t) - IIOP_Connector::")
00248                 ACE_TEXT ("make_parallel_connection, ")
00249                 ACE_TEXT ("to %d endpoints\n"), max_count));
00250   TAO_IIOP_Endpoint **eplist = 0;
00251   TAO_IIOP_Connection_Handler **shlist = 0;
00252   ACE_NEW_RETURN (shlist, TAO_IIOP_Connection_Handler *[max_count], 0);
00253   ACE_NEW_RETURN (eplist, TAO_IIOP_Endpoint *[max_count], 0);
00254 
00255   TAO_LF_Multi_Event mev;
00256   int result = 0;
00257   unsigned count = 0;
00258   for (TAO_Endpoint *ep = root_ep->next_filtered (this->orb_core(),0);
00259        ep != 0;
00260        ep = ep->next_filtered(this->orb_core(),root_ep))
00261     {
00262       eplist[count] = this->remote_endpoint (ep);
00263       shlist[count] = 0;
00264       result = this->begin_connection (shlist[count],
00265                                        r,
00266                                        eplist[count],
00267                                        timeout);
00268 
00269       // The connection may fail because it is slow, or for other reasons.
00270       // If it was an incomplete non-blocking connection, add it to the list
00271       // to be waited on, otherwise remove the reference to the handler and
00272       // move on to the next endpoint.
00273       if (result == -1)
00274         {
00275           if (errno == EWOULDBLOCK)
00276             {
00277               mev.add_event(shlist[count++]);
00278               if (ep->next() != 0)
00279                 {
00280                   struct timespec nsleep = {sec_stagger, ns_stagger};
00281                   ACE_OS::nanosleep (&nsleep);
00282                   result = this->active_connect_strategy_->poll (&mev);
00283                   if (result != -1)
00284                     break;
00285                 }
00286             }
00287           else
00288             {
00289               shlist[count]->remove_reference(); // done bump the list count
00290             }
00291           continue;
00292         }
00293 
00294       if (result != -1) // we have a winner!
00295         {
00296           count++;
00297           break; // no waiting involved since a connection is completed
00298         }
00299     }
00300 
00301   TAO_Transport *winner = 0;
00302   if (count > 0) // only complete if at least one pending or success
00303     winner = this->complete_connection (result,
00304                                         desc,
00305                                         shlist,
00306                                         eplist,
00307                                         count,r,
00308                                         &mev,
00309                                         timeout);
00310 
00311   delete [] shlist; // reference reductions should have been done already
00312   delete [] eplist;
00313   return winner;
00314 }

TAO_Profile * TAO_IIOP_Connector::make_profile ( void   )  [protected, virtual]

More TAO_Connector methods, please check the documentation on Transport_Connector.h

Implements TAO_Connector.

Definition at line 657 of file IIOP_Connector.cpp.

References CORBA::SystemException::_tao_minor_code(), ACE_NEW_THROW_EX, and CORBA::COMPLETED_NO.

00658 {
00659   // The endpoint should be of the form:
00660   //    N.n@host:port/object_key
00661   // or:
00662   //    host:port/object_key
00663 
00664   TAO_Profile *profile = 0;
00665   ACE_NEW_THROW_EX (profile,
00666                     TAO_IIOP_Profile (this->orb_core ()),
00667                     CORBA::NO_MEMORY (
00668                       CORBA::SystemException::_tao_minor_code (
00669                         0,
00670                         ENOMEM),
00671                       CORBA::COMPLETED_NO));
00672 
00673   return profile;
00674 }

char TAO_IIOP_Connector::object_key_delimiter ( void   )  const [virtual]

Return the object key delimiter to use or expect.

Implements TAO_Connector.

Definition at line 705 of file IIOP_Connector.cpp.

References TAO_IIOP_Profile::object_key_delimiter_.

00706 {
00707   return TAO_IIOP_Profile::object_key_delimiter_;
00708 }

int TAO_IIOP_Connector::open ( TAO_ORB_Core orb_core  )  [virtual]

Initialize object and register with reactor.

Implements TAO_Connector.

Definition at line 97 of file IIOP_Connector.cpp.

References ACE_NEW_RETURN, base_connector_, connect_strategy_, ACE_Strategy_Connector< SVC_HANDLER, >::open(), TAO_Connector::orb_core(), and TAO_ORB_Core::thr_mgr().

00098 {
00099   // @todo: The functionality of the following two statements could
00100   // be done in the constructor, but that involves changing the
00101   // interface of the pluggable transport factory.
00102 
00103   // Set the ORB Core
00104   this->orb_core (orb_core);
00105 
00106   // Create our connect strategy
00107   if (this->create_connect_strategy () == -1)
00108     return -1;
00109 
00110   /// Our connect creation strategy
00111   TAO_IIOP_CONNECT_CREATION_STRATEGY *connect_creation_strategy = 0;
00112 
00113   ACE_NEW_RETURN (connect_creation_strategy,
00114                   TAO_IIOP_CONNECT_CREATION_STRATEGY
00115                       (orb_core->thr_mgr (),
00116                        orb_core),
00117                   -1);
00118 
00119   /// Our activation strategy
00120   TAO_IIOP_CONNECT_CONCURRENCY_STRATEGY *concurrency_strategy = 0;
00121 
00122   ACE_NEW_RETURN (concurrency_strategy,
00123                   TAO_IIOP_CONNECT_CONCURRENCY_STRATEGY (orb_core),
00124                   -1);
00125 
00126   return this->base_connector_.open (this->orb_core ()->reactor (),
00127                                      connect_creation_strategy,
00128                                      &this->connect_strategy_,
00129                                      concurrency_strategy);
00130 }

TAO_IIOP_Endpoint * TAO_IIOP_Connector::remote_endpoint ( TAO_Endpoint ep  )  [private]

Return the remote endpoint, a helper function.

Definition at line 711 of file IIOP_Connector.cpp.

References TAO_Endpoint::tag().

Referenced by make_connection(), make_parallel_connection(), and set_validate_endpoint().

00712 {
00713   if (endpoint->tag () != IOP::TAG_INTERNET_IOP)
00714     return 0;
00715 
00716   TAO_IIOP_Endpoint *iiop_endpoint =
00717     dynamic_cast<TAO_IIOP_Endpoint *> (endpoint );
00718 
00719   if (iiop_endpoint == 0)
00720     return 0;
00721 
00722   return iiop_endpoint;
00723 }

int TAO_IIOP_Connector::set_validate_endpoint ( TAO_Endpoint ep  )  [protected, virtual]

Set and validate endpoint. We need to do this to initialize our remote *_Addr's which have not been done during IOR decode.

Implements TAO_Connector.

Definition at line 147 of file IIOP_Connector.cpp.

References ACE_DEBUG, ACE_TEXT, AF_INET, ACE_Addr::get_type(), LM_DEBUG, TAO_IIOP_Endpoint::object_addr(), remote_endpoint(), and TAO_debug_level.

00148 {
00149   TAO_IIOP_Endpoint *iiop_endpoint =
00150     this->remote_endpoint (endpoint);
00151 
00152   if (iiop_endpoint == 0)
00153     return -1;
00154 
00155    const ACE_INET_Addr &remote_address =
00156      iiop_endpoint->object_addr ();
00157 
00158    // Verify that the remote ACE_INET_Addr was initialized properly.
00159    // Failure can occur if hostname lookup failed when initializing the
00160    // remote ACE_INET_Addr.
00161 #if defined (ACE_HAS_IPV6)
00162    if (remote_address.get_type () != AF_INET &&
00163        remote_address.get_type () != AF_INET6)
00164 #else /* ACE_HAS_IPV6 */
00165    if (remote_address.get_type () != AF_INET)
00166 #endif /* !ACE_HAS_IPV6 */
00167      {
00168        if (TAO_debug_level > 0)
00169          {
00170            ACE_DEBUG ((LM_DEBUG,
00171                        ACE_TEXT ("TAO (%P|%t) - IIOP connection failed.\n")
00172                        ACE_TEXT ("     This is most likely ")
00173                        ACE_TEXT ("due to a hostname lookup ")
00174                        ACE_TEXT ("failure.\n")));
00175          }
00176 
00177        return -1;
00178      }
00179 
00180    return 0;
00181 }

int TAO_IIOP_Connector::supports_parallel_connects ( void   )  const [protected, virtual]

A flag indicating the actual connector supports parallel connection attempts. The base implementation always returns 0. Override to return non-zero if parallel connection attempts may be tried.

Reimplemented from TAO_Connector.

Definition at line 141 of file IIOP_Connector.cpp.

00142 {
00143   return 1;
00144 }


Member Data Documentation

TAO_IIOP_BASE_CONNECTOR TAO_IIOP_Connector::base_connector_ [private]

The connector initiating connection requests for IIOP.

Definition at line 158 of file IIOP_Connector.h.

Referenced by begin_connection(), cancel_svc_handler(), close(), and open().

TAO_IIOP_CONNECT_STRATEGY TAO_IIOP_Connector::connect_strategy_ [private]

Our connect strategy.

Definition at line 155 of file IIOP_Connector.h.

Referenced by open().


The documentation for this class was generated from the following files:
Generated on Tue Feb 2 17:39:32 2010 for TAO by  doxygen 1.4.7