From de1f6739215b8afb1dba4d98fee1a06663f20786 Mon Sep 17 00:00:00 2001 From: Salem Yaslem Date: Thu, 15 Aug 2024 00:36:20 +0300 Subject: [PATCH] replace tls_parser by rustls to prepare for QUIC support --- Cargo.lock | 441 ++++++++++++++++++++++++++++++------------ Cargo.toml | 4 +- src/services/http.rs | 24 +-- src/services/https.rs | 82 ++++---- 4 files changed, 373 insertions(+), 178 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index ca2659c..11f2f46 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -83,7 +83,7 @@ checksum = "6e0c28dcc82d7c8ead5cb13beb15405b57b8546e93215673ff8ca0349a028107" dependencies = [ "proc-macro2", "quote", - "syn 2.0.69", + "syn", ] [[package]] @@ -92,6 +92,33 @@ version = "1.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0c4b4d0bd25bd0b74681c0ad21497610ce1b7c91b1022cd21c80c6fbdd9476b0" +[[package]] +name = "aws-lc-rs" +version = "1.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4ae74d9bd0a7530e8afd1770739ad34b36838829d6ad61818f9230f683f5ad77" +dependencies = [ + "aws-lc-sys", + "mirai-annotations", + "paste", + "zeroize", +] + +[[package]] +name = "aws-lc-sys" +version = "0.20.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0f0e249228c6ad2d240c2dc94b714d711629d52bad946075d8e9b2f5391f0703" +dependencies = [ + "bindgen", + "cc", + "cmake", + "dunce", + "fs_extra", + "libc", + "paste", +] + [[package]] name = "backtrace" version = "0.3.73" @@ -107,6 +134,35 @@ dependencies = [ "rustc-demangle", ] +[[package]] +name = "bindgen" +version = "0.69.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a00dc851838a2120612785d195287475a3ac45514741da670b735818822129a0" +dependencies = [ + "bitflags", + "cexpr", + "clang-sys", + "itertools", + "lazy_static", + "lazycell", + "log", + "prettyplease", + "proc-macro2", + "quote", + "regex", + "rustc-hash", + "shlex", + "syn", + "which", +] + +[[package]] +name = "bitflags" +version = "2.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b048fb63fd8b5923fc5aa7b340d8e156aec7ec02f0c78fa8a6ddc2613f6f71de" + [[package]] name = "bridge46" version = "0.1.0" @@ -115,7 +171,7 @@ dependencies = [ "hickory-client", "hickory-proto", "log", - "tls-parser", + "rustls", "tokio", ] @@ -130,6 +186,20 @@ name = "cc" version = "1.0.105" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5208975e568d83b6b05cc0a063c8e7e9acc2b43bee6da15616a5b73e109d7437" +dependencies = [ + "jobserver", + "libc", + "once_cell", +] + +[[package]] +name = "cexpr" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6fac387a98bb7c37292057cffc56d62ecb629900026402633ae9160df93a8766" +dependencies = [ + "nom", +] [[package]] name = "cfg-if" @@ -137,6 +207,26 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" +[[package]] +name = "clang-sys" +version = "1.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b023947811758c97c59bf9d1c188fd619ad4718dcaa767947df1cadb14f39f4" +dependencies = [ + "glob", + "libc", + "libloading", +] + +[[package]] +name = "cmake" +version = "0.1.50" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a31c789563b815f77f4250caee12365734369f942439b7defd71e18a48197130" +dependencies = [ + "cc", +] + [[package]] name = "colorchoice" version = "1.0.1" @@ -149,6 +239,18 @@ version = "2.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e8566979429cf69b49a5c740c60791108e86440e8be149bbea4fe54d2c32d6e2" +[[package]] +name = "dunce" +version = "1.0.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "92773504d58c093f6de2459af4af33faa518c13451eb8f2b5698ed3d36e7c813" + +[[package]] +name = "either" +version = "1.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60b1af1c220855b6ceac025d3f6ecdd2b7c4894bfe9cd9bda4fbb4bc7c0d4cf0" + [[package]] name = "endian-type" version = "0.1.2" @@ -164,16 +266,7 @@ dependencies = [ "heck", "proc-macro2", "quote", - "syn 2.0.69", -] - -[[package]] -name = "enum_primitive" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "be4551092f4d519593039259a9ed8daedf0da12e5109c5280338073eaeb81180" -dependencies = [ - "num-traits 0.1.43", + "syn", ] [[package]] @@ -199,6 +292,16 @@ dependencies = [ "log", ] +[[package]] +name = "errno" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "534c5cf6194dfab3db3242765c03bbe257cf92f22b38f6bc0c58d59108a820ba" +dependencies = [ + "libc", + "windows-sys 0.52.0", +] + [[package]] name = "form_urlencoded" version = "1.2.1" @@ -208,6 +311,12 @@ dependencies = [ "percent-encoding", ] +[[package]] +name = "fs_extra" +version = "1.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "42703706b716c37f96a77aea830392ad231f44c9e9a67872fa5548707e11b11c" + [[package]] name = "futures-channel" version = "0.3.30" @@ -265,6 +374,12 @@ version = "0.29.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "40ecd4077b5ae9fd2e9e169b102c6c330d0605168eb0e8bf79952b256dbefffd" +[[package]] +name = "glob" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b" + [[package]] name = "heck" version = "0.4.1" @@ -320,6 +435,15 @@ dependencies = [ "url", ] +[[package]] +name = "home" +version = "0.5.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3d1354bf6b7235cb4a0576c2619fd4ed18183f689b12b006a0ee7329eeff9a5" +dependencies = [ + "windows-sys 0.52.0", +] + [[package]] name = "humantime" version = "2.1.0" @@ -358,12 +482,58 @@ version = "1.70.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f8478577c03552c21db0e2724ffb8986a5ce7af88107e6be5d2ee6e158c12800" +[[package]] +name = "itertools" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba291022dbbd398a455acf126c1e341954079855bc60dfdda641363bd6922569" +dependencies = [ + "either", +] + +[[package]] +name = "jobserver" +version = "0.1.32" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "48d1dbcbbeb6a7fec7e059840aa538bd62aaccf972c7346c4d9d2059312853d0" +dependencies = [ + "libc", +] + +[[package]] +name = "lazy_static" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbd2bcb4c963f2ddae06a2efc7e9f3591312473c50c6685e1f298068316e66fe" + +[[package]] +name = "lazycell" +version = "1.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "830d08ce1d1d941e6b30645f1a0eb5643013d835ce3779a5fc208261dbe10f55" + [[package]] name = "libc" version = "0.2.155" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "97b3888a4aecf77e811145cadf6eef5901f4782c53886191b2f693f24761847c" +[[package]] +name = "libloading" +version = "0.8.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4979f22fdb869068da03c9f7528f8297c6fd2606bc3a4affe42e6a823fdb8da4" +dependencies = [ + "cfg-if", + "windows-targets 0.52.6", +] + +[[package]] +name = "linux-raw-sys" +version = "0.4.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "78b3ae25bc7c8c38cec158d1f2757ee79e9b3740fbc7ccf0e59e4b08d793fa89" + [[package]] name = "log" version = "0.4.22" @@ -402,6 +572,12 @@ dependencies = [ "windows-sys 0.48.0", ] +[[package]] +name = "mirai-annotations" +version = "1.12.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c9be0862c1b3f26a88803c4a49de6889c10e608b3ee9344e6ef5b45fb37ad3d1" + [[package]] name = "nibble_vec" version = "0.1.0" @@ -421,46 +597,6 @@ dependencies = [ "minimal-lexical", ] -[[package]] -name = "nom-derive" -version = "0.10.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ff943d68b88d0b87a6e0d58615e8fa07f9fd5a1319fa0a72efc1f62275c79a7" -dependencies = [ - "nom", - "nom-derive-impl", - "rustversion", -] - -[[package]] -name = "nom-derive-impl" -version = "0.10.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cd0b9a93a84b0d3ec3e70e02d332dc33ac6dfac9cde63e17fcb77172dededa62" -dependencies = [ - "proc-macro2", - "quote", - "syn 1.0.109", -] - -[[package]] -name = "num-traits" -version = "0.1.43" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "92e5113e9fd4cc14ded8e499429f396a20f98c772a47cc8622a736e1ec843c31" -dependencies = [ - "num-traits 0.2.19", -] - -[[package]] -name = "num-traits" -version = "0.2.19" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "071dfc062690e90b734c0b2273ce72ad0ffa95f0c74596bc250dcfd960262841" -dependencies = [ - "autocfg", -] - [[package]] name = "num_cpus" version = "1.16.0" @@ -487,48 +623,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3fdb12b2476b595f9358c5161aa467c2438859caa136dec86c26fdd2efe17b92" [[package]] -name = "percent-encoding" -version = "2.3.1" +name = "paste" +version = "1.0.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" +checksum = "57c0d7b74b563b49d38dae00a0c37d4d6de9b432382b2892f0574ddcae73fd0a" [[package]] -name = "phf" -version = "0.10.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fabbf1ead8a5bcbc20f5f8b939ee3f5b0f6f281b6ad3468b84656b658b455259" -dependencies = [ - "phf_shared", -] - -[[package]] -name = "phf_codegen" -version = "0.10.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4fb1c3a8bc4dd4e5cfce29b44ffc14bedd2ee294559a294e2a4d4c9e9a6a13cd" -dependencies = [ - "phf_generator", - "phf_shared", -] - -[[package]] -name = "phf_generator" -version = "0.10.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5d5285893bb5eb82e6aaf5d59ee909a06a16737a8970984dd7746ba9283498d6" -dependencies = [ - "phf_shared", - "rand", -] - -[[package]] -name = "phf_shared" -version = "0.10.0" +name = "percent-encoding" +version = "2.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6796ad771acdc0123d2a88dc428b5e38ef24456743ddb1744ed628f9815c096" -dependencies = [ - "siphasher", -] +checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" [[package]] name = "pin-project-lite" @@ -548,6 +652,16 @@ version = "0.2.17" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de" +[[package]] +name = "prettyplease" +version = "0.2.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5f12335488a2f3b0a83b14edad48dca9879ce89b2edd10e80237e4e852dd645e" +dependencies = [ + "proc-macro2", + "syn", +] + [[package]] name = "proc-macro2" version = "1.0.86" @@ -635,6 +749,21 @@ version = "0.8.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7a66a03ae7c801facd77a29370b4faec201768915ac14a721ba36f20bc9c209b" +[[package]] +name = "ring" +version = "0.17.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c17fa4cb658e3583423e915b9f3acc01cceaee1860e33d59ebae66adc3a2dc0d" +dependencies = [ + "cc", + "cfg-if", + "getrandom", + "libc", + "spin", + "untrusted", + "windows-sys 0.52.0", +] + [[package]] name = "rustc-demangle" version = "0.1.24" @@ -642,25 +771,62 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "719b953e2095829ee67db738b3bfa9fa368c94900df327b3f07fe6e794d2fe1f" [[package]] -name = "rusticata-macros" -version = "4.1.0" +name = "rustc-hash" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "08d43f7aa6b08d49f382cde6a7982047c3426db949b1424bc4b7ec9ae12c6ce2" + +[[package]] +name = "rustix" +version = "0.38.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "faf0c4a6ece9950b9abdb62b1cfcf2a68b3b67a10ba445b3bb85be2a293d0632" +checksum = "70dc5ec042f7a43c4a73241207cecc9873a06d45debb38b329f8541d85c2730f" dependencies = [ - "nom", + "bitflags", + "errno", + "libc", + "linux-raw-sys", + "windows-sys 0.52.0", ] [[package]] -name = "rustversion" -version = "1.0.17" +name = "rustls" +version = "0.23.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "955d28af4278de8121b7ebeb796b6a45735dc01436d898801014aced2773a3d6" +checksum = "c58f8c84392efc0a126acce10fa59ff7b3d2ac06ab451a33f2741989b806b044" +dependencies = [ + "aws-lc-rs", + "log", + "once_cell", + "rustls-pki-types", + "rustls-webpki", + "subtle", + "zeroize", +] [[package]] -name = "siphasher" -version = "0.3.11" +name = "rustls-pki-types" +version = "1.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "38b58827f4464d87d377d175e90bf58eb00fd8716ff0a62f80356b5e61555d0d" +checksum = "fc0a2ce646f8655401bb81e7927b812614bd5d91dbc968696be50603510fcaf0" + +[[package]] +name = "rustls-webpki" +version = "0.102.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8e6b52d4fda176fd835fdc55a835d4a89b8499cad995885a21149d5ad62f852e" +dependencies = [ + "aws-lc-rs", + "ring", + "rustls-pki-types", + "untrusted", +] + +[[package]] +name = "shlex" +version = "1.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0fda2ff0d084019ba4d7c6f371c95d8fd75ce3524c3cb8fb653a3023f6323e64" [[package]] name = "slab" @@ -688,15 +854,16 @@ dependencies = [ ] [[package]] -name = "syn" -version = "1.0.109" +name = "spin" +version = "0.9.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237" -dependencies = [ - "proc-macro2", - "quote", - "unicode-ident", -] +checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67" + +[[package]] +name = "subtle" +version = "2.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "13c2bddecc57b384dee18652358fb23172facb8a2c51ccc10d74c157bdea3292" [[package]] name = "syn" @@ -726,7 +893,7 @@ checksum = "46c3384250002a6d5af4d114f2845d37b57521033f30d5c3f46c4d70e1197533" dependencies = [ "proc-macro2", "quote", - "syn 2.0.69", + "syn", ] [[package]] @@ -744,20 +911,6 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" -[[package]] -name = "tls-parser" -version = "0.11.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "409206e2de64edbf7ea99a44ac31680daf9ef1a57895fb3c5bd738a903691be0" -dependencies = [ - "enum_primitive", - "nom", - "nom-derive", - "phf", - "phf_codegen", - "rusticata-macros", -] - [[package]] name = "tokio" version = "1.38.0" @@ -783,7 +936,7 @@ checksum = "5f5ae998a069d4b5aba8ee9dad856af7d520c3699e6159b185c2acd48155d39a" dependencies = [ "proc-macro2", "quote", - "syn 2.0.69", + "syn", ] [[package]] @@ -805,7 +958,7 @@ checksum = "34704c8d6ebcbc939824180af020566b01a7c01f80641264eba0999f6c2b6be7" dependencies = [ "proc-macro2", "quote", - "syn 2.0.69", + "syn", ] [[package]] @@ -838,6 +991,12 @@ dependencies = [ "tinyvec", ] +[[package]] +name = "untrusted" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8ecb6da28b8a351d773b68d5825ac39017e680750f980f3a1a85cd8dd28a47c1" + [[package]] name = "url" version = "2.5.2" @@ -861,6 +1020,18 @@ version = "0.11.0+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" +[[package]] +name = "which" +version = "4.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "87ba24419a2078cd2b0f2ede2691b6c66d8e47836da3b6db8265ebad47afbfc7" +dependencies = [ + "either", + "home", + "once_cell", + "rustix", +] + [[package]] name = "windows-sys" version = "0.48.0" @@ -999,3 +1170,23 @@ name = "windows_x86_64_msvc" version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec" + +[[package]] +name = "zeroize" +version = "1.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ced3678a2879b30306d323f4542626697a464a97c0a07c9aebf7ebca65cd4dde" +dependencies = [ + "zeroize_derive", +] + +[[package]] +name = "zeroize_derive" +version = "1.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ce36e65b0d2999d2aafac989fb249189a141aee1f53c612c1f37d72631959f69" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] diff --git a/Cargo.toml b/Cargo.toml index c1bfad7..e8aafa6 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -5,12 +5,12 @@ version = "0.1.0" edition = "2021" [dependencies] -tls-parser = "0.11.0" tokio = { version = "1.38", features = ["rt","net", "macros"] } hickory-client = "0.24.1" hickory-proto = "0.24.1" env_logger = "0.11.3" log = "0.4.22" +rustls = "0.23.12" [profile.release] -opt-level = 3 \ No newline at end of file +opt-level = 3 diff --git a/src/services/http.rs b/src/services/http.rs index 51ee9bb..68a919b 100644 --- a/src/services/http.rs +++ b/src/services/http.rs @@ -7,17 +7,16 @@ async fn handle_connection(client: TcpStream, port: u16) -> Option<()> { let src_addr = client.peer_addr().ok()?; // read request header and get the host - let mut buf: [u8; 256] = [0; 256]; - client.peek(&mut buf).await.expect("peek failed"); - let mut request = String::from_utf8_lossy(&buf); + let mut buf: Vec = vec![0; 256]; + let mut last_buf_read_len = client.peek(&mut buf).await.expect("peek failed"); + + let request_buf = buf.clone(); + let mut request = String::from_utf8_lossy(&request_buf); let mut host: Option = request .lines() .find(|line| line.to_lowercase().starts_with("host: ")) .map(|line| String::from(line.to_lowercase().trim_start_matches("host: ").trim())); - let mut fragment_buffer: [u8; 256] = [0; 256]; - let mut fragments: Vec = buf.to_vec(); - loop { if let Some(host_string) = host.clone() { let resolved_address: Result = @@ -53,7 +52,7 @@ async fn handle_connection(client: TcpStream, port: u16) -> Option<()> { tokio::spawn(async move { io::copy(&mut oread, &mut ewrite).await }); return Some(()); } else { - if fragments.len() > 4096 || (fragments.len() > 0 && fragment_buffer.len() == 0) { + if buf.len() > 4096 || last_buf_read_len == 0 { log::error!( "HTTP {} Failed to resolve AAAA record for {}: {}", src_addr, @@ -63,14 +62,15 @@ async fn handle_connection(client: TcpStream, port: u16) -> Option<()> { break; } - fragment_buffer = [0; 256]; + let buf_new_len = buf.len() + 256; + buf = vec![0; buf_new_len]; - client - .peek(&mut fragment_buffer) + last_buf_read_len = client + .peek(&mut buf) .await .expect("peek failed"); - fragments = [fragments, fragment_buffer.to_vec()].concat(); - request = String::from_utf8_lossy(fragments.as_slice()); + + request = String::from_utf8_lossy(&buf); host = request .lines() diff --git a/src/services/https.rs b/src/services/https.rs index 60b4cd3..12fb518 100644 --- a/src/services/https.rs +++ b/src/services/https.rs @@ -1,50 +1,54 @@ -use tls_parser::{parse_tls_extensions, parse_tls_plaintext}; use tokio::io; +use rustls::server::{Accepted, Acceptor}; use tokio::net::{TcpListener, TcpStream}; - use crate::utils::{get_bind_address, resolve_addr}; -pub fn get_sni_from_packet(packet: &[u8]) -> Option { - let parse_tls_plaintext = parse_tls_plaintext(&packet); - if parse_tls_plaintext.is_err() { - log::error!("Error parsing TLS packet: {:?}", parse_tls_plaintext.err()); - return None; - } +pub async fn get_sni_from_packet(packet: Vec) -> Option { + let mut acceptor: Acceptor = Acceptor::default(); + let cursor: &mut dyn std::io::Read = &mut &packet[..]; - let tls_message = &parse_tls_plaintext.ok()?.1.msg[0]; - if let tls_parser::TlsMessage::Handshake(handshake) = tls_message { - if let tls_parser::TlsMessageHandshake::ClientHello(client_hello) = handshake { - let extensions: &[u8] = client_hello.ext?; - let parsed_extensions = parse_tls_extensions(extensions).ok()?; - for extension in parsed_extensions.1 { - if let tls_parser::TlsExtension::SNI(sni) = extension { - return match String::from_utf8(sni[0].1.to_vec()) { - Ok(sni) => Some(sni), - Err(err) => { - log::error!("Error parsing SNI: {:?}", err); - None - } - }; - } + match &acceptor.read_tls(cursor) { + Ok(size) => { + if *size == 0 { + log::error!("No data read from TLS packet"); + return None; } } + Err(err) => { + log::error!("Error reading TLS packet: {:?}", err); + return None; + } + }; + + let accepted: Accepted = match acceptor.accept() { + Ok(Some(acceptor)) => acceptor, + Err(err) => { + log::error!("Error processing new packets: {:?}", err); + return None; + } + _ => { + log::error!("Packet not enough to process SNI (will increase buffer size by 256 bytes)"); + return None; + } + }; + return match accepted.client_hello().server_name() { + Some(sni) => Some(sni.to_string()), + None => { + log::error!("No SNI found in packet"); + None + } } - None } pub async fn handle_connection(client: TcpStream, port: u16) -> Option<()> { let src_addr = client.peer_addr().ok()?; - let mut buf = [0; 256]; - client.peek(&mut buf).await.expect("peek failed"); - - let mut fragment_buffer: [u8; 256] = [0; 256]; - let mut fragments: Vec = vec![]; - - let mut sni_buffer: Vec = buf.to_vec(); + let mut buf: Vec = vec![0; 256]; + let mut last_buf_read_len = client.peek(&mut buf).await.expect("peek failed"); loop { - if let Some(sni_string) = get_sni_from_packet(&sni_buffer) { + println!("buf length: {}", buf.len()); + if let Some(sni_string) = get_sni_from_packet(buf.clone()).await { let resolved_address: Result = resolve_addr(&sni_string).await; if let Ok(ip) = resolved_address { @@ -87,20 +91,20 @@ pub async fn handle_connection(client: TcpStream, port: u16) -> Option<()> { break; } } else { - if fragments.len() > 4096 || (fragments.len() > 0 && fragment_buffer.len() == 0) { + if buf.len() > 4096 || last_buf_read_len == 0 { log::error!("HTTPS {} No SNI", src_addr); break; } - fragment_buffer = [0; 256]; + let buf_new_len = buf.len() + 256; + + buf = vec![0; buf_new_len]; + buf.resize(buf_new_len, 0); - client - .peek(&mut fragment_buffer) + last_buf_read_len = client + .peek(&mut buf[..buf_new_len]) .await .expect("peek failed"); - fragments = [fragments, fragment_buffer.to_vec()].concat(); - - sni_buffer = [&buf, fragments.as_slice()].concat(); continue; } }