diff --git a/satrs-example/Cargo.toml b/satrs-example/Cargo.toml index af13dad..2c285ec 100644 --- a/satrs-example/Cargo.toml +++ b/satrs-example/Cargo.toml @@ -24,6 +24,7 @@ cfg-if = "1" arbitrary-int = "2" bitbybit = "2" postcard = "1" +ctrlc = "3" serde = { version = "1", features = ["derive"] } serde_json = "1" diff --git a/satrs-example/src/interface/tcp.rs b/satrs-example/src/interface/tcp.rs index b1ce05d..40b05bf 100644 --- a/satrs-example/src/interface/tcp.rs +++ b/satrs-example/src/interface/tcp.rs @@ -129,15 +129,13 @@ impl TcpTask { } pub fn periodic_operation(&mut self) { - loop { - let result = self - .0 - .handle_all_connections(Some(Duration::from_millis(400))); - match result { - Ok(_conn_result) => (), - Err(e) => { - warn!("TCP server error: {e:?}"); - } + let result = self + .0 + .handle_all_connections(Some(Duration::from_millis(400))); + match result { + Ok(_conn_result) => (), + Err(e) => { + warn!("TCP server error: {e:?}"); } } } diff --git a/satrs-example/src/main.rs b/satrs-example/src/main.rs index 2302941..1495746 100644 --- a/satrs-example/src/main.rs +++ b/satrs-example/src/main.rs @@ -1,6 +1,10 @@ use std::{ net::{IpAddr, SocketAddr}, - sync::{Arc, Mutex, mpsc}, + sync::{ + Arc, Mutex, + atomic::{AtomicBool, Ordering}, + mpsc, + }, thread, time::Duration, }; @@ -52,10 +56,16 @@ mod event_manager; mod interface; mod logger; mod tmtc; - fn main() { + static KILL_SIGNAL: AtomicBool = AtomicBool::new(false); + setup_logger().expect("setting up logging with fern failed"); println!("Runng OBSW example"); + ctrlc::set_handler(move || { + log::info!("Received Ctrl-C, shutting down"); + KILL_SIGNAL.store(true, Ordering::Relaxed); + }) + .expect("Error setting Ctrl-C handler"); let (tc_source_tx, tc_source_rx) = mpsc::sync_channel(50); let (tm_sink_tx, tm_sink_rx) = mpsc::sync_channel(50); @@ -242,6 +252,9 @@ fn main() { .spawn(move || { info!("Running UDP server on port {SERVER_PORT}"); loop { + if KILL_SIGNAL.load(Ordering::Relaxed) { + break; + } udp_tmtc_server.periodic_operation(); tc_source.periodic_operation(); thread::sleep(Duration::from_millis(FREQ_MS_UDP_TMTC)); @@ -255,6 +268,9 @@ fn main() { .spawn(move || { info!("Running TCP server on port {SERVER_PORT}"); loop { + if KILL_SIGNAL.load(Ordering::Relaxed) { + break; + } tcp_server.periodic_operation(); } }) @@ -265,6 +281,9 @@ fn main() { .name("TM SINK".to_string()) .spawn(move || { loop { + if KILL_SIGNAL.load(Ordering::Relaxed) { + break; + } tm_sink.operation(); } }) @@ -278,6 +297,9 @@ fn main() { .name("SIM ADAPTER".to_string()) .spawn(move || { loop { + if KILL_SIGNAL.load(Ordering::Relaxed) { + break; + } if sim_client.operation() == HandlingStatus::Empty { std::thread::sleep(Duration::from_millis(SIM_CLIENT_IDLE_DELAY_MS)); } @@ -292,6 +314,9 @@ fn main() { .name("AOCS".to_string()) .spawn(move || { loop { + if KILL_SIGNAL.load(Ordering::Relaxed) { + break; + } mgm_0_handler.periodic_operation(); mgm_1_handler.periodic_operation(); mgm_assembly.periodic_operation(); @@ -305,6 +330,9 @@ fn main() { .name("EPS".to_string()) .spawn(move || { loop { + if KILL_SIGNAL.load(Ordering::Relaxed) { + break; + } // TODO: We should introduce something like a fixed timeslot helper to allow a more // declarative API. It would also be very useful for the AOCS task. // @@ -325,6 +353,9 @@ fn main() { .name("CTRL".to_string()) .spawn(move || { loop { + if KILL_SIGNAL.load(Ordering::Relaxed) { + break; + } controller.periodic_operation(); event_manager.periodic_operation(); thread::sleep(Duration::from_millis(FREQ_MS_CONTROLLER)); diff --git a/satrs-example/src/tmtc/tm_sink.rs b/satrs-example/src/tmtc/tm_sink.rs index f5092de..0cb2724 100644 --- a/satrs-example/src/tmtc/tm_sink.rs +++ b/satrs-example/src/tmtc/tm_sink.rs @@ -46,7 +46,7 @@ impl TmSink { } pub fn operation(&mut self) { - if let Ok(mut tm) = self.tm_funnel_rx.recv() { + if let Ok(mut tm) = self.tm_funnel_rx.try_recv() { tm.sp_header .set_seq_count(self.seq_counter_map.get_and_increment(tm.sp_header.apid())); self.sync_tm_tcp_source.add_tm(&tm.to_vec());