From 6ac1b5214ea2960d0cbe9e968c1d0b6d32b36f66 Mon Sep 17 00:00:00 2001 From: Michael Mikovsky <77305074+Astatin3@users.noreply.github.com> Date: Sun, 8 Jun 2025 19:17:23 -0600 Subject: [PATCH] get UI updates working --- src/client/client.rs | 94 +----------------------- src/client/gui.rs | 71 +++++++++--------- src/server/config.rs | 2 - src/server/server.rs | 14 +--- unshell-rs-lib/src/connection/packets.rs | 5 +- unshell-rs-lib/src/networkers/mod.rs | 2 - unshell-rs-lib/src/networkers/tcp.rs | 9 +-- 7 files changed, 46 insertions(+), 151 deletions(-) diff --git a/src/client/client.rs b/src/client/client.rs index 299f123..478ac3f 100644 --- a/src/client/client.rs +++ b/src/client/client.rs @@ -1,10 +1,7 @@ use std::{ error::Error, - mem, net::SocketAddr, sync::{Arc, Mutex}, - thread, - time::Duration, }; use crossbeam_channel::{Receiver, Sender}; @@ -14,9 +11,10 @@ use unshell_rs_lib::{ }; pub struct UnshellClient { + #[allow(dead_code)] addr: SocketAddr, tx: Sender, - rx: Receiver, + pub rx: Receiver, parameters: Arc>, } @@ -26,97 +24,13 @@ impl UnshellClient { let (tx, rx) = TCPConnection::as_async(client); - // mpsc - - // let poll = Poll::new()?; - - // let events = Events::with_capacity(128); - - // const SERVER: Token = Token(0); - // poll.registry() - // .register(&mut listener, SERVER, Interest::READABLE)?; - - // let client = Arc::new(Mutex::new()); - // let outgoing_packets = Arc::new(Mutex::new(Vec::::new())); let parameters = Arc::new(Mutex::new(Parameters::new())); - // let tx_client = Arc::clone(&client); - // let tx_packets = Arc::clone(&outgoing_packets); - - // // Recieve thread - // thread::spawn(move || { - // loop { - // info!("Lock 2"); - // let mut packets_lock = tx_packets.lock().unwrap(); - // info!("Lock 2"); - // if !packets_lock.is_empty() { - // info!("Lock 3"); - // if let Ok(packet) = packets_lock.pop().unwrap().encode() { - // info!("Lock 3"); - // info!("Lock 4"); - // let mut client_lock = tx_client.lock().unwrap(); - // info!("Lock 4"); - // info!("Wrote {}", packet.as_str()); - // match client_lock.write(packet.as_str()) { - // Err(e) => { - // error!("Failed to send packet: {:?}", e); - // } - // _ => {} - // }; - // } - // } - // std::mem::drop(packets_lock); - - // thread::sleep(Duration::from_millis(10)); - // } - // }); - - // let rx_client = Arc::clone(&client); - // let rx_params = Arc::clone(¶meters); - // thread::spawn(move || { - // loop { - // info!("Lock 5"); - // let mut client = rx_client.lock().unwrap(); - // info!("Lock 5"); - // if !client.is_alive() { - // error!("Disconnected from {}!", client.get_info()); - // } - // if let Ok(data) = client.read() { - // info!("Got {}", data); - // if let Ok(packet) = GuiPacket::decode(data.as_str()) { - // match packet { - // GuiPacket::ParameterUpate(name, parameter) => { - // rx_params.lock().unwrap().insert(name, parameter); - // } - // GuiPacket::Error(error_packet) => { - // error!("Got error: {}", print_type_of(&error_packet)) - // } - // GuiPacket::SetAllParameters(parameters) => { - // let mut params_lock = rx_params.lock().unwrap(); - // params_lock.clear(); - // params_lock.extend(parameters); - // } - // _ => { - // error!("Unsupported packet: {}", data) - // } - // } - // } - // } - // // std::mem::drop(client); - - // thread::sleep(Duration::from_millis(10)); - // } - // }); - Ok(Self { addr, - tx, rx, - - // client, parameters, - // outgoing_packets, }) } @@ -130,7 +44,3 @@ impl UnshellClient { self.parameters.lock().unwrap().get(key).cloned() } } - -fn print_type_of(_: &T) -> &'static str { - std::any::type_name::() -} diff --git a/src/client/gui.rs b/src/client/gui.rs index ef8f9ff..6cd3182 100644 --- a/src/client/gui.rs +++ b/src/client/gui.rs @@ -1,22 +1,20 @@ -use slint::{ComponentHandle, ModelRc, VecModel}; +use slint::{ComponentHandle, Weak}; use std::{ error::Error, sync::{Arc, Mutex}, + thread, }; -use unshell_rs_lib::{config::campaign::CampaignConfig, connection::Parameter}; +use unshell_rs_lib::connection::{C2Packet, Parameter}; use crate::client::UnshellClient; -pub struct UnshellGui { - client: UnshellClient, - ui: AppWindow, - campaign: Option>>, -} +pub struct UnshellGui {} slint::include_modules!(); impl UnshellGui { pub fn start(client: UnshellClient) -> Result<(), Box> { let ui = AppWindow::new()?; + let rx = client.rx.clone(); let client = Arc::new(Mutex::new(client)); let ui_handle = ui.as_weak(); @@ -24,9 +22,7 @@ impl UnshellGui { ui.on_tab_clicked(move |index| { let ui = ui_handle.unwrap(); ui.set_current_tab(index); - info!("Lock 1 "); let mut client_lock = client_clone.lock().unwrap(); - info!("Lock 1 "); client_lock.set_parameter("Current Tab".to_string(), Parameter::CurrentTab(index)); trace!("Tab {} selected", index); }); @@ -40,32 +36,41 @@ impl UnshellGui { .into() }); + let ui_handle = ui.as_weak(); + thread::spawn(move || { + fn on_param_update(ui_handle: Weak, parameter: &Parameter) { + // info!("{}", name); + match parameter { + Parameter::Test1 => todo!(), + Parameter::CurrentTab(i) => { + let i = i.clone(); + slint::invoke_from_event_loop(move || { + ui_handle.unwrap().set_current_tab(i) + }) + .unwrap(); + } + } + } + + loop { + if let Ok(data) = rx.recv() { + match data { + C2Packet::SetAllParameters(parameters) => { + for key in parameters.keys() { + on_param_update(ui_handle.clone(), parameters.get(key).unwrap()); + } + } + C2Packet::ParameterUpate(name, parameter) => { + on_param_update(ui_handle.clone(), ¶meter); + } + _ => {} + } + } + } + }); + ui.run()?; Ok(()) } - - fn update(&mut self) { - // self.ui.set_listeners(ModelRc::new(VecModel::from( - // self.campaign - // .listeners - // .iter() - // .map(|l| match l { - // ListenerConfig::Tcp { - // enabled, - // name, - // addr, - // layers, - // .. - // } => UITcpListener { - // enabled: *enabled, - // name: name.clone().into(), - // remote_host: addr.to_string().into(), - // }, - // }) - // .collect::>(), - // ))); - } } - -// trait diff --git a/src/server/config.rs b/src/server/config.rs index 07a18f9..fc8da8e 100644 --- a/src/server/config.rs +++ b/src/server/config.rs @@ -2,8 +2,6 @@ use lazy_static::lazy_static; use serde::{Deserialize, Serialize}; use unshell_rs_lib::config::campaign::CampaignConfig; -use std::collections::HashMap; - use unshell_rs_lib::connection::Parameters; lazy_static! { diff --git a/src/server/server.rs b/src/server/server.rs index 30d477a..0e0ba6b 100644 --- a/src/server/server.rs +++ b/src/server/server.rs @@ -1,23 +1,19 @@ use std::{ - collections::HashMap, error::Error, fs::File, io::Read, net::SocketAddr, sync::{Arc, Mutex}, thread, - time::Duration, }; -use crossbeam_channel::{Receiver, Sender}; +use crossbeam_channel::Sender; use serde::{Deserialize, Serialize}; use unshell_rs_lib::{ config::campaign::CampaignConfig, connection::{C2Packet, ErrorPacket, Parameters}, - networkers::{ - AsyncConnection, Connection, ServerTrait, TCPConnection, TCPServer, run_listener_state, - }, + networkers::{AsyncConnection, ServerTrait, TCPConnection, TCPServer, run_listener_state}, }; use crate::server::{DEFAULT_CAMPAIGN, DEFAULT_USERS, User, config::DEFAULT_PARAMETERS}; @@ -73,12 +69,6 @@ impl UnshellServer { } }); - // let (broadcast_tx, broadcast_rx) = crossbeam_channel::unbounded::(); - // let mut config_lock = s.config.lock().unwrap(); - // config_lock.broadcast_tx = Some(broadcast_tx); - // config_lock.broadcast_rx = Some(broadcast_rx); - // std::mem::drop(config_lock); - s } diff --git a/unshell-rs-lib/src/connection/packets.rs b/unshell-rs-lib/src/connection/packets.rs index d846e08..934f29c 100644 --- a/unshell-rs-lib/src/connection/packets.rs +++ b/unshell-rs-lib/src/connection/packets.rs @@ -1,7 +1,4 @@ -use std::{ - collections::HashMap, - fmt::{self, Display}, -}; +use std::{collections::HashMap, fmt}; use serde::{Deserialize, Serialize}; use serde_json::Result; diff --git a/unshell-rs-lib/src/networkers/mod.rs b/unshell-rs-lib/src/networkers/mod.rs index 9fb2bcb..7cba4df 100644 --- a/unshell-rs-lib/src/networkers/mod.rs +++ b/unshell-rs-lib/src/networkers/mod.rs @@ -113,5 +113,3 @@ use serde::de::DeserializeOwned; pub use tcp::TCPClient; pub use tcp::TCPConnection; pub use tcp::TCPServer; - -use crate::connection; diff --git a/unshell-rs-lib/src/networkers/tcp.rs b/unshell-rs-lib/src/networkers/tcp.rs index 7ffa341..fd00e26 100644 --- a/unshell-rs-lib/src/networkers/tcp.rs +++ b/unshell-rs-lib/src/networkers/tcp.rs @@ -1,5 +1,4 @@ use std::{ - error::Error, io::{self, BufRead, BufReader, Write}, net::{SocketAddr, TcpListener, TcpStream}, thread, @@ -62,13 +61,12 @@ impl AsyncConnection for TCPConnection { let (send_tx, send_rx) = crossbeam_channel::unbounded::(); let (recv_tx, recv_rx) = crossbeam_channel::unbounded::(); - let tx_clone = send_tx.clone(); thread::spawn(move || { let mut reader = connection.reader; let mut read = || -> Result { let mut line = String::new(); - let n = reader.read_line(&mut line)?; + let _ = reader.read_line(&mut line)?; Ok(line.trim_end().to_string()) }; @@ -80,7 +78,7 @@ impl AsyncConnection for TCPConnection { } info!("Got {}", data); if let Ok(decoded) = serde_json::from_str::(&data) { - if let Err(e) = tx_clone.send(decoded) { + if let Err(e) = send_tx.send(decoded) { error!("Got error: {}", e); } } @@ -88,7 +86,6 @@ impl AsyncConnection for TCPConnection { } }); - let rx_clone = recv_rx.clone(); thread::spawn(move || { let mut stream = connection.stream; @@ -99,7 +96,7 @@ impl AsyncConnection for TCPConnection { }; loop { - if let Ok(data) = rx_clone.recv() { + if let Ok(data) = recv_rx.recv() { if let Ok(encoded) = serde_json::to_string(&data) { info!("Write {}", encoded); if let Err(e) = write(encoded) {