summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorDavid Lönnhager <david.l@mullvad.net>2023-10-23 22:53:28 +0200
committerDavid Lönnhager <david.l@mullvad.net>2023-10-24 09:45:34 +0200
commit3aabe487c6247a053d11dac345215737cee7cfb0 (patch)
tree76cd2c3a994b418258ff154edd44863cd5da3c7d
parent51b34719239a8780ef3885017d2d450cae6da87c (diff)
downloadmullvadvpn-3aabe487c6247a053d11dac345215737cee7cfb0.tar.xz
mullvadvpn-3aabe487c6247a053d11dac345215737cee7cfb0.zip
Set up dummy interface on macOS
-rw-r--r--test/test-manager/src/vm/network/macos.rs38
1 files changed, 36 insertions, 2 deletions
diff --git a/test/test-manager/src/vm/network/macos.rs b/test/test-manager/src/vm/network/macos.rs
index bfef3a9ddb..ef815f203a 100644
--- a/test/test-manager/src/vm/network/macos.rs
+++ b/test/test-manager/src/vm/network/macos.rs
@@ -1,11 +1,11 @@
use std::net::{Ipv4Addr, SocketAddrV4};
use anyhow::{anyhow, Context, Result};
+use futures::future::{self, Either};
use tokio::{io::AsyncWriteExt, process::Command};
/// Pingable dummy LAN interface (IP)
-/// TODO: This should probably be a different host, not the gateway
-pub const DUMMY_LAN_INTERFACE_IP: Ipv4Addr = Ipv4Addr::new(192, 168, 64, 1);
+pub const DUMMY_LAN_INTERFACE_IP: Ipv4Addr = Ipv4Addr::new(192, 168, 64, 254);
// Private key of the wireguard remote peer on host.
const CUSTOM_TUN_REMOTE_PRIVKEY: &str = "gLvQuyqazziyf+pUCAFUgTnWIwn6fPE5MOReOqPEGHU=";
@@ -36,6 +36,8 @@ pub const NON_TUN_GATEWAY: Ipv4Addr = Ipv4Addr::new(192, 168, 64, 1);
/// Name of the wireguard interface on the host
pub const CUSTOM_TUN_INTERFACE_NAME: &str = "utun123";
+use std::time::Duration;
+
/// Timeout for wireguard-go to create an interface
const INTERFACE_SETUP_TIMEOUT: Duration = Duration::from_secs(5);
@@ -48,9 +50,41 @@ pub async fn setup_test_network() -> Result<()> {
.await
.context("Failed to create WireGuard interface")?;
+ // A bit of trickery to detect when the bridge is available.
+ tokio::spawn(async move {
+ for _ in 0..30 {
+ let Ok(interface) = find_vm_bridge() else {
+ tokio::time::sleep(Duration::from_secs(1)).await;
+ continue;
+ };
+ match create_dummy_interface(interface).await {
+ Ok(_) => log::debug!("Created dummy interface"),
+ Err(error) => log::error!("Failed to create dummy interface: {error}"),
+ }
+ return;
+ }
+ log::error!("Failed to create dummy interface: timed out");
+ });
+
Ok(())
}
+async fn create_dummy_interface(interface: String) -> Result<()> {
+ let mut cmd = Command::new("/usr/bin/sudo");
+ cmd.args([
+ "/sbin/ifconfig",
+ &interface,
+ "alias",
+ &DUMMY_LAN_INTERFACE_IP.to_string(),
+ ]);
+ let output = cmd.output().await.context("Create dummy interface")?;
+ if output.status.success() {
+ Ok(())
+ } else {
+ Err(anyhow!("ifconfig failed: {:?}", output.status.code()))
+ }
+}
+
/// A hack to find the Tart bridge interface using `NON_TUN_GATEWAY`.
/// It should be possible to retrieve this using the virtualization framework instead,
/// but that requires an entitlement.