linux下可以用ifconfig命令来查看所有网口的连接状态及其他详细信息。
根据ifconfig的源码,我们可以实现检测网口状态并获取网口的名字和IP地址。
#include <stdio.h> #include <sys/types.h> #include <ifaddrs.h> #include <netinet/in.h> #include <string.h> #include <arpa/inet.h> #include <unistd.h> #include <fcntl.h> #include <net/if.h> #include <time.h> #include <stdlib.h> #include <sys/ioctl.h> #include <arpa/inet.h> #include <stdlib.h> typedef struct _gEthIfaceInfo { unsigned int etherIP; char etherName[IF_NAMESIZE]; }EtherIfaceInfo_t; EtherIfaceInfo_t gEtherIfaceInfo; ////////////////////////////////////////////////////// //@usage: get avail iface ////////////////////////////////////////////////////// static bool getAvailIface(EtherIfaceInfo_t &ifaceInfo) { int i, flags; struct ifconf data; struct ifreq device[IF_NAMESIZE];//16 data.ifc_len = sizeof(device); data.ifc_req = device; memset(data.ifc_buf, 0, data.ifc_len); flags = IFF_UP | IFF_RUNNING | IFF_MULTICAST; int sockfd = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP); if(sockfd < 0) { perror("socket fails"); return false; } /* get list of network interfaces */ if (ioctl(sockfd, SIOCGIFCONF, &data) < 0) { ERROR_LOG("failed query network interfaces"); return false; } if (data.ifc_len >= sizeof(device)) { WARN_LOG("device list may exceed allocated space"); } /* search through interfaces */ for (i = 0; i < data.ifc_len / sizeof(device[0]); ++i) { DEBUG_LOG("%d %s %s", i, device[i].ifr_name, inet_ntoa(((struct sockaddr_in *)&device[i].ifr_addr)->sin_addr)); if (ioctl(sockfd, SIOCGIFFLAGS, &device[i]) < 0) { ERROR_LOG("failed to get device flags"); continue; } else if ((device[i].ifr_flags & flags) != flags) { WARN_LOG("does not meet requirements""(%08x, %08x)", device[i].ifr_flags, flags); continue; } else if (ioctl(sockfd, SIOCGIFHWADDR, &device[i]) < 0) { ERROR_LOG("failed to get hardware address"); continue; } else if (ioctl(sockfd, SIOCGIFADDR, &device[i]) < 0) { ERROR_LOG("failed to get ip address"); continue; } else { DEBUG_LOG("found available interface (%s)", device[i].ifr_name); ifaceInfo.etherIP = ((struct sockaddr_in *)&device[i].ifr_addr)->sin_addr.s_addr; memcpy(ifaceInfo.etherName, device[i].ifr_name, IF_NAMESIZE); return true; } } close(sockfd); return false; }