谁能告诉我如何从接口IP地址获取接口索引? 例如如果接口IP地址是192.168.23.25,那么它的接口索引是什么。
我想补充一点,我需要在一个用c编写的代码中使用它,所以如果有任何函数 有一些选项可以给我基础上的接口索引号 接口IP地址。
答案 0 :(得分:3)
您应该可以使用getifaddrs()执行此操作。它应该说明MarkR对二级地址的关注。作为测试,
添加如下内容后:
ip addr add 192.168.25.23/24 dev eth0
在手册页上编译和运行示例程序应该显示如下内容:
lo address family: 17 (AF_PACKET)
eth0 address family: 17 (AF_PACKET)
lo address family: 2 (AF_INET)
address: <127.0.0.1>
eth0 address family: 2 (AF_INET)
address: <192.168.1.105>
eth0 address family: 2 (AF_INET)
address: <192.168.25.23>
lo address family: 10 (AF_INET6)
address: <::1>
eth0 address family: 10 (AF_INET6)
address: <fe84::82d6:baaf:fe14:4c22%eth0>
您应该能够在遍历列表时获取索引,但您还可以查看if_nametoindex(),if_indextoname()和if_nameindex()函数。由于您可以将地址与接口名称相关联,因此您可以根据需要调用它们。
答案 1 :(得分:2)
你不能那样做,你必须查看所有接口,然后遍历所有IP地址,直到找到你想要的那个。我认为这段代码可以满足您的需求。
#include <sys/ioctl.h>
#include <net/if.h>
#include <netinet/in.h>
#include <stdio.h>
#include <arpa/inet.h>
int main(int argc, char *argv[])
{
in_addr_t ia;
int id;
ia = inet_addr(argv[1]);
id = do_lookup(ia);
}
int do_lookup(in_addr_t ia) {
char buf[1024];
struct ifconf ifc;
struct ifreq *ifr;
int sck;
int nInterfaces;
int i;
/* Get a socket handle. */
sck = socket(AF_INET, SOCK_DGRAM, 0);
if(sck < 0)
{
perror("socket");
return -1;
}
/* Query available interfaces. */
ifc.ifc_len = sizeof(buf);
ifc.ifc_buf = buf;
if(ioctl(sck, SIOCGIFCONF, &ifc) < 0)
{
perror("ioctl(SIOCGIFCONF)");
return -1;
}
/* Iterate through the list of interfaces. */
ifr = ifc.ifc_req;
nInterfaces = ifc.ifc_len / sizeof(struct ifreq);
for(i = 0; i < nInterfaces; i++)
{
struct ifreq *item = &ifr[i];
if(((struct sockaddr_in *)&item->ifr_addr)->sin_addr.s_addr == ia) {
return i;
}
}
return -1;
}
答案 2 :(得分:0)
你可以用这个:它将列出Linux机器上的网络接口。
#include <sys/ioctl.h>
#include <net/if.h>
#include <netinet/in.h>
#include <stdio.h>
#include <arpa/inet.h>
int main(void)
{
char buf[1024];
struct ifconf ifc;
struct ifreq *ifr;
int sck;
int nInterfaces;
int i;
/* Get a socket handle. */
sck = socket(AF_INET, SOCK_DGRAM, 0);
if(sck < 0)
{
perror("socket");
return 1;
}
/* Query available interfaces. */
ifc.ifc_len = sizeof(buf);
ifc.ifc_buf = buf;
if(ioctl(sck, SIOCGIFCONF, &ifc) < 0)
{
perror("ioctl(SIOCGIFCONF)");
return 1;
}
/* Iterate through the list of interfaces. */
ifr = ifc.ifc_req;
nInterfaces = ifc.ifc_len / sizeof(struct ifreq);
for(i = 0; i < nInterfaces; i++)
{
struct ifreq *item = &ifr[i];
/* Show the device name and IP address */
printf("%s: IP %s",
item->ifr_name,
inet_ntoa(((struct sockaddr_in *)&item->ifr_addr)->sin_addr));
/* Get the MAC address */
if(ioctl(sck, SIOCGIFHWADDR, item) < 0)
{
perror("ioctl(SIOCGIFHWADDR)");
return 1;
}
/* Get the broadcast address (added by Eric) */
if(ioctl(sck, SIOCGIFBRDADDR, item) >= 0)
printf(", BROADCAST %s", inet_ntoa(((struct sockaddr_in *)&item->ifr_broadaddr)->sin_addr));
printf("\n");
}
return 0;
}
我是从here获得的。
答案 3 :(得分:0)
SIOCGIFCONF不会为使用
添加的辅助IP地址剪切它ip addr add 192.168.25.23/24 dev eth1
如果你真的需要这样做,那么看看“ip addr sh”使用的是什么 - 可能是一个netlink套接字操作(涉及非常奇怪的宏)
答案 4 :(得分:0)
以编程方式使用if_nametoindex()。我已经在Ubuntu 12.04(内核3.11.0-15-generic)上验证了这一点。
以下是示例代码段
#include <net/if.h>
#include <stdio.h>
#include <errno.h>
int main(int argc, char *argv[])
{
for (int ix=1; ix<argc; ix++)
{
unsigned int rc = if_nametoindex(argv[ix]);
if (rc) {
printf("interface [%s] has index : %d\n", argv[ix], rc);
}
else {
perror("if_nametoindex");
}
}
}
用法示例:
$ ./if_index eth0
interface [eth0] has index : 2
另外,非编程方法是读取/ proc / net / if_inet6条目。第二列是相应的接口索引。
$ cat /proc/net/if_inet6
00000000000000000000000000000001 01 80 10 80 lo
fe800000000000000a0027fffe1a2a32 03 40 20 80 eth1
fe800000000000000a0027fffe08b9ca 02 40 20 80 eth0