Я пытаюсь определить, активно ли VPN-подключение в macOS из изолированного приложения, но мне трудно найти общее решение для различных служб VPN.В настоящее время я использую 2 подхода (см. Ниже), но эти методы не являются надежными для всех услуг / клиентов VPN.
Приведенные ниже методы отлично работают для клиента Cisco AnyConnect и моей службы VPN, но для других клиентов / служб VPN, таких как Visidity (и, вероятно, другие клиенты OpenVPN), эти методы просто не работают.При сравнении значений от неактивное -VPN-соединение с активное -VPN-соединение изменения не обнаруживаются ни в DNS-серверах, ни в значении первичной службы.
Я должен также упомянуть, что я видел этот пост и не думаю, что это хорошее решение для этого конкретного случая использования.Я не хочу предполагать, что для каждой VPN-службы, которая всегда будет хостом, который только доступен, когда VPN-соединение активно.
Любое руководство будет оченьоценили.Заранее спасибо.
1) Просмотр текущих DNS-серверов (взято с здесь )
- (NSString *)getDNSAddressesCSV
{
NSMutableArray *addresses = [NSMutableArray new];
union res_sockaddr_union servers[NI_MAXSERV];
int serversFound = res_9_getservers(_state, servers, NI_MAXSERV);
char hostBuffer[NI_MAXHOST];
for (int i = 0; i < serversFound; i ++)
{
union res_sockaddr_union s = servers[i];
if (s.sin.sin_len > 0)
{
if (EXIT_SUCCESS == getnameinfo((struct sockaddr *)&s.sin, // Pointer to your struct sockaddr
(socklen_t)s.sin.sin_len, // Size of this struct
(char *)&hostBuffer, // Pointer to hostname string
sizeof(hostBuffer), // Size of this string
nil, // Pointer to service name string
0,
NI_NUMERICHOST))
{ // Flags given
[addresses addObject:[NSString stringWithUTF8String:hostBuffer]];
}
}
}
return [addresses componentsJoinedByString:@","];
}
и 2) Получение текущей первичной услуги от SCDynamicStore (взято из здесь )
- (NSString *) getVPNService
{
SCDynamicStoreRef dynamicStoreDomainState = SCDynamicStoreCreate(NULL,
CFSTR("appNameGoesHere"),
NULL,
NULL);
if (dynamicStoreDomainState)
{
NSString *netIPv4Key = [NSString stringWithFormat:@"%@/%@/%@/%@",
kSCDynamicStoreDomainState,
kSCCompNetwork,
kSCCompGlobal,
kSCEntNetIPv4];
NSMutableDictionary *netIPv4Dictionary = (NSMutableDictionary *) CFBridgingRelease(SCDynamicStoreCopyValue(dynamicStoreDomainState, (CFStringRef)netIPv4Key));
if (netIPv4Dictionary )
{
NSString *primaryService = [netIPv4Dictionary objectForKey:(NSString *)kSCDynamicStorePropNetPrimaryService];
if (primaryService)
{
CFRelease(dynamicStoreDomainState);
CFRelease((__bridge CFTypeRef)(netIPv4Key));
return primaryService;
}
else
{
CFRelease(dynamicStoreDomainState);
CFRelease((__bridge CFTypeRef)(netIPv4Key));
return @"";
}
}
CFRelease(dynamicStoreDomainState);
}
return @"";
}