|
a/libupnpp/getsyshwaddr.c |
|
b/libupnpp/getsyshwaddr.c |
|
... |
|
... |
54 |
#endif
|
54 |
#endif
|
55 |
#endif
|
55 |
#endif
|
56 |
|
56 |
|
57 |
#include "getsyshwaddr.h"
|
57 |
#include "getsyshwaddr.h"
|
58 |
|
58 |
|
|
|
59 |
#define MACADDR_IS_ZERO(x) \
|
|
|
60 |
((x[0] == 0x00) && \
|
|
|
61 |
(x[1] == 0x00) && \
|
|
|
62 |
(x[2] == 0x00) && \
|
|
|
63 |
(x[3] == 0x00) && \
|
|
|
64 |
(x[4] == 0x00) && \
|
|
|
65 |
(x[5] == 0x00))
|
|
|
66 |
|
59 |
#define DPRINTF(A,B,C,D)
|
67 |
#define DPRINTF(A,B,C,D)
|
60 |
|
68 |
|
61 |
int
|
69 |
int getsyshwaddr(const char *iface, char *ip, int ilen, char *buf, int hlen)
|
62 |
getsyshwaddr(char *buf, int len)
|
|
|
63 |
{
|
70 |
{
|
64 |
unsigned char mac[6];
|
71 |
unsigned char mac[6];
|
65 |
int ret = -1;
|
72 |
int ret = -1;
|
|
|
73 |
|
|
|
74 |
memset(&mac, 0, sizeof(mac));
|
|
|
75 |
|
66 |
#if HAVE_GETIFADDRS
|
76 |
#if HAVE_GETIFADDRS
|
67 |
struct ifaddrs *ifap, *p;
|
77 |
struct ifaddrs *ifap, *p;
|
68 |
struct sockaddr_in *addr_in;
|
|
|
69 |
uint8_t a;
|
|
|
70 |
|
78 |
|
71 |
if (getifaddrs(&ifap) != 0)
|
79 |
if (getifaddrs(&ifap) != 0)
|
72 |
{
|
80 |
{
|
73 |
DPRINTF(E_ERROR, L_GENERAL, "getifaddrs(): %s\n", strerror(errno));
|
81 |
DPRINTF(E_ERROR, L_GENERAL, "getifaddrs(): %s\n", strerror(errno));
|
74 |
return -1;
|
82 |
return -1;
|
75 |
}
|
83 |
}
|
76 |
for (p = ifap; p != NULL; p = p->ifa_next)
|
84 |
for (p = ifap; p != NULL; p = p->ifa_next)
|
77 |
{
|
85 |
{
|
78 |
if (p->ifa_addr && p->ifa_addr->sa_family == AF_LINK)
|
86 |
if (p->ifa_addr && p->ifa_addr->sa_family == AF_LINK)
|
79 |
{
|
87 |
{
|
|
|
88 |
struct sockaddr_in *addr_in;
|
|
|
89 |
uint8_t a;
|
|
|
90 |
|
|
|
91 |
if (iface && *iface &&
|
|
|
92 |
strncmp(iface, p->ifa_name, strnlen(iface, 20)) != 0 )
|
|
|
93 |
continue;
|
|
|
94 |
|
80 |
addr_in = (struct sockaddr_in *)p->ifa_addr;
|
95 |
addr_in = (struct sockaddr_in *)p->ifa_addr;
|
81 |
a = (htonl(addr_in->sin_addr.s_addr) >> 0x18) & 0xFF;
|
96 |
a = (htonl(addr_in->sin_addr.s_addr) >> 0x18) & 0xFF;
|
82 |
if (a == 127)
|
97 |
if (a == 127)
|
83 |
continue;
|
98 |
continue;
|
|
|
99 |
|
|
|
100 |
if (ip)
|
|
|
101 |
inet_ntop(AF_INET, (const void *) &(addr_in->sin_addr),
|
|
|
102 |
ip, ilen);
|
|
|
103 |
|
84 |
#ifdef __linux__
|
104 |
#ifdef __linux__
|
85 |
struct ifreq ifr;
|
105 |
struct ifreq ifr;
|
86 |
int fd;
|
106 |
int fd;
|
87 |
fd = socket(AF_INET, SOCK_DGRAM, 0);
|
107 |
fd = socket(AF_INET, SOCK_DGRAM, 0);
|
88 |
if (fd < 0)
|
108 |
if (fd < 0)
|
|
... |
|
... |
92 |
{
|
112 |
{
|
93 |
close(fd);
|
113 |
close(fd);
|
94 |
continue;
|
114 |
continue;
|
95 |
}
|
115 |
}
|
96 |
memcpy(mac, ifr.ifr_hwaddr.sa_data, 6);
|
116 |
memcpy(mac, ifr.ifr_hwaddr.sa_data, 6);
|
|
|
117 |
close(fd);
|
97 |
#else
|
118 |
#else
|
98 |
struct sockaddr_dl *sdl;
|
119 |
struct sockaddr_dl *sdl;
|
99 |
sdl = (struct sockaddr_dl*)p->ifa_addr;
|
120 |
sdl = (struct sockaddr_dl*)p->ifa_addr;
|
100 |
memcpy(mac, LLADDR(sdl), sdl->sdl_alen);
|
121 |
memcpy(mac, LLADDR(sdl), sdl->sdl_alen);
|
101 |
#endif
|
122 |
#endif
|
|
... |
|
... |
104 |
ret = 0;
|
125 |
ret = 0;
|
105 |
break;
|
126 |
break;
|
106 |
}
|
127 |
}
|
107 |
}
|
128 |
}
|
108 |
freeifaddrs(ifap);
|
129 |
freeifaddrs(ifap);
|
|
|
130 |
|
109 |
#else
|
131 |
#else
|
|
|
132 |
|
110 |
struct if_nameindex *ifaces, *if_idx;
|
133 |
struct if_nameindex *ifaces, *if_idx;
|
111 |
struct ifreq ifr;
|
134 |
struct ifreq ifr;
|
112 |
int fd;
|
135 |
int fd;
|
113 |
|
136 |
|
114 |
memset(&mac, '\0', sizeof(mac));
|
|
|
115 |
/* Get the spatially unique node identifier */
|
137 |
/* Get the spatially unique node identifier */
|
116 |
fd = socket(AF_INET, SOCK_DGRAM, 0);
|
138 |
fd = socket(AF_INET, SOCK_DGRAM, 0);
|
117 |
if (fd < 0)
|
139 |
if (fd < 0)
|
118 |
return ret;
|
140 |
return ret;
|
119 |
|
141 |
|
|
... |
|
... |
121 |
if (!ifaces)
|
143 |
if (!ifaces)
|
122 |
return ret;
|
144 |
return ret;
|
123 |
|
145 |
|
124 |
for (if_idx = ifaces; if_idx->if_index; if_idx++)
|
146 |
for (if_idx = ifaces; if_idx->if_index; if_idx++)
|
125 |
{
|
147 |
{
|
|
|
148 |
if (iface && *iface &&
|
|
|
149 |
strncmp(name, if_idx->if_name, strnlen(name, 20)) != 0 )
|
|
|
150 |
continue;
|
|
|
151 |
|
126 |
strncpy(ifr.ifr_name, if_idx->if_name, IFNAMSIZ);
|
152 |
strncpy(ifr.ifr_name, if_idx->if_name, IFNAMSIZ);
|
127 |
if (ioctl(fd, SIOCGIFFLAGS, &ifr) < 0)
|
153 |
if (ioctl(fd, SIOCGIFFLAGS, &ifr) < 0)
|
128 |
continue;
|
154 |
continue;
|
129 |
if (ifr.ifr_ifru.ifru_flags & IFF_LOOPBACK)
|
155 |
if (ifr.ifr_ifru.ifru_flags & IFF_LOOPBACK)
|
130 |
continue;
|
156 |
continue;
|
131 |
if (ioctl(fd, SIOCGIFHWADDR, &ifr) < 0)
|
157 |
if (ioctl(fd, SIOCGIFHWADDR, &ifr) < 0)
|
132 |
continue;
|
158 |
continue;
|
133 |
if (MACADDR_IS_ZERO(ifr.ifr_hwaddr.sa_data))
|
159 |
if (MACADDR_IS_ZERO(ifr.ifr_hwaddr.sa_data))
|
134 |
continue;
|
160 |
continue;
|
135 |
memcpy(mac, ifr.ifr_hwaddr.sa_data, 6);
|
161 |
memcpy(mac, ifr.ifr_hwaddr.sa_data, 6);
|
|
|
162 |
if (ip) {
|
|
|
163 |
if (ioctl(fd, SIOCGIFADDR, &ifr) == 0) {
|
|
|
164 |
// Not sure at all that this branch is ever used on modern
|
|
|
165 |
// systems. So just procrastinate until/if we ever need this.
|
|
|
166 |
#error please fill in the code to retrieve the IP address,
|
|
|
167 |
}
|
|
|
168 |
}
|
|
|
169 |
|
136 |
ret = 0;
|
170 |
ret = 0;
|
137 |
break;
|
171 |
break;
|
138 |
}
|
172 |
}
|
139 |
if_freenameindex(ifaces);
|
173 |
if_freenameindex(ifaces);
|
140 |
close(fd);
|
174 |
close(fd);
|
141 |
#endif
|
175 |
#endif
|
|
|
176 |
|
142 |
if (ret == 0)
|
177 |
if (ret == 0)
|
143 |
{
|
178 |
{
|
144 |
if (len > 12)
|
179 |
if (ilen > 12)
|
145 |
sprintf(buf, "%02x%02x%02x%02x%02x%02x",
|
180 |
sprintf(buf, "%02x%02x%02x%02x%02x%02x",
|
146 |
mac[0]&0xFF, mac[1]&0xFF, mac[2]&0xFF,
|
181 |
mac[0]&0xFF, mac[1]&0xFF, mac[2]&0xFF,
|
147 |
mac[3]&0xFF, mac[4]&0xFF, mac[5]&0xFF);
|
182 |
mac[3]&0xFF, mac[4]&0xFF, mac[5]&0xFF);
|
148 |
else if (len == 6)
|
183 |
else if (ilen == 6)
|
149 |
memmove(buf, mac, 6);
|
184 |
memmove(buf, mac, 6);
|
150 |
}
|
185 |
}
|
151 |
return ret;
|
186 |
return ret;
|
152 |
}
|
187 |
}
|
|
|
188 |
|
|
|
189 |
/* Local Variables: */
|
|
|
190 |
/* mode: c++ */
|
|
|
191 |
/* c-basic-offset: 4 */
|
|
|
192 |
/* tab-width: 4 */
|
|
|
193 |
/* indent-tabs-mode: t */
|
|
|
194 |
/* End: */
|