Skip to content

STM32 LPT optimisation #5862

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jan 18, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 2 additions & 9 deletions targets/TARGET_STM/lp_ticker.c
Original file line number Diff line number Diff line change
Expand Up @@ -292,15 +292,8 @@ void lp_ticker_init(void)

uint32_t lp_ticker_read(void)
{
uint32_t usecs = 0;
time_t time = 0;

do {
time = rtc_read();
usecs = rtc_read_subseconds();
} while (time != rtc_read());

return (time * 1000000) + usecs;
uint32_t usecs = rtc_read_us();
return usecs;
}

void lp_ticker_set_interrupt(timestamp_t timestamp)
Expand Down
30 changes: 28 additions & 2 deletions targets/TARGET_STM/rtc_api.c
Original file line number Diff line number Diff line change
Expand Up @@ -36,8 +36,12 @@
static RTC_HandleTypeDef RtcHandle;

#if DEVICE_LOWPOWERTIMER && !MBED_CONF_TARGET_LOWPOWERTIMER_LPTIM

#define GET_TICK_PERIOD(VALUE) (2048 * 1000000 / VALUE) /* 1s / SynchPrediv value * 2^11 (value to get the maximum precision value with no u32 overflow) */

static void (*irq_handler)(void);
static void RTC_IRQHandler(void);
static uint32_t lp_TickPeriod_us = GET_TICK_PERIOD(4095); /* default SynchPrediv value = 4095 */
#endif /* DEVICE_LOWPOWERTIMER && !MBED_CONF_TARGET_LOWPOWERTIMER_LPTIM */

void rtc_init(void)
Expand Down Expand Up @@ -123,6 +127,10 @@ void rtc_init(void)
RtcHandle.Init.OutPutType = RTC_OUTPUT_TYPE_OPENDRAIN;
#endif /* TARGET_STM32F1 */

#if DEVICE_LOWPOWERTIMER && !MBED_CONF_TARGET_LOWPOWERTIMER_LPTIM
lp_TickPeriod_us = GET_TICK_PERIOD(RtcHandle.Init.SynchPrediv);
#endif

if (HAL_RTC_Init(&RtcHandle) != HAL_OK) {
error("RTC initialization failed");
}
Expand Down Expand Up @@ -309,9 +317,27 @@ static void RTC_IRQHandler(void)
}
}

uint32_t rtc_read_subseconds(void)
uint32_t rtc_read_us(void)
{
return 1000000.f * ((double)((RTC->PRER & RTC_PRER_PREDIV_S) - RTC->SSR) / ((RTC->PRER & RTC_PRER_PREDIV_S) + 1));
RTC_TimeTypeDef timeStruct = {0};
RTC_DateTypeDef dateStruct = {0};

RtcHandle.Instance = RTC;
HAL_RTC_GetTime(&RtcHandle, &timeStruct, RTC_FORMAT_BIN);

/* Reading RTC current time locks the values in calendar shadow registers until Current date is read
to ensure consistency between the time and date values */
HAL_RTC_GetDate(&RtcHandle, &dateStruct, RTC_FORMAT_BIN);

if (timeStruct.SubSeconds > timeStruct.SecondFraction) {
/* SS can be larger than PREDIV_S only after a shift operation. In that case, the correct
time/date is one second less than as indicated by RTC_TR/RTC_DR. */
timeStruct.Seconds -= 1;
}
uint32_t RTCTime = timeStruct.Seconds + timeStruct.Minutes * 60 + timeStruct.Hours * 60 * 60;
uint32_t Time_us = ((timeStruct.SecondFraction - timeStruct.SubSeconds) * lp_TickPeriod_us) >> 11;

return (RTCTime * 1000000) + Time_us ;
}

void rtc_set_wake_up_timer(uint32_t delta)
Expand Down
6 changes: 3 additions & 3 deletions targets/TARGET_STM/rtc_api_hal.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,11 +51,11 @@ extern "C" {
#define RTC_CLOCK LSI_VALUE
#endif

/** Read the subsecond register.
/** Read RTC time with subsecond precision.
*
* @return The remaining time as microseconds (0-999999)
* @return Time is microsecond
*/
uint32_t rtc_read_subseconds(void);
uint32_t rtc_read_us(void);

/** Program a wake up timer event in delta microseconds.
*
Expand Down