diff --git a/Cargo.lock b/Cargo.lock index c5c8a82..6d0ae7e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1102,6 +1102,7 @@ dependencies = [ "embassy-net", "embassy-net-driver", "embassy-time", + "embedded-hal-async", "embedded-io-async", "esp-backtrace", "esp-hal", diff --git a/Cargo.toml b/Cargo.toml index dd22f0e..ce8a768 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -22,6 +22,7 @@ embassy-net = { version = "0.4.0", features = ["dhcpv4", "proto-ipv4", "tcp"] } embedded-io-async = "0.6.1" embassy-net-driver = "0.2.0" const_format = "0.2.32" +embedded-hal-async = "1.0.0" [profile.dev] # Rust debug is too slow. diff --git a/src/main.rs b/src/main.rs index 1a67aea..e983953 100644 --- a/src/main.rs +++ b/src/main.rs @@ -5,12 +5,14 @@ use embassy_executor::Spawner; use embassy_net::tcp::TcpSocket; use embassy_net::{Config, Ipv4Address, Stack, StackResources}; -use esp_hal; +use esp_hal::{self, IO}; use const_format::formatcp; use embassy_time::{Duration, Timer}; +use embedded_hal_async::digital::Wait; use esp_backtrace as _; use esp_hal::clock::ClockControl; +use esp_hal::gpio::{AnyPin, Input, PullUp}; use esp_hal::Rng; use esp_hal::{embassy, peripherals::Peripherals, prelude::*, timer::TimerGroup}; use esp_println::println; @@ -23,7 +25,7 @@ const SSID: &str = env!("SSID"); const PASSWORD: &str = env!("PASSWORD"); #[main] -async fn main(spawner: Spawner) -> ! { +async fn main(spawner: Spawner) { #[cfg(feature = "log")] esp_println::logger::init_logger(log::LevelFilter::Info); @@ -67,9 +69,6 @@ async fn main(spawner: Spawner) -> ! { spawner.spawn(connection(controller)).ok(); spawner.spawn(net_task(&stack)).ok(); - let mut rx_buffer = [0; 4096]; - let mut tx_buffer = [0; 4096]; - loop { if stack.is_link_up() { break; @@ -86,53 +85,79 @@ async fn main(spawner: Spawner) -> ! { Timer::after(Duration::from_millis(500)).await; } - loop { - Timer::after(Duration::from_millis(1_000)).await; + let io = IO::new(peripherals.GPIO, peripherals.IO_MUX); + let button = io.pins.gpio12.into_pull_up_input(); + println!("Spawning button task"); + spawner.must_spawn(button_task(button.into(), stack)); +} - let mut socket = TcpSocket::new(&stack, &mut rx_buffer, &mut tx_buffer); +async fn ring(stack: &'static Stack>) -> Result<(), &str> { + let mut rx_buffer = [0; 4096]; + let mut tx_buffer = [0; 4096]; - socket.set_timeout(Some(embassy_time::Duration::from_secs(10))); + Timer::after(Duration::from_millis(1_000)).await; - let remote_endpoint = (Ipv4Address::new(104, 20, 43, 236), 80); - println!("connecting..."); - let r = socket.connect(remote_endpoint).await; - if let Err(e) = r { - println!("connect error: {:?}", e); - continue; - } + let mut socket = TcpSocket::new(&stack, &mut rx_buffer, &mut tx_buffer); - const json: &'static str = "{ + socket.set_timeout(Some(embassy_time::Duration::from_secs(10))); + + let remote_endpoint = (Ipv4Address::new(104, 20, 43, 236), 80); + println!("connecting..."); + let r = socket.connect(remote_endpoint).await; + if let Err(e) = r { + println!("connect error: {:?}", e); + return Err("connect error"); + } + + const JSON: &'static str = "{ \"token\": \"ahgvt9acdx5sowxfobadt9cmpqhrzp\", \"user\": \"ud2btptjwvy92xi8y77tfurfew6z7a\", \"message\": \"DOOR BELL!!!\" }"; - const json_len: usize = json.len(); + const JSON_LEN: usize = JSON.len(); - println!("connected!"); - let mut buf = [0; 1024]; - loop { - use embedded_io_async::Write; - let req = formatcp!("POST /1/messages.json HTTP/1.0\r\nHost: api.pushover.net\r\nContent-Type: application/json\r\nContent-Length: {}\r\n\r\n{}\r\n\r\n", json_len, json); - println!("{}", req); - let r = socket.write_all(req.as_bytes()).await; - if let Err(e) = r { - println!("write error: {:?}", e); + println!("connected!"); + let mut buf = [0; 1024]; + loop { + use embedded_io_async::Write; + let req = formatcp!("POST /1/messages.json HTTP/1.0\r\nHost: api.pushover.net\r\nContent-Type: application/json\r\nContent-Length: {}\r\n\r\n{}\r\n\r\n", JSON_LEN, JSON); + println!("{}", req); + let r = socket.write_all(req.as_bytes()).await; + if let Err(e) = r { + println!("write error: {:?}", e); + break; + } + let n = match socket.read(&mut buf).await { + Ok(0) => { + println!("read EOF"); break; } - let n = match socket.read(&mut buf).await { - Ok(0) => { - println!("read EOF"); - break; - } - Ok(n) => n, - Err(e) => { - println!("read error: {:?}", e); - break; - } - }; - println!("{}", core::str::from_utf8(&buf[..n]).unwrap()); + Ok(n) => n, + Err(e) => { + println!("read error: {:?}", e); + break; + } + }; + println!("{}", core::str::from_utf8(&buf[..n]).unwrap()); + } + Timer::after(Duration::from_millis(5000)).await; + Ok(()) +} + +#[embassy_executor::task] +async fn button_task( + mut button: AnyPin>, + stack: &'static Stack>, +) { + loop { + button.wait_for_falling_edge().await.unwrap(); + Timer::after_millis(10).await; + if button.is_low().unwrap() { + println!("Button pressed"); + ring(stack) + .await + .unwrap_or_else(|e| println!("ring error: {}", e)); } - Timer::after(Duration::from_millis(5000)).await; } }