问题
I am using the following code to retrieve all MAC addresses for current computer:
ifreq ifr;
ifconf ifc;
char buf[1024];
int sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_IP);
if (sock == -1) { ... };
ifc.ifc_len = sizeof(buf);
ifc.ifc_buf = buf;
if (ioctl(sock, SIOCGIFCONF, &ifc) == -1) { ... }
ifreq *it = ifc.ifc_req;
const ifreq* const end = it + (ifc.ifc_len / sizeof(ifreq));
for (; it != end; ++it) {
strcpy(ifr.ifr_name, it->ifr_name);
if (ioctl(sock, SIOCGIFFLAGS, &ifr) == 0) {
if (!(ifr.ifr_flags & IFF_LOOPBACK)) {
if (ioctl(sock, SIOCGIFHWADDR, &ifr) == 0) {
unsigned char mac_address[6];
memcpy(mac_address, ifr.ifr_hwaddr.sa_data, 6);
...
}
}
}
else { ... }
}
By running simple shell command ifconfig i can see lo, eth0 and wlan0. I would like to retrieve MAC addresses for eth0 and wlan0 by my C/C++ code. But only wlan0 is returned - eth0 is missing (I got ifr_names lo, lo, wlan0). Probably because eth0 is not active (no ethernet cable connected, with cable it is returned). Can I somehow alter that ioctl(SIOCGIFCONF) command to retrieve eth0 too even if it is "turned off"?
I can get its HW address by using directly
struct ifreq s;
int fd = socket(PF_INET, SOCK_DGRAM, IPPROTO_IP);
strcpy(s.ifr_name, "eth0");
if (0 == ioctl(fd, SIOCGIFHWADDR, &s)) { ... }
but what if the name would be not eth0 but something else (eth1, em0,...)? I would like to get all of them. Thanks for help.
回答1:
You should stop using net-tools and the archaic ioctl interface, and start on using the modern Netlink/sysfs interfaces. You have no less than 5 possibilities:
- write your own Netlink-interfacing code
- your own NL code, in combination utilizing libmnl (-> see rtnl-link-dump in Examples
- or utilize autonomous libs like libnl3
- parse text output of
ip -o link
(-o is to get output meant for text parsing, unlike ifconfig) - or use sysfs and just look at
/sys/class/net/eth0/address
回答2:
You can find a solution here: Get mac address given a specific interface
You can just skip the specific interface part.
回答3:
Maybe not as elegant, but you could capture & parse the results from ifconfig, since it sounds like it has just what you are looking for.
来源:https://stackoverflow.com/questions/9034575/c-c-linux-mac-address-of-all-interfaces