00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00036 #include "OW_config.h"
00037
00038 #if !defined(OW_WIN32) && !defined(OW_NETWARE)
00039
00040 extern "C"
00041 {
00042 #ifdef OW_HAVE_UNISTD_H
00043 #include <unistd.h>
00044 #endif
00045
00046 #include <stdlib.h>
00047 #include <stdio.h>
00048 #include <sys/types.h>
00049
00050 #ifdef OW_HAVE_SYS_SOCKET_H
00051 #include <sys/socket.h>
00052 #endif
00053
00054 #include <arpa/inet.h>
00055 #include <errno.h>
00056
00057 #ifdef OW_GNU_LINUX
00058 #include <sys/ioctl.h>
00059 #include <linux/if.h>
00060 #include <string.h>
00061
00062 #elif defined (OW_OPENSERVER)
00063 #include <string.h>
00064 #include <stropts.h>
00065 #include <net/if.h>
00066 #include <netinet/in.h>
00067 #include <strings.h>
00068 #include <arpa/inet.h>
00069 #include <fcntl.h>
00070 #include <paths.h>
00071 #include <sys/mdi.h>
00072
00073 #elif defined (OW_DARWIN)
00074 #include <net/if.h>
00075 #include <sys/ioctl.h>
00076 #else
00077
00078 #ifdef OW_HAVE_STROPTS_H
00079 #include <stropts.h>
00080 #endif
00081
00082 #include <net/if.h>
00083 #include <netinet/in.h>
00084
00085 #if defined (OW_HAVE_SYS_SOCKIO_H)
00086 #include <sys/sockio.h>
00087 #endif
00088
00089 #include <strings.h>
00090 #include <fcntl.h>
00091 #endif
00092
00093 #include <string.h>
00094 }
00095
00096
00097 #include "OW_NwIface.hpp"
00098 #include "OW_String.hpp"
00099 #include "OW_Exception.hpp"
00100 #include "OW_SocketUtils.hpp"
00101
00102 namespace OW_NAMESPACE
00103 {
00104
00106 NwIface::NwIface()
00107 {
00108 int s, lerrno;
00109 struct ifreq ifr;
00110 struct sockaddr_in *sin(0);
00111 if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
00112 {
00113 OW_THROW(SocketException, "socket");
00114 }
00115 getInterfaceName(s);
00116 bzero(&ifr, sizeof(ifr));
00117 strncpy(ifr.ifr_name, m_name.c_str(), sizeof(ifr.ifr_name));
00119
00120 if (ioctl(s, SIOCGIFADDR, &ifr) < 0)
00121 {
00122 lerrno = errno;
00123 close(s);
00124 OW_THROW(SocketException, "ioctl:SIOCGIFADDR");
00125 }
00126 sin = reinterpret_cast<struct sockaddr_in *>(&ifr.ifr_addr);
00127 m_addr = sin->sin_addr.s_addr;
00129
00130
00131 if (ioctl(s, SIOCGIFBRDADDR, &ifr) < 0)
00132 {
00133 lerrno = errno;
00134 close(s);
00135 OW_THROW(SocketException, "ioctl:SIOCGIFBRDADDR");
00136 }
00137 sin = reinterpret_cast<struct sockaddr_in*>(&ifr.ifr_broadaddr);
00138 m_bcastAddr = sin->sin_addr.s_addr;
00140
00141 if (ioctl(s, SIOCGIFNETMASK, &ifr) < 0)
00142 {
00143 lerrno = errno;
00144 close(s);
00145 OW_THROW(SocketException, "ioctl:SIOCGIFNETMASK");
00146 }
00147 #ifdef OW_GNU_LINUX
00148 sin = reinterpret_cast<struct sockaddr_in *>(&ifr.ifr_netmask);
00149 #else
00150 sin = reinterpret_cast<struct sockaddr_in *>(&ifr.ifr_broadaddr);
00151 #endif
00152 m_netmask = sin->sin_addr.s_addr;
00153 close(s);
00154 }
00156 String
00157 NwIface::getName()
00158 {
00159 return m_name;
00160 }
00162 unsigned long
00163 NwIface::getIPAddress()
00164 {
00165 return m_addr;
00166 }
00168 String
00169 NwIface::getIPAddressString()
00170 {
00171 return SocketUtils::inetAddrToString(m_addr);
00172 }
00174 unsigned long
00175 NwIface::getBroadcastAddress()
00176 {
00177 return m_bcastAddr;
00178 }
00180 String
00181 NwIface::getBroadcastAddressString()
00182 {
00183 return SocketUtils::inetAddrToString(m_bcastAddr);
00184 }
00186
00187
00188
00189
00190
00191
00192
00194 unsigned long
00195 NwIface::getNetmask()
00196 {
00197 return m_netmask;
00198 }
00200 String
00201 NwIface::getNetmaskString()
00202 {
00203 return SocketUtils::inetAddrToString(m_netmask);
00204 }
00206 bool
00207 NwIface::sameNetwork(unsigned long addr)
00208 {
00209 return ((addr & m_netmask) == (m_addr & m_netmask));
00210 }
00212 bool
00213 NwIface::sameNetwork(const String& straddr)
00214 {
00215 return sameNetwork(stringToAddress(straddr));
00216 }
00218 unsigned long
00219 NwIface::stringToAddress(const String& straddr)
00220 {
00221 return inet_addr(straddr.c_str());
00222 }
00224 void
00225 NwIface::getInterfaceName(SocketHandle_t sockfd)
00226 {
00227 char *p(0);
00228 int numreqs = 30;
00229 struct ifconf ifc;
00230 struct ifreq *ifr(0);
00231 struct ifreq ifrcopy;
00232 int n;
00233 int oldlen = -1;
00234 int lerrno = 0;
00235 const char* appliesTo(0);
00236 ifc.ifc_buf = NULL;
00237 for (;;)
00238 {
00239 ifc.ifc_len = sizeof(struct ifreq) * numreqs;
00240 if (ifc.ifc_buf == NULL)
00241 {
00242 ifc.ifc_buf = new char[ifc.ifc_len];
00243 }
00244 else
00245 {
00246 p = new char[ifc.ifc_len];
00247 memmove(p, ifc.ifc_buf, oldlen);
00248 delete [] ifc.ifc_buf;
00249 ifc.ifc_buf = p;
00250 }
00251 oldlen = ifc.ifc_len;
00252 if (ioctl(sockfd, SIOCGIFCONF, &ifc) < 0)
00253 {
00254 lerrno = errno;
00255 appliesTo = "ioctl:SIOCGIFCONF";
00256 break;
00257 }
00258 if (ifc.ifc_len == static_cast<int>(sizeof(struct ifreq) * numreqs))
00259 {
00260
00261 numreqs += 10;
00262 continue;
00263 }
00264 break;
00265 }
00266 if (lerrno == 0)
00267 {
00268 lerrno = ENODEV;
00269 appliesTo = "No interfaces found";
00270 ifr = ifc.ifc_req;
00271 for (n = 0; n < ifc.ifc_len; n += sizeof(struct ifreq))
00272 {
00273 ifrcopy = *ifr;
00274 if (ioctl(sockfd, SIOCGIFFLAGS, &ifrcopy) < 0)
00275 {
00276 lerrno = errno;
00277 appliesTo = "ioctl:SIOCGIFFLAGS";
00278 break;
00279 }
00280 #ifdef OW_GNU_LINUX
00281 if ((ifrcopy.ifr_flags & IFF_UP) && !(ifrcopy.ifr_flags & (IFF_LOOPBACK | IFF_DYNAMIC)))
00282 #else
00283 if ((ifrcopy.ifr_flags & IFF_UP))
00284 #endif
00285 {
00286 m_name = ifr->ifr_name;
00287 lerrno = 0;
00288 break;
00289 }
00290 ifr++;
00291 }
00292 }
00293 if (ifc.ifc_buf != NULL)
00294 {
00295 delete [] ifc.ifc_buf;
00296 }
00297 if (lerrno != 0)
00298 {
00299 OW_THROW(SocketException, "NwIface::getInterfaceName");
00300 }
00301 }
00302
00303 }
00304
00305 #endif // #if !defined(OW_WIN32) && !defined(OW_NETWARE)
00306