static FskErr sFskNetInterfaceEnumerate(FskNetInterfaceRecord **interfaceList) { FskErr err = kFskErrNone; FskNetInterfaceRecord *nir; int fd; struct ifreq ifr; struct sockaddr_in *sa; #if TARGET_OS_MAC // BSD struct ifreq ibuf[32]; #endif /* TARGET_OS_MAC */ #if TARGET_OS_LINUX #if TARGET_OS_ANDROID DIR *d; struct dirent *dir; *interfaceList = NULL; fd = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP); if (fd < 0) goto skip; FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation, "Enumerate Interfaces:"); d = opendir("/sys/class/net"); if (0 == d) { BAIL(kFskErrNetworkInterfaceError); } while ((dir = readdir(d))) { #if IGNORE_NETINTERFACE Boolean ignore = false; int i; #endif char *ifname; unsigned theIP = 0, theNetmask = 0, theStatus = 0; if (dir->d_name[0] == '.') continue; ifname = dir->d_name; FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation,"%s: ", ifname); #if IGNORE_NETINTERFACE i = NUM_IGNORE_NET; while (i) { if (FskStrCompare(ignoreInterfaces[i-1], ifname) == 0) { FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation, "IGNORED"); ignore = true; } i--; } if (ignore) continue; #endif /* IGNORE_NETINTERFACE */ memset(&ifr, 0, sizeof(struct ifreq)); strncpy(ifr.ifr_name, ifname, IFNAMSIZ); ifr.ifr_name[IFNAMSIZ - 1] = 0; if (ioctl(fd, SIOCGIFADDR, &ifr) >= 0) { sa = (struct sockaddr_in*)(void*)&(ifr.ifr_addr); theIP = ntohl( sa->sin_addr.s_addr); } if (ioctl(fd, SIOCGIFNETMASK, &ifr) >= 0) { sa = (struct sockaddr_in*)(void*)&(ifr.ifr_addr); theNetmask = ntohl( sa->sin_addr.s_addr); } if (ioctl(fd, SIOCGIFFLAGS, &ifr) >= 0) { if (ifr.ifr_flags & 1) theStatus = 1; } if (theIP == 0) theStatus = 0; FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation,"IP: %x, Netmask: %x [%s]", theIP, theNetmask, theStatus ? "UP " : "DOWN "); if (ioctl(fd, SIOCGIFHWADDR, &ifr) >= 0) { FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation, "Got HWADDR "); if (ifr.ifr_hwaddr.sa_family == ARPHRD_ETHER) { FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation, " ETHER"); FskMemPtrNewClear(sizeof(FskNetInterfaceRecord), (FskMemPtr*)(void*)&nir); if (!nir) { closedir(d); BAIL(kFskErrMemFull); } FskMemCopy(nir->MAC, ifr.ifr_hwaddr.sa_data, 6); nir->name = FskStrDoCopy(ifname); nir->ip = theIP; nir->netmask = theNetmask; nir->status = theStatus; FskListAppend((FskList*)interfaceList, nir); } else { FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation, " Family not ETHER Huh?"); } } } closedir(d); skip: #else /* !TARGET_OS_ANDROID */ FILE *fp; char buf[256]; #if IGNORE_NETINTERFACE Boolean ignore = false; int i; #endif *interfaceList = NULL; fd = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP); if (fd < 0) goto skip; fp = fopen("/proc/net/dev", "r"); if (!fp) { BAIL(kFskErrNetworkInterfaceError); } // ignore two lines fgets(buf, sizeof(buf), fp); fgets(buf, sizeof(buf), fp); while (fgets(buf, sizeof(buf), fp)) { char *ifname = strtok(buf, " :"); if (!ifname) continue; FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation,"%s: ", ifname); #if IGNORE_NETINTERFACE i = NUM_IGNORE_NET; while (i) { if (FskStrCompare(ignoreInterfaces[i-1], ifname) == 0) { FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation, "IGNORED"); ignore = true; } i--; } if (ignore) continue; #endif /* IGNORE_NETINTERFACE */ strcpy(ifr.ifr_name, ifname); if ((ioctl(fd, SIOCGIFHWADDR, &ifr) != -1) && (ifr.ifr_hwaddr.sa_family == ARPHRD_ETHER)) { FskMemPtrNewClear(sizeof(FskNetInterfaceRecord), (FskMemPtr *)&nir); if (!nir) { err = kFskErrMemFull; fclose(fp); goto bail; } FskMemCopy(nir->MAC, ifr.ifr_hwaddr.sa_data, 6); nir->name = FskStrDoCopy(ifname); nir->ip = 0; if (ioctl(fd, SIOCGIFADDR, &ifr) != -1) { sa = (struct sockaddr_in*)(void*)&(ifr.ifr_addr); nir->ip = ntohl( sa->sin_addr.s_addr); } if (ioctl(fd, SIOCGIFNETMASK, &ifr) != -1) { sa = (struct sockaddr_in*)(void*)&(ifr.ifr_addr); nir->netmask = ntohl( sa->sin_addr.s_addr); } if (ioctl(fd, SIOCGIFFLAGS, &ifr) != -1) { if (ifr.ifr_flags & IFF_UP) { nir->status = 1; } else { nir->status = 0; } } if (nir->ip == 0) nir->status = 0; FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation,"IP: %x, Netmask: %x [%s] HWADDR [%02x:%02x:%02x:%02x:%02x:%02x]", theIP, theNetmask, theStatus ? "UP " : "DOWN ", nir->MAC[0], nir->MAC[1], nir->MAC[2], nir->MAC[3], nir->MAC[4], nir->MAC[5]); FskListAppend((FskList*)interfaceList, nir); } else { FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation, " Family not ETHER or no HWADDR"); } } fclose(fp); skip: #endif /* !TARGET_OS_ANDROID */ #elif TARGET_OS_MAC && !TARGET_OS_IPHONE struct ifreq *ifrp, *ifend; unsigned int r; struct ifconf ifc; #if IGNORE_NETINTERFACE Boolean ignore = false; int i; #endif *interfaceList = NULL; fd = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP); ifc.ifc_len = sizeof(ibuf); ifc.ifc_buf = (caddr_t)ibuf; if (ioctl(fd, SIOCGIFCONF, &ifc) == -1 || ifc.ifc_len < (int)sizeof(struct ifreq)) { BAIL(kFskErrNetworkInterfaceError); } ifrp = ibuf; ifend = (struct ifreq*)((char*)ibuf + ifc.ifc_len); while (ifrp < ifend) { if (ifrp->ifr_addr.sa_family == AF_LINK && ((struct sockaddr_dl *)&ifrp->ifr_addr)->sdl_type == IFT_ETHER) { err = FskMemPtrNewClear(sizeof(FskNetInterfaceRecord), (FskMemPtr *)&nir); BAIL_IF_ERR(err); nir->name = FskStrDoCopy(ifrp->ifr_name); FskMemCopy((char*)nir->MAC, (char*)LLADDR((struct sockaddr_dl *)&ifrp->ifr_addr), 6); FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation,"%s: ", nir->name); #if IGNORE_NETINTERFACE i = NUM_IGNORE_NET; ignore = false; while (i) { if (FskStrCompare(ignoreInterfaces[i-1], nir->name) == 0) { FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation, "IGNORED"); ignore = true; } i--; } if (ignore) { FskMemPtrDispose(nir->name); FskMemPtrDisposeAt(&nir); goto nextOne; } #endif /* IGNORE_NETINTERFACE */ strcpy(ifr.ifr_name, nir->name); //@@ bounds check needed? if (ioctl(fd, SIOCGIFADDR, &ifr) != -1) { sa = (struct sockaddr_in*)(void*)&(ifr.ifr_addr); nir->ip = ntohl( sa->sin_addr.s_addr); } if (nir->ip) { if (ioctl(fd, SIOCGIFNETMASK, &ifr) != -1) { sa = (struct sockaddr_in*)(void*)&(ifr.ifr_addr); nir->netmask = ntohl( sa->sin_addr.s_addr); } if (ioctl(fd, SIOCGIFFLAGS, &ifr) != -1) { if (ifr.ifr_flags & IFF_UP) nir->status = 1; } FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation,"IP: %x, Netmask: %x [%s] HWADDR [%02x:%02x:%02x:%02x:%02x:%02x]", nir->ip, nir->netmask, nir->status ? "UP " : "DOWN ", nir->MAC[0], nir->MAC[1], nir->MAC[2], nir->MAC[3], nir->MAC[4], nir->MAC[5]); FskListAppend(interfaceList, nir); } else { FskMemPtrDispose(nir->name); FskMemPtrDisposeAt(&nir); } } nextOne: r = ifrp->ifr_addr.sa_len + sizeof(ifrp->ifr_name); if (r < sizeof(*ifrp)) r = sizeof(*ifrp); ifrp = (struct ifreq*)((char*)ifrp+r); } #elif TARGET_OS_IPHONE struct ifaddrs *iflist; if (getifaddrs(&iflist) != 0) return kFskErrNetworkInterfaceError; *interfaceList = NULL; for (struct ifaddrs *ifa = iflist; ifa != NULL; ifa = ifa->ifa_next) { if (ifa->ifa_name == NULL || ifa->ifa_addr == NULL || ifa->ifa_netmask == NULL || ((struct sockaddr_in*)(void*)ifa->ifa_addr)->sin_addr.s_addr == 0) continue; for (FskNetInterface ni = *interfaceList; ni != NULL; ni = ni->next) { if (FskStrCompare(ni->name, ifa->ifa_name) == 0) goto next; } if ((err = FskMemPtrNewClear(sizeof(FskNetInterfaceRecord), (FskMemPtr *)&nir)) != kFskErrNone) return err; nir->name = FskStrDoCopy(ifa->ifa_name); nir->ip = ntohl(((struct sockaddr_in*)(void*)ifa->ifa_addr)->sin_addr.s_addr); nir->netmask = ntohl(((struct sockaddr_in*)(void*)ifa->ifa_netmask)->sin_addr.s_addr); nir->status = ifa->ifa_flags & IFF_UP ? 1 : 0; FskListAppend((FskList *)interfaceList, nir); next:; } freeifaddrs(iflist); return kFskErrNone; #endif /* TARGET_OS_IPHONE */ // add loop back I/F to total number of IP addresses err = FskMemPtrNewClear(sizeof(FskNetInterfaceRecord), (FskMemPtr*)(void*)&nir); if (kFskErrNone == err) { nir->name = FskStrDoCopy("localhost"); nir->ip = FskNetMakeIP(127,0,0,1); nir->netmask = 0xff000000; nir->status = 1; FskListAppend((FskList*)interfaceList, nir); } bail: if (fd >= 0) // coverity 10587 close (fd); return err; }
FskErr KplNetInterfaceEnumerate(KplNetInterfaceRecord **interfaceList) { FskErr err = kFskErrNone; KplNetInterfaceRecord *nir; int fd; struct ifreq ifr; struct sockaddr_in *sa; DIR *d; struct dirent *dir; *interfaceList = NULL; fd = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP); if (fd < 0) goto skip; fprintf(stderr, "Kpl-ANDROID Enumerate Interfaces:\n"); d = opendir("/sys/class/net"); if (0 == d) { BAIL(kFskErrNetworkInterfaceError); } while ((dir = readdir(d))) { #if IGNORE_NETINTERFACE Boolean ignore = false; int i; #endif char *ifname; unsigned int theIP = 0, theNetmask = 0, theStatus = 0; if (dir->d_name[0] == '.') continue; ifname = dir->d_name; fprintf(stderr, " -- %s: ", ifname); #if IGNORE_NETINTERFACE i = NUM_IGNORE_NET; while (i) { if (FskStrCompare(ignoreInterfaces[i-1], ifname) == 0) { fprintf(stderr, " IGNORED"); ignore = true; } i--; } if (ignore) continue; #endif /* IGNORE_NETINTERFACE */ memset (&ifr, 0, sizeof(struct ifreq)); strncpy(ifr.ifr_name, ifname, IFNAMSIZ); ifr.ifr_name[IFNAMSIZ - 1] = 0; if (ioctl(fd, SIOCGIFADDR, &ifr) >= 0) { sa = (struct sockaddr_in*)(void*)&(ifr.ifr_addr); theIP = ntohl(sa->sin_addr.s_addr); } if (ioctl(fd, SIOCGIFNETMASK, &ifr) >= 0) { sa = (struct sockaddr_in*)(void*)&(ifr.ifr_addr); theNetmask = ntohl(sa->sin_addr.s_addr); } if (ioctl(fd, SIOCGIFFLAGS, &ifr) >= 0) { if (ifr.ifr_flags & 1) theStatus = 1; } if (theIP == 0) theStatus = 0; fprintf(stderr, "IP: %x, Netmask: %x [%s]", theIP, theNetmask, theStatus ? "UP" : "DOWN"); if (ioctl(fd, SIOCGIFHWADDR, &ifr) >= 0) { fprintf(stderr, " Got HWADDR "); if (ifr.ifr_hwaddr.sa_family == ARPHRD_ETHER) { fprintf(stderr, "ETHER"); FskMemPtrNewClear(sizeof(KplNetInterfaceRecord), (FskMemPtr*)(void*)&nir); if (!nir) { closedir(d); BAIL(kFskErrMemFull); } FskMemCopy(nir->MAC, ifr.ifr_hwaddr.sa_data, 6); nir->name = FskStrDoCopy(ifname); nir->ip = theIP; nir->netmask = theNetmask; nir->status = theStatus; FskListAppend((FskList*)interfaceList, nir); } else { fprintf(stderr, " Family not ETHER -- huh?"); } } } closedir(d); skip: err = FskMemPtrNewClear(sizeof(KplNetInterfaceRecord), (FskMemPtr*)(void*)&nir); if (kFskErrNone == err) { nir->name = FskStrDoCopy("localhost"); nir->ip = FskNetMakeIP(127, 0, 0, 1); nir->netmask = 0xff000000; nir->status = 1; FskListAppend((FskList*)interfaceList, nir); } bail: if (fd >= 0) close(fd); return err; }
// --------------------------------------------------------------------- static FskErr sFskNetInterfaceEnumerate(FskNetInterfaceRecord **interfaceList) { DWORD bytes, result; FskNetInterfaceRecord *nir; IP_ADAPTER_INFO *adapters = NULL, *pAdapter; FskErr err = kFskErrNone; *interfaceList = NULL; result = GetAdaptersInfo(NULL, &bytes); if (result == ERROR_NO_DATA) return kFskErrNetworkInterfaceError; if (( ERROR_SUCCESS != result ) && (ERROR_BUFFER_OVERFLOW != result)) return kFskErrNetworkInterfaceError; FskMemPtrNew(bytes, (FskMemPtr*)&adapters); result = GetAdaptersInfo(adapters, &bytes); if ( ERROR_SUCCESS != result ) BAIL(kFskErrNetworkInterfaceError); for (pAdapter = adapters ; NULL != pAdapter ; pAdapter = pAdapter->Next){ const IP_ADDR_STRING* ip = &pAdapter->IpAddressList; // NOTE: there may be more than one IP per interface - this does not handle that case FskInstrumentedTypePrintfDebug(&gNetInterfaceNotifierTypeInstrumentation,"Network Adapter %s", ip->IpAddress.String); // check for ppp, 0.0.0.0, etc. if (pAdapter->Type == IF_TYPE_PPP) continue; if (FskStrCompare("0.0.0.0", ip->IpAddress.String) == 0) continue; FskMemPtrNewClear(sizeof(FskNetInterfaceRecord), (FskMemPtr*)&nir); if (nir) { UInt32 j; nir->name = FskStrDoCopy(pAdapter->AdapterName); if (6 == pAdapter->AddressLength) { for(j = 0; j < pAdapter->AddressLength; j++) nir->MAC[j] = pAdapter->Address[j]; } FskNetStringToIPandPort(ip->IpAddress.String, &nir->ip, NULL); FskNetStringToIPandPort(ip->IpMask.String, &nir->netmask, NULL); nir->status = 1; FskListAppend((FskList *)interfaceList, nir); } } // add loop back I/F to total number of IP addresses FskMemPtrNewClear(sizeof(FskNetInterfaceRecord), (FskMemPtr*)&nir); if (nir) { int j; nir->name = FskStrDoCopy("localhost"); for(j = 0; j < 6; j++) nir->MAC[j] = 0; nir->ip = FskNetMakeIP(127,0,0,1); nir->netmask = 0xff000000; nir->status = 1; FskListAppend((FskList *)interfaceList, nir); } bail: FskMemPtrDispose(adapters); return err; }