mirror of
https://github.com/stakwork/sphinx-key.git
synced 2026-02-10 10:15:30 +01:00
sphinx-key: fetch ota update in the main thread
we previously spawned a separate led thread, which caused two problems 1) starved the main thread, preventing any progress on signing a solution here could have been to sleep the ota fetch thread every so often 2) also increased memory usage a solution here is much smaller buffer for ota thread both of these solutions significantly hindered the speed of the ota update i like much better keeping the ota fetch blocking in the main thread, and giving it the appropriate resources to perform the ota fetch fast this commit also only sends a new status into the led_tx-led_rx channel when necessary - we previously sent new statuses into the channel even if the led was already at that state
This commit is contained in:
@@ -143,6 +143,7 @@ pub fn make_event_loop(
|
||||
log::info!("=> starting the main signing loop...");
|
||||
let flash_db = ctrlr.persister();
|
||||
let mut expected_sequence = None;
|
||||
let mut current_status = Status::ConnectingToMqtt;
|
||||
while let Ok(event) = rx.recv() {
|
||||
log::info!("new event loop!");
|
||||
check_memory();
|
||||
@@ -153,14 +154,14 @@ pub fn make_event_loop(
|
||||
thread::sleep(std::time::Duration::from_secs(1));
|
||||
// send the initial HELLO again
|
||||
mqtt_pub(&mut mqtt, &client_id, topics::HELLO, &[]);
|
||||
led_tx.send(Status::Connected).unwrap();
|
||||
current_status = update_led(current_status, Status::Connected, &led_tx);
|
||||
}
|
||||
Event::Disconnected => {
|
||||
led_tx.send(Status::ConnectingToMqtt).unwrap();
|
||||
current_status = update_led(current_status, Status::ConnectingToMqtt, &led_tx);
|
||||
log::info!("GOT A Event::Disconnected msg!");
|
||||
}
|
||||
Event::VlsMessage(msg_bytes) => {
|
||||
led_tx.send(Status::Signing).unwrap();
|
||||
current_status = update_led(current_status, Status::Signing, &led_tx);
|
||||
let state1 = approver.control().get_state();
|
||||
//log::info!("FULL MSG {:?}", &msg_bytes);
|
||||
let _ret = match sphinx_signer::root::handle_with_lss(
|
||||
@@ -246,18 +247,32 @@ pub fn make_event_loop(
|
||||
Event::Control(ref msg_bytes) => {
|
||||
log::info!("GOT A CONTROL MSG");
|
||||
let cres = ctrlr.handle(msg_bytes);
|
||||
if let Some(res) =
|
||||
handle_control_response(&root_handler, &approver, cres, led_tx.clone())
|
||||
{
|
||||
let mut bb = ByteBuf::new();
|
||||
serialize_controlresponse(&mut bb, &res).expect("failed serialize_lssresponse");
|
||||
mqtt_pub(&mut mqtt, &client_id, topics::CONTROL_RES, bb.as_slice());
|
||||
let res = handle_control_response(&root_handler, &approver, cres, led_tx.clone());
|
||||
let mut bb = ByteBuf::new();
|
||||
serialize_controlresponse(&mut bb, &res).expect("failed serialize_lssresponse");
|
||||
mqtt_pub(&mut mqtt, &client_id, topics::CONTROL_RES, bb.as_slice());
|
||||
if let ControlResponse::OtaConfirm(params) = res {
|
||||
if let Err(e) = update_sphinx_key(params) {
|
||||
log::error!("OTA update failed {:?}", e.to_string());
|
||||
} else {
|
||||
log::info!("OTA flow complete, restarting esp...");
|
||||
unsafe { esp_idf_svc::sys::esp_restart() };
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn update_led(current: Status, new: Status, led_tx: &mpsc::Sender<Status>) -> Status {
|
||||
if current != new {
|
||||
led_tx.send(new).unwrap();
|
||||
new
|
||||
} else {
|
||||
current
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn restart_esp_if_memory_low() {
|
||||
unsafe {
|
||||
let size = esp_idf_svc::sys::heap_caps_get_free_size(4);
|
||||
@@ -289,7 +304,7 @@ fn handle_control_response(
|
||||
approver: &SphinxApprover,
|
||||
cres: anyhow::Result<(ControlMessage, ControlResponse)>,
|
||||
led_tx: mpsc::Sender<Status>,
|
||||
) -> Option<ControlResponse> {
|
||||
) -> ControlResponse {
|
||||
match cres {
|
||||
Ok((control_msg, mut control_res)) => {
|
||||
// the following msg types require other actions besides Flash persistence
|
||||
@@ -325,30 +340,18 @@ fn handle_control_response(
|
||||
control_res =
|
||||
ControlResponse::Error(format!("OTA update cannot launch {:?}", e))
|
||||
} else {
|
||||
// A 10kB size stack was consistently overflowing when doing a factory reset
|
||||
let builder = thread::Builder::new().stack_size(15000usize);
|
||||
builder
|
||||
.spawn(move || {
|
||||
led_tx.send(Status::Ota).unwrap();
|
||||
if let Err(e) = update_sphinx_key(params, led_tx) {
|
||||
log::error!("OTA update failed {:?}", e.to_string());
|
||||
} else {
|
||||
log::info!("OTA flow complete, restarting esp...");
|
||||
unsafe { esp_idf_svc::sys::esp_restart() };
|
||||
}
|
||||
})
|
||||
.unwrap();
|
||||
log::info!("OTA update launched...");
|
||||
led_tx.send(Status::Ota).unwrap();
|
||||
log::info!("Launching OTA update...");
|
||||
}
|
||||
}
|
||||
_ => (),
|
||||
};
|
||||
Some(control_res)
|
||||
control_res
|
||||
}
|
||||
Err(e) => {
|
||||
let control_res = ControlResponse::Error(e.to_string());
|
||||
log::warn!("error parsing ctrl msg {:?}", e);
|
||||
Some(control_res)
|
||||
control_res
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
use crate::status::Status;
|
||||
use anyhow::{anyhow, Result};
|
||||
use esp_idf_svc::http::client::Configuration;
|
||||
use esp_idf_svc::http::client::EspHttpConnection;
|
||||
@@ -10,9 +9,8 @@ use sphinx_signer::sphinx_glyph::control::OtaParams;
|
||||
use std::fs::{remove_file, File};
|
||||
use std::io::BufWriter;
|
||||
use std::io::Write;
|
||||
use std::sync::mpsc;
|
||||
|
||||
const BUFFER_LEN: usize = 512;
|
||||
const BUFFER_LEN: usize = 1024;
|
||||
const UPDATE_BIN_PATH: &str = "/sdcard/update.bin";
|
||||
|
||||
fn factory_reset() -> Result<()> {
|
||||
@@ -28,7 +26,7 @@ fn factory_reset() -> Result<()> {
|
||||
}
|
||||
}
|
||||
|
||||
fn get_update(params: OtaParams, led_tx: mpsc::Sender<Status>) -> Result<()> {
|
||||
fn get_update(params: OtaParams) -> Result<()> {
|
||||
let configuration = Configuration {
|
||||
buffer_size: Some(BUFFER_LEN),
|
||||
buffer_size_tx: Some(BUFFER_LEN / 3),
|
||||
@@ -49,7 +47,6 @@ fn get_update(params: OtaParams, led_tx: mpsc::Sender<Status>) -> Result<()> {
|
||||
let mut buf = [0_u8; BUFFER_LEN];
|
||||
let mut read_tot: usize = 0;
|
||||
let mut write_tot: usize = 0;
|
||||
let mut i = 0;
|
||||
loop {
|
||||
let r = reader.read(&mut buf)?;
|
||||
if r == 0 {
|
||||
@@ -58,21 +55,15 @@ fn get_update(params: OtaParams, led_tx: mpsc::Sender<Status>) -> Result<()> {
|
||||
let w = writer.write(&buf[..r])?;
|
||||
read_tot += r;
|
||||
write_tot += w;
|
||||
i += 1;
|
||||
if i % 20 == 0 {
|
||||
led_tx.send(Status::Ota).unwrap();
|
||||
info!("Cumulative bytes read: {}", read_tot);
|
||||
info!("Cumulative bytes written: {}", write_tot);
|
||||
}
|
||||
}
|
||||
info!("TOTAL read: {}", read_tot);
|
||||
info!("TOTAL written: {}", write_tot);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn update_sphinx_key(params: OtaParams, led_tx: mpsc::Sender<Status>) -> Result<()> {
|
||||
pub fn update_sphinx_key(params: OtaParams) -> Result<()> {
|
||||
info!("Getting the update...");
|
||||
get_update(params, led_tx)?;
|
||||
get_update(params)?;
|
||||
info!("Update written to sd card, performing factory reset");
|
||||
factory_reset()?;
|
||||
info!("Factory reset completed!");
|
||||
|
||||
Reference in New Issue
Block a user