diff options
| author | David Lönnhager <david.l@mullvad.net> | 2022-06-23 17:32:05 +0200 |
|---|---|---|
| committer | David Lönnhager <david.l@mullvad.net> | 2022-07-20 15:03:50 +0200 |
| commit | 2958c5dc60cd34dc283854bb8bc6124a09f73f9b (patch) | |
| tree | 265efe91f3064bd75cc51e0de9b2d3bfca8bf486 /talpid-core/src | |
| parent | 678733d46c6ebcee7ce1df376fb1e2e9c4238c07 (diff) | |
| download | mullvadvpn-2958c5dc60cd34dc283854bb8bc6124a09f73f9b.tar.xz mullvadvpn-2958c5dc60cd34dc283854bb8bc6124a09f73f9b.zip | |
Remove WinNet_InterfaceLuidToIpAddress
Diffstat (limited to 'talpid-core/src')
| -rw-r--r-- | talpid-core/src/split_tunnel/windows/mod.rs | 65 | ||||
| -rw-r--r-- | talpid-core/src/windows/mod.rs | 15 | ||||
| -rw-r--r-- | talpid-core/src/winnet.rs | 29 |
3 files changed, 62 insertions, 47 deletions
diff --git a/talpid-core/src/split_tunnel/windows/mod.rs b/talpid-core/src/split_tunnel/windows/mod.rs index d177b4f198..24679aa934 100644 --- a/talpid-core/src/split_tunnel/windows/mod.rs +++ b/talpid-core/src/split_tunnel/windows/mod.rs @@ -6,10 +6,12 @@ mod windows; use crate::{ tunnel::TunnelMetadata, tunnel_state_machine::TunnelCommand, - windows::window::{PowerManagementEvent, PowerManagementListener}, - winnet::{ - self, get_best_default_route, interface_luid_to_ip, WinNetAddrFamily, WinNetCallbackHandle, + windows::{ + get_ip_address_for_interface, + window::{PowerManagementEvent, PowerManagementListener}, + AddressFamily, }, + winnet::{self, get_best_default_route, WinNetAddrFamily, WinNetCallbackHandle}, }; use futures::channel::{mpsc, oneshot}; use std::{ @@ -27,7 +29,7 @@ use std::{ time::Duration, }; use talpid_types::{tunnel::ErrorStateCause, ErrorExt}; -use winapi::shared::winerror::ERROR_OPERATION_ABORTED; +use winapi::shared::{ifdef::NET_LUID, winerror::ERROR_OPERATION_ABORTED}; const DRIVER_EVENT_BUFFER_SIZE: usize = 2048; const RESERVED_IP_V4: Ipv4Addr = Ipv4Addr::new(192, 0, 2, 123); @@ -66,7 +68,7 @@ pub enum Error { /// Failed to obtain an IP address given a network interface LUID #[error(display = "Failed to obtain IP address for interface LUID")] - LuidToIp(#[error(source)] winnet::Error), + LuidToIp(#[error(source)] crate::windows::Error), /// Failed to set up callback for monitoring default route changes #[error(display = "Failed to register default route change callback")] @@ -761,11 +763,19 @@ impl SplitTunnelDefaultRouteChangeHandlerContext { let internet_ipv4 = get_best_default_route(WinNetAddrFamily::IPV4) .map_err(Error::ObtainDefaultRoute)? .map(|route| { - interface_luid_to_ip(WinNetAddrFamily::IPV4, route.interface_luid).map(|ip| { - ip.or_else(|| { + get_ip_address_for_interface( + AddressFamily::Ipv4, + NET_LUID { + Value: route.interface_luid, + }, + ) + .map(|ip| match ip { + Some(IpAddr::V4(addr)) => Some(addr), + Some(_) => unreachable!("wrong address family (expected IPv4)"), + None => { log::warn!("No IPv4 address was found for the default route interface"); None - }) + } }) }) .transpose() @@ -774,23 +784,28 @@ impl SplitTunnelDefaultRouteChangeHandlerContext { let internet_ipv6 = get_best_default_route(WinNetAddrFamily::IPV6) .map_err(Error::ObtainDefaultRoute)? .map(|route| { - interface_luid_to_ip(WinNetAddrFamily::IPV6, route.interface_luid).map(|ip| { - ip.or_else(|| { + get_ip_address_for_interface( + AddressFamily::Ipv6, + NET_LUID { + Value: route.interface_luid, + }, + ) + .map(|ip| match ip { + Some(IpAddr::V6(addr)) => Some(addr), + Some(_) => unreachable!("wrong address family (expected IPv6)"), + None => { log::warn!("No IPv6 address was found for the default route interface"); None - }) + } }) }) .transpose() .map_err(Error::LuidToIp)? .flatten(); - self.addresses.internet_ipv4 = internet_ipv4 - .map(|addr| Ipv4Addr::try_from(addr).map_err(|_| Error::IpParseError)) - .transpose()?; - self.addresses.internet_ipv6 = internet_ipv6 - .map(|addr| Ipv6Addr::try_from(addr).map_err(|_| Error::IpParseError)) - .transpose()?; + self.addresses.internet_ipv4 = internet_ipv4; + self.addresses.internet_ipv6 = internet_ipv6; + Ok(()) } } @@ -814,9 +829,16 @@ unsafe extern "system" fn split_tunnel_default_route_change_handler( } }; + let translated_family = winnet_to_talpid_family(address_family); + let result = match event_type { DefaultRouteChanged | DefaultRouteUpdatedDetails => { - match interface_luid_to_ip(address_family, default_route.interface_luid) { + match get_ip_address_for_interface( + translated_family, + NET_LUID { + Value: default_route.interface_luid, + }, + ) { Ok(Some(ip)) => match IpAddr::from(ip) { IpAddr::V4(addr) => ctx.addresses.internet_ipv4 = Some(addr), IpAddr::V6(addr) => ctx.addresses.internet_ipv6 = Some(addr), @@ -868,3 +890,10 @@ unsafe extern "system" fn split_tunnel_default_route_change_handler( maybe_send(TunnelCommand::Block(ErrorStateCause::SplitTunnelError)); } } + +fn winnet_to_talpid_family(address_family: WinNetAddrFamily) -> AddressFamily { + match address_family { + WinNetAddrFamily::IPV4 => AddressFamily::Ipv4, + WinNetAddrFamily::IPV6 => AddressFamily::Ipv6, + } +} diff --git a/talpid-core/src/windows/mod.rs b/talpid-core/src/windows/mod.rs index ae15c9cb9c..342e939cdb 100644 --- a/talpid-core/src/windows/mod.rs +++ b/talpid-core/src/windows/mod.rs @@ -342,6 +342,21 @@ pub async fn wait_for_addresses(luid: NET_LUID) -> Result<()> { rx.await.map_err(|_| Error::UnicastSenderDropped)? } +/// Returns the first unicast IP address for the given interface. +pub fn get_ip_address_for_interface( + family: AddressFamily, + luid: NET_LUID, +) -> Result<Option<IpAddr>> { + match get_unicast_table(Some(family)) + .map_err(Error::ObtainUnicastAddress)? + .into_iter() + .find(|row| row.InterfaceLuid.Value == luid.Value) + { + Some(row) => Ok(Some(try_socketaddr_from_inet_sockaddr(row.Address)?.ip())), + None => Ok(None), + } +} + /// Returns the unicast IP address table. If `family` is `None`, then addresses for all families are /// returned. pub fn get_unicast_table( diff --git a/talpid-core/src/winnet.rs b/talpid-core/src/winnet.rs index 50ae88b6da..ff5988a37c 100644 --- a/talpid-core/src/winnet.rs +++ b/talpid-core/src/winnet.rs @@ -347,26 +347,6 @@ pub fn get_best_default_route( } } -pub fn interface_luid_to_ip( - family: WinNetAddrFamily, - luid: u64, -) -> Result<Option<WinNetIp>, Error> { - let mut ip = WinNetIp::default(); - match unsafe { - WinNet_InterfaceLuidToIpAddress( - family, - luid, - &mut ip as *mut _, - Some(log_sink), - logging_context(), - ) - } { - WinNetStatus::Success => Ok(Some(ip)), - WinNetStatus::NotFound => Ok(None), - WinNetStatus::Failure => Err(Error::GetIpAddressFromLuid), - } -} - pub fn add_device_ip_addresses(iface: &str, addresses: &[IpAddr]) -> bool { let raw_iface = WideCString::from_str(iface) .expect("Failed to convert UTF-8 string to null terminated UCS string") @@ -436,15 +416,6 @@ mod api { sink_context: *const u8, ) -> WinNetStatus; - #[link_name = "WinNet_InterfaceLuidToIpAddress"] - pub fn WinNet_InterfaceLuidToIpAddress( - family: super::WinNetAddrFamily, - luid: u64, - ip: *mut super::WinNetIp, - sink: Option<LogSink>, - sink_context: *const u8, - ) -> WinNetStatus; - #[link_name = "WinNet_RegisterDefaultRouteChangedCallback"] pub fn WinNet_RegisterDefaultRouteChangedCallback( callback: Option<DefaultRouteChangedCallback>, |
