diff --git a/firmware/Cargo.lock b/firmware/Cargo.lock index ae5c94a..d7da016 100644 --- a/firmware/Cargo.lock +++ b/firmware/Cargo.lock @@ -1051,6 +1051,7 @@ dependencies = [ "dotenvy", "embassy-executor", "embassy-net", + "embassy-sync 0.8.0", "embassy-time", "embedded-io 0.7.1", "embedded-io-async 0.7.0", diff --git a/firmware/Cargo.toml b/firmware/Cargo.toml index 3150e6f..5560713 100644 --- a/firmware/Cargo.toml +++ b/firmware/Cargo.toml @@ -38,6 +38,7 @@ esp-backtrace = { version = "0.19.0", features = [ esp-println = { version = "0.17.0", features = ["esp32", "log-04"] } # for more networking protocol support see https://crates.io/crates/edge-net embassy-executor = { version = "0.10.0", features = ["log"] } +embassy-sync = "0.8.0" embassy-time = { version = "0.5.0", features = ["log"] } esp-radio = { version = "0.18.0", features = ["esp32", "log-04", "unstable", "wifi-eap"] } smoltcp = { version = "0.13.0", default-features = false, features = [ diff --git a/firmware/build.rs b/firmware/build.rs index 883fa49..dafd7ee 100644 --- a/firmware/build.rs +++ b/firmware/build.rs @@ -11,6 +11,7 @@ fn main() { set_env!("SSID"); set_env!("PASSWORD"); + set_env!("SERVER_IP"); linker_be_nice(); // make sure linkall.x is the last linker script (otherwise might cause problems with flip-link) diff --git a/firmware/src/main.rs b/firmware/src/main.rs index 0078660..940cb69 100644 --- a/firmware/src/main.rs +++ b/firmware/src/main.rs @@ -7,8 +7,12 @@ )] #![deny(clippy::large_stack_frames)] +use core::str::FromStr; + use embassy_net::tcp::TcpSocket; use embassy_net::{IpAddress, IpEndpoint, Stack}; +use embassy_sync::blocking_mutex::raw::NoopRawMutex; +use embassy_sync::channel::{Channel, Receiver, Sender}; use esp_hal::timer::timg::TimerGroup; use esp_hal::{clock::CpuClock, peripherals::Peripherals}; @@ -24,6 +28,7 @@ use embedded_io_async::Write; use esp_backtrace as _; use packets::Packet; +use static_cell::StaticCell; extern crate alloc; @@ -31,6 +36,10 @@ pub mod wifi; esp_bootloader_esp_idf::esp_app_desc!(); +pub type RegisterEventChannel = Channel; +pub type RegisterEventSender = Sender<'static, NoopRawMutex, (), 1>; +pub type RegisterEventReceiver = Receiver<'static, NoopRawMutex, (), 1>; + fn init_hardware() -> Peripherals { esp_println::logger::init_logger_from_env(); @@ -59,11 +68,21 @@ async fn main(spawner: Spawner) { info!("RTOS initialized!"); - let stack = wifi::init_wifi(peripherals.WIFI, &spawner, peripherals.GPIO2).await; - stack.wait_config_up().await; + static REGISTER_CHANNEL: StaticCell = StaticCell::new(); + let register_event_channel = REGISTER_CHANNEL.init(Channel::new()); + let stack = wifi::init_wifi( + peripherals.WIFI, + &spawner, + peripherals.GPIO2, + register_event_channel.sender(), + ) + .await; + + stack.wait_config_up().await; info!("WiFi initialized! {:?}", stack.config_v4()); - register_at_server(stack.clone()).await; + + spawner.spawn(listen_register_events(stack, register_event_channel.receiver()).unwrap()); spawner.spawn(listen_tcp(stack.clone()).unwrap()); } @@ -83,6 +102,16 @@ impl<'a> packets::PacketSocket for PacketSocket<'a> { } } +#[embassy_executor::task] +async fn listen_register_events(stack: Stack<'static>, receiver: RegisterEventReceiver) { + loop { + receiver.receive().await; + info!("Register event received"); + + register_at_server(stack.clone()).await; + } +} + async fn register_at_server(stack: Stack<'static>) { let mut rx_buffer = [0; 4096]; let mut tx_buffer = [0; 4096]; @@ -91,7 +120,7 @@ async fn register_at_server(stack: Stack<'static>) { let mut stream = TcpSocket::new(stack, &mut rx_buffer, &mut tx_buffer); stream .connect(IpEndpoint::new( - IpAddress::Ipv4(Ipv4Address::new(172, 20, 10, 3)), + IpAddress::Ipv4(Ipv4Address::from_str(env!("SERVER_IP")).unwrap()), 1234, )) .await diff --git a/firmware/src/wifi.rs b/firmware/src/wifi.rs index 001b101..bb9998c 100644 --- a/firmware/src/wifi.rs +++ b/firmware/src/wifi.rs @@ -12,6 +12,8 @@ use esp_radio::wifi::{ use log::info; use static_cell::StaticCell; +use crate::RegisterEventSender; + #[allow( clippy::large_stack_frames, reason = "embassy StackResources is to large nothing we can do" @@ -20,6 +22,7 @@ pub async fn init_wifi( wifi: esp_hal::peripherals::WIFI<'static>, spawner: &Spawner, led_pin: GPIO2<'static>, + register_event_sender: RegisterEventSender, ) -> Stack<'static> { let station_config = Config::Station( StationConfig::default() @@ -49,7 +52,7 @@ pub async fn init_wifi( seed, ); - spawner.spawn(connection(wifi_controller, led_pin).unwrap()); + spawner.spawn(connection(wifi_controller, led_pin, register_event_sender).unwrap()); spawner.spawn(net_task(runner).unwrap()); stack @@ -57,7 +60,11 @@ pub async fn init_wifi( #[allow(clippy::large_stack_frames)] #[embassy_executor::task] -async fn connection(mut controller: WifiController<'static>, led_pin: GPIO2<'static>) { +async fn connection( + mut controller: WifiController<'static>, + led_pin: GPIO2<'static>, + register_event_sender: RegisterEventSender, +) { info!("start connection task"); let mut pin = Output::new(led_pin, esp_hal::gpio::Level::Low, OutputConfig::default()); @@ -68,7 +75,9 @@ async fn connection(mut controller: WifiController<'static>, led_pin: GPIO2<'sta match controller.connect_async().await { Ok(info) => { info!("Wifi connected to {:?}", info); + pin.set_high(); + register_event_sender.send(()).await; // wait until we're no longer connected let info = controller.wait_for_disconnect_async().await.ok();