summaryrefslogtreecommitdiffhomepage
path: root/mullvad-ios/src/tunnel_obfuscator_proxy/mod.rs
blob: 2bf8397b7f6569bd6971f1d05270cc8ed6095c8e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
use std::{
    io,
    net::{Ipv4Addr, SocketAddr},
};
use tokio::task::JoinHandle;
use tunnel_obfuscation::{
    Settings as ObfuscationSettings, create_obfuscator, quic, shadowsocks, udp2tcp,
};

mod ffi;

use crate::mullvad_ios_runtime;

pub struct TunnelObfuscatorRuntime {
    settings: ObfuscationSettings,
}

impl TunnelObfuscatorRuntime {
    pub fn new_udp2tcp(peer: SocketAddr) -> Self {
        let settings = ObfuscationSettings::Udp2Tcp(udp2tcp::Settings { peer });
        Self { settings }
    }

    pub fn new_shadowsocks(peer: SocketAddr) -> Self {
        let settings = ObfuscationSettings::Shadowsocks(shadowsocks::Settings {
            shadowsocks_endpoint: peer,
            wireguard_endpoint: SocketAddr::from((Ipv4Addr::LOCALHOST, 51820)),
        });
        Self { settings }
    }

    pub fn new_quic(peer: SocketAddr, hostname: String, token: String) -> Self {
        let wireguard_endpoint = SocketAddr::from((Ipv4Addr::LOCALHOST, 51820));
        let token: quic::AuthToken = token.parse().unwrap();
        let quic = quic::Settings::new(peer, hostname, token, wireguard_endpoint);
        let settings = ObfuscationSettings::Quic(quic);
        Self { settings }
    }

    pub fn run(self) -> io::Result<(SocketAddr, TunnelObfuscatorHandle)> {
        let runtime = mullvad_ios_runtime().map_err(io::Error::other)?;

        let obfuscator = runtime.block_on(async move {
            create_obfuscator(&self.settings)
                .await
                .map_err(io::Error::other)
        })?;

        let endpoint = obfuscator.endpoint();
        let join_handle = runtime.spawn(async move {
            let _ = obfuscator.run().await;
        });

        Ok((
            endpoint,
            TunnelObfuscatorHandle {
                obfuscator_abort_handle: join_handle,
            },
        ))
    }
}

pub struct TunnelObfuscatorHandle {
    obfuscator_abort_handle: JoinHandle<()>,
}

impl TunnelObfuscatorHandle {
    pub fn stop(self) {
        self.obfuscator_abort_handle.abort();
    }
}