diff --git a/.vscode/settings.json b/.vscode/settings.json index 0cff074..3df3c9a 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -9,6 +9,7 @@ "consts", "devicename", "distro", + "gpclient", "gpcommon", "gpconf", "gpgui", @@ -25,6 +26,7 @@ "prelogon", "prelogonuserauthcookie", "repr", + "reqwest", "rustc", "servercert", "shlex", diff --git a/Cargo.lock b/Cargo.lock index bad8cc0..4ba25d7 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -88,6 +88,54 @@ dependencies = [ "libc", ] +[[package]] +name = "anstream" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b1f58811cfac344940f1a400b6e6231ce35171f614f26439e80f8c1465c5cc0c" +dependencies = [ + "anstyle", + "anstyle-parse", + "anstyle-query", + "anstyle-wincon", + "colorchoice", + "utf8parse", +] + +[[package]] +name = "anstyle" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "15c4c2c83f81532e5845a733998b6971faca23490340a418e9b72a3ec9de12ea" + +[[package]] +name = "anstyle-parse" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "938874ff5980b03a87c5524b3ae5b59cf99b1d6bc836848df7bc5ada9643c333" +dependencies = [ + "utf8parse", +] + +[[package]] +name = "anstyle-query" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5ca11d4be1bab0c8bc8734a9aa7bf4ee8316d462a08c6ac5052f888fef5b494b" +dependencies = [ + "windows-sys 0.48.0", +] + +[[package]] +name = "anstyle-wincon" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "58f54d10c6dfa51283a066ceab3ec1ab78d13fae00aa49243a45e4571fb79dfd" +dependencies = [ + "anstyle", + "windows-sys 0.48.0", +] + [[package]] name = "anyhow" version = "1.0.69" @@ -552,6 +600,33 @@ dependencies = [ "inout", ] +[[package]] +name = "clap" +version = "4.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6a13b88d2c62ff462f88e4a121f17a82c1af05693a2f192b5c38d14de73c19f6" +dependencies = [ + "clap_builder", +] + +[[package]] +name = "clap_builder" +version = "4.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2bb9faaa7c2ef94b2743a21f5a29e6f0010dff4caa69ac8e9d6cf8b6fa74da08" +dependencies = [ + "anstream", + "anstyle", + "clap_lex", + "strsim", +] + +[[package]] +name = "clap_lex" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cd7cc57abe963c6d3b9d8be5b06ba7c8957a930305ca90304f24ef040aa6f961" + [[package]] name = "cocoa" version = "0.24.1" @@ -589,6 +664,12 @@ version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3d7b894f5411737b7867f4827955924d7c254fc9f4d91a6aad6b097804b1018b" +[[package]] +name = "colorchoice" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "acbf1af155f9b9ef647e42cdc158db4b64a1b61f743629225fde6f3e0be2a7c7" + [[package]] name = "colored" version = "1.9.3" @@ -912,7 +993,7 @@ dependencies = [ "rustc_version 0.4.0", "toml 0.7.3", "vswhom", - "winreg", + "winreg 0.11.0", ] [[package]] @@ -1058,9 +1139,9 @@ checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b" [[package]] name = "form_urlencoded" -version = "1.1.0" +version = "1.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a9c384f161156f5260c24a097c56119f9be8c798586aecc13afbcbe7b7e26bf8" +checksum = "a62bc1cf6f830c2ec14a513a9fb124d0a213a629668a4186f329db21fe045652" dependencies = [ "percent-encoding", ] @@ -1421,8 +1502,12 @@ dependencies = [ name = "gpclient" version = "0.1.0" dependencies = [ + "anyhow", + "clap", "gpcommon", + "reqwest", "tokio", + "url", ] [[package]] @@ -1514,6 +1599,25 @@ dependencies = [ "syn 1.0.107", ] +[[package]] +name = "h2" +version = "0.3.21" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "91fc23aa11be92976ef4729127f1a74adf36d8436f7816b185d18df956790833" +dependencies = [ + "bytes", + "fnv", + "futures-core", + "futures-sink", + "futures-util", + "http", + "indexmap", + "slab", + "tokio", + "tokio-util", + "tracing", +] + [[package]] name = "hashbrown" version = "0.12.3" @@ -1608,18 +1712,78 @@ dependencies = [ "itoa 1.0.5", ] +[[package]] +name = "http-body" +version = "0.4.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d5f38f16d184e36f2408a55281cd658ecbd3ca05cce6d6510a176eca393e26d1" +dependencies = [ + "bytes", + "http", + "pin-project-lite", +] + [[package]] name = "http-range" version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "21dec9db110f5f872ed9699c3ecf50cf16f423502706ba5c72462e28d3157573" +[[package]] +name = "httparse" +version = "1.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d897f394bad6a705d5f4104762e116a75639e470d80901eed05a860a95cb1904" + +[[package]] +name = "httpdate" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df3b46402a9d5adb4c86a0cf463f42e19994e3ee891101b1841f30a545cb49a9" + [[package]] name = "humantime" version = "2.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4" +[[package]] +name = "hyper" +version = "0.14.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ffb1cfd654a8219eaef89881fdb3bb3b1cdc5fa75ded05d6933b2b382e395468" +dependencies = [ + "bytes", + "futures-channel", + "futures-core", + "futures-util", + "h2", + "http", + "http-body", + "httparse", + "httpdate", + "itoa 1.0.5", + "pin-project-lite", + "socket2", + "tokio", + "tower-service", + "tracing", + "want", +] + +[[package]] +name = "hyper-tls" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d6183ddfa99b85da61a140bea0efc93fdf56ceaa041b37d553518030827f9905" +dependencies = [ + "bytes", + "hyper", + "native-tls", + "tokio", + "tokio-native-tls", +] + [[package]] name = "iana-time-zone" version = "0.1.56" @@ -1661,9 +1825,9 @@ checksum = "b9e0384b61958566e926dc50660321d12159025e767c18e043daf26b70104c39" [[package]] name = "idna" -version = "0.3.0" +version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e14ddfc70884202db2244c223200c204c2bda1bc6e0998d11b5e024d657209e6" +checksum = "7d20d6b07bfbc108882d88ed8e37d39636dcc260e15e30c45e6ba089610b917c" dependencies = [ "unicode-bidi", "unicode-normalization", @@ -1749,6 +1913,12 @@ dependencies = [ "windows-sys 0.48.0", ] +[[package]] +name = "ipnet" +version = "2.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "28b29a3cd74f0f4598934efe3aeba42bae0eb4680554128851ebbecb02af14e6" + [[package]] name = "is_executable" version = "1.0.1" @@ -2012,6 +2182,12 @@ dependencies = [ "autocfg", ] +[[package]] +name = "mime" +version = "0.3.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6877bb514081ee2a7ff5ef9de3281f14a4dd4bceac4c09388074a6b5df8a139a" + [[package]] name = "miniz_oxide" version = "0.6.2" @@ -2414,9 +2590,9 @@ checksum = "8835116a5c179084a830efb3adc117ab007512b535bc1a21c991d3b32a6b44dd" [[package]] name = "percent-encoding" -version = "2.2.0" +version = "2.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "478c572c3d73181ff3c2539045f6eb99e5491218eae919370993b890cdbdd98e" +checksum = "9b2a4787296e9989611394c33f193f676704af1686e70b8f8033ab5ba9a35a94" [[package]] name = "pest" @@ -2822,6 +2998,43 @@ version = "0.6.28" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "456c603be3e8d448b072f410900c09faf164fbce2d480456f50eea6e25f9c848" +[[package]] +name = "reqwest" +version = "0.11.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3e9ad3fe7488d7e34558a2033d45a0c90b72d97b4f80705666fea71472e2e6a1" +dependencies = [ + "base64 0.21.0", + "bytes", + "encoding_rs", + "futures-core", + "futures-util", + "h2", + "http", + "http-body", + "hyper", + "hyper-tls", + "ipnet", + "js-sys", + "log", + "mime", + "native-tls", + "once_cell", + "percent-encoding", + "pin-project-lite", + "serde", + "serde_json", + "serde_urlencoded", + "tokio", + "tokio-native-tls", + "tower-service", + "url", + "wasm-bindgen", + "wasm-bindgen-futures", + "web-sys", + "winreg 0.50.0", +] + [[package]] name = "ring" version = "0.16.20" @@ -3771,6 +3984,16 @@ dependencies = [ "syn 1.0.107", ] +[[package]] +name = "tokio-native-tls" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbae76ab933c85776efabc971569dd6119c580d8f5d448769dec1764bf796ef2" +dependencies = [ + "native-tls", + "tokio", +] + [[package]] name = "tokio-util" version = "0.7.8" @@ -3782,6 +4005,7 @@ dependencies = [ "futures-sink", "pin-project-lite", "tokio", + "tracing", ] [[package]] @@ -3827,6 +4051,12 @@ dependencies = [ "winnow", ] +[[package]] +name = "tower-service" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6bc1c9ce2b5135ac7f93c72918fc37feb872bdc6a5533a8b85eb4b86bfdae52" + [[package]] name = "tracing" version = "0.1.37" @@ -3898,6 +4128,12 @@ dependencies = [ "serde_json", ] +[[package]] +name = "try-lock" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" + [[package]] name = "typenum" version = "1.16.0" @@ -3965,9 +4201,9 @@ checksum = "a156c684c91ea7d62626509bce3cb4e1d9ed5c4d978f7b4352658f96a4c26b4a" [[package]] name = "url" -version = "2.3.1" +version = "2.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d68c799ae75762b8c3fe375feb6600ef5602c883c5d21eb51c09f22b83c4643" +checksum = "143b538f18257fac9cad154828a57c6bf5157e1aa604d4816b5995bf6de87ae5" dependencies = [ "form_urlencoded", "idna", @@ -3987,6 +4223,12 @@ version = "0.1.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5190c9442dcdaf0ddd50f37420417d219ae5261bbf5db120d0f9bab996c9cba1" +[[package]] +name = "utf8parse" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a" + [[package]] name = "uuid" version = "1.3.0" @@ -4094,6 +4336,15 @@ dependencies = [ "winapi-util", ] +[[package]] +name = "want" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfa7760aed19e106de2c7c0b581b509f2f25d3dacaf737cb82ac61bc6d760b0e" +dependencies = [ + "try-lock", +] + [[package]] name = "wasi" version = "0.9.0+wasi-snapshot-preview1" @@ -4131,6 +4382,18 @@ dependencies = [ "wasm-bindgen-shared", ] +[[package]] +name = "wasm-bindgen-futures" +version = "0.4.34" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f219e0d211ba40266969f6dbdd90636da12f75bee4fc9d6c23d1260dadb51454" +dependencies = [ + "cfg-if", + "js-sys", + "wasm-bindgen", + "web-sys", +] + [[package]] name = "wasm-bindgen-macro" version = "0.2.84" @@ -4556,6 +4819,16 @@ dependencies = [ "winapi", ] +[[package]] +name = "winreg" +version = "0.50.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "524e57b2c537c0f9b1e69f1965311ec12182b4122e45035b1508cd24d2adadb1" +dependencies = [ + "cfg-if", + "windows-sys 0.48.0", +] + [[package]] name = "wry" version = "0.24.3" diff --git a/Cargo.toml b/Cargo.toml index d988db9..ae4a4e7 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,12 +1,32 @@ [workspace] -members = [ - "gpcommon", - "gpclient", - "gpservice", - "gpgui/src-tauri" -] +members = ["gpcommon", "gpclient", "gpservice", "gpgui/src-tauri"] + +[workspace.package] +version = "0.1.0" [profile.release] strip = true opt-level = "z" + +[workspace.dependencies] +anyhow = "1.0" +async-trait = "0.1" +bytes = "1.0" +clap = "4.4.2" +configparser = "3.0" +data-encoding = "2.3" +is_executable = "1.0" +lexopt = "0.3.0" +log = "0.4" +regex = "1" +reqwest = "0.11" +ring = "0.16" +serde = { version = "1.0", features = ["derive"] } +serde_json = "1.0" +shlex = "1.0" +tempfile = "3.8" +thiserror = "1.0" +tokio = { version = "1.0", features = ["full"] } +tokio-util = "0.7" +url = "2.4" diff --git a/gpclient/Cargo.toml b/gpclient/Cargo.toml index 9419e0a..480561a 100644 --- a/gpclient/Cargo.toml +++ b/gpclient/Cargo.toml @@ -1,10 +1,14 @@ [package] name = "gpclient" -version = "0.1.0" +version.workspace = true edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html [dependencies] gpcommon = { path = "../gpcommon" } -tokio = { version = "1.0", features = ["full"] } +anyhow.workspace = true +clap.workspace = true +reqwest.workspace = true +tokio.workspace = true +url.workspace = true diff --git a/gpclient/src/main.rs b/gpclient/src/main.rs index 36e2077..94815ae 100644 --- a/gpclient/src/main.rs +++ b/gpclient/src/main.rs @@ -1,5 +1,24 @@ +use clap::{arg, Command, Parser}; use gpcommon::{Client, SOCKET_PATH}; +use portal::Portal; use tokio::{io::AsyncReadExt, net::UnixStream, sync::mpsc}; +use url::Url; + +mod portal; + +fn cli() -> Command { + Command::new("gpclient") + .about("GlobalProtect-openconnect CLI client") + .subcommand_required(true) + .arg_required_else_help(true) + .subcommand( + Command::new("connect") + .about("Connect to GlobalProtect VPN") + .arg(arg!( "The GlobalProtect server")) + .arg_required_else_help(true), + ) + .subcommand(Command::new("disconnect").about("Disconnect from GlobalProtect VPN")) +} #[tokio::main] async fn main() { @@ -14,12 +33,33 @@ async fn main() { // println!("http_port: {http_port}"); // println!("aes_key: {aes_key:?}"); - let (output_tx, mut output_rx) = mpsc::channel::(32); - let client = Client::default(); + // let (output_tx, mut output_rx) = mpsc::channel::(32); + // let client = Client::default(); - tokio::select! { - _ = client.run() => { - println!("Client finished"); + // tokio::select! { + // _ = client.run() => { + // println!("Client finished"); + // } + // } + + let matches = cli().get_matches(); + match matches.subcommand() { + Some(("connect", sub_m)) => { + let server = sub_m.get_one::("SERVER").expect("Missing server"); + let server = if server.starts_with("https://") || server.starts_with("http://") { + server.to_string() + } else { + format!("https://{}", server) + }; + + let url = Url::parse(&server).expect("Invalid server URL"); + let host = url.host_str().expect("Invalid server URL"); + + let portal = Portal::new(host); } + Some(("disconnect", _)) => { + println!("Disconnecting..."); + } + _ => unreachable!(), } } diff --git a/gpclient/src/portal.rs b/gpclient/src/portal.rs new file mode 100644 index 0000000..92605ff --- /dev/null +++ b/gpclient/src/portal.rs @@ -0,0 +1,46 @@ +use anyhow::Result; + +pub(crate) struct Portal<'a> { + address: &'a str, +} + +struct SamlPrelogin {} + +struct StandardPrelogin {} + +enum Prelogin { + Saml(SamlPrelogin), + Standard(StandardPrelogin), +} + +impl<'a> Portal<'a> { + pub fn new(address: &'a str) -> Self { + Self { address } + } + + // Preform the Portal prelogin + async fn prelogin(&self) -> Result { + let prelogin_url = format!("https://{}/global-protect/prelogin.esp", self.address); + let res_xml = reqwest::get(prelogin_url).await?.text().await?; + println!("{}", res_xml); + + Ok(Prelogin::Standard(StandardPrelogin {})) + } +} + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn test_new() { + let portal = Portal::new("vpn.example.com"); + assert_eq!(portal.address, "vpn.example.com"); + } + + #[test] + fn test_prelogin() { + let portal = Portal::new("vpn.example.com"); + let prelogin = portal.prelogin(); + } +} diff --git a/gpcommon/Cargo.toml b/gpcommon/Cargo.toml index 946dab6..9580e0f 100644 --- a/gpcommon/Cargo.toml +++ b/gpcommon/Cargo.toml @@ -1,27 +1,27 @@ [package] name = "gpcommon" -version = "0.1.0" +version.workspace = true edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html [dependencies] -tokio = { version = "1.14", features = ["full"] } -tokio-util = "0.7" -thiserror = "1.0" -serde = { version = "1.0", features = ["derive"] } -bytes = "1.0" -serde_json = "1.0" -async-trait = "0.1" -ring = "0.16" -data-encoding = "2.3" -log = "0.4" -is_executable = "1.0" -configparser = "3.0" -shlex = "1.0" -anyhow = "1.0" -tempfile = "3.8" -lexopt = "0.3.0" +anyhow.workspace = true +async-trait.workspace = true +bytes.workspace = true +configparser.workspace = true +data-encoding.workspace = true +is_executable.workspace = true +lexopt.workspace = true +log.workspace = true +ring.workspace = true +serde_json.workspace = true +serde.workspace = true +shlex.workspace = true +tempfile.workspace = true +thiserror.workspace = true +tokio-util.workspace = true +tokio.workspace = true [build-dependencies] cc = "1.0" diff --git a/gpgui/src-tauri/Cargo.toml b/gpgui/src-tauri/Cargo.toml index 5057aa4..5a56ce9 100644 --- a/gpgui/src-tauri/Cargo.toml +++ b/gpgui/src-tauri/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "app" -version = "0.1.0" +version.workspace = true description = "A Tauri App" authors = ["you"] license = "" @@ -20,21 +20,21 @@ tauri = { version = "1.3", features = ["fs-write-file", "http-all", "os-all", "p tauri-plugin-log = { git = "https://github.com/tauri-apps/plugins-workspace", branch = "v1", features = [ "colored", ] } -serde_json = "1.0" -serde = { version = "1.0", features = ["derive"] } -log = "0.4" -webkit2gtk = "0.18.2" -regex = "1" -url = "2.3" -tokio = { version = "1.14", features = ["full"] } -veil = "0.1.6" -whoami = "1.4.1" -tauri-plugin-store = { git = "https://github.com/tauri-apps/plugins-workspace", branch = "v1" } -openssl = "0.10" -keyring = "2" aes-gcm = { version = "0.10", features = ["std"] } +anyhow.workspace = true hex = "0.4" -anyhow = "1.0" +keyring = "2" +log.workspace = true +openssl = "0.10" +regex.workspace = true +serde_json.workspace = true +serde.workspace = true +tauri-plugin-store = { git = "https://github.com/tauri-apps/plugins-workspace", branch = "v1" } +tokio.workspace = true +url.workspace = true +veil = "0.1.6" +webkit2gtk = "0.18.2" +whoami = "1.4.1" [features] # by default Tauri runs in production mode diff --git a/gpservice/Cargo.toml b/gpservice/Cargo.toml index 80831c5..8d49a36 100644 --- a/gpservice/Cargo.toml +++ b/gpservice/Cargo.toml @@ -1,19 +1,14 @@ [package] name = "gpservice" -version = "0.1.0" +version.workspace = true edition = "2021" -# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html - [dependencies] gpcommon = { path = "../gpcommon" } -tokio = { version = "1", features = ["full"] } -log = "0.4" +tokio.workspace = true +log.workspace = true fern = "0.6" humantime = "2.1" -# warp = "0.3" -# aes-gcm = "0.10" -# procfs = "0.15" [build-dependencies] gpcommon = { path = "../gpcommon" }