From 6fd5e6845f7014fd32750f34d402d05614ba6f82 Mon Sep 17 00:00:00 2001 From: Markus Pettersson Date: Thu, 17 Oct 2024 17:23:36 +0200 Subject: [PATCH] Remove `block_when_disconnected` setting on Android --- mullvad-daemon/src/lib.rs | 28 ++++++++++++++----- mullvad-daemon/src/management_interface.rs | 9 ++++++ mullvad-daemon/src/settings/mod.rs | 22 +++++++-------- .../src/types/conversions/settings.rs | 4 +++ .../src/types/conversions/states.rs | 6 ++++ mullvad-types/src/features.rs | 4 ++- mullvad-types/src/settings/mod.rs | 2 ++ mullvad-types/src/states.rs | 1 + .../tunnel_state_machine/connected_state.rs | 1 + .../tunnel_state_machine/connecting_state.rs | 1 + .../disconnected_state.rs | 9 ++++++ .../disconnecting_state.rs | 3 ++ .../src/tunnel_state_machine/error_state.rs | 1 + talpid-core/src/tunnel_state_machine/mod.rs | 9 ++++++ talpid-types/src/tunnel.rs | 4 +++ 15 files changed, 84 insertions(+), 20 deletions(-) diff --git a/mullvad-daemon/src/lib.rs b/mullvad-daemon/src/lib.rs index dd6c828802da..21dbc98c3109 100644 --- a/mullvad-daemon/src/lib.rs +++ b/mullvad-daemon/src/lib.rs @@ -249,6 +249,7 @@ pub enum DaemonCommand { /// Set the beta program setting. SetShowBetaReleases(ResponseTx<(), settings::Error>, bool), /// Set the block_when_disconnected setting. + #[cfg(not(target_os = "android"))] SetBlockWhenDisconnected(ResponseTx<(), settings::Error>, bool), /// Set the auto-connect setting. SetAutoConnect(ResponseTx<(), settings::Error>, bool), @@ -757,6 +758,7 @@ impl Daemon { let tunnel_state_machine_handle = tunnel_state_machine::spawn( tunnel_state_machine::InitialTunnelState { allow_lan: settings.allow_lan, + #[cfg(not(target_os = "android"))] block_when_disconnected: settings.block_when_disconnected, dns_config: dns::addresses_from_options(&settings.tunnel_options.dns_options), allowed_endpoint: access_mode_handler @@ -820,6 +822,7 @@ impl Daemon { let daemon = Daemon { tunnel_state: TunnelState::Disconnected { location: None, + #[cfg(not(target_os = "android"))] locked_down: settings.block_when_disconnected, }, target_state, @@ -979,10 +982,13 @@ impl Daemon { .handle_state_transition(&tunnel_state_transition); let tunnel_state = match tunnel_state_transition { + #[cfg(not(target_os = "android"))] TunnelStateTransition::Disconnected { locked_down } => TunnelState::Disconnected { location: None, locked_down, }, + #[cfg(target_os = "android")] + TunnelStateTransition::Disconnected => TunnelState::Disconnected { location: None }, TunnelStateTransition::Connecting(endpoint) => { let feature_indicators = compute_feature_indicators( &self.settings.to_settings(), @@ -1119,7 +1125,8 @@ impl Daemon { match self.tunnel_state { TunnelState::Disconnected { ref mut location, - locked_down: _, + #[cfg(not(target_os = "android"))] + locked_down: _, } => *location = Some(fetched_location), TunnelState::Connected { ref mut location, .. @@ -1243,6 +1250,7 @@ impl Daemon { SetRelaySettings(tx, update) => self.on_set_relay_settings(tx, update).await, SetAllowLan(tx, allow_lan) => self.on_set_allow_lan(tx, allow_lan).await, SetShowBetaReleases(tx, enabled) => self.on_set_show_beta_releases(tx, enabled).await, + #[cfg(not(target_os = "android"))] SetBlockWhenDisconnected(tx, block_when_disconnected) => { self.on_set_block_when_disconnected(tx, block_when_disconnected) .await @@ -2118,6 +2126,7 @@ impl Daemon { } } + #[cfg(not(target_os = "android"))] async fn on_set_block_when_disconnected( &mut self, tx: ResponseTx<(), settings::Error>, @@ -2797,11 +2806,14 @@ impl Daemon { self.send_tunnel_command(TunnelCommand::SetExcludedApps(tx, vec![])); } - let (tx, _rx) = oneshot::channel(); - self.send_tunnel_command(TunnelCommand::BlockWhenDisconnected( - self.settings.block_when_disconnected, - tx, - )); + #[cfg(not(target_os = "android"))] + { + let (tx, _rx) = oneshot::channel(); + self.send_tunnel_command(TunnelCommand::BlockWhenDisconnected( + self.settings.block_when_disconnected, + tx, + )); + } let (tx, _rx) = oneshot::channel(); self.send_tunnel_command(TunnelCommand::AllowLan(self.settings.allow_lan, tx)); @@ -2843,9 +2855,11 @@ impl Daemon { } } + #[cfg_attr(target_os = "android", allow(unused_variables))] fn on_trigger_shutdown(&mut self, user_init_shutdown: bool) { // Block all traffic before shutting down to ensure that no traffic can leak on boot or // shutdown. + #[cfg(not(target_os = "android"))] if !user_init_shutdown && (*self.target_state == TargetState::Secured || self.settings.auto_connect) { @@ -2864,7 +2878,7 @@ impl Daemon { fn on_prepare_restart(&mut self, shutdown: bool) { // TODO: See if this can be made to also shut down the daemon // without causing the service to be restarted. - + #[cfg(not(target_os = "android"))] if *self.target_state == TargetState::Secured { let (tx, _rx) = oneshot::channel(); self.send_tunnel_command(TunnelCommand::BlockWhenDisconnected(true, tx)); diff --git a/mullvad-daemon/src/management_interface.rs b/mullvad-daemon/src/management_interface.rs index eadfd9980699..23d50f24b3af 100644 --- a/mullvad-daemon/src/management_interface.rs +++ b/mullvad-daemon/src/management_interface.rs @@ -273,6 +273,7 @@ impl ManagementService for ManagementServiceImpl { Ok(Response::new(())) } + #[cfg(not(target_os = "android"))] async fn set_block_when_disconnected(&self, request: Request) -> ServiceResult<()> { let block_when_disconnected = request.into_inner(); log::debug!("set_block_when_disconnected({})", block_when_disconnected); @@ -285,6 +286,14 @@ impl ManagementService for ManagementServiceImpl { Ok(Response::new(())) } + #[cfg(target_os = "android")] + async fn set_block_when_disconnected(&self, request: Request) -> ServiceResult<()> { + let block_when_disconnected = request.into_inner(); + log::debug!("set_block_when_disconnected({})", block_when_disconnected); + log::warn!("Setting Lockdown mode on Android is not supported - this is handled by the OS, not the daemon"); + Ok(Response::new(())) + } + async fn set_auto_connect(&self, request: Request) -> ServiceResult<()> { let auto_connect = request.into_inner(); log::debug!("set_auto_connect({})", auto_connect); diff --git a/mullvad-daemon/src/settings/mod.rs b/mullvad-daemon/src/settings/mod.rs index d03f5a520435..33513d90daac 100644 --- a/mullvad-daemon/src/settings/mod.rs +++ b/mullvad-daemon/src/settings/mod.rs @@ -114,9 +114,6 @@ impl SettingsPersister { // Auto-connect is managed by Android itself. settings.auto_connect = false; - - // Lockdown mode is managed by the Android OS. - settings.block_when_disconnected = false; } if crate::version::is_beta_version() { should_save |= !settings.show_beta_releases; @@ -171,15 +168,16 @@ impl SettingsPersister { "{}", error.display_chain_with_msg("Failed to load settings. Using defaults.") ); - let mut settings = Self::default_settings(); - - // Protect the user by blocking the internet by default. Previous settings may - // not have caused the daemon to enter the non-blocking disconnected state. - // On android lockdown mode is handled by the OS so setting this to true - // has no effect. - if cfg!(not(target_os = "android")) { - settings.block_when_disconnected = true; - } + + let settings = Settings { + // Protect the user by blocking the internet by default. Previous settings may + // not have caused the daemon to enter the non-blocking disconnected state. + // On android lockdown mode is handled by the OS so setting this to true + // has no effect. + #[cfg(not(target_os = "android"))] + block_when_disconnected: true, + ..Self::default_settings() + }; LoadSettingsResult { settings, diff --git a/mullvad-management-interface/src/types/conversions/settings.rs b/mullvad-management-interface/src/types/conversions/settings.rs index d3be7f75a2dc..a1e18a031883 100644 --- a/mullvad-management-interface/src/types/conversions/settings.rs +++ b/mullvad-management-interface/src/types/conversions/settings.rs @@ -34,7 +34,10 @@ impl From<&mullvad_types::settings::Settings> for proto::Settings { )), bridge_state: Some(proto::BridgeState::from(settings.bridge_state)), allow_lan: settings.allow_lan, + #[cfg(not(target_os = "android"))] block_when_disconnected: settings.block_when_disconnected, + #[cfg(target_os = "android")] + block_when_disconnected: false, auto_connect: settings.auto_connect, tunnel_options: Some(proto::TunnelOptions::from(&settings.tunnel_options)), show_beta_releases: settings.show_beta_releases, @@ -175,6 +178,7 @@ impl TryFrom for mullvad_types::settings::Settings { )?, bridge_state, allow_lan: settings.allow_lan, + #[cfg(not(target_os = "android"))] block_when_disconnected: settings.block_when_disconnected, auto_connect: settings.auto_connect, tunnel_options: mullvad_types::settings::TunnelOptions::try_from(tunnel_options)?, diff --git a/mullvad-management-interface/src/types/conversions/states.rs b/mullvad-management-interface/src/types/conversions/states.rs index 777c661c6d3f..4eff82f3c13e 100644 --- a/mullvad-management-interface/src/types/conversions/states.rs +++ b/mullvad-management-interface/src/types/conversions/states.rs @@ -34,10 +34,14 @@ impl From for proto::TunnelState { let state = match state { MullvadTunnelState::Disconnected { location: disconnected_location, + #[cfg(not(target_os = "android"))] locked_down, } => proto::tunnel_state::State::Disconnected(proto::tunnel_state::Disconnected { disconnected_location: disconnected_location.map(proto::GeoIpLocation::from), + #[cfg(not(target_os = "android"))] locked_down, + #[cfg(target_os = "android")] + locked_down: false, }), MullvadTunnelState::Connecting { endpoint, @@ -224,6 +228,7 @@ impl TryFrom for mullvad_types::states::TunnelState { use talpid_types::{net as talpid_net, tunnel as talpid_tunnel}; let state = match state.state { + #[cfg_attr(target_os = "android", allow(unused_variables))] Some(proto::tunnel_state::State::Disconnected(proto::tunnel_state::Disconnected { disconnected_location, locked_down, @@ -231,6 +236,7 @@ impl TryFrom for mullvad_types::states::TunnelState { location: disconnected_location .map(mullvad_types::location::GeoIpLocation::try_from) .transpose()?, + #[cfg(not(target_os = "android"))] locked_down, }, Some(proto::tunnel_state::State::Connecting(proto::tunnel_state::Connecting { diff --git a/mullvad-types/src/features.rs b/mullvad-types/src/features.rs index 0e25f5a59ceb..15f64e999256 100644 --- a/mullvad-types/src/features.rs +++ b/mullvad-types/src/features.rs @@ -127,6 +127,7 @@ pub fn compute_feature_indicators( #[cfg(not(any(windows, target_os = "android", target_os = "macos")))] let split_tunneling = false; + #[cfg(not(target_os = "android"))] let lockdown_mode = settings.block_when_disconnected; let lan_sharing = settings.allow_lan; let dns_content_blockers = settings @@ -138,11 +139,12 @@ pub fn compute_feature_indicators( let generic_features = [ (split_tunneling, FeatureIndicator::SplitTunneling), - (lockdown_mode, FeatureIndicator::LockdownMode), (lan_sharing, FeatureIndicator::LanSharing), (dns_content_blockers, FeatureIndicator::DnsContentBlockers), (custom_dns, FeatureIndicator::CustomDns), (server_ip_override, FeatureIndicator::ServerIpOverride), + #[cfg(not(target_os = "android"))] + (lockdown_mode, FeatureIndicator::LockdownMode), ]; // Pick protocol-specific features and whether they are currently enabled. diff --git a/mullvad-types/src/settings/mod.rs b/mullvad-types/src/settings/mod.rs index aeff9042361c..e65c21c14857 100644 --- a/mullvad-types/src/settings/mod.rs +++ b/mullvad-types/src/settings/mod.rs @@ -83,6 +83,7 @@ pub struct Settings { pub allow_lan: bool, /// Extra level of kill switch. When this setting is on, the disconnected state will block /// the firewall to not allow any traffic in or out. + #[cfg(not(target_os = "android"))] pub block_when_disconnected: bool, /// If the daemon should connect the VPN tunnel directly on start or not. pub auto_connect: bool, @@ -200,6 +201,7 @@ impl Default for Settings { custom_lists: CustomListsSettings::default(), api_access_methods: access_method::Settings::default(), allow_lan: false, + #[cfg(not(target_os = "android"))] block_when_disconnected: false, auto_connect: false, tunnel_options: TunnelOptions::default(), diff --git a/mullvad-types/src/states.rs b/mullvad-types/src/states.rs index c3eba078e87c..e0c097236d8a 100644 --- a/mullvad-types/src/states.rs +++ b/mullvad-types/src/states.rs @@ -72,6 +72,7 @@ pub enum TunnelState { Disconnected { location: Option, /// Whether internet access is blocked due to lockdown mode + #[cfg(not(target_os = "android"))] locked_down: bool, }, Connecting { diff --git a/talpid-core/src/tunnel_state_machine/connected_state.rs b/talpid-core/src/tunnel_state_machine/connected_state.rs index 10d9ac9b723d..f76d376dc363 100644 --- a/talpid-core/src/tunnel_state_machine/connected_state.rs +++ b/talpid-core/src/tunnel_state_machine/connected_state.rs @@ -314,6 +314,7 @@ impl ConnectedState { let _ = complete_tx.send(()); consequence } + #[cfg(not(target_os = "android"))] Some(TunnelCommand::BlockWhenDisconnected(block_when_disconnected, complete_tx)) => { shared_values.block_when_disconnected = block_when_disconnected; let _ = complete_tx.send(()); diff --git a/talpid-core/src/tunnel_state_machine/connecting_state.rs b/talpid-core/src/tunnel_state_machine/connecting_state.rs index bc3840114778..a7ea244893c9 100644 --- a/talpid-core/src/tunnel_state_machine/connecting_state.rs +++ b/talpid-core/src/tunnel_state_machine/connecting_state.rs @@ -473,6 +473,7 @@ impl ConnectingState { let _ = complete_tx.send(()); consequence } + #[cfg(not(target_os = "android"))] Some(TunnelCommand::BlockWhenDisconnected(block_when_disconnected, complete_tx)) => { shared_values.block_when_disconnected = block_when_disconnected; let _ = complete_tx.send(()); diff --git a/talpid-core/src/tunnel_state_machine/disconnected_state.rs b/talpid-core/src/tunnel_state_machine/disconnected_state.rs index baf60121034a..c0b608792e8d 100644 --- a/talpid-core/src/tunnel_state_machine/disconnected_state.rs +++ b/talpid-core/src/tunnel_state_machine/disconnected_state.rs @@ -2,6 +2,7 @@ use super::{ ConnectingState, EventConsequence, SharedTunnelStateValues, TunnelCommand, TunnelCommandReceiver, TunnelState, TunnelStateTransition, }; +#[cfg(not(target_os = "android"))] use crate::firewall::FirewallPolicy; #[cfg(target_os = "macos")] use crate::{dns, tunnel_state_machine::ErrorState}; @@ -55,6 +56,7 @@ impl DisconnectedState { Self::construct_state_transition(shared_values) } + #[cfg_attr(target_os = "android", allow(unused_variables))] fn construct_state_transition( shared_values: &mut SharedTunnelStateValues, ) -> (Box, TunnelStateTransition) { @@ -63,11 +65,13 @@ impl DisconnectedState { TunnelStateTransition::Disconnected { // Being disconnected and having lockdown mode enabled implies that your internet // access is locked down + #[cfg(not(target_os = "android"))] locked_down: shared_values.block_when_disconnected, }, ) } + #[cfg(not(target_os = "android"))] fn set_firewall_policy( shared_values: &mut SharedTunnelStateValues, should_reset_firewall: bool, @@ -98,6 +102,10 @@ impl DisconnectedState { } } + /// TODO: Document why this fn looks like this. + #[cfg(target_os = "android")] + fn set_firewall_policy(_: &mut SharedTunnelStateValues, _: bool) {} + #[cfg(windows)] fn register_split_tunnel_addresses( shared_values: &mut SharedTunnelStateValues, @@ -173,6 +181,7 @@ impl TunnelState for DisconnectedState { let _ = complete_tx.send(()); SameState(self) } + #[cfg(not(target_os = "android"))] Some(TunnelCommand::BlockWhenDisconnected(block_when_disconnected, complete_tx)) => { if shared_values.block_when_disconnected != block_when_disconnected { shared_values.block_when_disconnected = block_when_disconnected; diff --git a/talpid-core/src/tunnel_state_machine/disconnecting_state.rs b/talpid-core/src/tunnel_state_machine/disconnecting_state.rs index 4a108788e151..b8d43ac7e9a9 100644 --- a/talpid-core/src/tunnel_state_machine/disconnecting_state.rs +++ b/talpid-core/src/tunnel_state_machine/disconnecting_state.rs @@ -55,6 +55,7 @@ impl DisconnectingState { let _ = complete_tx.send(()); AfterDisconnect::Nothing } + #[cfg(not(target_os = "android"))] Some(TunnelCommand::BlockWhenDisconnected( block_when_disconnected, complete_tx, @@ -109,6 +110,7 @@ impl DisconnectingState { let _ = complete_tx.send(()); AfterDisconnect::Block(reason) } + #[cfg(not(target_os = "android"))] Some(TunnelCommand::BlockWhenDisconnected( block_when_disconnected, complete_tx, @@ -167,6 +169,7 @@ impl DisconnectingState { let _ = complete_tx.send(()); AfterDisconnect::Reconnect(retry_attempt) } + #[cfg(not(target_os = "android"))] Some(TunnelCommand::BlockWhenDisconnected( block_when_disconnected, complete_tx, diff --git a/talpid-core/src/tunnel_state_machine/error_state.rs b/talpid-core/src/tunnel_state_machine/error_state.rs index eeaf48956b8c..1700779f46f3 100644 --- a/talpid-core/src/tunnel_state_machine/error_state.rs +++ b/talpid-core/src/tunnel_state_machine/error_state.rs @@ -178,6 +178,7 @@ impl TunnelState for ErrorState { let _ = complete_tx.send(()); consequence } + #[cfg(not(target_os = "android"))] Some(TunnelCommand::BlockWhenDisconnected(block_when_disconnected, complete_tx)) => { shared_values.block_when_disconnected = block_when_disconnected; let _ = complete_tx.send(()); diff --git a/talpid-core/src/tunnel_state_machine/mod.rs b/talpid-core/src/tunnel_state_machine/mod.rs index e0ef07850d6d..8839f165cf4f 100644 --- a/talpid-core/src/tunnel_state_machine/mod.rs +++ b/talpid-core/src/tunnel_state_machine/mod.rs @@ -90,6 +90,7 @@ pub struct InitialTunnelState { /// Whether to allow LAN traffic when not in the (non-blocking) disconnected state. pub allow_lan: bool, /// Block traffic unless connected to the VPN. + #[cfg(not(target_os = "android"))] pub block_when_disconnected: bool, /// DNS configuration to use pub dns_config: DnsConfig, @@ -190,6 +191,7 @@ pub enum TunnelCommand { /// Set DNS configuration to use. Dns(crate::dns::DnsConfig, oneshot::Sender<()>), /// Enable or disable the block_when_disconnected feature. + #[cfg(not(target_os = "android"))] BlockWhenDisconnected(bool, oneshot::Sender<()>), /// Notify the state machine of the connectivity of the device. Connectivity(Connectivity), @@ -292,12 +294,17 @@ impl TunnelStateMachine { split_tunnel::SplitTunnel::spawn(args.command_tx.clone(), route_manager.clone()); let fw_args = FirewallArguments { + #[cfg(not(target_os = "android"))] initial_state: if args.settings.block_when_disconnected || !args.settings.reset_firewall { InitialFirewallState::Blocked(args.settings.allowed_endpoint.clone()) } else { InitialFirewallState::None }, + // TODO: This really has no effect. In all honesty, we should probably remove the + // firewall stub completely. + #[cfg(target_os = "android")] + initial_state: InitialFirewallState::Blocked(args.settings.allowed_endpoint.clone()), allow_lan: args.settings.allow_lan, #[cfg(target_os = "linux")] fwmark: args.linux_ids.fwmark, @@ -371,6 +378,7 @@ impl TunnelStateMachine { route_manager, _offline_monitor: offline_monitor, allow_lan: args.settings.allow_lan, + #[cfg(not(target_os = "android"))] block_when_disconnected: args.settings.block_when_disconnected, connectivity, dns_config: args.settings.dns_config, @@ -463,6 +471,7 @@ struct SharedTunnelStateValues { /// Should LAN access be allowed outside the tunnel. allow_lan: bool, /// Should network access be allowed when in the disconnected state. + #[cfg(not(target_os = "android"))] block_when_disconnected: bool, /// True when the computer is known to be offline. connectivity: Connectivity, diff --git a/talpid-types/src/tunnel.rs b/talpid-types/src/tunnel.rs index eb8d155e35bf..598501929427 100644 --- a/talpid-types/src/tunnel.rs +++ b/talpid-types/src/tunnel.rs @@ -9,10 +9,14 @@ use std::net::IpAddr; #[derive(Clone, Debug)] pub enum TunnelStateTransition { /// No connection is established and network is unsecured. + #[cfg(not(target_os = "android"))] Disconnected { /// Whether internet access is blocked due to lockdown mode locked_down: bool, }, + #[cfg(target_os = "android")] + /// No connection is established and network is unsecured. + Disconnected, /// Network is secured but tunnel is still connecting. Connecting(TunnelEndpoint), /// Tunnel is connected.