dev: make paths unlikely, simplify code
[netsniff-ng.git] / dev.c
blobec27178259da1e33f35d7e6145dad1dda6c674de
1 #include <string.h>
2 #include <errno.h>
3 #include <sys/ioctl.h>
4 #include <sys/types.h>
5 #include <ifaddrs.h>
7 #include "dev.h"
8 #include "str.h"
9 #include "sock.h"
10 #include "die.h"
11 #include "link.h"
12 #include "built_in.h"
14 int device_ifindex(const char *ifname)
16 int ret, sock, index;
17 struct ifreq ifr;
19 if (!strncmp("any", ifname, strlen("any")))
20 return 0;
22 sock = af_socket(AF_INET);
24 memset(&ifr, 0, sizeof(ifr));
25 strlcpy(ifr.ifr_name, ifname, IFNAMSIZ);
27 ret = ioctl(sock, SIOCGIFINDEX, &ifr);
28 if (unlikely(ret))
29 panic("Cannot get ifindex from device!\n");
31 index = ifr.ifr_ifindex;
32 close(sock);
34 return index;
37 static int __device_address6(const char *ifname, struct sockaddr_storage *ss)
39 int ret, family, found = -EINVAL;
40 struct ifaddrs *ifaddr, *ifa;
42 ret = getifaddrs(&ifaddr);
43 if (unlikely(ret < 0))
44 panic("Cannot get device addresses for IPv6!\n");
46 for (ifa = ifaddr; ifa != NULL; ifa = ifa->ifa_next) {
47 family = ifa->ifa_addr->sa_family;
48 if (family != AF_INET6)
49 continue;
50 if (strcmp(ifa->ifa_name, ifname))
51 continue;
53 memcpy(ss, ifa->ifa_addr, sizeof(*ss));
54 found = 0;
55 break;
58 freeifaddrs(ifaddr);
59 return found;
62 int device_address(const char *ifname, int af, struct sockaddr_storage *ss)
64 int ret, sock;
65 struct ifreq ifr;
67 if (unlikely(!ss))
68 return -EINVAL;
69 if (!strncmp("any", ifname, strlen("any")))
70 return -EINVAL;
71 if (af == AF_INET6)
72 return __device_address6(ifname, ss);
74 sock = af_socket(af);
76 memset(&ifr, 0, sizeof(ifr));
77 strlcpy(ifr.ifr_name, ifname, IFNAMSIZ);
79 ifr.ifr_addr.sa_family = af;
81 ret = ioctl(sock, SIOCGIFADDR, &ifr);
82 if (!ret)
83 memcpy(ss, &ifr.ifr_addr, sizeof(ifr.ifr_addr));
85 close(sock);
86 return ret;
89 int device_mtu(const char *ifname)
91 int ret, sock, mtu = 0;
92 struct ifreq ifr;
94 sock = af_socket(AF_INET);
96 memset(&ifr, 0, sizeof(ifr));
97 strlcpy(ifr.ifr_name, ifname, IFNAMSIZ);
99 ret = ioctl(sock, SIOCGIFMTU, &ifr);
100 if (!ret)
101 mtu = ifr.ifr_mtu;
103 close(sock);
104 return mtu;
107 short device_get_flags(const char *ifname)
109 short flags = 0;
110 int ret, sock;
111 struct ifreq ifr;
113 sock = af_socket(AF_INET);
115 memset(&ifr, 0, sizeof(ifr));
116 strlcpy(ifr.ifr_name, ifname, IFNAMSIZ);
118 ret = ioctl(sock, SIOCGIFFLAGS, &ifr);
119 if (!ret)
120 flags = ifr.ifr_flags;
122 close(sock);
123 return flags;
126 void device_set_flags(const char *ifname, const short flags)
128 int ret, sock;
129 struct ifreq ifr;
131 sock = af_socket(AF_INET);
133 memset(&ifr, 0, sizeof(ifr));
134 strlcpy(ifr.ifr_name, ifname, IFNAMSIZ);
135 ifr.ifr_flags = flags;
137 ret = ioctl(sock, SIOCSIFFLAGS, &ifr);
138 if (ret < 0)
139 panic("Cannot set NIC flags!\n");
141 close(sock);
144 int device_up_and_running(char *ifname)
146 if (!ifname)
147 return -EINVAL;
148 if (!strncmp("any", ifname, strlen("any")))
149 return 1;
151 return (device_get_flags(ifname) &
152 (IFF_UP | IFF_RUNNING)) ==
153 (IFF_UP | IFF_RUNNING);
156 u32 device_bitrate(const char *ifname)
158 u32 scopper, swireless;
160 scopper = ethtool_bitrate(ifname);
161 swireless = wireless_bitrate(ifname);
163 return scopper ? : swireless;