From b551f4521ff3828901f1ba103abca4757be219b5 Mon Sep 17 00:00:00 2001 From: Philipp_EndevourOS Date: Tue, 9 Sep 2025 17:24:47 +0200 Subject: [PATCH] sd card detection works (own embassy task) --- src/feedback.rs | 71 ++++++++++++++++++++++++++++++++++++-------- src/init/hardware.rs | 60 ++++++++----------------------------- src/main.rs | 39 +++++++++++++++++++++--- 3 files changed, 105 insertions(+), 65 deletions(-) diff --git a/src/feedback.rs b/src/feedback.rs index c26a5c6..7302d79 100644 --- a/src/feedback.rs +++ b/src/feedback.rs @@ -1,11 +1,11 @@ use embassy_time::{Delay, Duration, Timer}; use esp_hal::{delay, gpio::Output, peripherals, rmt::ConstChannelAccess}; use esp_hal_smartled::SmartLedsAdapterAsync; -use log::{debug, error, info}; use init::hardware; +use log::{debug, error, info}; +use smart_leds::SmartLedsWriteAsync; use smart_leds::colors::{BLACK, GREEN, RED, YELLOW}; use smart_leds::{brightness, colors::BLUE}; -use smart_leds::SmartLedsWriteAsync; use crate::{FEEDBACK_STATE, init}; @@ -21,24 +21,40 @@ pub enum FeedbackState { const LED_LEVEL: u8 = 255; -//TODO ERROR STATE: 1 Blink = unknows error, 3 Blink = no sd card +//TODO ERROR STATE: 1 Blink = unknows error, 3 Blink = no sd card #[embassy_executor::task] -pub async fn feedback_task(mut led: SmartLedsAdapterAsync, { init::hardware::LED_BUFFER_SIZE }>, buzzer: peripherals::GPIO21<'static>) { +pub async fn feedback_task( + mut led: SmartLedsAdapterAsync< + ConstChannelAccess, + { init::hardware::LED_BUFFER_SIZE }, + >, + buzzer: peripherals::GPIO21<'static>, +) { debug!("Starting feedback task"); let mut buzzer = init::hardware::setup_buzzer(buzzer); loop { let feedback_state = FEEDBACK_STATE.wait().await; match feedback_state { FeedbackState::Ack => { - led.write(brightness([GREEN; init::hardware::NUM_LEDS].into_iter(), LED_LEVEL)).await.unwrap(); + led.write(brightness( + [GREEN; init::hardware::NUM_LEDS].into_iter(), + LED_LEVEL, + )) + .await + .unwrap(); buzzer.set_high(); Timer::after(Duration::from_millis(100)).await; buzzer.set_low(); Timer::after(Duration::from_millis(50)).await; } FeedbackState::Nack => { - led.write(brightness([YELLOW; init::hardware::NUM_LEDS].into_iter(), LED_LEVEL)).await.unwrap(); + led.write(brightness( + [YELLOW; init::hardware::NUM_LEDS].into_iter(), + LED_LEVEL, + )) + .await + .unwrap(); buzzer.set_high(); Timer::after(Duration::from_millis(100)).await; buzzer.set_low(); @@ -46,10 +62,20 @@ pub async fn feedback_task(mut led: SmartLedsAdapterAsync { - led.write(brightness([RED; init::hardware::NUM_LEDS].into_iter(), LED_LEVEL)).await.unwrap(); + led.write(brightness( + [RED; init::hardware::NUM_LEDS].into_iter(), + LED_LEVEL, + )) + .await + .unwrap(); buzzer.set_high(); Timer::after(Duration::from_millis(500)).await; buzzer.set_low(); @@ -59,7 +85,12 @@ pub async fn feedback_task(mut led: SmartLedsAdapterAsync { - led.write(brightness([GREEN; init::hardware::NUM_LEDS].into_iter(), LED_LEVEL)).await.unwrap(); + led.write(brightness( + [GREEN; init::hardware::NUM_LEDS].into_iter(), + LED_LEVEL, + )) + .await + .unwrap(); buzzer.set_high(); Timer::after(Duration::from_millis(10)).await; buzzer.set_low(); @@ -71,20 +102,34 @@ pub async fn feedback_task(mut led: SmartLedsAdapterAsync { - led.write(brightness([BLUE; init::hardware::NUM_LEDS].into_iter(), LED_LEVEL)).await.unwrap(); + led.write(brightness( + [BLUE; init::hardware::NUM_LEDS].into_iter(), + LED_LEVEL, + )) + .await + .unwrap(); } FeedbackState::Idle => { - led.write(brightness([GREEN; init::hardware::NUM_LEDS].into_iter(), LED_LEVEL)).await.unwrap(); + led.write(brightness( + [GREEN; init::hardware::NUM_LEDS].into_iter(), + LED_LEVEL, + )) + .await + .unwrap(); } }; debug!("Feedback state: {:?}", feedback_state); } } - // async fn beep_ack() { // buzzer.set_high(); // buzzer.set_low(); diff --git a/src/init/hardware.rs b/src/init/hardware.rs index 5303bdc..c5effe6 100644 --- a/src/init/hardware.rs +++ b/src/init/hardware.rs @@ -7,9 +7,8 @@ use embassy_executor::Spawner; use embassy_net::Stack; use embassy_time::{Duration, Timer}; -use esp_hal::gpio::{Input, InputConfig, Io}; +use esp_hal::gpio::{Input, InputConfig}; use esp_hal::i2c::master::Config; -use esp_hal::interrupt::InterruptHandler; use esp_hal::peripherals::{ GPIO0, GPIO1, GPIO16, GPIO17, GPIO18, GPIO19, GPIO20, GPIO21, GPIO22, GPIO23, I2C0, RMT, SPI2, UART1, @@ -17,7 +16,7 @@ use esp_hal::peripherals::{ use esp_hal::rmt::{ConstChannelAccess, Rmt}; use esp_hal::spi::master::{Config as Spi_config, Spi}; -use esp_hal::{Blocking, handler}; +use esp_hal::Blocking; use esp_hal::time::Rate; use esp_hal::timer::timg::TimerGroup; use esp_hal::{ @@ -28,7 +27,6 @@ use esp_hal::{ timer::systimer::SystemTimer, uart::Uart, }; -use esp_hal_embassy::InterruptExecutor; use esp_hal_smartled::{SmartLedsAdapterAsync, buffer_size_async}; use esp_println::dbg; use esp_println::logger::init_logger; @@ -80,6 +78,7 @@ pub async fn hardware_init( I2c<'static, Async>, SmartLedsAdapterAsync, LED_BUFFER_SIZE>, GPIO21<'static>, + GPIO0<'static>, ) { let config = esp_hal::Config::default().with_cpu_clock(CpuClock::max()); let peripherals = esp_hal::init(config); @@ -105,17 +104,7 @@ pub async fn hardware_init( let i2c_device = setup_i2c(peripherals.I2C0, peripherals.GPIO22, peripherals.GPIO23); - let mut io = Io::new(peripherals.IO_MUX); - io.set_interrupt_handler(handler); - let mut sd_det = Input::new(peripherals.GPIO0, InputConfig::default()); - critical_section::with(|cs| { - // Here we are listening for a low level to demonstrate - // that you need to stop listening for level interrupts, - // but usually you'd probably use `FallingEdge`. - sd_det.listen(esp_hal::gpio::Event::AnyEdge); - SD_DET.borrow_ref_mut(cs).replace(sd_det); -}); - + let mut sd_det_gpio = peripherals.GPIO0; let spi_bus = setup_spi( peripherals.SPI2, @@ -140,10 +129,16 @@ pub async fn hardware_init( debug!("hardware init done"); - (uart_device, stack, i2c_device, led, buzzer_gpio) + ( + uart_device, + stack, + i2c_device, + led, + buzzer_gpio, + sd_det_gpio, + ) } - fn setup_uart( uart1: UART1<'static>, uart_tx: GPIO16<'static>, @@ -218,34 +213,3 @@ fn setup_led( led } - - -#[handler] -fn handler() { - critical_section::with(|cs| { - let mut sd_det = SD_DET.borrow_ref_mut(cs); - let Some(sd_det) = sd_det.as_mut() else { - // Some other interrupt has occurred - // before the button was set up. - return; - }; - - if sd_det.is_interrupt_set() { - //card is insert on high - if sd_det.is_high() { - debug!("card insert"); - //FEEDBACK_STATE.signal(crate::feedback::FeedbackState::Ack); - //sd_det.unlisten(); - //sd_det.listen(esp_hal::gpio::Event::FallingEdge); - - } - //card is not insert on low - else { - debug!("card removed"); - //FEEDBACK_STATE.signal(crate::feedback::FeedbackState::Nack); - //sd_det.unlisten(); - sd_det.listen(esp_hal::gpio::Event::RisingEdge); - } - } - }); -} \ No newline at end of file diff --git a/src/main.rs b/src/main.rs index dca0898..e677ba3 100644 --- a/src/main.rs +++ b/src/main.rs @@ -6,16 +6,21 @@ use embassy_executor::Spawner; use embassy_net::Stack; use embassy_sync::{ - blocking_mutex::raw::{CriticalSectionRawMutex, NoopRawMutex}, channel::Channel, pubsub::{ + blocking_mutex::raw::{CriticalSectionRawMutex, NoopRawMutex}, + channel::Channel, + pubsub::{ PubSubChannel, Publisher, WaitResult::{Lagged, Message}, - }, signal::Signal + }, + signal::Signal, }; use embassy_time::{Duration, Timer}; +use esp_hal::gpio::Input; +use esp_hal::{gpio::InputConfig, peripherals}; use log::{debug, info}; use static_cell::make_static; -use crate::{store::TallyID}; +use crate::store::TallyID; extern crate alloc; @@ -32,7 +37,7 @@ type TallyPublisher = Publisher<'static, NoopRawMutex, TallyID, 8, 2, 1>; #[esp_hal_embassy::main] async fn main(mut spawner: Spawner) { - let (uart_device, stack, _i2c, _led, buzzer_gpio) = + let (uart_device, stack, _i2c, _led, buzzer_gpio, sd_det_gpio) = init::hardware::hardware_init(&mut spawner).await; wait_for_stack_up(stack).await; @@ -56,6 +61,9 @@ async fn main(mut spawner: Spawner) { debug!("spawing feedback task.."); spawner.must_spawn(feedback::feedback_task(_led, buzzer_gpio)); + + debug!("spawn sd detect task"); + spawner.must_spawn(sd_detect_task(sd_det_gpio)); /******************************************************************************/ let mut sub = chan.subscriber().unwrap(); @@ -76,6 +84,29 @@ async fn main(mut spawner: Spawner) { } } +#[embassy_executor::task] +async fn sd_detect_task(sd_det_gpio: peripherals::GPIO0<'static>) { + let mut sd_det = Input::new(sd_det_gpio, InputConfig::default()); + sd_det.wait_for(esp_hal::gpio::Event::AnyEdge); + + loop { + sd_det.wait_for_any_edge().await; + { + if sd_det.is_high() { + FEEDBACK_STATE.signal(feedback::FeedbackState::Ack); + debug!("card insert"); + } + //card is not insert on low + else { + FEEDBACK_STATE.signal(feedback::FeedbackState::Nack); + debug!("card removed"); + } + } + //debounce time + Timer::after(Duration::from_millis(100)).await; + } +} + async fn wait_for_stack_up(stack: Stack<'static>) { loop { if stack.is_link_up() {