STAR
Cal STAR — firmware, DAQ server, and engine design
Loading...
Searching...
No Matches
board_sleep.c
Go to the documentation of this file.
1#include "board_sleep.h"
2
3#include "FreeRTOS.h"
4#include "board_time.h"
5#include "cmsis_os2.h"
6#include "main.h"
7#include "sleep_math.h"
8#include "task.h"
9#include "usbd_cdc_if.h"
10
12void SystemClock_Config(void);
13
15static volatile bool rtc_fired;
16
17/* HAL weak override, from RTC_WKUP_IRQHandler. */
22
23static uint32_t rtc_stamp(void) {
27 (void)HAL_RTC_GetDate(&hrtc, &d, RTC_FORMAT_BIN); /* unlocks shadows */
28 return sleep_rtc_steps(t.Hours, t.Minutes, t.Seconds, t.SubSeconds);
29}
30
31/* Count 125 sub-second steps (0.5 s nominal) against TIM2. */
32static uint32_t measure_lsi(void) {
33 const uint32_t steps = 125U;
34 uint32_t start = board_time_us(), ssr = RTC->SSR;
35 while (RTC->SSR == ssr) { /* align to a step edge */
36 if (board_time_us() - start > 20000U) {
37 return 0; /* RTC not counting: LSI dead */
38 }
39 }
40 uint32_t t0 = board_time_us();
41 for (uint32_t n = 0; n < steps; ++n) {
42 ssr = RTC->SSR;
43 while (RTC->SSR == ssr) {
44 if (board_time_us() - t0 > 1000000U) {
45 return 0;
46 }
47 }
48 }
49 return sleep_lsi_hz(steps, board_time_us() - t0);
50}
51
52bool board_sleep_init(void) {
53 info.stop_allowed = (FLASH->OPTSR_CUR & FLASH_OPTSR_NRST_STOP_D1) != 0U;
54 info.lsi_hz = measure_lsi();
55 /* RM0468: LSI is 32 kHz nominal; refuse a reading far from it. */
56 info.ready = info.lsi_hz > 24000U && info.lsi_hz < 40000U;
60 }
61 return info.ready;
62}
63
65 return &info;
66}
67
68uint32_t board_sleep(uint32_t ms, bool (*wake_now)(void)) {
69 /* Stop gates off the USB clocks: stay awake while a host is attached. */
70 if (!info.ready || !info.stop_allowed || usb_configured()) {
71 info.awake_waits++;
72 return 0;
73 }
75 if (wake_now && wake_now()) {
76 (void)xTaskResumeAll();
77 return 0;
78 }
79 rtc_fired = false;
82 uint32_t before = rtc_stamp();
83 HAL_SuspendTick(); /* TIM6, HAL timebase */
84 SysTick->CTRL &= ~SysTick_CTRL_ENABLE_Msk; /* FreeRTOS tick */
85
86 /* D2 and D3 to DStop (not DStandby), then D1: SLEEPDEEP + WFI. */
88 PWR_D2_DOMAIN);
93
94 /* Awake: clocks first, then read how long that was. */
98 (void)HAL_RTC_WaitForSynchro(&hrtc); /* shadow registers stale after Stop */
100 uint32_t slept = sleep_elapsed_ms(before, rtc_stamp(), info.lsi_hz);
103
104 info.sleeps++;
105 if (rtc_fired) {
106 info.rtc_wakes++;
107 } else {
108 info.early_wakes++;
109 }
110 info.last_slept_ms = slept;
111 (void)xTaskResumeAll();
112 (void)xTaskCatchUpTicks(pdMS_TO_TICKS(slept));
113 return slept;
114}
static uint32_t measure_lsi(void)
Definition board_sleep.c:32
static board_sleep_info_t info
Definition board_sleep.c:14
uint32_t board_sleep(uint32_t ms, bool(*wake_now)(void))
Definition board_sleep.c:68
static volatile bool rtc_fired
Definition board_sleep.c:15
const board_sleep_info_t * board_sleep_info(void)
Definition board_sleep.c:64
void SystemClock_Config(void)
System Clock Configuration.
Definition main.c:203
bool board_sleep_init(void)
Definition board_sleep.c:52
static uint32_t rtc_stamp(void)
Definition board_sleep.c:23
uint32_t board_time_us(void)
Definition board_time.c:34
static void start(gnss_frame_parser_t *p, uint8_t byte)
Definition gnss_frame.c:45
#define SysTick_CTRL_ENABLE_Msk
SysTick CTRL: ENABLE Mask.
#define SysTick
SysTick configuration struct.
#define CoreDebug
Core Debug configuration struct.
#define CoreDebug_DHCSR_C_DEBUGEN_Msk
CoreDebug DHCSR: C_DEBUGEN Mask.
#define SET_BIT(REG, BIT)
Definition stm32h7xx.h:207
void HAL_ResumeTick(void)
Resume Tick increment.
void HAL_SuspendTick(void)
Suspend Tick increment.
#define PWR_D1_DOMAIN
#define PWR_D3_DOMAIN
void HAL_PWREx_EnterSTOPMode(uint32_t Regulator, uint8_t STOPEntry, uint32_t Domain)
#define PWR_LOWPOWERREGULATOR_ON
#define PWR_STOPENTRY_WFI
#define FLASH_OPTSR_NRST_STOP_D1
D1 domain DStop entry reset option status bit.
#define DBGMCU_CR_DBG_STOPD1
#define DBGMCU_CR_DBG_SLEEPD1
#define DBGMCU_CR_DBG_STOPD3
#define RTC
#define FLASH
#define DBGMCU
HAL_StatusTypeDef HAL_RTCEx_DeactivateWakeUpTimer(RTC_HandleTypeDef *hrtc)
HAL_StatusTypeDef HAL_RTCEx_SetWakeUpTimer_IT(RTC_HandleTypeDef *hrtc, uint32_t WakeUpCounter, uint32_t WakeUpClock)
void HAL_RTCEx_WakeUpTimerEventCallback(RTC_HandleTypeDef *h)
Definition board_sleep.c:18
#define RTC_WAKEUPCLOCK_RTCCLK_DIV16
HAL_StatusTypeDef HAL_RTC_GetDate(const RTC_HandleTypeDef *hrtc, RTC_DateTypeDef *sDate, uint32_t Format)
HAL_StatusTypeDef HAL_RTC_GetTime(const RTC_HandleTypeDef *hrtc, RTC_TimeTypeDef *sTime, uint32_t Format)
HAL_StatusTypeDef HAL_RTC_WaitForSynchro(RTC_HandleTypeDef *hrtc)
#define __HAL_RTC_WRITEPROTECTION_ENABLE(__HANDLE__)
Enable the write protection for RTC registers.
#define __HAL_RTC_WRITEPROTECTION_DISABLE(__HANDLE__)
Disable the write protection for RTC registers.
#define RTC_FORMAT_BIN
bool usb_configured(void)
RTC_HandleTypeDef hrtc
Definition main.c:52
*brief user defined string literal for JSON values *sa std::size_t n
Definition json.hpp:24474
#define pdMS_TO_TICKS(xTimeInMs)
Definition projdefs.h:42
uint32_t sleep_elapsed_ms(uint32_t from_steps, uint32_t to_steps, uint32_t lsi_hz)
Definition sleep_math.c:23
uint32_t sleep_lsi_hz(uint32_t steps, uint32_t us)
Definition sleep_math.c:33
uint32_t sleep_rtc_steps(uint8_t hours, uint8_t minutes, uint8_t seconds, uint32_t ssr)
Definition sleep_math.c:14
uint16_t sleep_wut_reload(uint32_t ms, uint32_t lsi_hz)
Definition sleep_math.c:3
RTC Date structure definition.
RTC Handle Structure definition.
RTC Time structure definition.
BaseType_t xTaskResumeAll(void) PRIVILEGED_FUNCTION
Definition tasks.c:2187
void vTaskSuspendAll(void) PRIVILEGED_FUNCTION
Definition tasks.c:2103
BaseType_t xTaskCatchUpTicks(TickType_t xTicksToCatchUp) PRIVILEGED_FUNCTION
Definition tasks.c:2676
: Header for usbd_cdc_if.c file.