241 lines
5.3 KiB
Rust
241 lines
5.3 KiB
Rust
use std::str::FromStr;
|
|
|
|
use fltk::{
|
|
app,
|
|
button::Button,
|
|
enums::CallbackTrigger,
|
|
frame::Frame,
|
|
input::*,
|
|
prelude::*,
|
|
window::Window
|
|
};
|
|
use structopt::StructOpt;
|
|
|
|
use quic_demo::{
|
|
client_proxy::*,
|
|
prelude::*,
|
|
protocol::PeerId,
|
|
};
|
|
|
|
#[derive (Debug, StructOpt)]
|
|
struct Opt {
|
|
#[structopt (long)]
|
|
window_title: Option <String>,
|
|
#[structopt (long)]
|
|
relay_addr: Option <String>,
|
|
#[structopt (long)]
|
|
client_id: Option <PeerId>,
|
|
}
|
|
|
|
#[derive (Clone, Copy)]
|
|
enum Message {
|
|
OpenPort (usize),
|
|
ClosePort (usize),
|
|
}
|
|
|
|
fn main () -> anyhow::Result <()> {
|
|
tracing_subscriber::fmt::init ();
|
|
let rt = tokio::runtime::Runtime::new ()?;
|
|
|
|
let opt = Opt::from_args ();
|
|
|
|
let (fltk_tx, fltk_rx) = app::channel::<Message> ();
|
|
|
|
let app = app::App::default ();
|
|
let window_title = opt.window_title.clone ().unwrap_or_else (|| "PTTH client proxy".to_string ());
|
|
let mut wind = Window::new (100, 100, 800, 600, None)
|
|
.with_label (&window_title);
|
|
|
|
let margin = 10;
|
|
let h = 30;
|
|
let mut x = margin;
|
|
let mut y = margin;
|
|
|
|
let mut frame_status = Frame::new (x, y, 800 - 20, h, "Forwarding 0 ports");
|
|
|
|
y += h + margin;
|
|
x = margin;
|
|
|
|
{
|
|
let w = 80;
|
|
Frame::new (x, y, w, h, "Local port");
|
|
x += w + margin;
|
|
|
|
let w = 120;
|
|
Frame::new (x, y, w, h, "Server ID");
|
|
x += w + margin;
|
|
|
|
let w = 80;
|
|
Frame::new (x, y, w, h, "Server port");
|
|
// x += w + margin;
|
|
}
|
|
|
|
y += h + margin;
|
|
x = margin;
|
|
|
|
let gui_port_0 = GuiPort::new (fltk_tx, &mut x, y, 0);
|
|
y += h + margin;
|
|
x = margin;
|
|
|
|
let gui_port_1 = GuiPort::new (fltk_tx, &mut x, y, 1);
|
|
y += h + margin;
|
|
x = margin;
|
|
|
|
let gui_port_2 = GuiPort::new (fltk_tx, &mut x, y, 2);
|
|
// y += h + margin;
|
|
// x = margin;
|
|
|
|
let mut gui_ports = vec! [
|
|
gui_port_0,
|
|
gui_port_1,
|
|
gui_port_2,
|
|
];
|
|
|
|
let mut forwarding_instances = vec! [
|
|
None,
|
|
None,
|
|
None,
|
|
];
|
|
|
|
// y += h + margin;
|
|
|
|
wind.end ();
|
|
wind.show ();
|
|
|
|
let connection_p2_p3 = rt.block_on (async move {
|
|
let server_cert = tokio::fs::read ("quic_server.crt").await?;
|
|
let relay_addr = opt.relay_addr.unwrap_or_else (|| String::from ("127.0.0.1:30380")).parse ()?;
|
|
let endpoint = make_client_endpoint ("0.0.0.0:0".parse ()?, &[&server_cert])?;
|
|
|
|
trace! ("Connecting to relay server");
|
|
|
|
let client_id = opt.client_id.unwrap_or_else (|| "bogus_client".to_string ());
|
|
|
|
let quinn::NewConnection {
|
|
connection,
|
|
..
|
|
} = protocol::p2_connect_to_p3 (&endpoint, &relay_addr, &client_id).await?;
|
|
|
|
Ok::<_, anyhow::Error> (connection)
|
|
})?;
|
|
|
|
while app.wait () {
|
|
match fltk_rx.recv () {
|
|
Some (Message::OpenPort (port_idx)) => {
|
|
if let Ok (params) = gui_ports [port_idx].get_params () {
|
|
let connection_p2_p3 = connection_p2_p3.clone ();
|
|
|
|
let _guard = rt.enter ();
|
|
forwarding_instances [port_idx].replace (ForwardingInstance::new (
|
|
connection_p2_p3,
|
|
params,
|
|
));
|
|
|
|
gui_ports [port_idx].set_forwarding (true);
|
|
|
|
frame_status.set_label ("Forwarding 1 port");
|
|
}
|
|
},
|
|
Some (Message::ClosePort (port_idx)) => {
|
|
if let Some (old_instance) = forwarding_instances [port_idx].take () {
|
|
rt.block_on (old_instance.close ())?;
|
|
}
|
|
|
|
gui_ports [port_idx].set_forwarding (false);
|
|
frame_status.set_label ("Forwarding 0 ports");
|
|
},
|
|
None => (),
|
|
}
|
|
}
|
|
|
|
Ok (())
|
|
}
|
|
|
|
fn set_active <W: WidgetExt> (w: &mut W, b: bool) {
|
|
if b {
|
|
w.activate ();
|
|
}
|
|
else {
|
|
w.deactivate ();
|
|
}
|
|
}
|
|
|
|
struct GuiPort {
|
|
input_client_port: Input,
|
|
input_server_id: Input,
|
|
input_server_port: Input,
|
|
but_open: Button,
|
|
but_close: Button,
|
|
}
|
|
|
|
impl GuiPort {
|
|
fn new (fltk_tx: fltk::app::Sender <Message>, x: &mut i32, y: i32, port_idx: usize) -> Self {
|
|
let margin = 10;
|
|
let h = 30;
|
|
|
|
let w = 80;
|
|
let mut input_client_port = Input::new (*x, y, w, h, "");
|
|
*x += w + margin;
|
|
|
|
let w = 120;
|
|
let mut input_server_id = Input::new (*x, y, w, h, "");
|
|
*x += w + margin;
|
|
|
|
let w = 80;
|
|
let mut input_server_port = Input::new (*x, y, w, h, "");
|
|
*x += w + margin;
|
|
|
|
let w = 80;
|
|
let mut but_open = Button::new (*x, y, w, h, "Open");
|
|
*x += w + margin;
|
|
|
|
let w = 80;
|
|
let mut but_close = Button::new (*x, y, w, h, "Close");
|
|
// *x += w + margin;
|
|
|
|
input_client_port.set_value ("5901");
|
|
input_server_id.set_value ("bogus_server");
|
|
input_server_port.set_value ("5900");
|
|
|
|
but_open.set_trigger (CallbackTrigger::Changed);
|
|
but_open.emit (fltk_tx, Message::OpenPort (port_idx));
|
|
but_close.set_trigger (CallbackTrigger::Changed);
|
|
but_close.emit (fltk_tx, Message::ClosePort (port_idx));
|
|
|
|
set_active (&mut but_open, true);
|
|
set_active (&mut but_close, false);
|
|
|
|
Self {
|
|
input_client_port,
|
|
input_server_id,
|
|
input_server_port,
|
|
but_open,
|
|
but_close,
|
|
}
|
|
}
|
|
|
|
fn get_params (&self) -> anyhow::Result <ForwardingParams>
|
|
{
|
|
let client_tcp_port = u16::from_str (&self.input_client_port.value ())?;
|
|
let server_id = self.input_server_id.value ();
|
|
let server_tcp_port = u16::from_str (&self.input_server_port.value ())?;
|
|
|
|
Ok (ForwardingParams {
|
|
client_tcp_port,
|
|
server_id,
|
|
server_tcp_port,
|
|
})
|
|
}
|
|
|
|
fn set_forwarding (&mut self, x: bool) {
|
|
set_active (&mut self.input_client_port, !x);
|
|
set_active (&mut self.input_server_id, !x);
|
|
set_active (&mut self.input_server_port, !x);
|
|
set_active (&mut self.but_open, !x);
|
|
set_active (&mut self.but_close, x);
|
|
|
|
self.but_open.set (x);
|
|
self.but_close.set (!x);
|
|
}
|
|
}
|