From 2b1365e6c55e7999a2fb6708a075823b3acebef4 Mon Sep 17 00:00:00 2001 From: Ossama Othman Date: Fri, 25 Feb 2000 17:02:17 +0000 Subject: Fri Feb 25 08:59:59 2000 Ossama Othman --- TAO/tao/IIOP_Acceptor.cpp | 322 ++++++++++++++++++++++++++++++++++------------ TAO/tao/IIOP_Acceptor.h | 21 +-- TAO/tao/IIOP_Acceptor.i | 9 +- TAO/tao/Makefile | 62 ++++++++- 4 files changed, 318 insertions(+), 96 deletions(-) diff --git a/TAO/tao/IIOP_Acceptor.cpp b/TAO/tao/IIOP_Acceptor.cpp index a0d0cb2cf30..8bffcab686b 100644 --- a/TAO/tao/IIOP_Acceptor.cpp +++ b/TAO/tao/IIOP_Acceptor.cpp @@ -9,6 +9,8 @@ #include "tao/GIOP.h" #include "tao/debug.h" +#include "ace/Auto_Ptr.h" + #if !defined(__ACE_INLINE__) #include "tao/IIOP_Acceptor.i" #endif /* __ACE_INLINE__ */ @@ -43,6 +45,9 @@ template class TAO_Accept_Strategycreation_strategy_; delete this->concurrency_strategy_; delete this->accept_strategy_; + + delete [] this->addrs_; + delete [] this->hosts_; } // TODO = // 2) For V1.[1,2] there are tagged components -// 3) Create multiple profiles for wild carded endpoints (may be multiple -// interfaces over which we can receive requests. Thus a profile -// must be made for each one. int TAO_IIOP_Acceptor::create_mprofile (const TAO_ObjectKey &object_key, TAO_MProfile &mprofile) { - // @@ we only make one for now + // Adding this->num_hosts_ to the TAO_MProfile. int count = mprofile.profile_count (); - if ((mprofile.size () - count) < 1 - && mprofile.grow (count + 1) == -1) + if ((mprofile.size () - count) < this->num_hosts_ + && mprofile.grow (count + this->num_hosts_) == -1) return -1; - TAO_IIOP_Profile *pfile = 0; - ACE_NEW_RETURN (pfile, - TAO_IIOP_Profile (this->host_.c_str (), - this->address_.get_port_number (), - object_key, - this->address_, - this->version_, - this->orb_core_), - -1); - - if (mprofile.give_profile (pfile) == -1) + for (size_t i = 0; i < this->num_hosts_; ++i) { - pfile->_decr_refcnt (); - pfile = 0; - return -1; - } + TAO_IIOP_Profile *pfile = 0; + ACE_NEW_RETURN (pfile, + TAO_IIOP_Profile (this->hosts_[i].c_str (), + this->addrs_[i].get_port_number (), + object_key, + this->addrs_[i], + this->version_, + this->orb_core_), + -1); + + if (mprofile.give_profile (pfile) == -1) + { + pfile->_decr_refcnt (); + pfile = 0; + return -1; + } - if (this->orb_core_->orb_params ()->std_profile_components () == 0) - return 0; + if (this->orb_core_->orb_params ()->std_profile_components () == 0) + continue; - pfile->tagged_components ().set_orb_type (TAO_ORB_TYPE); + pfile->tagged_components ().set_orb_type (TAO_ORB_TYPE); - CONV_FRAME::CodeSetComponentInfo code_set_info; - code_set_info.ForCharData.native_code_set = - TAO_DEFAULT_CHAR_CODESET_ID; - code_set_info.ForWcharData.native_code_set = - TAO_DEFAULT_WCHAR_CODESET_ID; - pfile->tagged_components ().set_code_sets (code_set_info); + CONV_FRAME::CodeSetComponentInfo code_set_info; + code_set_info.ForCharData.native_code_set = + TAO_DEFAULT_CHAR_CODESET_ID; + code_set_info.ForWcharData.native_code_set = + TAO_DEFAULT_WCHAR_CODESET_ID; + pfile->tagged_components ().set_code_sets (code_set_info); - pfile->tagged_components ().set_tao_priority (this->priority ()); + pfile->tagged_components ().set_tao_priority (this->priority ()); + } return 0; } @@ -113,11 +121,17 @@ int TAO_IIOP_Acceptor::is_collocated (const TAO_Profile *pfile) { const TAO_IIOP_Profile *profile = - ACE_dynamic_cast(const TAO_IIOP_Profile *, - pfile); + ACE_dynamic_cast (const TAO_IIOP_Profile *, + pfile); - // compare the port and sin_addr (numeric host address) - return profile->object_addr () == this->address_; + for (size_t i = 0; i < this->num_hosts_; ++i) + { + // compare the port and sin_addr (numeric host address) + if (profile->object_addr () == this->addrs_[i]) + return 1; // Collocated + } + + return 0; // Not collocated } int @@ -133,6 +147,17 @@ TAO_IIOP_Acceptor::open (TAO_ORB_Core *orb_core, const char *address, const char *options) { + if (this->hosts_ != 0) + { + // The hostname cache has already been set! + // This is bad mojo, i.e. an internal TAO error. + ACE_ERROR_RETURN ((LM_ERROR, + ASYS_TEXT ("TAO (%P|%t) ") + ASYS_TEXT ("IIOP_Acceptor::open - "), + ASYS_TEXT ("hostname already set\n\n")), + -1); + } + if (address == 0) return -1; @@ -178,6 +203,48 @@ TAO_IIOP_Acceptor::open (TAO_ORB_Core *orb_core, // Host and port were specified. return -1; + + this->num_hosts_ = 1; // Only one hostname to store + + ACE_NEW_RETURN (this->addrs_, + ACE_INET_Addr[this->num_hosts_], + -1); + + ACE_NEW_RETURN (this->hosts_, + ACE_CString[this->num_hosts_], + -1); + + if (orb_core->orb_params ()->use_dotted_decimal_addresses ()) + { + const char *tmp = addr.get_host_addr (); + if (tmp == 0) + { + if (TAO_debug_level > 0) + ACE_DEBUG ((LM_DEBUG, + ASYS_TEXT ("\n\nTAO (%P|%t) ") + ASYS_TEXT ("IIOP_Acceptor::open - %p\n\n"), + ASYS_TEXT ("cannot cache hostname"))); + return -1; + } + + this->hosts_[0] = tmp; + } + else + { + char tmp_host[MAXHOSTNAMELEN + 1]; + if (addr.get_host_name (tmp_host, + sizeof (tmp_host)) != 0) + { + if (TAO_debug_level > 0) + ACE_DEBUG ((LM_DEBUG, + ASYS_TEXT ("\n\nTAO (%P|%t) ") + ASYS_TEXT ("IIOP_Acceptor::open - %p\n\n"), + ASYS_TEXT ("cannot cache hostname"))); + return -1; + } + this->hosts_[0] = tmp_host; + } + return this->open_i (orb_core, addr); } @@ -185,27 +252,128 @@ int TAO_IIOP_Acceptor::open_default (TAO_ORB_Core *orb_core, const char *options) { + if (this->hosts_ != 0) + { + // The hostname cache has already been set! + // This is bad mojo, i.e. an internal TAO error. + ACE_ERROR_RETURN ((LM_ERROR, + ASYS_TEXT ("TAO (%P|%t) ") + ASYS_TEXT ("IIOP_Acceptor::open_default - "), + ASYS_TEXT ("hostname already set\n\n")), + -1); + } + // Parse options if (this->parse_options (options) == -1) return -1; - // @@ Until we can support multihomed machines correctly we must - // pick the "default interface" and only listen on that IP - // address. + // Extract the hostname for each network interface, and then cache + // it. The hostnames will then be used when creating a + // TAO_IIOP_Profile for each endpoint setup on the probed + // network interfaces. + ACE_INET_Addr *if_addrs = 0; + size_t if_cnt = 0; - ACE_INET_Addr addr; - char buffer[MAXHOSTNAMELEN + 1]; - if (addr.get_host_name (buffer, - sizeof (buffer)) != 0) + if (ACE::get_ip_interfaces (if_cnt, + if_addrs) != 0) return -1; - if (addr.set (u_short(0), - buffer, + // Scan for the loopback interface since it shouldn't be included in + // the list of cached hostnames unless it is the only interface. + size_t lo_cnt = 0; + for (size_t j = 0; j < if_cnt; ++j) + if (if_addrs[j].get_ip_address() == INADDR_LOOPBACK) + lo_cnt++; + + + { // Begin ACE_Auto_Basic_Array_Ptr scope. + + // @@ It's either this or release the array from the + // ACE_Auto_Basic_Array_Ptr<> and delete it manually. This + // seemed like a more elegant solution, i.e. create a scope for + // it. + // -Ossama + + // The instantiation for this template is in + // tao/IIOP_Connector.cpp. + ACE_Auto_Basic_Array_Ptr safe_if_addrs (if_addrs); + + // If the loopback interface is the only interface then include it + // in the list of interfaces to query for a hostname, otherwise + // exclude it from the list. + if (if_cnt == lo_cnt) + this->num_hosts_ = if_cnt; + else + this->num_hosts_ = if_cnt - lo_cnt; + + ACE_NEW_RETURN (this->addrs_, + ACE_INET_Addr[this->num_hosts_], + -1); + + ACE_NEW_RETURN (this->hosts_, + ACE_CString[this->num_hosts_], + -1); + + // The number of hosts/interfaces we want to cache may not be the + // same as the number of detected interfaces so keep a separate + // count. + size_t host_cnt = 0; + + for (size_t i = 0; i < if_cnt; ++i) + { + // Ignore any loopback interface if there are other + // non-loopback interfaces. + if (if_cnt != lo_cnt && + if_addrs[i].get_ip_address() == INADDR_LOOPBACK) + continue; + + if (orb_core->orb_params ()->use_dotted_decimal_addresses ()) + { + const char *tmp = if_addrs[i].get_host_addr (); + if (tmp == 0) + { + if (TAO_debug_level > 0) + ACE_DEBUG ((LM_DEBUG, + ASYS_TEXT ("\n\nTAO (%P|%t) ") + ASYS_TEXT ("IIOP_Acceptor::open_default ") + ASYS_TEXT ("- %p\n\n"), + ASYS_TEXT ("cannot cache hostname"))); + return -1; + } + this->hosts_[host_cnt] = tmp; + } + else + { + char tmp_host[MAXHOSTNAMELEN + 1]; + if (if_addrs[i].get_host_name (tmp_host, + sizeof (tmp_host)) != 0) + { + if (TAO_debug_level > 0) + ACE_DEBUG ((LM_DEBUG, + ASYS_TEXT ("\n\nTAO (%P|%t) ") + ASYS_TEXT ("IIOP_Acceptor::open_default ") + ASYS_TEXT ("- %p\n\n"), + ASYS_TEXT ("cannot cache hostname"))); + return -1; + } + this->hosts_[host_cnt] = tmp_host; + } + + this->addrs_[host_cnt] = if_addrs[i]; // Copy the addr. + host_cnt++; + } + } // End ACE_Auto_Basic_Array_Ptr scope. + + // Now that each network interface's hostname has been cached, open + // an endpoint on each network interface using the INADDR_ANY + // address. + ACE_INET_Addr addr; + + if (addr.set (ACE_static_cast(u_short, 0), + ACE_static_cast(ACE_UINT32, INADDR_ANY), 1) != 0) return -1; - this->host_ = buffer; - return this->open_i (orb_core, addr); } @@ -241,62 +409,48 @@ TAO_IIOP_Acceptor::open_i (TAO_ORB_Core* orb_core, return -1; } - // @@ Should this be a catastrophic error??? - if (this->base_acceptor_.acceptor ().get_local_addr (this->address_) != 0) + ACE_INET_Addr address; + + // We do this make sure the port number the endpoint is listening on + // gets set in the addr. + if (this->base_acceptor_.acceptor ().get_local_addr (address) != 0) { + // @@ Should this be a catastrophic error??? if (TAO_debug_level > 0) ACE_DEBUG ((LM_DEBUG, - ASYS_TEXT ("\n\nTAO (%P|%t) IIOP_Acceptor::open_i - %p\n\n"), + ASYS_TEXT ("\n\nTAO (%P|%t) IIOP_Acceptor::open_i ") + ASYS_TEXT ("- %p\n\n"), ASYS_TEXT ("cannot get local addr"))); return -1; } - if (orb_core->orb_params ()->use_dotted_decimal_addresses ()) - { - const char *tmp = addr.get_host_addr (); - if (tmp == 0) - { - if (TAO_debug_level > 0) - ACE_DEBUG ((LM_DEBUG, - ASYS_TEXT ("\n\nTAO (%P|%t) IIOP_Acceptor::open_i - %p\n\n"), - ASYS_TEXT ("cannot cache hostname"))); - return -1; - } - this->host_ = tmp; - } - else + // Set the port for each addr. If there is more than one network + // interface then the endpoint created on each interface will be on + // the same port. This is how a wildcard socket bind() is supposed + // to work. + u_short port = address.get_port_number (); + for (size_t j = 0; j < this->num_hosts_; ++j) + this->addrs_[j].set_port_number (port, 1); + + if (TAO_debug_level > 5) { - char tmp_host[MAXHOSTNAMELEN+1]; - if (addr.get_host_name (tmp_host, - sizeof tmp_host) != 0) + for (size_t i = 0; i < this->num_hosts_; ++i) { - if (TAO_debug_level > 0) - ACE_DEBUG ((LM_DEBUG, - ASYS_TEXT ("\n\nTAO (%P|%t) IIOP_Acceptor::open_i - %p\n\n"), - ASYS_TEXT ("cannot cache hostname"))); - return -1; + ACE_DEBUG ((LM_DEBUG, + ASYS_TEXT ("\nTAO (%P|%t) IIOP_Acceptor::open_i - ") + ASYS_TEXT ("listening on: <%s:%u>\n"), + this->hosts_[i].c_str (), + this->addrs_[i].get_port_number ())); } - this->host_ = tmp_host; } - if (TAO_debug_level > 5) - { - ACE_DEBUG ((LM_DEBUG, - ASYS_TEXT ("\nTAO (%P|%t) IIOP_Acceptor::open_i - ") - ASYS_TEXT ("listening on: <%s:%u>\n"), - this->host_.c_str (), - this->address_.get_port_number ())); - } return 0; } CORBA::ULong TAO_IIOP_Acceptor::endpoint_count (void) { - // @@ for now just assume one! - // we should take a look at the local address, if it is zero then - // get the list of available IP interfaces and return this number. - return 1; + return this->num_hosts_; } int diff --git a/TAO/tao/IIOP_Acceptor.h b/TAO/tao/IIOP_Acceptor.h index 82139d5a746..6e9d8ddc1ff 100644 --- a/TAO/tao/IIOP_Acceptor.h +++ b/TAO/tao/IIOP_Acceptor.h @@ -1,7 +1,7 @@ // This may look like C, but it's really -*- C++ -*- // $Id$ -// ============================================================================ +//============================================================================ // // = LIBRARY // TAO @@ -15,7 +15,7 @@ // = AUTHOR // Fred Kuhns // -// ============================================================================ +//============================================================================ #ifndef TAO_IIOP_ACCEPTOR_H #define TAO_IIOP_ACCEPTOR_H @@ -82,14 +82,17 @@ private: // Parse protocol specific options. protected: - ACE_INET_Addr address_; - ACE_CString host_; - // Cache the information about the endpoint serviced by this + ACE_INET_Addr *addrs_; + + ACE_CString *hosts_; + // Cache the information about the endpoints serviced by this // acceptor. - // @@ TODO there may in fact be multiple hostnames for this - // endpoint. For example it the IP address is INADDR_ANY - // (0.0.0.0) then there will be possibly a different hostname for - // each interface. + // There may in fact be multiple hostnames for this endpoint. For + // example, if the IP address is INADDR_ANY (0.0.0.0) then there + // will be possibly a different hostname for each interface. + + size_t num_hosts_; + // The number of host names cached in the hosts_ array. TAO_GIOP_Version version_; // The GIOP version for this endpoint diff --git a/TAO/tao/IIOP_Acceptor.i b/TAO/tao/IIOP_Acceptor.i index 28e5f46ce72..f7c171d6e5e 100644 --- a/TAO/tao/IIOP_Acceptor.i +++ b/TAO/tao/IIOP_Acceptor.i @@ -4,5 +4,12 @@ ACE_INLINE const ACE_INET_Addr& TAO_IIOP_Acceptor::address (void) const { - return this->address_; + ACE_ASSERT (this->addrs_ != 0); + + // @@ This is busted. + // The Implementation Repository will have to start supporting + // IORs with multiple profiles. For now, we just return the + // first addr. + // -Ossama + return this->addrs_[0]; } diff --git a/TAO/tao/Makefile b/TAO/tao/Makefile index accf6753467..bfffce99e03 100644 --- a/TAO/tao/Makefile +++ b/TAO/tao/Makefile @@ -5058,7 +5058,10 @@ realclean: $(TAO_ROOT)/tao/Object_KeyC.i \ $(TAO_ROOT)/tao/IIOP_Profile.i \ $(TAO_ROOT)/tao/MProfile.h \ - $(TAO_ROOT)/tao/MProfile.i + $(TAO_ROOT)/tao/MProfile.i \ + $(ACE_ROOT)/ace/Auto_Ptr.h \ + $(ACE_ROOT)/ace/Auto_Ptr.i \ + $(ACE_ROOT)/ace/Auto_Ptr.cpp .obj/IIOP_Connect.o .obj/IIOP_Connect.so .shobj/IIOP_Connect.o .shobj/IIOP_Connect.so: IIOP_Connect.cpp \ $(TAO_ROOT)/tao/IIOP_Connect.h \ @@ -11767,7 +11770,8 @@ realclean: $(ACE_ROOT)/ace/Map_Manager.cpp \ $(TAO_ROOT)/tao/ORB_Core.i \ $(ACE_ROOT)/ace/Dynamic_Service.h \ - $(ACE_ROOT)/ace/Dynamic_Service.cpp + $(ACE_ROOT)/ace/Dynamic_Service.cpp \ + $(TAO_ROOT)/tao/singletons.h .obj/CurrentC.o .obj/CurrentC.so .shobj/CurrentC.o .shobj/CurrentC.so: CurrentC.cpp \ $(TAO_ROOT)/tao/CurrentC.h \ @@ -15088,6 +15092,60 @@ realclean: $(TAO_ROOT)/tao/varout.i \ $(TAO_ROOT)/tao/varout.cpp \ $(TAO_ROOT)/tao/Principal.i \ + $(TAO_ROOT)/tao/singletons.h \ + $(TAO_ROOT)/tao/Marshal.h \ + $(TAO_ROOT)/tao/ORB.h \ + $(TAO_ROOT)/tao/IOR_LookupTable.h \ + $(ACE_ROOT)/ace/Hash_Map_Manager.h \ + $(ACE_ROOT)/ace/Functor.h \ + $(ACE_ROOT)/ace/Functor.i \ + $(ACE_ROOT)/ace/Functor_T.h \ + $(ACE_ROOT)/ace/Functor_T.i \ + $(ACE_ROOT)/ace/Functor_T.cpp \ + $(ACE_ROOT)/ace/Hash_Map_Manager.i \ + $(ACE_ROOT)/ace/Hash_Map_Manager_T.h \ + $(ACE_ROOT)/ace/Hash_Map_Manager_T.i \ + $(ACE_ROOT)/ace/Hash_Map_Manager_T.cpp \ + $(ACE_ROOT)/ace/Service_Config.h \ + $(ACE_ROOT)/ace/Service_Object.h \ + $(ACE_ROOT)/ace/Shared_Object.h \ + $(ACE_ROOT)/ace/Shared_Object.i \ + $(ACE_ROOT)/ace/Service_Object.i \ + $(ACE_ROOT)/ace/Service_Config.i \ + $(ACE_ROOT)/ace/Reactor.h \ + $(ACE_ROOT)/ace/Handle_Set.h \ + $(ACE_ROOT)/ace/Handle_Set.i \ + $(ACE_ROOT)/ace/Timer_Queue.h \ + $(ACE_ROOT)/ace/Timer_Queue_T.h \ + $(ACE_ROOT)/ace/Timer_Queue_T.i \ + $(ACE_ROOT)/ace/Timer_Queue_T.cpp \ + $(ACE_ROOT)/ace/Reactor.i \ + $(ACE_ROOT)/ace/Reactor_Impl.h \ + $(ACE_ROOT)/ace/Svc_Conf_Tokens.h \ + $(TAO_ROOT)/tao/Services.h \ + $(TAO_ROOT)/tao/Services.i \ + $(TAO_ROOT)/tao/IORManipulation.h \ + $(TAO_ROOT)/tao/IORS.h \ + $(TAO_ROOT)/tao/IORC.h \ + $(TAO_ROOT)/tao/IORC.i \ + $(TAO_ROOT)/tao/Servant_Base.h \ + $(TAO_ROOT)/tao/POAC.h \ + $(TAO_ROOT)/tao/PolicyC.h \ + $(TAO_ROOT)/tao/CurrentC.h \ + $(TAO_ROOT)/tao/CurrentC.i \ + $(TAO_ROOT)/tao/PolicyC.i \ + $(TAO_ROOT)/tao/POAC.i \ + $(TAO_ROOT)/tao/Servant_Base.i \ + $(TAO_ROOT)/tao/IORS.i \ + $(TAO_ROOT)/tao/Interceptor.h \ + $(TAO_ROOT)/tao/InterceptorS.h \ + $(TAO_ROOT)/tao/InterceptorC.h \ + $(TAO_ROOT)/tao/IOPC.h \ + $(TAO_ROOT)/tao/IOPC.i \ + $(TAO_ROOT)/tao/InterceptorC.i \ + $(TAO_ROOT)/tao/Interceptor.i \ + $(TAO_ROOT)/tao/ORB.i \ + $(TAO_ROOT)/tao/Marshal.i \ $(TAO_ROOT)/tao/debug.h .obj/ValueBase.o .obj/ValueBase.so .shobj/ValueBase.o .shobj/ValueBase.so: ValueBase.cpp \ -- cgit v1.2.1