Reputation: 1492
I want to find the route of a packet in user space. I have dst ip and I want to read the kernel tables, so it will give me the result according to current ip route cfg. any way of doing that in C?
Upvotes: 1
Views: 793
Reputation: 18420
You can do the following to get the interface index:
First, create a UDP socket to your destination:
int fd = socket(AF_INET, SOCK_DGRAM, 0);
struct sockaddr_in in;
in.sin_family = AF_INET;
in.sin_port = htons(1234);
in.sin_addr.s_addr = inet_addr("1.2.3.4");
connect(fd, (struct sockaddr *)&in, sizeof(struct sockaddr_in));
Then, call getsockname()
to determine the interface addr of the outgoing interface for this socket:
int inlen = sizeof(in);
getsockname(fd, (struct sockaddr *)&in, &inlen);
Now, get all system interface structures and look for the correct interface address:
struct ifaddrs *ifa, *ifap;
getifaddrs(&ifa);
ifap = ifa;
char *ifname = NULL;
while (ifa) {
if (((struct sockaddr_in *)ifa->ifa_addr)->sin_addr.s_addr ==
in.sin_addr.s_addr) {
ifname = strdup(ifa->ifa_name);
break;
}
ifa = ifa->ifa_next;
}
freeifaddrs(ifap);
Finally, get the interface index for the interface name:
struct ifreq iface;
strncpy(iface.ifr_name, interface, IFNAMSIZ);
iface.ifr_name[IFNAMSIZ-1] = 0;
int len = sizeof(iface);
ioctl(fd, SIOCGIFINDEX, &iface, &len);
int ifindex = iface.ifr_ifindex;
Looks a bit complicated, but is independent from netlink (which isn't much easier either).
Upvotes: 2
Reputation: 501
Asking the kernel via nlmsg looks legit and worked for me in the past.
I started off from this answer back then:
https://stackoverflow.com/a/27331273/6232305
Upvotes: 2