void clock_init(void) { /* * The initial state : * SYSCLK from HSI (=8MHz), no divider on AHB, APB1, APB2 * PLL unlocked, RTC enabled on LSE */ config_hispeed_clock(); /* configure RTC clock */ wait_rtc_ready(); prepare_rtc_write(); /* set RTC divider to /1 */ STM32_RTC_PRLH = 0; STM32_RTC_PRLL = 0; finalize_rtc_write(); /* setup RTC EXTINT17 to wake up us from STOP mode */ STM32_EXTI_IMR |= (1 << 17); STM32_EXTI_RTSR |= (1 << 17); /* * Our deep sleep mode is STOP mode. * clear PDDS (stop mode) , set LDDS (regulator in low power mode) */ STM32_PWR_CR = (STM32_PWR_CR & ~2) | 1; /* Enable RTC interrupts */ task_enable_irq(STM32_IRQ_RTC_WAKEUP); task_enable_irq(STM32_IRQ_RTC_ALARM); }
void runtime_init(void) { /* * put 1 Wait-State for flash access to ensure proper reads at 48Mhz * and enable prefetch buffer. */ STM32_FLASH_ACR = STM32_FLASH_ACR_LATENCY | STM32_FLASH_ACR_PRFTEN; config_hispeed_clock(); rtc_init(); }
/* Idle task. Executed when no tasks are ready to be scheduled. */ void __idle(void) { timestamp_t t0, t1; int next_delay; uint32_t rtc_t0, rtc_t1; while (1) { asm volatile("cpsid i"); t0 = get_time(); next_delay = __hw_clock_event_get() - t0.le.lo; if (DEEP_SLEEP_ALLOWED && (next_delay > STOP_MODE_LATENCY)) { /* deep-sleep in STOP mode */ enable_serial_wakeup(1); /* set deep sleep bit */ CPU_SCB_SYSCTRL |= 0x4; rtc_t0 = set_rtc_alarm(0, next_delay - STOP_MODE_LATENCY); asm("wfi"); CPU_SCB_SYSCTRL &= ~0x4; enable_serial_wakeup(0); /* re-lock the PLL */ config_hispeed_clock(); /* fast forward timer according to RTC counter */ rtc_t1 = reset_rtc_alarm(); t1.val = t0.val + (rtc_t1 - rtc_t0) * US_PER_RTC_TICK; force_time(t1); } else { /* normal idle : only CPU clock stopped */ asm("wfi"); } asm volatile("cpsie i"); } }