00001
00002
00003 #include "ace/Sock_Connect.h"
00004 #include "ace/INET_Addr.h"
00005 #include "ace/Log_Msg.h"
00006 #include "ace/Handle_Set.h"
00007 #include "ace/Auto_Ptr.h"
00008 #include "ace/SString.h"
00009 #include "ace/OS_Memory.h"
00010 #include "ace/OS_NS_stdio.h"
00011 #include "ace/ACE.h"
00012
00013 #if defined (sparc)
00014 # include "ace/OS_NS_fcntl.h"
00015 #endif // sparc
00016
00017 #include "ace/OS_NS_stdlib.h"
00018 #include "ace/OS_NS_string.h"
00019 #include "ace/OS_NS_sys_socket.h"
00020 #include "ace/OS_NS_netdb.h"
00021 #include "ace/OS_NS_unistd.h"
00022 #include "ace/os_include/net/os_if.h"
00023
00024 #if defined (ACE_HAS_IPV6)
00025 # include "ace/Guard_T.h"
00026 # include "ace/Recursive_Thread_Mutex.h"
00027 # if defined (_AIX)
00028 # include <netinet/in6_var.h>
00029 # endif
00030 #endif
00031
00032 # if defined (ACE_HAS_GETIFADDRS)
00033 # if defined (ACE_VXWORKS)
00034 # include <net/ifaddrs.h>
00035 # else
00036 # include <ifaddrs.h>
00037 # endif
00038 # endif
00039
00040 #if defined (ACE_VXWORKS) && (ACE_VXWORKS < 0x600)
00041 #include <inetLib.h>
00042 #include <netinet/in_var.h>
00043 #if defined (ACE_HAS_IPV6)
00044 #include <ifLib.h>
00045 extern "C" {
00046 extern struct in_ifaddr* in_ifaddr;
00047 extern LIST_HEAD(in_ifaddrhashhead, in_ifaddr) *in_ifaddrhashtbl;
00048 }
00049 #endif
00050 #include "ace/OS_NS_stdio.h"
00051 #endif
00052
00053 #if defined (ACE_VXWORKS) && ((ACE_VXWORKS == 0x630) || (ACE_VXWORKS == 0x640)) && defined (__RTP__) && defined (ACE_HAS_IPV6)
00054 const struct in6_addr in6addr_any = IN6ADDR_ANY_INIT;
00055 const struct in6_addr in6addr_nodelocal_allnodes = IN6ADDR_NODELOCAL_ALLNODES_INIT;
00056 const struct in6_addr in6addr_linklocal_allnodes = IN6ADDR_LINKLOCAL_ALLNODES_INIT;
00057 const struct in6_addr in6addr_linklocal_allrouters = IN6ADDR_LINKLOCAL_ALLROUTERS_INIT;
00058 #endif
00059
00060 #if defined (ACE_HAS_WINCE)
00061 #include <Iphlpapi.h>
00062
00063
00064
00065 # include <ws2tcpip.h>
00066 const struct in6_addr in6addr_any = IN6ADDR_ANY_INIT;
00067 const struct in6_addr in6addr_loopback = IN6ADDR_LOOPBACK_INIT;
00068 #endif // ACE_HAS_WINCE
00069
00070 #if defined (ACE_WIN32) && defined (ACE_HAS_PHARLAP)
00071 # include "ace/OS_NS_stdio.h"
00072 #endif
00073
00074 #if defined (ACE_HAS_IPV6)
00075
00076
00077
00078
00079 # if defined (SIOCGLIFCONF)
00080 # define SIOCGIFCONF_CMD SIOCGLIFCONF
00081 # if defined (__hpux)
00082 # define IFREQ if_laddrreq
00083 # define IFCONF if_laddrconf
00084 # define IFC_REQ iflc_req
00085 # define IFC_LEN iflc_len
00086 # define IFC_BUF iflc_buf
00087 # define IFR_ADDR iflr_addr
00088 # define IFR_NAME iflr_name
00089 # define IFR_FLAGS iflr_flags
00090 # undef SETFAMILY
00091 # define SA_FAMILY sa_family
00092 # else
00093 # define IFREQ lifreq
00094 # define IFCONF lifconf
00095 # define IFC_REQ lifc_req
00096 # define IFC_LEN lifc_len
00097 # define IFC_BUF lifc_buf
00098 # define IFR_ADDR lifr_addr
00099 # define IFR_NAME lifr_name
00100 # define IFR_FLAGS lifr_flags
00101 # define SETFAMILY
00102 # define IFC_FAMILY lifc_family
00103 # define IFC_FLAGS lifc_flags
00104 # define SA_FAMILY ss_family
00105 # endif
00106 # else
00107 # define SIOCGIFCONF_CMD SIOCGIFCONF
00108 # define IFREQ ifreq
00109 # define IFCONF ifconf
00110 # define IFC_REQ ifc_req
00111 # define IFC_LEN ifc_len
00112 # define IFC_BUF ifc_buf
00113 # define IFR_ADDR ifr_addr
00114 # define IFR_NAME ifr_name
00115 # define IFR_FLAGS ifr_flags
00116 # undef SETFAMILY
00117 # define SA_FAMILY sa_family
00118 # endif
00119
00120 # if defined (ACE_HAS_THREADS)
00121 # include "ace/Object_Manager.h"
00122 # endif
00123
00124 namespace
00125 {
00126
00127
00128
00129
00130 int ace_ipv4_enabled = -1;
00131
00132
00133 int ace_ipv6_enabled = -1;
00134
00135 }
00136 #else
00137 # define SIOCGIFCONF_CMD SIOCGIFCONF
00138 # define IFREQ ifreq
00139 # define IFCONF ifconf
00140 # define IFC_REQ ifc_req
00141 # define IFC_LEN ifc_len
00142 # define IFC_BUF ifc_buf
00143 # define IFR_ADDR ifr_addr
00144 # define IFR_NAME ifr_name
00145 # define IFR_FLAGS ifr_flags
00146 # undef SETFAMILY
00147 # define SA_FAMILY sa_family
00148 #endif
00149
00150
00151
00152
00153
00154
00155
00156 #if defined (AIX) && defined (__IBMCPP__) && (__IBMCPP__ >= 500) && (__IBMCPP__ < 700)
00157 static ACE_Auto_Array_Ptr<sockaddr> force_compiler_to_include_socket_h;
00158 #endif
00159
00160
00161 ACE_RCSID (ace,
00162 Sock_Connect,
00163 "$Id: Sock_Connect.cpp 81696 2008-05-14 18:15:31Z johnnyw $")
00164
00165
00166 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00167
00168
00169
00170 int
00171 ACE::bind_port (ACE_HANDLE handle, ACE_UINT32 ip_addr, int address_family)
00172 {
00173 ACE_TRACE ("ACE::bind_port");
00174
00175 ACE_INET_Addr addr;
00176
00177 #if defined (ACE_HAS_IPV6)
00178 if (address_family != PF_INET6)
00179
00180
00181 #else
00182 ACE_UNUSED_ARG (address_family);
00183 #endif
00184 addr = ACE_INET_Addr ((u_short)0, ip_addr);
00185 #if defined (ACE_HAS_IPV6)
00186 else if (ip_addr != INADDR_ANY)
00187
00188
00189 addr.set ((u_short)0, ip_addr, 1, 1);
00190 #endif
00191
00192 #if !defined (ACE_LACKS_WILDCARD_BIND)
00193
00194 return ACE_OS::bind (handle,
00195 (sockaddr*)addr.get_addr(),
00196 addr.get_size());
00197 #else
00198 static u_short upper_limit = ACE_MAX_DEFAULT_PORT;
00199 int round_trip = upper_limit;
00200 int lower_limit = IPPORT_RESERVED;
00201
00202
00203
00204 for (;;)
00205 {
00206 addr.set((u_short)upper_limit,ip_addr);
00207
00208 if (ACE_OS::bind (handle,
00209 (sockaddr*)addr.get_addr()
00210 addr.get_size()) >= 0)
00211 {
00212 #if defined (ACE_WIN32)
00213 upper_limit--;
00214 #endif
00215 return 0;
00216 }
00217 else if (errno != EADDRINUSE)
00218 return -1;
00219 else
00220 {
00221 upper_limit--;
00222
00223
00224 if (upper_limit <= lower_limit)
00225 upper_limit = ACE_MAX_DEFAULT_PORT;
00226
00227
00228 if (upper_limit == round_trip)
00229 {
00230 errno = EAGAIN;
00231 return -1;
00232 }
00233 }
00234 }
00235 #endif
00236 }
00237
00238 int
00239 ACE::get_bcast_addr (ACE_UINT32 &bcast_addr,
00240 const ACE_TCHAR *host_name,
00241 ACE_UINT32 host_addr,
00242 ACE_HANDLE handle)
00243 {
00244 ACE_TRACE ("ACE::get_bcast_addr");
00245
00246 #if defined (ACE_LACKS_GET_BCAST_ADDR)
00247 ACE_UNUSED_ARG (bcast_addr);
00248 ACE_UNUSED_ARG (host_name);
00249 ACE_UNUSED_ARG (host_addr);
00250 ACE_UNUSED_ARG (handle);
00251 ACE_NOTSUP_RETURN (-1);
00252 #elif !defined(ACE_WIN32) && !defined(__INTERIX)
00253 ACE_HANDLE s = handle;
00254
00255 if (s == ACE_INVALID_HANDLE)
00256 s = ACE_OS::socket (AF_INET, SOCK_STREAM, 0);
00257
00258 if (s == ACE_INVALID_HANDLE)
00259 ACE_ERROR_RETURN ((LM_ERROR,
00260 ACE_TEXT ("%p\n"),
00261 ACE_TEXT ("ACE_OS::socket")),
00262 -1);
00263
00264 struct ifconf ifc;
00265 char buf[BUFSIZ];
00266
00267 ifc.ifc_len = sizeof buf;
00268 ifc.ifc_buf = buf;
00269
00270
00271
00272 if (ACE_OS::ioctl (s, SIOCGIFCONF_CMD, (char *) &ifc) == -1)
00273 ACE_ERROR_RETURN ((LM_ERROR,
00274 ACE_TEXT ("%p\n"),
00275 ACE_TEXT ("ACE::get_bcast_addr:")
00276 ACE_TEXT ("ioctl (get interface configuration)")),
00277 -1);
00278
00279 struct ifreq *ifr = ifc.ifc_req;
00280
00281 struct sockaddr_in ip_addr;
00282
00283
00284 if (host_name)
00285 {
00286 hostent *hp = ACE_OS::gethostbyname (ACE_TEXT_ALWAYS_CHAR (host_name));
00287
00288 if (hp == 0)
00289 return -1;
00290 else
00291 #if !defined(_UNICOS)
00292 ACE_OS::memcpy ((char *) &ip_addr.sin_addr.s_addr,
00293 (char *) hp->h_addr,
00294 hp->h_length);
00295 #else
00296 {
00297 ACE_UINT64 haddr;
00298 char * haddrp = (char *) &haddr;
00299 ACE_OS::memcpy(haddrp,(char *) hp->h_addr,hp->h_length);
00300 ip_addr.sin_addr.s_addr = haddr;
00301 }
00302 #endif
00303 }
00304 else
00305 {
00306 ACE_OS::memset ((void *) &ip_addr, 0, sizeof ip_addr);
00307 #if !defined(_UNICOS)
00308 ACE_OS::memcpy ((void *) &ip_addr.sin_addr,
00309 (void*) &host_addr,
00310 sizeof ip_addr.sin_addr);
00311 #else
00312 ip_addr.sin_addr.s_addr = host_addr;
00313 #endif
00314 }
00315
00316 #if !defined(AIX) && !defined (__QNX__) && !defined (__FreeBSD__) && !defined(__NetBSD__)
00317 for (int n = ifc.ifc_len / sizeof (struct ifreq) ; n > 0;
00318 n--, ifr++)
00319 #else
00320
00321 for (int nbytes = ifc.ifc_len; nbytes >= (int) sizeof (struct ifreq) &&
00322 ((ifr->ifr_addr.sa_len > sizeof (struct sockaddr)) ?
00323 (nbytes >= (int) sizeof (ifr->ifr_name) + ifr->ifr_addr.sa_len) : 1);
00324 ((ifr->ifr_addr.sa_len > sizeof (struct sockaddr)) ?
00325 (nbytes -= sizeof (ifr->ifr_name) + ifr->ifr_addr.sa_len,
00326 ifr = (struct ifreq *)
00327 ((caddr_t) &ifr->ifr_addr + ifr->ifr_addr.sa_len)) :
00328 (nbytes -= sizeof (struct ifreq), ifr++)))
00329 #endif
00330 {
00331 struct sockaddr_in if_addr;
00332
00333
00334 ACE_OS::memcpy (&if_addr,
00335 &ifr->ifr_addr,
00336 sizeof if_addr);
00337
00338 if (ip_addr.sin_addr.s_addr != if_addr.sin_addr.s_addr)
00339 continue;
00340
00341 if (ifr->ifr_addr.sa_family != AF_INET)
00342 {
00343 ACE_ERROR ((LM_ERROR,
00344 ACE_TEXT ("%p\n"),
00345 ACE_TEXT ("ACE::get_bcast_addr:")
00346 ACE_TEXT ("Not AF_INET")));
00347 continue;
00348 }
00349
00350 struct ifreq flags = *ifr;
00351 struct ifreq if_req = *ifr;
00352
00353 if (ACE_OS::ioctl (s, SIOCGIFFLAGS, (char *) &flags) == -1)
00354 {
00355 ACE_ERROR ((LM_ERROR,
00356 ACE_TEXT ("%p\n"),
00357 ACE_TEXT ("ACE::get_bcast_addr:")
00358 ACE_TEXT (" ioctl (get interface flags)")));
00359 continue;
00360 }
00361
00362 if (ACE_BIT_DISABLED (flags.ifr_flags, IFF_UP))
00363 {
00364 ACE_ERROR ((LM_ERROR,
00365 ACE_TEXT ("%p\n"),
00366 ACE_TEXT ("ACE::get_bcast_addr:")
00367 ACE_TEXT ("Network interface is not up")));
00368 continue;
00369 }
00370
00371 if (ACE_BIT_ENABLED (flags.ifr_flags, IFF_LOOPBACK))
00372 continue;
00373
00374 if (ACE_BIT_ENABLED (flags.ifr_flags, IFF_BROADCAST))
00375 {
00376 if (ACE_OS::ioctl (s,
00377 SIOCGIFBRDADDR,
00378 (char *) &if_req) == -1)
00379 ACE_ERROR ((LM_ERROR,
00380 ACE_TEXT ("%p\n"),
00381 ACE_TEXT ("ACE::get_bcast_addr:")
00382 ACE_TEXT ("ioctl (get broadaddr)")));
00383 else
00384 {
00385 ACE_OS::memcpy (&ip_addr,
00386 &if_req.ifr_broadaddr,
00387 sizeof if_req.ifr_broadaddr);
00388
00389 ACE_OS::memcpy ((void *) &host_addr,
00390 (void *) &ip_addr.sin_addr,
00391 sizeof host_addr);
00392
00393 if (handle == ACE_INVALID_HANDLE)
00394 ACE_OS::close (s);
00395
00396 bcast_addr = host_addr;
00397 return 0;
00398 }
00399 }
00400 else
00401 ACE_ERROR ((LM_ERROR,
00402 ACE_TEXT ("%p\n"),
00403 ACE_TEXT ("ACE::get_bcast_addr:")
00404 ACE_TEXT ("Broadcast is not enable for this interface.")));
00405
00406 if (handle == ACE_INVALID_HANDLE)
00407 ACE_OS::close (s);
00408
00409 bcast_addr = host_addr;
00410 return 0;
00411 }
00412
00413 return 0;
00414 #else
00415 ACE_UNUSED_ARG (handle);
00416 ACE_UNUSED_ARG (host_addr);
00417 ACE_UNUSED_ARG (host_name);
00418 bcast_addr = (ACE_UINT32 (INADDR_BROADCAST));
00419 return 0;
00420 #endif
00421 }
00422
00423 int
00424 ACE::get_fqdn (ACE_INET_Addr const & addr,
00425 char hostname[],
00426 size_t len)
00427 {
00428 int h_error;
00429 hostent hentry;
00430 ACE_HOSTENT_DATA buf;
00431
00432 char * ip_addr = 0;
00433 int ip_addr_size = 0;
00434 if (addr.get_type () == AF_INET)
00435 {
00436 sockaddr_in * const sock_addr =
00437 reinterpret_cast<sockaddr_in *> (addr.get_addr ());
00438 ip_addr_size = sizeof sock_addr->sin_addr;
00439 ip_addr = (char*) &sock_addr->sin_addr;
00440 }
00441 #ifdef ACE_HAS_IPV6
00442 else
00443 {
00444 sockaddr_in6 * sock_addr =
00445 reinterpret_cast<sockaddr_in6 *> (addr.get_addr ());
00446
00447 ip_addr_size = sizeof sock_addr->sin6_addr;
00448 ip_addr = (char*) &sock_addr->sin6_addr;
00449 }
00450 #endif
00451
00452
00453 hostent * const hp = ACE_OS::gethostbyaddr_r (ip_addr,
00454 ip_addr_size,
00455 addr.get_type (),
00456 &hentry,
00457 buf,
00458 &h_error);
00459
00460
00461
00462 if (hp == 0 || hp->h_name == 0)
00463 return -1;
00464
00465 if (ACE::debug())
00466 ACE_DEBUG ((LM_DEBUG,
00467 ACE_TEXT ("(%P|%t) - ACE::get_fqdn, ")
00468 ACE_TEXT ("canonical host name is %s\n"),
00469 ACE_TEXT_CHAR_TO_TCHAR (hp->h_name)));
00470
00471
00472 if (!ACE_OS::strchr(hp->h_name, '.'))
00473 {
00474
00475 char** p;
00476
00477 char** q;
00478
00479
00480
00481 for (p = hp->h_addr_list; *p != 0; ++p)
00482 {
00483 for (q = hp->h_aliases; *q != 0; ++q)
00484 {
00485 if (ACE_OS::strchr(*q, '.'))
00486 {
00487
00488 if (ACE_OS::strlen (*q) >= len)
00489
00490
00491
00492
00493
00494
00495
00496 continue;
00497
00498 if (ACE::debug ())
00499 ACE_DEBUG ((LM_DEBUG,
00500 ACE_TEXT ("(%P|%t) - ACE::get_fqdn, ")
00501 ACE_TEXT ("found fqdn within alias as %s\n"),
00502 ACE_TEXT_CHAR_TO_TCHAR(*q)));
00503 ACE_OS::strcpy (hostname, *q);
00504
00505 return 0;
00506 }
00507 }
00508 }
00509 }
00510
00511
00512
00513
00514 if (ACE_OS::strlen (hp->h_name) >= len)
00515 {
00516
00517
00518 return -2;
00519 }
00520 else
00521 {
00522 ACE_OS::strcpy (hostname, hp->h_name);
00523 }
00524
00525 return 0;
00526 }
00527
00528 #if defined (ACE_WIN32)
00529
00530 static int
00531 get_ip_interfaces_win32 (size_t &count,
00532 ACE_INET_Addr *&addrs)
00533 {
00534 # if defined (ACE_HAS_WINCE)
00535
00536
00537
00538 PIP_ADAPTER_ADDRESSES AdapterAddresses = 0;
00539 ULONG OutBufferLength = 0;
00540 ULONG RetVal = 0;
00541 unsigned char *octet_buffer = 0;
00542
00543 RetVal =
00544 GetAdaptersAddresses(AF_UNSPEC,
00545 0,
00546 0,
00547 AdapterAddresses,
00548 &OutBufferLength);
00549
00550 if (RetVal != ERROR_BUFFER_OVERFLOW)
00551 {
00552 return -1;
00553 }
00554
00555 ACE_NEW_RETURN (octet_buffer, unsigned char[OutBufferLength],-1);
00556 AdapterAddresses = (IP_ADAPTER_ADDRESSES *)octet_buffer;
00557
00558 RetVal =
00559 GetAdaptersAddresses(AF_UNSPEC,
00560 0,
00561 0,
00562 AdapterAddresses,
00563 &OutBufferLength);
00564
00565 if (RetVal != NO_ERROR)
00566 {
00567 delete [] octet_buffer;
00568 return -1;
00569 }
00570
00571
00572 PIP_ADAPTER_ADDRESSES AdapterList = AdapterAddresses;
00573 while (AdapterList)
00574 {
00575 if (AdapterList->OperStatus == IfOperStatusUp)
00576 {
00577 if (AdapterList->IfIndex != 0)
00578 ++count;
00579 if (AdapterList->Ipv6IfIndex != 0)
00580 ++count;
00581 }
00582 AdapterList = AdapterList->Next;
00583 }
00584
00585 AdapterList = AdapterAddresses;
00586
00587 ACE_NEW_RETURN (addrs, ACE_INET_Addr[count],-1);
00588 count = 0;
00589 for (AdapterList = AdapterAddresses;
00590 AdapterList != 0;
00591 AdapterList = AdapterList->Next)
00592 {
00593 if (AdapterList->OperStatus != IfOperStatusUp)
00594 continue;
00595
00596 IP_ADAPTER_UNICAST_ADDRESS *uni = 0;
00597 if (AdapterList->IfIndex != 0)
00598 for (uni = AdapterList->FirstUnicastAddress;
00599 uni != 0;
00600 uni = uni->Next)
00601 {
00602 SOCKET_ADDRESS *sa_addr = &uni->Address;
00603 if (sa_addr->lpSockaddr->sa_family == AF_INET)
00604 {
00605 sockaddr_in *sin = (sockaddr_in*)sa_addr->lpSockaddr;
00606 addrs[count].set(sin,sa_addr->iSockaddrLength);
00607 ++count;
00608 break;
00609 }
00610 }
00611 if (AdapterList->Ipv6IfIndex != 0)
00612 {
00613 for (uni = AdapterList->FirstUnicastAddress;
00614 uni != 0;
00615 uni = uni->Next)
00616 {
00617 SOCKET_ADDRESS *sa_addr = &uni->Address;
00618 if (sa_addr->lpSockaddr->sa_family == AF_INET6)
00619 {
00620 sockaddr_in *sin = (sockaddr_in*)sa_addr->lpSockaddr;
00621 addrs[count].set(sin,sa_addr->iSockaddrLength);
00622 ++count;
00623 break;
00624 }
00625 }
00626 }
00627 }
00628
00629 delete [] octet_buffer;
00630 return 0;
00631
00632 # elif defined (ACE_HAS_PHARLAP)
00633
00634
00635 # if !defined (ACE_HAS_PHARLAP_RT)
00636 ACE_NOTSUP_RETURN (-1);
00637 # endif
00638
00639
00640
00641
00642
00643
00644 const size_t ACE_MAX_ETS_DEVICES = 64;
00645 DEVHANDLE ip_dev[ACE_MAX_ETS_DEVICES];
00646 EK_TCPIPCFG *devp;
00647 size_t i, j;
00648 ACE_TCHAR dev_name[16];
00649
00650 count = 0;
00651 for (i = 0; count < ACE_MAX_ETS_DEVICES; i++, ++count)
00652 {
00653
00654 ACE_OS::sprintf (dev_name,
00655 "ether%d",
00656 i);
00657 ip_dev[count] = EtsTCPGetDeviceHandle (dev_name);
00658 if (ip_dev[count] == 0)
00659 break;
00660 }
00661 for (i = 0; count < ACE_MAX_ETS_DEVICES; i++, ++count)
00662 {
00663
00664 ACE_OS::sprintf (dev_name,
00665 "sl%d",
00666 i);
00667 ip_dev[count] = EtsTCPGetDeviceHandle (dev_name);
00668 if (ip_dev[count] == 0)
00669 break;
00670 }
00671 for (i = 0; count < ACE_MAX_ETS_DEVICES; i++, ++count)
00672 {
00673
00674 ACE_OS::sprintf (dev_name,
00675 "ppp%d",
00676 i);
00677 ip_dev[count] = EtsTCPGetDeviceHandle (dev_name);
00678 if (ip_dev[count] == 0)
00679 break;
00680 }
00681
00682 if (count > 0)
00683 ACE_NEW_RETURN (addrs,
00684 ACE_INET_Addr[count],
00685 -1);
00686 else
00687 addrs = 0;
00688
00689 for (i = 0, j = 0; i < count; i++)
00690 {
00691 devp = EtsTCPGetDeviceCfg (ip_dev[i]);
00692 if (devp != 0)
00693 {
00694 addrs[j].set (0,
00695 devp->nwIPAddress,
00696 0);
00697 ++j;
00698 }
00699
00700 }
00701
00702 count = j;
00703 if (count == 0 && addrs != 0)
00704 {
00705 delete [] addrs;
00706 addrs = 0;
00707 }
00708
00709 return 0;
00710
00711
00712 # else
00713
00714
00715 int i, n_interfaces, status;
00716
00717 INTERFACE_INFO info[64];
00718 SOCKET sock;
00719
00720
00721 sock = socket (AF_INET, SOCK_DGRAM, 0);
00722 if (sock == INVALID_SOCKET)
00723 return -1;
00724
00725 DWORD bytes;
00726 status = WSAIoctl(sock,
00727 SIO_GET_INTERFACE_LIST,
00728 0,
00729 0,
00730 info,
00731 sizeof(info),
00732 &bytes,
00733 0,
00734 0);
00735 closesocket (sock);
00736 if (status == SOCKET_ERROR)
00737 return -1;
00738
00739 n_interfaces = bytes / sizeof(INTERFACE_INFO);
00740
00741
00742
00743
00744
00745 int n_v6_interfaces = 0;
00746
00747 # if defined (ACE_HAS_IPV6) && defined (SIO_ADDRESS_LIST_QUERY)
00748
00749 LPSOCKET_ADDRESS_LIST v6info;
00750 char *buffer;
00751 DWORD buflen = sizeof (SOCKET_ADDRESS_LIST) + (63 * sizeof (SOCKET_ADDRESS));
00752 ACE_NEW_RETURN (buffer,
00753 char[buflen],
00754 -1);
00755 v6info = reinterpret_cast<LPSOCKET_ADDRESS_LIST> (buffer);
00756
00757
00758
00759 sock = socket (AF_INET6, SOCK_DGRAM, IPPROTO_UDP);
00760 if (sock != INVALID_SOCKET)
00761 {
00762 status = WSAIoctl(sock,
00763 SIO_ADDRESS_LIST_QUERY,
00764 0,
00765 0,
00766 v6info,
00767 buflen,
00768 &bytes,
00769 0,
00770 0);
00771 closesocket (sock);
00772 if (status != SOCKET_ERROR)
00773 n_v6_interfaces = v6info->iAddressCount;
00774 }
00775 # endif
00776
00777 ACE_NEW_RETURN (addrs,
00778 ACE_INET_Addr[n_interfaces + n_v6_interfaces],
00779 -1);
00780
00781
00782
00783 for (count = 0, i = 0; i < n_interfaces; ++i)
00784 {
00785 LPINTERFACE_INFO lpii;
00786 struct sockaddr_in *addrp = 0;
00787
00788 lpii = &info[i];
00789 if (!(lpii->iiFlags & IFF_UP))
00790 continue;
00791
00792
00793 addrp = reinterpret_cast<struct sockaddr_in *> (&lpii->iiAddress.AddressIn);
00794 if (addrp->sin_addr.s_addr == INADDR_ANY)
00795 continue;
00796
00797
00798 addrs[count].set(addrp, sizeof(sockaddr_in));
00799 ++count;
00800 }
00801
00802 # if defined (ACE_HAS_IPV6) && defined (SIO_ADDRESS_LIST_QUERY)
00803
00804
00805 for (i = 0; i < n_v6_interfaces; i++)
00806 {
00807 struct sockaddr_in6 *addr6p;
00808
00809 if (v6info->Address[i].lpSockaddr->sa_family != AF_INET6)
00810 continue;
00811
00812 addr6p = reinterpret_cast<struct sockaddr_in6 *> (v6info->Address[i].lpSockaddr);
00813 if (IN6_IS_ADDR_UNSPECIFIED(&addr6p->sin6_addr))
00814 continue;
00815
00816
00817 addrs[count].set(reinterpret_cast<struct sockaddr_in *> (addr6p), sizeof(sockaddr_in6));
00818 ++count;
00819 }
00820
00821 delete [] buffer;
00822 # endif
00823
00824 if (count == 0)
00825 {
00826 delete [] addrs;
00827 addrs = 0;
00828 }
00829
00830 return 0;
00831
00832 # endif
00833 }
00834 #elif defined (ACE_HAS_GETIFADDRS)
00835 static int
00836 get_ip_interfaces_getifaddrs (size_t &count,
00837 ACE_INET_Addr *&addrs)
00838 {
00839
00840
00841 struct ifaddrs *ifap = 0;
00842 struct ifaddrs *p_if = 0;
00843
00844 if (::getifaddrs (&ifap) != 0)
00845 return -1;
00846
00847
00848 size_t num_ifs = 0;
00849 for (p_if = ifap; p_if != 0; p_if = p_if->ifa_next)
00850 ++num_ifs;
00851
00852
00853 ACE_NEW_RETURN (addrs,
00854 ACE_INET_Addr[num_ifs],
00855 -1);
00856
00857
00858
00859
00860
00861 count = 0;
00862
00863 for (p_if = ifap;
00864 p_if != 0;
00865 p_if = p_if->ifa_next)
00866 {
00867 if (p_if->ifa_addr &&
00868 p_if->ifa_addr->sa_family == AF_INET)
00869 {
00870 struct sockaddr_in *addr =
00871 reinterpret_cast<sockaddr_in *> (p_if->ifa_addr);
00872
00873
00874
00875 if (addr->sin_addr.s_addr != INADDR_ANY)
00876 {
00877 addrs[count].set ((u_short) 0,
00878 addr->sin_addr.s_addr,
00879 0);
00880 ++count;
00881 }
00882 }
00883 # if defined (ACE_HAS_IPV6)
00884 else if (p_if->ifa_addr &&
00885 p_if->ifa_addr->sa_family == AF_INET6)
00886 {
00887 struct sockaddr_in6 *addr =
00888 reinterpret_cast<sockaddr_in6 *> (p_if->ifa_addr);
00889
00890
00891 if (!IN6_IS_ADDR_UNSPECIFIED(&addr->sin6_addr))
00892 {
00893 addrs[count].set(reinterpret_cast<struct sockaddr_in *> (addr),
00894 sizeof(sockaddr_in6));
00895 ++count;
00896 }
00897 }
00898 # endif
00899 }
00900
00901 ::freeifaddrs (ifap);
00902
00903 return 0;
00904 }
00905 #elif defined (__hpux)
00906 static int
00907 get_ip_interfaces_hpux (size_t &count,
00908 ACE_INET_Addr *&addrs)
00909 {
00910 size_t num_ifs = 0;
00911 size_t num_ifs_found = 0;
00912
00913
00914 ACE_HANDLE handle = ACE_OS::socket (PF_INET, SOCK_DGRAM, 0);
00915 ACE_HANDLE handle_ipv6 = ACE_INVALID_HANDLE;
00916
00917 if (handle == ACE_INVALID_HANDLE)
00918 ACE_ERROR_RETURN ((LM_ERROR,
00919 ACE_TEXT ("%p\n"),
00920 ACE_TEXT ("ACE::get_ip_interfaces:open")),
00921 -1);
00922
00923 int result = 0;
00924 int tmp_how_many = 0;
00925
00926 result = ACE_OS::ioctl (handle,
00927 SIOCGIFNUM,
00928 (caddr_t) &tmp_how_many);
00929 if (result != -1)
00930 num_ifs = (size_t)tmp_how_many;
00931
00932 # if defined (ACE_HAS_IPV6)
00933 tmp_how_many = 0;
00934 handle_ipv6 = ACE_OS::socket (PF_INET6, SOCK_DGRAM, 0);
00935 result = ACE_OS::ioctl (handle_ipv6,
00936 SIOCGLIFNUM,
00937 (caddr_t) &tmp_how_many);
00938 if (result != -1)
00939 num_ifs += (size_t)tmp_how_many;
00940 # endif
00941
00942 if (num_ifs == 0)
00943 {
00944 ACE_OS::close (handle);
00945 ACE_OS::close (handle_ipv6);
00946 return -1;
00947 }
00948
00949
00950
00951 ++num_ifs;
00952
00953
00954
00955 struct ifreq *ifs = 0;
00956 ACE_NEW_RETURN (ifs,
00957 struct ifreq[num_ifs],
00958 -1);
00959 ACE_OS::memset (ifs, 0, num_ifs * sizeof (struct ifreq));
00960
00961 ACE_Auto_Array_Ptr<struct ifreq> p_ifs (ifs);
00962
00963 if (p_ifs.get() == 0)
00964 {
00965 ACE_OS::close (handle);
00966 ACE_OS::close (handle_ipv6);
00967 errno = ENOMEM;
00968 return -1;
00969 }
00970
00971 struct ifconf ifcfg;
00972 ACE_OS::memset (&ifcfg, 0, sizeof (struct ifconf));
00973
00974 ifcfg.ifc_req = p_ifs.get ();
00975 ifcfg.ifc_len = num_ifs * sizeof (struct ifreq);
00976
00977 if (ACE_OS::ioctl (handle,
00978 SIOCGIFCONF,
00979 (char *) &ifcfg) == -1)
00980 {
00981 ACE_OS::close (handle);
00982 ACE_ERROR_RETURN ((LM_ERROR,
00983 ACE_TEXT ("%p\n"),
00984 ACE_TEXT ("ACE::get_ip_interfaces:")
00985 ACE_TEXT ("ioctl - SIOCGIFCONF failed")),
00986 -1);
00987 }
00988
00989 ACE_OS::close (handle);
00990
00991
00992
00993 ACE_NEW_RETURN (addrs,
00994 ACE_INET_Addr[num_ifs],
00995 -1);
00996
00997 struct ifreq *pcur = p_ifs.get ();
00998 num_ifs_found = ifcfg.ifc_len / sizeof (struct ifreq);
00999
01000 for (size_t i = 0;
01001 i < num_ifs_found;
01002 i++)
01003 {
01004 struct sockaddr_in *addr =
01005 reinterpret_cast<sockaddr_in *> (&pcur->ifr_addr);
01006 if (addr->sin_addr.s_addr != 0)
01007 {
01008 addrs[count].set ((u_short) 0,
01009 addr->sin_addr.s_addr,
01010 0);
01011 ++count;
01012 }
01013 ++pcur;
01014 }
01015
01016 # if defined (ACE_HAS_IPV6)
01017
01018 if (handle_ipv6 != ACE_INVALID_HANDLE)
01019 {
01020 struct if_laddrreq *lifs = 0;
01021 ACE_NEW_RETURN (lifs,
01022 struct if_laddrreq[num_ifs],
01023 -1);
01024 ACE_OS::memset (lifs, 0, num_ifs * sizeof (struct if_laddrreq));
01025
01026 ACE_Auto_Array_Ptr<struct if_laddrreq> p_lifs (lifs);
01027
01028 if (p_lifs.get() == 0)
01029 {
01030 ACE_OS::close (handle);
01031 ACE_OS::close (handle_ipv6);
01032 errno = ENOMEM;
01033 return -1;
01034 }
01035
01036 struct if_laddrconf lifcfg;
01037 ACE_OS::memset (&lifcfg, 0, sizeof (struct if_laddrconf));
01038
01039 lifcfg.iflc_req = p_lifs.get ();
01040 lifcfg.iflc_len = num_ifs * sizeof (struct if_laddrreq);
01041
01042 if (ACE_OS::ioctl (handle_ipv6,
01043 SIOCGLIFCONF,
01044 (char *) &lifcfg) == -1)
01045 {
01046 ACE_OS::close (handle);
01047 ACE_ERROR_RETURN ((LM_ERROR,
01048 ACE_TEXT ("%p\n"),
01049 ACE_TEXT ("ACE::get_ip_interfaces:")
01050 ACE_TEXT ("ioctl - SIOCGLIFCONF failed")),
01051 -1);
01052 }
01053
01054 ACE_OS::close (handle_ipv6);
01055
01056 struct if_laddrreq *plcur = p_lifs.get ();
01057 num_ifs_found = lifcfg.iflc_len / sizeof (struct if_laddrreq);
01058
01059 for (size_t i = 0;
01060 i < num_ifs_found;
01061 i++)
01062 {
01063 struct sockaddr_in *addr =
01064 reinterpret_cast<sockaddr_in *> (&plcur->iflr_addr);
01065 if (!IN6_IS_ADDR_UNSPECIFIED(&reinterpret_cast<sockaddr_in6 *>(addr)->sin6_addr))
01066 {
01067 addrs[count].set(addr, sizeof(struct sockaddr_in6));
01068 ++count;
01069 }
01070 ++plcur;
01071 }
01072 }
01073 # endif
01074 return 0;
01075 }
01076 #elif defined (_AIX)
01077 static int
01078 get_ip_interfaces_aix (size_t &count,
01079 ACE_INET_Addr *&addrs)
01080 {
01081 ACE_HANDLE handle = ACE::get_handle();
01082 size_t num_ifs = 0;
01083 struct ifconf ifc;
01084
01085 if (handle == ACE_INVALID_HANDLE)
01086 ACE_ERROR_RETURN ((LM_ERROR,
01087 ACE_TEXT ("%p\n"),
01088 ACE_TEXT ("ACE::get_ip_interfaces_aix:")),
01089 -1);
01090
01091 if (ACE_OS::ioctl (handle,
01092 SIOCGSIZIFCONF,
01093 (caddr_t)&ifc.ifc_len) == -1)
01094 {
01095 ACE_OS::close (handle);
01096 ACE_ERROR_RETURN((LM_ERROR,
01097 ACE_TEXT ("%p\n"),
01098 ACE_TEXT ("get ifconf size")),
01099 -1);
01100 }
01101
01102 ACE_NEW_RETURN (ifc.ifc_buf,char [ifc.ifc_len], -1);
01103
01104 ACE_Auto_Array_Ptr<char> safe_buf (ifc.ifc_buf);
01105 ACE_OS::memset (safe_buf.get(), 0, ifc.ifc_len);
01106
01107 if (ACE_OS::ioctl(handle, SIOCGIFCONF, (caddr_t)&ifc) == -1)
01108 {
01109 ACE_OS::close (handle);
01110 ACE_ERROR_RETURN((LM_ERROR,
01111 ACE_TEXT ("%p\n"),
01112 ACE_TEXT ("get ifconf")),
01113 -1);
01114 }
01115
01116 ACE_OS::close (handle);
01117
01118 char *buf_start = safe_buf.get();
01119 char *buf_end = buf_start + ifc.ifc_len;
01120
01121 num_ifs = 0;
01122 for (char *ptr = buf_start; ptr < buf_end; )
01123 {
01124 struct ifreq *req = reinterpret_cast<struct ifreq *>(ptr);
01125 ptr += IFNAMSIZ;
01126 ptr += req->ifr_addr.sa_len;
01127 if (req->ifr_addr.sa_family == AF_INET
01128 # if defined (ACE_HAS_IPV6)
01129 || req->ifr_addr.sa_family == AF_INET6
01130 # endif
01131 )
01132 ++num_ifs;
01133 }
01134 ACE_NEW_RETURN (addrs,ACE_INET_Addr[num_ifs], -1);
01135
01136 for (char * ptr = buf_start; ptr < buf_end; )
01137 {
01138 struct ifreq *req = reinterpret_cast<struct ifreq *>(ptr);
01139
01140 ptr += IFNAMSIZ;
01141 if (req->ifr_addr.sa_family == AF_INET
01142 # if defined (ACE_HAS_IPV6)
01143 || req->ifr_addr.sa_family == AF_INET6
01144 # endif
01145 )
01146 {
01147 sockaddr_in *addr = (sockaddr_in*)&req->ifr_addr;
01148 addrs[count++].set(addr, addr->sin_len);
01149 }
01150 ptr += req->ifr_addr.sa_len;
01151 }
01152
01153 return 0;
01154 }
01155
01156 #elif defined (ACE_VXWORKS) && (ACE_VXWORKS < 0x600) && !defined (ACE_HAS_VXWORKS551_MEDUSA)
01157 int
01158 get_ip_interfaces_vxworks_lt600 (size_t &count,
01159 ACE_INET_Addr *&addrs)
01160 {
01161 count = 0;
01162
01163
01164 # if defined (ACE_HAS_IPV6) && defined (TAILQ_ENTRY)
01165 # define ia_next ia_link.tqe_next
01166 # endif
01167
01168 for (struct in_ifaddr* ia = in_ifaddr; ia != 0; ia = ia->ia_next)
01169 {
01170 ++count;
01171 }
01172
01173
01174 ACE_NEW_RETURN (addrs,
01175 ACE_INET_Addr[count],
01176 -1);
01177 count = 0;
01178 for (struct in_ifaddr* ia = in_ifaddr; ia != 0; ia = ia->ia_next)
01179 {
01180 struct ifnet* ifp = ia->ia_ifa.ifa_ifp;
01181 if (ifp != 0)
01182 {
01183
01184 char interface[64];
01185 ACE_OS::sprintf(interface, "%s%d", ifp->if_name, ifp->if_unit);
01186
01187
01188 char address [INET_ADDR_LEN];
01189 STATUS status = ifAddrGet(interface, address);
01190
01191 if (status == OK)
01192 {
01193
01194
01195
01196
01197
01198 ACE_OS::strcat (address, ":");
01199 addrs[count].set (address);
01200 }
01201 else
01202 {
01203 ACE_ERROR_RETURN ((LM_ERROR,
01204 ACE_TEXT ("ACE::get_ip_interface failed\n")
01205 ACE_TEXT ("Couldnt get the IP Address\n")),
01206 -1);
01207 }
01208 ++count;
01209 }
01210 }
01211 return 0;
01212 }
01213 #endif // ACE_WIN32 || ACE_HAS_GETIFADDRS || __hpux || _AIX || ACE_VXWORKS < 0x600
01214
01215
01216
01217
01218
01219
01220 int
01221 ACE::get_ip_interfaces (size_t &count,
01222 ACE_INET_Addr *&addrs)
01223 {
01224 ACE_TRACE ("ACE::get_ip_interfaces");
01225
01226 count = 0;
01227 addrs = 0;
01228
01229 #if defined (ACE_WIN32)
01230 return get_ip_interfaces_win32 (count, addrs);
01231 #elif defined (ACE_HAS_GETIFADDRS)
01232 return get_ip_interfaces_getifaddrs (count, addrs);
01233 #elif defined (__hpux)
01234 return get_ip_interfaces_hpux (count, addrs);
01235 #elif defined (_AIX)
01236 return get_ip_interfaces_aix (count, addrs);
01237 #elif defined (ACE_VXWORKS) && (ACE_VXWORKS < 0x600) && !defined (ACE_HAS_VXWORKS551_MEDUSA)
01238 return get_ip_interfaces_vxworks_lt600 (count, addrs);
01239 #elif (defined (__unix) || defined (__unix__) || defined (__Lynx__) || defined (ACE_OPENVMS) || (defined (ACE_VXWORKS) && (ACE_VXWORKS == 0x650)) || defined (ACE_HAS_RTEMS)) && !defined (ACE_LACKS_NETWORKING)
01240
01241
01242
01243 ACE_HANDLE handle = ACE::get_handle();
01244
01245 if (handle == ACE_INVALID_HANDLE)
01246 ACE_ERROR_RETURN ((LM_ERROR,
01247 ACE_TEXT ("%p\n"),
01248 ACE_TEXT ("ACE::get_ip_interfaces:open")),
01249 -1);
01250
01251 size_t num_ifs, num_ifs_found;
01252
01253 if (ACE::count_interfaces (handle, num_ifs))
01254 {
01255 ACE_OS::close (handle);
01256 return -1;
01257 }
01258
01259
01260
01261 ++num_ifs;
01262
01263 struct IFREQ *ifs = 0;
01264 ACE_NEW_RETURN (ifs,
01265 struct IFREQ[num_ifs],
01266 -1);
01267 ACE_OS::memset (ifs, 0, num_ifs * sizeof (struct IFREQ));
01268
01269 ACE_Auto_Array_Ptr<struct IFREQ> p_ifs (ifs);
01270
01271 if (p_ifs.get() == 0)
01272 {
01273 ACE_OS::close (handle);
01274 errno = ENOMEM;
01275 return -1;
01276 }
01277
01278 struct IFCONF ifcfg;
01279 ACE_OS::memset (&ifcfg, 0, sizeof (struct IFCONF));
01280
01281 # ifdef SETFAMILY
01282 ifcfg.IFC_FAMILY = AF_UNSPEC;
01283 ifcfg.IFC_FLAGS = 0;
01284 # endif
01285
01286 ifcfg.IFC_REQ = p_ifs.get ();
01287 ifcfg.IFC_LEN = num_ifs * sizeof (struct IFREQ);
01288
01289 if (ACE_OS::ioctl (handle,
01290 SIOCGIFCONF_CMD,
01291 (caddr_t) &ifcfg) == -1)
01292 {
01293 ACE_OS::close (handle);
01294 ACE_ERROR_RETURN ((LM_ERROR,
01295 ACE_TEXT ("%p\n"),
01296 ACE_TEXT ("ACE::get_ip_interfaces:")
01297 ACE_TEXT ("ioctl - SIOCGIFCONF failed")),
01298 -1);
01299 }
01300
01301 ACE_OS::close (handle);
01302
01303
01304
01305 ACE_NEW_RETURN (addrs,
01306 ACE_INET_Addr[num_ifs],
01307 -1);
01308
01309 struct IFREQ *pcur = p_ifs.get ();
01310 num_ifs_found = ifcfg.IFC_LEN / sizeof (struct IFREQ);
01311
01312
01313
01314
01315
01316 count = 0;
01317
01318 for (size_t i = 0;
01319 i < num_ifs_found;
01320 i++)
01321 {
01322 if (pcur->IFR_ADDR.SA_FAMILY == AF_INET
01323 # if defined (ACE_HAS_IPV6)
01324 || pcur->IFR_ADDR.SA_FAMILY == AF_INET6
01325 # endif
01326 )
01327
01328 {
01329 # if !defined(_UNICOS)
01330 struct sockaddr_in *addr =
01331 reinterpret_cast<sockaddr_in *> (&pcur->IFR_ADDR);
01332
01333
01334
01335 if (addr->sin_addr.s_addr != 0
01336 # if defined (ACE_HAS_IPV6)
01337 || (addr->sin_family == AF_INET6 &&
01338 !IN6_IS_ADDR_UNSPECIFIED(&reinterpret_cast<sockaddr_in6 *>(addr)->sin6_addr))
01339 # endif
01340 )
01341 {
01342 int addrlen = static_cast<int> (sizeof (struct sockaddr_in));
01343 # if defined (ACE_HAS_IPV6)
01344 if (addr->sin_family == AF_INET6)
01345 addrlen = static_cast<int> (sizeof (struct sockaddr_in6));
01346 # endif
01347 addrs[count].set (addr, addrlen);
01348 ++count;
01349 }
01350 # else
01351
01352
01353 struct sockaddr_in inAddr;
01354
01355 inAddr.sin_len = pcur->IFR_ADDR.sa_len;
01356 inAddr.sin_family = pcur->IFR_ADDR.sa_family;
01357 memcpy((void *)&(inAddr.sin_addr),
01358 (const void *)&(pcur->IFR_ADDR.sa_data[8]),
01359 sizeof(struct in_addr));
01360
01361 if (inAddr.sin_addr.s_addr != 0)
01362 {
01363 addrs[count].set(&inAddr, sizeof(struct sockaddr_in));
01364 ++count;
01365 }
01366 # endif
01367 }
01368
01369 #if !defined (__QNX__) && !defined (__FreeBSD__) && !defined(__NetBSD__) && !defined (ACE_HAS_RTEMS)
01370 ++pcur;
01371 #else
01372 if (pcur->ifr_addr.sa_len <= sizeof (struct sockaddr))
01373 {
01374 ++pcur;
01375 }
01376 else
01377 {
01378 pcur = (struct ifreq *)
01379 (pcur->ifr_addr.sa_len + (caddr_t) &pcur->ifr_addr);
01380 }
01381 #endif
01382 }
01383
01384 # if defined (ACE_HAS_IPV6)
01385
01386
01387
01388 FILE* fp;
01389 char addr_p[8][5];
01390 char s_ipaddr[64];
01391 int scopeid;
01392 struct addrinfo hints, *res0;
01393 int error;
01394
01395 ACE_OS::memset (&hints, 0, sizeof (hints));
01396 hints.ai_flags = AI_NUMERICHOST;
01397 hints.ai_family = AF_INET6;
01398
01399 if ((fp = ACE_OS::fopen (ACE_TEXT ("/proc/net/if_inet6"), ACE_TEXT ("r"))) != 0)
01400 {
01401 while (fscanf (fp,
01402 "%4s%4s%4s%4s%4s%4s%4s%4s %02x %*02x %*02x %*02x %*8s\n",
01403 addr_p[0], addr_p[1], addr_p[2], addr_p[3],
01404 addr_p[4], addr_p[5], addr_p[6], addr_p[7], &scopeid) != EOF)
01405 {
01406
01407
01408
01409 const char* ip_fmt = "%s:%s:%s:%s:%s:%s:%s:%s%%%d";
01410 ACE_OS::sprintf (s_ipaddr,
01411 ip_fmt,
01412 addr_p[0], addr_p[1], addr_p[2], addr_p[3],
01413 addr_p[4], addr_p[5], addr_p[6], addr_p[7], scopeid);
01414
01415 error = getaddrinfo (s_ipaddr, 0, &hints, &res0);
01416 if (error)
01417 continue;
01418
01419 if (res0->ai_family == AF_INET6 &&
01420 !IN6_IS_ADDR_UNSPECIFIED (&reinterpret_cast<sockaddr_in6 *> (res0->ai_addr)->sin6_addr))
01421 {
01422 addrs[count].set(reinterpret_cast<sockaddr_in *> (res0->ai_addr), res0->ai_addrlen);
01423 ++count;
01424 }
01425 freeaddrinfo (res0);
01426
01427 }
01428 ACE_OS::fclose (fp);
01429 }
01430 # endif
01431
01432 return 0;
01433 #else
01434 ACE_UNUSED_ARG (count);
01435 ACE_UNUSED_ARG (addrs);
01436 ACE_NOTSUP_RETURN (-1);
01437 #endif
01438 }
01439
01440
01441
01442
01443
01444 int
01445 ACE::count_interfaces (ACE_HANDLE handle,
01446 size_t &how_many)
01447 {
01448 #if defined (ACE_WIN32) || defined (ACE_HAS_GETIFADDRS) || defined (__hpux) || defined (_AIX) || (defined (ACE_VXWORKS) && (ACE_VXWORKS < 0x600))
01449
01450 ACE_UNUSED_ARG (handle);
01451 ACE_UNUSED_ARG (how_many);
01452 ACE_NOTSUP_RETURN (-1);
01453
01454 #elif defined (SIOCGIFNUM)
01455 # if defined (SIOCGLIFNUM)
01456 int cmd = SIOCGLIFNUM;
01457 struct lifnum if_num = {AF_UNSPEC,0,0};
01458 # else
01459 int cmd = SIOCGIFNUM;
01460 int if_num = 0;
01461 # endif
01462 if (ACE_OS::ioctl (handle, cmd, (caddr_t)&if_num) == -1)
01463 ACE_ERROR_RETURN ((LM_ERROR,
01464 ACE_TEXT ("%p\n"),
01465 ACE_TEXT ("ACE::count_interfaces:")
01466 ACE_TEXT ("ioctl - SIOCGLIFNUM failed")),
01467 -1);
01468 # if defined (SIOCGLIFNUM)
01469 how_many = if_num.lifn_count;
01470 # else
01471 how_many = if_num;
01472 # endif
01473 return 0;
01474
01475 #elif (defined (__unix) || defined (__unix__) || defined (__Lynx__) || defined (ACE_OPENVMS) || defined (ACE_HAS_RTEMS)) && !defined (ACE_LACKS_NETWORKING)
01476
01477
01478
01479
01480
01481
01482 const int MAX_IF = 50;
01483
01484
01485 int num_ifs = MAX_IF;
01486
01487 struct ifconf ifcfg;
01488 size_t ifreq_size = num_ifs * sizeof (struct ifreq);
01489 struct ifreq *p_ifs =
01490 (struct ifreq *) ACE_OS::malloc (ifreq_size);
01491
01492 if (!p_ifs)
01493 {
01494 errno = ENOMEM;
01495 return -1;
01496 }
01497
01498 ACE_OS::memset (p_ifs, 0, ifreq_size);
01499 ACE_OS::memset (&ifcfg, 0, sizeof (struct ifconf));
01500
01501 ifcfg.ifc_req = p_ifs;
01502 ifcfg.ifc_len = ifreq_size;
01503
01504 if (ACE_OS::ioctl (handle,
01505 SIOCGIFCONF_CMD,
01506 (caddr_t) &ifcfg) == -1)
01507 {
01508 ACE_OS::free (ifcfg.ifc_req);
01509 ACE_ERROR_RETURN ((LM_ERROR,
01510 ACE_TEXT ("%p\n"),
01511 ACE_TEXT ("ACE::count_interfaces:")
01512 ACE_TEXT ("ioctl - SIOCGIFCONF failed")),
01513 -1);
01514 }
01515
01516 int if_count = 0, i;
01517
01518
01519
01520 for (i = 0;
01521 i < num_ifs;
01522 i++)
01523 {
01524
01525 ifcfg.ifc_len -= sizeof (struct ifreq);
01526 if (ifcfg.ifc_len < 0)
01527 break;
01528
01529 ++if_count;
01530 #if !defined (__QNX__) && !defined (__FreeBSD__) && !defined(__NetBSD__) && !defined (ACE_HAS_RTEMS)
01531 ++p_ifs;
01532 #else
01533 if (p_ifs->ifr_addr.sa_len <= sizeof (struct sockaddr))
01534 {
01535 ++p_ifs;
01536 }
01537 else
01538 {
01539 p_ifs = (struct ifreq *)
01540 (p_ifs->ifr_addr.sa_len + (caddr_t) &p_ifs->ifr_addr);
01541 }
01542 #endif
01543 }
01544
01545 ACE_OS::free (ifcfg.ifc_req);
01546
01547 # if defined (ACE_HAS_IPV6)
01548 FILE* fp = 0;
01549
01550 if ((fp = ACE_OS::fopen (ACE_TEXT ("/proc/net/if_inet6"), ACE_TEXT ("r"))) != 0)
01551 {
01552
01553 while (fscanf (fp, "%*32s %*02x %*02x %*02x %*02x %*8s\n") != EOF)
01554 {
01555 ++if_count;
01556 }
01557 ACE_OS::fclose (fp);
01558 }
01559 # endif
01560
01561 how_many = if_count;
01562 return 0;
01563 #else
01564 ACE_UNUSED_ARG (handle);
01565 ACE_UNUSED_ARG (how_many);
01566 ACE_NOTSUP_RETURN (-1);
01567 #endif
01568 }
01569
01570
01571
01572 ACE_HANDLE
01573 ACE::get_handle (void)
01574 {
01575
01576 ACE_HANDLE handle = ACE_INVALID_HANDLE;
01577 #if defined (sparc)
01578 handle = ACE_OS::open ("/dev/udp", O_RDONLY);
01579 #elif defined (__unix) || defined (__unix__) || defined (__Lynx__) || defined (_AIX) || defined (__hpux) || (defined (ACE_VXWORKS) && (ACE_VXWORKS >= 0x600)) || defined (ACE_OPENVMS) || defined (ACE_HAS_RTEMS)
01580
01581
01582
01583 handle = ACE_OS::socket (PF_INET, SOCK_DGRAM, 0);
01584 #endif
01585 return handle;
01586 }
01587
01588
01589 #if defined (ACE_HAS_IPV6)
01590 static int
01591 ip_check (int &ipvn_enabled, int pf)
01592 {
01593
01594
01595 ACE_MT (ACE_GUARD_RETURN (ACE_Recursive_Thread_Mutex, ace_mon,
01596 *ACE_Static_Object_Lock::instance (), 0));
01597
01598 if (ipvn_enabled == -1)
01599 {
01600
01601
01602 ACE_HANDLE const s = ACE_OS::socket (pf, SOCK_DGRAM, 0);
01603 if (s == ACE_INVALID_HANDLE)
01604 {
01605 ipvn_enabled = 0;
01606 }
01607 else
01608 {
01609 ipvn_enabled = 1;
01610 ACE_OS::closesocket (s);
01611 }
01612 }
01613 return ipvn_enabled;
01614 }
01615 #endif
01616
01617 bool
01618 ACE::ipv4_enabled (void)
01619 {
01620 #if defined (ACE_HAS_IPV6)
01621 return static_cast<bool> (ace_ipv4_enabled == -1 ?
01622 ::ip_check (ace_ipv4_enabled, PF_INET) :
01623 ace_ipv4_enabled);
01624 #else
01625
01626
01627 return true;
01628 #endif
01629 }
01630
01631 int
01632 ACE::ipv6_enabled (void)
01633 {
01634 #if defined (ACE_HAS_IPV6)
01635 return ace_ipv6_enabled == -1 ?
01636 ::ip_check (ace_ipv6_enabled, PF_INET6) :
01637 ace_ipv6_enabled;
01638 #else
01639 return 0;
01640 #endif
01641 }
01642
01643 ACE_END_VERSIONED_NAMESPACE_DECL