查找网络设备
在新闻组上看到有人问如何通过名字查找某个网络设备,其实不难,首先想到的就是通过ioctl,示例代码见下:
[c]
int get_interface(const char interface)
{
int sock = socket(PF_INET, SOCK_STREAM, 0);
struct ifconf ifc;
struct ifreq ifr;
int ret = -1;
if (sock < 0)
return -1;
ifc.ifc_len = 0;
ifc.ifc_req = NULL;
if (ioctl(sock, SIOCGIFCONF, &ifc) 0) {
ifc.ifc_req = malloc(ifc.ifc_len);
if (ifc.ifc_req) {
if (ioctl(sock, SIOCGIFCONF, &ifc) < 0) {
free(ifc.ifc_req);
goto close;
} else
for (ifr = ifc.ifc_req;
(char *)ifr ifr_name);*/
if (!strcmp(ifr->ifr_name, interface)) {
ret = 0;
break;
}
}
} else
return -1;
free(ifc.ifc_req);
}
close:
close(sock);
return ret;
}
[/c]
然后有人说POSIX其实还有个if_nameindex(),它明显要比ioctl可移植性要高,用它重写上面的代码如下:
[c]
int get_interf(const char *interf)
{
int ret = -1;
struct if_nameindex *ifp, *ifpsave;
ifpsave = ifp = if_nameindex();
if (!ifp)
return -1;
while (ifp->if_index) {
if (strcmp(ifp->if_name, interf) == 0) {
ret = 0;
break;
}
ifp++;
}
if_freenameindex(ifpsave);
return ret;
}
[/c]
我查了一下glibc中的实现,发现在linux上其实如果不用netlink的话,if_nameindex()也就是对ioctl(…SIOCGIFCONF…)的一个包装,具体可参考sysdeps/unix/sysv/linux/if_index.c。netlink这个东西够奇怪的,在这里居然也能派上用场,有机会要研究研究~