mcast: IOR format.
More...
#include <MCAST_Parser.h>
Inheritance diagram for TAO_MCAST_Parser:


Public Member Functions | |
| TAO_MCAST_Parser (void) | |
| Constructor. | |
| virtual | ~TAO_MCAST_Parser (void) |
| The destructor. | |
| virtual bool | match_prefix (const char *ior_string) const |
| virtual CORBA::Object_ptr | parse_string (const char *ior, CORBA::ORB_ptr orb) |
| Parse the ior-string that is passed. | |
Private Member Functions | |
| CORBA::Object_ptr | multicast_to_service (const char *service_name, unsigned short port, const char *mcast_address, int mcast_ttl, const char *mcast_nic, CORBA::ORB_ptr orb, ACE_Time_Value *timeout) |
| int | multicast_query (char *&buf, const char *service_name, unsigned short port, const char *mcast_address, int mcast_ttl, const char *mcast_nic, ACE_Time_Value *timeout, CORBA::ORB_ptr orb) |
| void | assign_to_variables (char const *mcast_name_ptr) |
Private Attributes | |
| CORBA::String_var | mcast_address_ |
| unsigned short | mcast_port_ |
| Default multicast port (currently Name Service mcast port). | |
| CORBA::String_var | mcast_nic_ |
| Multicast network interface card. | |
| int | mcast_ttl_ |
| Default time-to-live (default is 1). | |
| CORBA::String_var | service_name_ |
| Multicast service name. | |
mcast: IOR format.
This class implements the mcast: IOR format. It is dynamically loaded by the ORB and used to parse the string to separate the individual from the list of object addresses .
Definition at line 41 of file MCAST_Parser.h.
|
|
Constructor.
|
|
|
The destructor.
Definition at line 30 of file MCAST_Parser.cpp.
00031 {
00032 }
|
|
|
Definition at line 350 of file MCAST_Parser.cpp. References ACE_CString, ACE_DEFAULT_MULTICAST_ADDR, ACE_ERROR, ACE_TEXT, ACE_OS::atoi(), LM_ERROR, mcast_address_, mcast_nic_, mcast_port_, mcast_ttl_, TAO_debug_level, TAO_DEFAULT_IMPLREPO_SERVER_REQUEST_PORT, TAO_DEFAULT_INTERFACEREPO_SERVER_REQUEST_PORT, and TAO_DEFAULT_TRADING_SERVER_REQUEST_PORT. Referenced by parse_string().
00351 {
00352 /*
00353 * The format now is "multicast_address:port:nicaddress:ttl/object_key"
00354 */
00355 ACE_CString mcast_name_cstring (mcast_name);
00356
00357 ACE_CString::size_type pos_colon1 =
00358 mcast_name_cstring.find (':', 0);
00359
00360 #if defined (ACE_HAS_IPV6)
00361 // IPv6 numeric address in host string?
00362 bool ipv6_in_host = false;
00363
00364 // Check if this is an mcast address containing a
00365 // decimal IPv6 address representation.
00366 if (mcast_name_cstring[0] == '[')
00367 {
00368 // In this case we have to find the end of the numeric address and
00369 // start looking for the port separator from there.
00370 ACE_CString::size_type const cp_pos =
00371 mcast_name_cstring.find (']', 0);
00372 if (cp_pos == 0)
00373 {
00374 // No valid IPv6 address specified.
00375 if (TAO_debug_level > 0)
00376 {
00377 ACE_ERROR ((LM_ERROR,
00378 ACE_TEXT ("\nTAO (%P|%t) MCAST_Parser: ")
00379 ACE_TEXT ("Invalid IPv6 decimal address specified.\n")));
00380 }
00381
00382 return;
00383 }
00384 else
00385 {
00386 if (mcast_name_cstring[cp_pos + 1] == ':') // Look for a port
00387 pos_colon1 = cp_pos + 1;
00388 else
00389 pos_colon1 = cp_pos;
00390 ipv6_in_host = true; // host string contains full IPv6 numeric address
00391 }
00392 }
00393 #endif /* ACE_HAS_IPV6 */
00394
00395 if (pos_colon1 == 0)
00396 {
00397 #if defined (ACE_HAS_IPV6)
00398 const char default_addr[] = ACE_DEFAULT_MULTICASTV6_ADDR;
00399 #else /* ACE_HAS_IPV6 */
00400 const char default_addr[] = ACE_DEFAULT_MULTICAST_ADDR;
00401 #endif /* !ACE_HAS_IPV6 */
00402 this->mcast_address_ = default_addr;
00403 }
00404 else
00405 {
00406 #if defined (ACE_HAS_IPV6)
00407 if (ipv6_in_host)
00408 this->mcast_address_ =
00409 mcast_name_cstring.substring (1,
00410 pos_colon1 - 2).c_str ();
00411 else
00412 #endif /* ACE_HAS_IPV6 */
00413 this->mcast_address_ =
00414 mcast_name_cstring.substring (0,
00415 pos_colon1).c_str ();
00416 }
00417 mcast_name_cstring =
00418 mcast_name_cstring.substring (pos_colon1 + 1,
00419 mcast_name_cstring.length() -
00420 pos_colon1);
00421
00422 ACE_CString::size_type const pos_colon2 =
00423 mcast_name_cstring.find (':', 0);
00424
00425 if (pos_colon2 == 0)
00426 {
00427 if (mcast_name_cstring.find ("InterfaceRepository") !=
00428 ACE_CString::npos)
00429 {
00430 this->mcast_port_ =
00431 TAO_DEFAULT_INTERFACEREPO_SERVER_REQUEST_PORT;
00432 }
00433 else if (mcast_name_cstring.find ("ImplRepoService") !=
00434 ACE_CString::npos)
00435 {
00436 this->mcast_port_ =
00437 TAO_DEFAULT_IMPLREPO_SERVER_REQUEST_PORT;
00438 }
00439 else if (mcast_name_cstring.find ("TradingService") !=
00440 ACE_CString::npos)
00441 {
00442 this->mcast_port_ = TAO_DEFAULT_TRADING_SERVER_REQUEST_PORT;
00443 }
00444 }
00445 else
00446 {
00447 int const the_port =
00448 ACE_OS::atoi (mcast_name_cstring.substring (0,
00449 pos_colon2).c_str ());
00450
00451 if (the_port > 0 && the_port < 0xffffL)
00452 this->mcast_port_ = the_port;
00453 }
00454
00455 mcast_name_cstring =
00456 mcast_name_cstring.substring (pos_colon2 + 1,
00457 mcast_name_cstring.length() - pos_colon2);
00458
00459
00460 ACE_CString::size_type const pos_colon3 = mcast_name_cstring.find (':', 0);
00461
00462 this->mcast_nic_ =
00463 mcast_name_cstring.substring (0,
00464 pos_colon3).c_str ();
00465
00466 mcast_name_cstring =
00467 mcast_name_cstring.substring (pos_colon3 + 1,
00468 mcast_name_cstring.length() - pos_colon3);
00469
00470 ACE_CString::size_type const pos_colon4 =
00471 mcast_name_cstring.find ('/', 0);
00472
00473 if (pos_colon4 != 0)
00474 {
00475 // Change TTL to non-default value.
00476 int const the_ttl =
00477 ACE_OS::atoi (mcast_name_cstring.substring (0, pos_colon4).c_str ());
00478
00479 if (the_ttl > 0 && the_ttl <= 255) // Valid TTLs: (0, 255]
00480 this->mcast_ttl_ = the_ttl;
00481 }
00482
00483 mcast_name_cstring =
00484 mcast_name_cstring.substring (pos_colon4,
00485 mcast_name_cstring.length() - pos_colon4);
00486
00487 this->service_name_ =
00488 mcast_name_cstring.substring (1,
00489 mcast_name_cstring.length() - 1).c_str ();
00490 }
|
|
|
= The IOR_Parser methods, please read the documentation in IOR_Parser.h Implements TAO_IOR_Parser. Definition at line 35 of file MCAST_Parser.cpp. References mcast_prefix, and ACE_OS::strncmp().
00036 {
00037 return (ACE_OS::strncmp (ior_string,
00038 ::mcast_prefix,
00039 sizeof (::mcast_prefix) - 1) == 0);
00040 }
|
|
||||||||||||||||||||||||||||||||||||
|
Definition at line 108 of file MCAST_Parser.cpp. References ACE_SOCK_Acceptor::accept(), ACE_CString, ACE_DEBUG, ACE_ERROR, ACE_HTONS, ACE_NTOHS, ACE_TCHAR, ACE_TEXT, ACE_TEXT_CHAR_TO_TCHAR, ACE_INET_Addr::addr_to_string(), ACE_SOCK_Acceptor::close(), ACE_SOCK::close(), ACE_SOCK_Stream::close(), ACE_SOCK::get_local_addr(), ACE_INET_Addr::get_port_number(), ACE_Addr::get_type(), IP_MULTICAST_TTL, IPPROTO_IP, LM_DEBUG, LM_ERROR, TAO_ORB_Parameters::mcast_discovery_endpoint(), ACE_SOCK_Dgram::open(), ACE_SOCK_Acceptor::open(), CORBA::ORB::orb_core(), TAO_ORB_Core::orb_params(), CORBA::ORB_ptr, ACE_SOCK_Stream::recv_n(), ACE_SOCK_Dgram::send(), ACE_INET_Addr::set(), ACE_SOCK_Dgram::set_nic(), ACE_SOCK::set_option(), ssize_t, ACE_OS::strcasecmp(), CORBA::string_alloc(), ACE_OS::strlen(), TAO_debug_level, TAO_DEFAULT_IOR_SIZE, and TAO_DEFAULT_SERVICE_RESOLUTION_TIMEOUT. Referenced by multicast_to_service().
00116 {
00117 ACE_INET_Addr my_addr;
00118 ACE_SOCK_Acceptor acceptor;
00119 ACE_SOCK_Stream stream;
00120 ACE_SOCK_Dgram dgram;
00121
00122 ssize_t result = 0;
00123
00124 // Bind listener to any port and then find out what the port was.
00125 #if defined (ACE_HAS_IPV6)
00126 if (acceptor.open (ACE_Addr::sap_any, 0, AF_INET6) == -1
00127 #else /* ACE_HAS_IPV6 */
00128 if (acceptor.open (ACE_Addr::sap_any) == -1
00129 #endif /* !ACE_HAS_IPV6 */
00130 || acceptor.get_local_addr (my_addr) == -1)
00131 {
00132 ACE_ERROR ((LM_ERROR,
00133 ACE_TEXT ("acceptor.open () || ")
00134 ACE_TEXT ("acceptor.get_local_addr () failed\n")));
00135 result = -1;
00136 }
00137 else
00138 {
00139 if (TAO_debug_level > 0)
00140 {
00141 ACE_TCHAR addr[64];
00142 my_addr.addr_to_string (addr, sizeof(addr));
00143 ACE_DEBUG ((LM_DEBUG,
00144 "(%P|%t) TAO_MCAST_Parser: acceptor local address %s.\n",
00145 addr));
00146 }
00147
00148 ACE_INET_Addr multicast_addr (port,
00149 mcast_address);
00150
00151 // Set the address if multicast_discovery_endpoint option
00152 // is specified for the Naming Service.
00153 ACE_CString mde (orb->orb_core ()->orb_params ()
00154 ->mcast_discovery_endpoint ());
00155
00156 if (ACE_OS::strcasecmp (service_name,
00157 "NameService") == 0
00158 && mde.length () != 0)
00159 if (multicast_addr.set (mde.c_str()) == -1)
00160 {
00161 ACE_ERROR ((LM_ERROR,
00162 ACE_TEXT("ORB.cpp: Multicast address setting failed\n")));
00163 stream.close ();
00164 dgram.close ();
00165 acceptor.close ();
00166 return -1;
00167 }
00168
00169 // Open the datagram.
00170 if (dgram.open (ACE_Addr::sap_any, multicast_addr.get_type ()) == -1)
00171 {
00172 ACE_ERROR ((LM_ERROR,
00173 ACE_TEXT ("Unable to open the Datagram!\n")));
00174 result = -1;
00175 }
00176 else
00177 {
00178 // Set NIC
00179 dgram.set_nic (ACE_TEXT_CHAR_TO_TCHAR (mcast_nic),
00180 multicast_addr.get_type ());
00181
00182 // Set TTL
00183 int mcast_ttl_optval = mcast_ttl;
00184
00185 #if defined (ACE_HAS_IPV6)
00186 if (multicast_addr.get_type () == AF_INET6)
00187 {
00188 if (dgram.set_option (
00189 IPPROTO_IPV6,
00190 IPV6_MULTICAST_HOPS,
00191 &mcast_ttl_optval,
00192 sizeof (mcast_ttl_optval)) != 0)
00193 return -1;
00194 }
00195 else
00196 #endif /* ACE_HAS_IPV6 */
00197 if (dgram.set_option (
00198 IPPROTO_IP,
00199 IP_MULTICAST_TTL,
00200 &mcast_ttl_optval,
00201 sizeof (mcast_ttl_optval)) != 0)
00202 result = -1;
00203
00204 // Convert the acceptor port into network byte order.
00205 ACE_UINT16 response_port =
00206 (ACE_UINT16) ACE_HTONS (my_addr.get_port_number ());
00207
00208 // Length of service name we will send.
00209 CORBA::Short data_len =
00210 (CORBA::Short) ACE_HTONS (ACE_OS::strlen (service_name) + 1);
00211
00212 // Vector we will send. It contains: 1) length of service
00213 // name string, 2)port on which we are listening for
00214 // replies, and 3) name of service we are looking for.
00215 const int iovcnt = 3;
00216 iovec iovp[iovcnt];
00217
00218 // The length of service name string.
00219 iovp[0].iov_base = (char *) &data_len;
00220 iovp[0].iov_len = sizeof (CORBA::Short);
00221
00222 // The port at which we are listening.
00223 iovp[1].iov_base = (char *) &response_port;
00224 iovp[1].iov_len = sizeof (ACE_UINT16);
00225
00226 // The service name string.
00227 iovp[2].iov_base = (char *) service_name;
00228 iovp[2].iov_len =
00229 static_cast<u_long> (ACE_OS::strlen (service_name) + 1);
00230
00231 // Send the multicast.
00232 result = dgram.send (iovp,
00233 iovcnt,
00234 multicast_addr);
00235
00236 if (TAO_debug_level > 0)
00237 ACE_DEBUG ((LM_DEBUG,
00238 ACE_TEXT ("\nsent multicast request.")));
00239
00240 // Check for errors.
00241 if (result == -1)
00242 ACE_ERROR ((LM_ERROR,
00243 ACE_TEXT ("%p\n"),
00244 ACE_TEXT ("error sending IIOP multicast")));
00245 else
00246 {
00247 if (TAO_debug_level > 0)
00248 ACE_DEBUG ((LM_DEBUG,
00249 ACE_TEXT ("\n%N; Sent multicast.")
00250 ACE_TEXT ("# of bytes sent is %d.\n"),
00251 result));
00252 // Wait for response until timeout.
00253 ACE_Time_Value tv (
00254 timeout == 0
00255 ? ACE_Time_Value (TAO_DEFAULT_SERVICE_RESOLUTION_TIMEOUT)
00256 : *timeout);
00257
00258 // Accept reply connection from server.
00259 if (acceptor.accept (stream,
00260 0,
00261 &tv) == -1)
00262 {
00263 ACE_ERROR ((LM_ERROR,
00264 ACE_TEXT ("%p\n"),
00265 ACE_TEXT ("multicast_query: unable to accept")));
00266 result = -1;
00267 }
00268 else
00269 {
00270 // Receive the IOR.
00271
00272 // IOR length.
00273 CORBA::Short ior_len;
00274 result = stream.recv_n (&ior_len,
00275 sizeof ior_len,
00276 0,
00277 &tv);
00278 if (result != sizeof (ior_len))
00279 {
00280 ACE_ERROR ((LM_ERROR,
00281 ACE_TEXT ("%p\n"),
00282 ACE_TEXT ("multicast_query: unable to receive ")
00283 ACE_TEXT ("ior length")));
00284 result = -1;
00285 }
00286 else
00287 {
00288 // Allocate more space for the ior if we don't
00289 // have enough.
00290 ior_len = (CORBA::Short) ACE_NTOHS (ior_len);
00291 if (ior_len >= TAO_DEFAULT_IOR_SIZE)
00292 {
00293 buf = CORBA::string_alloc (ior_len);
00294 if (buf == 0)
00295 {
00296 ACE_ERROR ((LM_ERROR,
00297 ACE_TEXT ("%p\n"),
00298 ACE_TEXT ("multicast_query: unable to ")
00299 ACE_TEXT ("allocate memory")));
00300 result = -1;
00301 }
00302 }
00303
00304 if (result != -1)
00305 {
00306 // Receive the ior.
00307 result = stream.recv_n (buf,
00308 ior_len,
00309 0,
00310 &tv);
00311 if (result == -1)
00312 ACE_ERROR ((LM_ERROR,
00313 ACE_TEXT ( "%p\n"),
00314 ACE_TEXT ("error reading ior")));
00315 else if (TAO_debug_level > 0)
00316 ACE_DEBUG ((LM_DEBUG,
00317 ACE_TEXT ("%N: service resolved to IOR <%s>\n"),
00318 ACE_TEXT_CHAR_TO_TCHAR (buf)));
00319 }
00320 }
00321 }
00322 }
00323 }
00324 if (result == -1)
00325 {
00326 ACE_ERROR ((LM_ERROR,
00327 ACE_TEXT("\nmulticast discovery of %s failed.\n"),
00328 ACE_TEXT_CHAR_TO_TCHAR (service_name)));
00329
00330 if (ACE_OS::strcasecmp (service_name,
00331 "NameService") == 0)
00332 {
00333 ACE_ERROR ((LM_ERROR,
00334 ACE_TEXT("Specify -m 1 when starting Naming_Service,\n")
00335 ACE_TEXT("or see http://www.theaceorb.com/faq/#115\n")
00336 ACE_TEXT("for using NameService without multicast.\n\n")));
00337 }
00338 }
00339 }
00340
00341 // Clean up.
00342 stream.close ();
00343 dgram.close ();
00344 acceptor.close ();
00345
00346 return result == -1 ? -1 : 0;
00347 }
|
|
||||||||||||||||||||||||||||||||
|
Definition at line 67 of file MCAST_Parser.cpp. References TAO_Pseudo_Var_T< T >::_retn(), multicast_query(), CORBA::Object_var, CORBA::ORB_ptr, CORBA::ORB::string_to_object(), CORBA::String_var, and TAO_DEFAULT_IOR_SIZE. Referenced by parse_string().
00074 {
00075 char buf[TAO_DEFAULT_IOR_SIZE];
00076 char * ior = buf;
00077
00078 // Use UDP multicast to locate the service.
00079 int const result = this->multicast_query (ior,
00080 service_name,
00081 port,
00082 mcast_address,
00083 mcast_ttl,
00084 mcast_nic,
00085 timeout,
00086 orb);
00087
00088 CORBA::Object_var return_value;
00089
00090 if (result == 0)
00091 {
00092 CORBA::String_var cleaner;
00093 // If the IOR didn't fit into <buf>, memory for it was dynamically
00094 // allocated - make sure it gets deallocated.
00095 if (ior != buf)
00096 cleaner = ior;
00097
00098 // Convert IOR to an object reference.
00099 return_value =
00100 orb->string_to_object (ior);
00101 }
00102
00103 // Return object reference.
00104 return return_value._retn ();
00105 }
|
|
||||||||||||
|
Parse the ior-string that is passed.
Implements TAO_IOR_Parser. Definition at line 43 of file MCAST_Parser.cpp. References assign_to_variables(), CORBA::ORB::get_timeout(), TAO::String_var< charT >::in(), mcast_address_, mcast_nic_, mcast_port_, mcast_ttl_, multicast_to_service(), and CORBA::ORB_ptr.
00044 {
00045 char const * const mcast_name =
00046 ior + sizeof (::mcast_prefix) + 1;
00047
00048 assign_to_variables (mcast_name);
00049
00050 /*
00051 * Now that we got the global variables.
00052 * we can invoke multicast_to_service and multicast_query
00053 */
00054 ACE_Time_Value *timeout = orb->get_timeout ();
00055
00056 return
00057 this->multicast_to_service (service_name_.in (),
00058 this->mcast_port_,
00059 this->mcast_address_.in (),
00060 this->mcast_ttl_,
00061 this->mcast_nic_.in (),
00062 orb,
00063 timeout);
00064 }
|
|
|
Definition at line 83 of file MCAST_Parser.h. Referenced by assign_to_variables(), and parse_string(). |
|
|
Multicast network interface card.
Definition at line 89 of file MCAST_Parser.h. Referenced by assign_to_variables(), and parse_string(). |
|
|
Default multicast port (currently Name Service mcast port).
Definition at line 86 of file MCAST_Parser.h. Referenced by assign_to_variables(), and parse_string(). |
|
|
Default time-to-live (default is 1).
Definition at line 92 of file MCAST_Parser.h. Referenced by assign_to_variables(), and parse_string(). |
|
|
Multicast service name.
Definition at line 95 of file MCAST_Parser.h. |
1.3.6