Closed Someone-Practice closed 3 months ago
https://github.com/pymumu/smartdns/blob/04d68e7797d32c02b76b51aa7556cc9e73b7892d/src/util.c#L911
Modify as follows
int rtalen = len;
https://github.com/pymumu/smartdns/blob/04d68e7797d32c02b76b51aa7556cc9e73b7892d/src/util.c#L911
Modify as follows
int rtalen = len;
Unfortunately, MAC rules ceased to function after changing that integer to signed. Tested on latest master and Release45.
int netlink_get_neighbors(int family,
int (*callback)(const uint8_t *net_addr, int net_addr_len, const uint8_t mac[6], void *arg),
void *arg)
{
if (netlink_neighbor_fd <= 0) {
netlink_neighbor_fd = socket(AF_NETLINK, SOCK_RAW | SOCK_CLOEXEC | SOCK_NONBLOCK, NETLINK_ROUTE);
if (netlink_neighbor_fd < 0) {
return -1;
}
}
struct nlmsghdr *nlh;
struct ndmsg *ndm;
char buf[1024 * 16];
struct iovec iov = {buf, sizeof(buf)};
struct sockaddr_nl sa;
struct msghdr msg;
int len;
int ret = 0;
memset(&msg, 0, sizeof(msg));
msg.msg_name = &sa;
msg.msg_namelen = sizeof(sa);
msg.msg_iov = &iov;
msg.msg_iovlen = 1;
nlh = (struct nlmsghdr *)buf;
nlh->nlmsg_len = NLMSG_LENGTH(sizeof(struct ndmsg));
nlh->nlmsg_type = RTM_GETNEIGH;
nlh->nlmsg_flags = NLM_F_REQUEST | NLM_F_DUMP;
nlh->nlmsg_seq = time(NULL);
nlh->nlmsg_pid = getpid();
ndm = NLMSG_DATA(nlh);
ndm->ndm_family = family;
if (send(netlink_neighbor_fd, buf, NLMSG_SPACE(sizeof(struct ndmsg)), 0) < 0) {
return -1;
}
while ((len = recvmsg(netlink_neighbor_fd, &msg, 0)) > 0) {
if (ret != 0) {
continue;
}
int nlh_len = len;
for (nlh = (struct nlmsghdr *)buf; NLMSG_OK(nlh, nlh_len); nlh = NLMSG_NEXT(nlh, nlh_len)) {
ndm = NLMSG_DATA(nlh);
struct rtattr *rta = RTM_RTA(ndm);
const uint8_t *mac = NULL;
const uint8_t *net_addr = NULL;
int net_addr_len = 0;
int rta_len = RTM_PAYLOAD(nlh);
for (; RTA_OK(rta, rta_len); rta = RTA_NEXT(rta, rta_len)) {
if (rta->rta_type == NDA_DST) {
if (ndm->ndm_family == AF_INET) {
struct in_addr *addr = RTA_DATA(rta);
if (IN_MULTICAST(ntohl(addr->s_addr))) {
continue;
}
if (ntohl(addr->s_addr) == 0) {
continue;
}
net_addr = (uint8_t *)&addr->s_addr;
net_addr_len = IPV4_ADDR_LEN;
} else if (ndm->ndm_family == AF_INET6) {
struct in6_addr *addr = RTA_DATA(rta);
if (IN6_IS_ADDR_MC_NODELOCAL(addr)) {
continue;
}
if (IN6_IS_ADDR_MC_LINKLOCAL(addr)) {
continue;
}
if (IN6_IS_ADDR_MC_SITELOCAL(addr)) {
continue;
}
if (IN6_IS_ADDR_UNSPECIFIED(addr)) {
continue;
}
net_addr = addr->s6_addr;
net_addr_len = IPV6_ADDR_LEN;
}
} else if (rta->rta_type == NDA_LLADDR) {
mac = RTA_DATA(rta);
}
}
if (net_addr != NULL && mac != NULL) {
ret = callback(net_addr, net_addr_len, mac, arg);
if (ret != 0) {
break;
}
}
}
}
return ret;
}
int netlink_get_neighbors(int family, int (*callback)(const uint8_t *net_addr, int net_addr_len, const uint8_t mac[6], void *arg), void *arg) /* TRUNCATED */
MAC rules are functional now. Ran it for a day and I haven't observed a crash yet. The test will continue til tomorrow.
Still no crashes. I think it's safe to assume the issue has been resolved now.
Issue
When using MAC addresses as client identifiers in client-rules, smartdns will crash occasionally.
Environment
To replicate
Core dump and executable
I stopped seeing crash traces in log after I turn on core dumping, but I do recall the log entry referred to a function called find_neighbors or something similar.
Core dump
Executable used