summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--mullvad-daemon/src/lib.rs40
-rw-r--r--mullvad-daemon/src/management_interface.rs60
-rw-r--r--mullvad-ipc-client/src/lib.rs13
3 files changed, 113 insertions, 0 deletions
diff --git a/mullvad-daemon/src/lib.rs b/mullvad-daemon/src/lib.rs
index cd9ddd39a1..783954a3b2 100644
--- a/mullvad-daemon/src/lib.rs
+++ b/mullvad-daemon/src/lib.rs
@@ -57,6 +57,7 @@ use std::{
};
use talpid_core::{
mpsc::Sender,
+ split,
tunnel_state_machine::{self, TunnelCommand, TunnelParametersGenerator},
};
#[cfg(target_os = "android")]
@@ -212,6 +213,15 @@ pub enum DaemonCommand {
/// Remove settings and clear the cache
#[cfg(not(target_os = "android"))]
FactoryReset(oneshot::Sender<()>),
+ /// Request list of processes excluded from the tunnel
+ #[cfg(unix)]
+ GetSplitTunnelProcesses(oneshot::Sender<Vec<i32>>),
+ /// Exclude traffic of a process (PID) from the tunnel
+ #[cfg(unix)]
+ AddSplitTunnelProcess(oneshot::Sender<()>, i32),
+ /// Remove process (PID) from list of processes excluded from the tunnel
+ #[cfg(unix)]
+ RemoveSplitTunnelProcess(oneshot::Sender<()>, i32),
/// Makes the daemon exit the main loop and quit.
Shutdown,
/// Saves the target tunnel state and enters a blocking state. The state is restored
@@ -992,6 +1002,12 @@ where
GetCurrentVersion(tx) => self.on_get_current_version(tx),
#[cfg(not(target_os = "android"))]
FactoryReset(tx) => self.on_factory_reset(tx),
+ #[cfg(unix)]
+ GetSplitTunnelProcesses(tx) => self.on_get_split_tunnel_processes(tx),
+ #[cfg(unix)]
+ AddSplitTunnelProcess(tx, pid) => self.on_add_split_tunnel_process(tx, pid),
+ #[cfg(unix)]
+ RemoveSplitTunnelProcess(tx, pid) => self.on_remove_split_tunnel_process(tx, pid),
Shutdown => self.trigger_shutdown_event(),
PrepareRestart => self.on_prepare_restart(),
}
@@ -1355,6 +1371,30 @@ where
}));
}
+ #[cfg(unix)]
+ fn on_get_split_tunnel_processes(&mut self, tx: oneshot::Sender<Vec<i32>>) {
+ match split::list_pids() {
+ Ok(pids) => Self::oneshot_send(tx, pids, "get_split_tunnel_processes response"),
+ Err(e) => error!("{}", e.display_chain_with_msg("Unable to obtain PIDs")),
+ }
+ }
+
+ #[cfg(unix)]
+ fn on_add_split_tunnel_process(&mut self, tx: oneshot::Sender<()>, pid: i32) {
+ match split::add_pid(pid) {
+ Ok(()) => Self::oneshot_send(tx, (), "add_split_tunnel_process response"),
+ Err(e) => error!("{}", e.display_chain_with_msg("Unable to add PID")),
+ }
+ }
+
+ #[cfg(unix)]
+ fn on_remove_split_tunnel_process(&mut self, tx: oneshot::Sender<()>, pid: i32) {
+ match split::remove_pid(pid) {
+ Ok(()) => Self::oneshot_send(tx, (), "remove_split_tunnel_process response"),
+ Err(e) => error!("{}", e.display_chain_with_msg("Unable to remove PID")),
+ }
+ }
+
fn on_update_relay_settings(&mut self, tx: oneshot::Sender<()>, update: RelaySettingsUpdate) {
let save_result = self.settings.update_relay_settings(update);
match save_result {
diff --git a/mullvad-daemon/src/management_interface.rs b/mullvad-daemon/src/management_interface.rs
index 84c5db8570..2839fc3d57 100644
--- a/mullvad-daemon/src/management_interface.rs
+++ b/mullvad-daemon/src/management_interface.rs
@@ -178,6 +178,18 @@ build_rpc_trait! {
#[rpc(meta, name = "factory_reset")]
fn factory_reset(&self, Self::Metadata) -> BoxFuture<(), Error>;
+ /// Retrieve PIDs to exclude from the tunnel
+ #[rpc(meta, name = "get_split_tunnel_processes")]
+ fn get_split_tunnel_processes(&self, Self::Metadata) -> BoxFuture<Vec<i32>, Error>;
+
+ /// Add a process to exclude from the tunnel
+ #[rpc(meta, name = "add_split_tunnel_process")]
+ fn add_split_tunnel_process(&self, Self::Metadata, i32) -> BoxFuture<(), Error>;
+
+ /// Remove a process excluded from the tunnel
+ #[rpc(meta, name = "remove_split_tunnel_process")]
+ fn remove_split_tunnel_process(&self, Self::Metadata, i32) -> BoxFuture<(), Error>;
+
#[pubsub(name = "daemon_event")] {
/// Subscribes to events from the daemon.
#[rpc(name = "daemon_event_subscribe")]
@@ -739,6 +751,54 @@ impl ManagementInterfaceApi for ManagementInterface {
}
}
+ fn get_split_tunnel_processes(&self, _: Self::Metadata) -> BoxFuture<Vec<i32>, Error> {
+ #[cfg(unix)]
+ {
+ log::debug!("get_split_tunnel_processes");
+ let (tx, rx) = sync::oneshot::channel();
+ let future = self
+ .send_command_to_daemon(DaemonCommand::GetSplitTunnelProcesses(tx))
+ .and_then(|_| rx.map_err(|_| Error::internal_error()));
+ Box::new(future)
+ }
+ #[cfg(not(unix))]
+ {
+ Box::new(future::ok(Vec::with_capacity(0)))
+ }
+ }
+
+ fn add_split_tunnel_process(&self, _: Self::Metadata, pid: i32) -> BoxFuture<(), Error> {
+ #[cfg(unix)]
+ {
+ log::debug!("add_split_tunnel_process");
+ let (tx, rx) = sync::oneshot::channel();
+ let future = self
+ .send_command_to_daemon(DaemonCommand::AddSplitTunnelProcess(tx, pid))
+ .and_then(|_| rx.map_err(|_| Error::internal_error()));
+ Box::new(future)
+ }
+ #[cfg(not(unix))]
+ {
+ Box::new(future::ok(()))
+ }
+ }
+
+ fn remove_split_tunnel_process(&self, _: Self::Metadata, pid: i32) -> BoxFuture<(), Error> {
+ #[cfg(unix)]
+ {
+ log::debug!("remove_split_tunnel_process");
+ let (tx, rx) = sync::oneshot::channel();
+ let future = self
+ .send_command_to_daemon(DaemonCommand::RemoveSplitTunnelProcess(tx, pid))
+ .and_then(|_| rx.map_err(|_| Error::internal_error()));
+ Box::new(future)
+ }
+ #[cfg(not(unix))]
+ {
+ Box::new(future::ok(()))
+ }
+ }
+
fn daemon_event_subscribe(
&self,
diff --git a/mullvad-ipc-client/src/lib.rs b/mullvad-ipc-client/src/lib.rs
index 511f68ae3e..47a26c9b75 100644
--- a/mullvad-ipc-client/src/lib.rs
+++ b/mullvad-ipc-client/src/lib.rs
@@ -235,6 +235,19 @@ impl DaemonRpcClient {
self.call("update_relay_settings", &[update])
}
+ pub fn get_split_tunnel_processes(&mut self) -> Result<Vec<i32>> {
+ self.call("get_split_tunnel_processes", &NO_ARGS)
+ }
+
+ pub fn add_split_tunnel_process(&mut self, pid: i32) -> Result<()> {
+ self.call("add_split_tunnel_process", &[pid])
+ }
+
+ pub fn remove_split_tunnel_process(&mut self, pid: i32) -> Result<()> {
+ self.call("remove_split_tunnel_process", &[pid])
+ }
+
+
pub fn call<A, O>(&mut self, method: &'static str, args: &A) -> Result<O>
where
A: Serialize + Send + 'static,