auto_socket: Windows-скан + список сокетов в Network Settings (add/remove, чистый rewrite конфига)

This commit is contained in:
Evgeny committed 2026-08-13 22:58:52 +03:00
1 parent d5119ac7c6
commit f82dca3185
8 files changed
+545 -160

No files matched your search

+79 -11
View File
@@ -281,26 +281,94 @@ uint32_t get_default_route_netif_index(int family) {
freeifaddrs(ifaddr);
return result;
}
#else
#else /* _WIN32 */
/* ── Windows: реализация через IP Helper (GetAdaptersAddresses) ── */
static PIP_ADAPTER_ADDRESSES plat_win_get_adapters(ULONG family) {
PIP_ADAPTER_ADDRESSES adapters = NULL;
ULONG size = 0;
ULONG flags = GAA_FLAG_SKIP_ANYCAST | GAA_FLAG_SKIP_MULTICAST | GAA_FLAG_SKIP_DNS_SERVER;
if (GetAdaptersAddresses(family, flags, NULL, NULL, &size) != ERROR_BUFFER_OVERFLOW) return NULL;
adapters = (PIP_ADAPTER_ADDRESSES)malloc(size);
if (!adapters) return NULL;
if (GetAdaptersAddresses(family, flags, NULL, adapters, &size) != NO_ERROR) { free(adapters); return NULL; }
return adapters;
}
static PIP_ADAPTER_ADDRESSES plat_win_find_adapter(PIP_ADAPTER_ADDRESSES adapters, uint32_t ifindex) {
for (PIP_ADAPTER_ADDRESSES a = adapters; a; a = a->Next) {
if (a->IfIndex == ifindex || a->Ipv4IfIndex == ifindex || a->Ipv6IfIndex == ifindex) return a;
}
return NULL;
}
uint32_t get_interface_ip_by_index(uint32_t netif_index) {
(void)netif_index;
return 0;
if (!netif_index) return 0;
PIP_ADAPTER_ADDRESSES adapters = plat_win_get_adapters(AF_INET);
if (!adapters) return 0;
uint32_t result = 0;
PIP_ADAPTER_ADDRESSES a = plat_win_find_adapter(adapters, netif_index);
if (a) {
for (PIP_ADAPTER_UNICAST_ADDRESS u = a->FirstUnicastAddress; u; u = u->Next) {
if (u->Address.lpSockaddr && u->Address.lpSockaddr->sa_family == AF_INET) {
result = ((const struct sockaddr_in*)u->Address.lpSockaddr)->sin_addr.s_addr;
break;
}
}
}
free(adapters);
return result;
}
int get_interface_ipv6_by_index(uint32_t netif_index, int temporary, uint8_t* addr_out) {
(void)netif_index; (void)temporary;
if (addr_out) memset(addr_out, 0, 16);
return -1;
/* Windows IP Helper не различает temporary/stable без запроса Addresses — отдаём первый не-link-local */
(void)temporary;
return get_interface_ipv6_addr_nl(netif_index, 1, addr_out);
}
int get_interface_ipv6_addr_nl(uint32_t netif_index, int prefer_stable, uint8_t* addr_out) {
(void)netif_index; (void)prefer_stable;
if (addr_out) memset(addr_out, 0, 16);
return -1;
(void)prefer_stable;
if (!addr_out) return -1;
memset(addr_out, 0, 16);
if (!netif_index) return -1;
PIP_ADAPTER_ADDRESSES adapters = plat_win_get_adapters(AF_INET6);
if (!adapters) return -1;
int found = 0;
PIP_ADAPTER_ADDRESSES a = plat_win_find_adapter(adapters, netif_index);
if (a) {
for (PIP_ADAPTER_UNICAST_ADDRESS u = a->FirstUnicastAddress; u; u = u->Next) {
if (!u->Address.lpSockaddr || u->Address.lpSockaddr->sa_family != AF_INET6) continue;
const uint8_t* b = ((const struct sockaddr_in6*)u->Address.lpSockaddr)->sin6_addr.s6_addr;
if ((b[0] == 0xfe && (b[1] & 0xc0) == 0x80)) continue; /* link-local */
{ static const uint8_t lb[16] = {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1};
if (memcmp(b, lb, 16) == 0) continue; } /* loopback */
{ static const uint8_t z[16]; if (memcmp(b, z, 16) == 0) continue; } /* :: */
memcpy(addr_out, b, 16);
found = 1;
break;
}
}
free(adapters);
return found ? 0 : -1;
}
uint32_t get_default_route_netif_index(int family) {
(void)family;
return 0;
struct sockaddr_storage dst;
memset(&dst, 0, sizeof(dst));
if (family == AF_INET) {
struct sockaddr_in* sin = (struct sockaddr_in*)&dst;
sin->sin_family = AF_INET;
inet_pton(AF_INET, "8.8.8.8", &sin->sin_addr);
} else if (family == AF_INET6) {
struct sockaddr_in6* sin6 = (struct sockaddr_in6*)&dst;
sin6->sin6_family = AF_INET6;
inet_pton(AF_INET6, "2001:4860:4860::8888", &sin6->sin6_addr);
} else {
return 0;
}
DWORD idx = 0;
if (GetBestInterfaceEx((const SOCKADDR*)&dst, &idx) != NO_ERROR) return 0;
return (uint32_t)idx;
}
#endif