diff --git a/semestralka_2/src/bin/main.rs b/semestralka_2/src/bin/main.rs index 51f1af7..a6b1f49 100644 --- a/semestralka_2/src/bin/main.rs +++ b/semestralka_2/src/bin/main.rs @@ -9,8 +9,10 @@ use embassy_executor::Spawner; use embassy_futures::yield_now; use embassy_stm32::bind_interrupts; use embassy_stm32::peripherals; -use embassy_stm32::usart::{BufferedUart, Config, BufferedInterruptHandler}; +use embassy_stm32::Config; +use embassy_stm32::usart::{BufferedUart, Config as UsartConfig, BufferedInterruptHandler}; use embassy_stm32::gpio::{Output, Level, Speed}; +use embassy_stm32::wdg::IndependentWatchdog; use embassy_time::{Duration, Timer}; use static_cell::StaticCell; @@ -25,52 +27,34 @@ bind_interrupts!(struct Irqs { }); unsafe extern "C" { - fn HAL_Init(); fn HAL_PWR_EnterSTANDBYMode(); - fn HAL_IWDG_Init(handle: *mut ()); - fn HAL_IWDG_Refresh(handle: *mut ()); - fn __HAL_PWR_GET_FLAG(flag: u32) -> u32; - fn __HAL_PWR_CLEAR_FLAG(flag: u32); } const PWR_FLAG_SBF: u32 = 1 << 1; -#[repr(C)] -struct IWDG_InitTypeDef { - prescaler: u32, - reload: u32, - window: u32, - ewi: u32, -} - -#[repr(C)] -struct IWDG_HandleTypeDef { - instance: *mut u32, - init: IWDG_InitTypeDef, -} - -const IWDG_PRESCALER_256: u32 = 0x06; // prescaler divider -const IWDG_BASE: u32 = 0x4000_3000; // IWDG base address (STM32U5) - -static mut IWDG_HANDLE: IWDG_HandleTypeDef = IWDG_HandleTypeDef { - instance: IWDG_BASE as *mut u32, - init: IWDG_InitTypeDef { - prescaler: IWDG_PRESCALER_256, - reload: 125, // ~1s timeout with 32kHz LSI - window: 0xFFF, // disabled window - ewi: 0, // no early wake-up interrupt - }, -}; - #[embassy_executor::main] async fn main(spawner: Spawner) { info!("boot"); - let p = embassy_stm32::init(Default::default()); - let mut led = Output::new(p.PB0, Level::Low, Speed::Low); + let mut config = Config::default(); + config.enable_debug_during_sleep = true; + let p = embassy_stm32::init(config); + let mut led = Output::new(p.PA3, Level::Low, Speed::Low); + let _led_ground = Output::new(p.PB0, Level::Low, Speed::Low); info!("init m8"); + // Clearing after the wakeup + let rcc = pac::RCC; + rcc.csr().write(|w| w.set_rmvf(true)); + + // Check wake source + let pwr = pac::PWR; + if pwr.sr().read().sbf() { + info!("Woke from Standby via watchdog"); + pwr.sr().write(|w| w.set_sbf(true)); + } + // HARDWARE UART to the PC - let mut cfg = Config::default(); + let mut cfg = UsartConfig::default(); cfg.baudrate = BAUD; static TX_BUF: StaticCell<[u8; 256]> = StaticCell::new(); static RX_BUF: StaticCell<[u8; 256]> = StaticCell::new(); @@ -87,42 +71,32 @@ async fn main(spawner: Spawner) { spawner.spawn(uart_task(uart, &PIPE_HW_TX, &PIPE_HW_RX).unwrap()); // END OF HARDWARE UART to the PC - let pwr = pac::PWR; + let dbg = pac::DBGMCU; + let cr = dbg.cr().read(); + info!("DBGMCU CR: dbg_stop={}, dbg_standby={}", cr.dbg_stop(), cr.dbg_standby()); - let from_standby = pwr.sr().read().sbf(); - if from_standby { - info!("Wake from Standby"); - pwr.sr().write(|w| w.set_sbf(true)); - } - let rcc = pac::RCC; - let csr = rcc.csr().read(); - if csr.iwdgrstf() { - info!("Reset source: IWDG"); - } - rcc.csr().write(|w| w.set_rmvf(true)); // clear reset flags - info!("Iwdg 1 init"); + // MAIN LOOP + info!("tick start"); + led.set_high(); + info!("LED IS HIGH"); + Timer::after(Duration::from_millis(500)).await; + led.set_low(); + info!("LED IS LOW"); + Timer::after(Duration::from_millis(500)).await; + led.set_high(); + info!("LED IS HIGH"); + + info!("Iwdg init"); + let mut watchdog = IndependentWatchdog::new(p.IWDG, 2_000_000); // 2 seconds + watchdog.unleash(); + Timer::after(Duration::from_millis(10)).await; + unsafe { - HAL_IWDG_Init(addr_of_mut!(IWDG_HANDLE) as *mut ()); + info!("Standby..."); + HAL_PWR_EnterSTANDBYMode(); } - info!("Iwdg 2 init"); + loop { - info!("tick start"); - led.set_high(); - info!("LED IS HIGH"); - Timer::after(Duration::from_millis(500)).await; - led.set_low(); - info!("LED IS LOW"); - Timer::after(Duration::from_millis(500)).await; - led.set_high(); - info!("LED IS HIGH"); - - unsafe { - info!("Standby..."); - led.set_low(); - HAL_IWDG_Refresh(addr_of_mut!(IWDG_HANDLE) as *mut ()); - HAL_PWR_EnterSTANDBYMode(); - } - - yield_now().await; + cortex_m::asm::wfi(); } }