ombrac_client/endpoint/socks/
mod.rs1mod v5;
2
3use std::error::Error;
4use std::net::SocketAddr;
5use std::sync::Arc;
6
7use ombrac::request::Address;
8use ombrac::Provider;
9use ombrac_macros::{error, info, try_or_return};
10use tokio::io::{AsyncRead, AsyncWrite};
11use tokio::net::{TcpListener, TcpStream};
12
13use crate::Client;
14
15pub struct Server {}
16
17pub enum Request {
18 TcpConnect(TcpStream, Address),
19}
20
21impl Server {
22 pub async fn listen<T, S>(addr: SocketAddr, ombrac: Client<T>) -> Result<(), Box<dyn Error>>
23 where
24 T: Provider<Item = S> + Send + Sync + 'static,
25 S: AsyncRead + AsyncWrite + Unpin + Send + Sync + 'static,
26 {
27 use ombrac::io::util::copy_bidirectional;
28
29 let ombrac = Arc::new(ombrac);
30 let listener = TcpListener::bind(addr).await?;
31
32 info!("SOCKS server listening on {}", listener.local_addr()?);
33
34 while let Ok((stream, _addr)) = listener.accept().await {
35 let ombrac = ombrac.clone();
36
37 tokio::spawn(async move {
38 let request = try_or_return!(Self::handler_v5(stream).await);
39
40 match request {
41 Request::TcpConnect(mut inbound, addr) => {
42 let mut retries = 0;
43 let mut outbound = loop {
44 match ombrac.tcp_connect(addr.clone()).await {
45 Ok(conn) => break conn,
46 Err(error) => {
47 if retries >= 2 {
48 error!("{error}");
49 return;
50 }
51 retries += 1;
52 }
53 }
54 };
55
56 let bytes =
57 try_or_return!(copy_bidirectional(&mut inbound, &mut outbound).await);
58
59 info!(
60 "TCP Connect {:?} Send {}, Receive {}",
61 addr, bytes.0, bytes.1
62 );
63 }
64 };
65 });
66 }
67
68 Ok(())
69 }
70}