HAL RTC initialization and configuration functions migration

The goal of this page is to show how to migrate the initialization sequence using STM32CubeMX2 :

  • Open STM32CubeMX2 RTC configuration panel.

  • Configure the SW layer HAL.

  • Configure the RTC main features.

  • Configure the RTC advanced features.

  • Configure the RTC GPIO pins.

  • Configure the NVIC if the application requires the RTC to be used in IT mode.

  • Generate the code.

Note

RTC initialization key changes:

  • RTC handle is removed.

  • Init and Deinit functions are removed, you can follow the sequence below to get the same result in HAL2. Generated RTC initialization and de-initialization sequences

  • Unitairy functions are provided to configure the RTC in HAL2.

  • In HAL2 you need to call HAL_RTC_DisableWriteProtection() & HAL_RTC_EnterInitMode() before starting the configuration and end it with HAL_RTC_EnableWriteProtection() & HAL_RTC_ExitInitMode() as highlighted in the HAL RTC Typical use cases for migration

HAL RTC configuration panel

Create a new project with the STM32CubeMX2, then start the initialization and the main configuration.

Project configuration panel

HAL RTC main features configuration

Configure the RTC main features.

RTC main feature configuration

HAL RTC advanced features configuration

Configure the advanced RTC features.

RTC advanced feature configuration

GPIO configuration

Configure GPIO pins.

RTC GPIO configuration

NVIC configuration

Configure the NVIC in case of an interrupt.

RTC NVIC configuration

Generated RTC initialization and de-initialization sequences

The RTC initialization and de-initialization sequences are generated in the mx_rtc_hal_init function in mx_rtc.c file under $PROJ_DIR$/generated/STM32Cube_CodeGen.

Related concepts:

STM32CubeMX2 Generated with default values

Topic

HAL1 code snippet

HAL2 code snippet

Initialization and configuration sequence

static void MX_RTC_Init(void)
{

  RTC_PrivilegeStateTypeDef privilegeState = {0};
  RTC_TimeTypeDef sTime = {0};
  RTC_DateTypeDef sDate = {0};
  RTC_AlarmTypeDef sAlarm = {0};

  /** Initialize RTC Only */
  hrtc.Instance = RTC;
  hrtc.Init.HourFormat = RTC_HOURFORMAT_24;
  hrtc.Init.AsynchPrediv = 127;
  hrtc.Init.SynchPrediv = 255;
  hrtc.Init.OutPut = RTC_OUTPUT_DISABLE;
  hrtc.Init.OutPutRemap = RTC_OUTPUT_REMAP_NONE;
  hrtc.Init.OutPutPolarity = RTC_OUTPUT_POLARITY_HIGH;
  hrtc.Init.OutPutType = RTC_OUTPUT_TYPE_OPENDRAIN;
  hrtc.Init.OutPutPullUp = RTC_OUTPUT_PULLUP_NONE;
  hrtc.Init.BinMode = RTC_BINARY_NONE;
  if (HAL_RTC_Init(&hrtc) != HAL_OK)
  {
    Error_Handler();
  }
  privilegeState.rtcPrivilegeFull = RTC_PRIVILEGE_FULL_NO;
  privilegeState.backupRegisterPrivZone = RTC_PRIVILEGE_BKUP_ZONE_NONE;
  privilegeState.backupRegisterStartZone2 = RTC_BKP_DR0;
  privilegeState.backupRegisterStartZone3 = RTC_BKP_DR0;
  if (HAL_RTCEx_PrivilegeModeSet(&hrtc, &privilegeState) != HAL_OK)
  {
    Error_Handler();
  }






  /** Initialize RTC and set the Time and Date */
  sTime.Hours = 0x0;
  sTime.Minutes = 0x0;
  sTime.Seconds = 0x0;
  sTime.DayLightSaving = RTC_DAYLIGHTSAVING_NONE;
  sTime.StoreOperation = RTC_STOREOPERATION_RESET;
  if (HAL_RTC_SetTime(&hrtc, &sTime, RTC_FORMAT_BCD) != HAL_OK)
  {
    Error_Handler();
  }
  sDate.WeekDay = RTC_WEEKDAY_MONDAY;
  sDate.Month = RTC_MONTH_JANUARY;
  sDate.Date = 0x1;
  sDate.Year = 0x0;

  if (HAL_RTC_SetDate(&hrtc, &sDate, RTC_FORMAT_BCD) != HAL_OK)
  {
    Error_Handler();
  }


  /** Enable the Alarm A */
  sAlarm.AlarmTime.Hours = 0x1;
  sAlarm.AlarmTime.Minutes = 0x23;
  sAlarm.AlarmTime.Seconds = 0x30;
  sAlarm.AlarmTime.SubSeconds = 0x0;
  sAlarm.AlarmMask = RTC_ALARMMASK_NONE;
  sAlarm.AlarmSubSecondMask = RTC_ALARMSUBSECONDMASK_ALL;
  sAlarm.AlarmDateWeekDaySel = RTC_ALARMDATEWEEKDAYSEL_DATE;
  sAlarm.AlarmDateWeekDay = 0x1;
  sAlarm.Alarm = RTC_ALARM_A;






  if (HAL_RTC_SetAlarm_IT(&hrtc, &sAlarm, RTC_FORMAT_BCD) != HAL_OK)
  {
    Error_Handler();
  }

}











void HAL_RTC_MspInit(RTC_HandleTypeDef* hrtc)
{
  RCC_PeriphCLKInitTypeDef PeriphClkInit = {0};
  if(hrtc->Instance==RTC)
  {

  /** Initializes the peripherals clock */
    PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_RTC;
    PeriphClkInit.RTCClockSelection = RCC_RTCCLKSOURCE_LSI;
    if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)
    {
      Error_Handler();
    }

    /* Peripheral clock enable */
    __HAL_RCC_RTC_ENABLE();
    __HAL_RCC_RTCAPB_CLK_ENABLE();
    __HAL_RCC_RTCAPB_CLKAM_ENABLE();
    /* RTC interrupt Init */
    HAL_NVIC_SetPriority(RTC_IRQn, 0, 0);
    HAL_NVIC_EnableIRQ(RTC_IRQn);
  }

}
system_status_t mx_rtc_init(void)
{
  hal_rtc_config_t rtc_config;
  hal_rtc_alarm_t alarm_a;
  hal_rtc_alarm_config_t alarm_a_config;
  hal_rtc_alarm_date_time_t alarm_a_date_time;
  hal_rtc_output_tampalarm_config_t output_tampalarm_config;
  hal_rtc_output_t output;

  /* Disable RTC Domain Write Protection */
  HAL_PWR_DisableRTCDomainWriteProtection();

  /* Clock configuration */
  /* Reset backup domain */
  HAL_RCC_ResetBackupDomain();

  if (HAL_RCC_RTC_SetKernelClkSource(HAL_RCC_RTC_CLK_SRC_LSI) != HAL_OK)
  {
    return SYSTEM_CLOCK_ERROR;
  }


  HAL_RCC_RTCAPB_EnableClock();
  HAL_RCC_RTC_EnableKernelClock();

  if (HAL_RTC_DisableWriteProtection() != HAL_OK)
  {
    return SYSTEM_PERIPHERAL_ERROR;
  }

  if (HAL_RTC_EnterInitMode() != HAL_OK)
  {
    return SYSTEM_PERIPHERAL_ERROR;
  }

  rtc_config.mode = HAL_RTC_MODE_BCD;
  rtc_config.asynch_prediv = 127;
  rtc_config.synch_prediv = 255;

  if (HAL_RTC_SetConfig(&rtc_config) != HAL_OK)
  {
    return SYSTEM_PERIPHERAL_ERROR;
  }

  if (HAL_RTC_ExitInitMode() != HAL_OK)
  {
    return SYSTEM_PERIPHERAL_ERROR;
  }

  alarm_a = HAL_RTC_ALARM_A;
  alarm_a_config.auto_clear = HAL_ALARM_AUTO_CLEAR_ENABLE;

  if (HAL_RTC_ALARM_SetConfig(alarm_a, &alarm_a_config) != HAL_OK)
  {
    return SYSTEM_PERIPHERAL_ERROR;
  }

  alarm_a_date_time.mday_wday_selection = HAL_RTC_ALARM_DAY_TYPE_SEL_MONTHDAY;
  alarm_a_date_time.wday_mday.mday = 1;
  alarm_a_date_time.time.hour = 1;
  alarm_a_date_time.time.min = 23;
  alarm_a_date_time.time.sec = 30;
  alarm_a_date_time.time.subsec = 0;
  alarm_a_date_time.mask = HAL_RTC_ALARM_MASK_NONE;
  alarm_a_date_time.subsec_mask = 0;

  if (HAL_RTC_ALARM_SetDateTime(alarm_a, &alarm_a_date_time) != HAL_OK)
  {
    return SYSTEM_PERIPHERAL_ERROR;
  }

  output_tampalarm_config.polarity = HAL_RTC_OUTPUT_TAMPALARM_POLARITY_HIGH;
  output_tampalarm_config.type = HAL_RTC_OUTPUT_TAMPALARM_TYPE_PUSHPULL;
  output_tampalarm_config.pullup = HAL_RTC_OUTPUT_TAMPALARM_PULLUP_DISABLE;

  if (HAL_RTC_OUTPUT_SetConfigTampalarm(&output_tampalarm_config) != HAL_OK)
  {
    return SYSTEM_PERIPHERAL_ERROR;
  }

  output = HAL_RTC_OUTPUT_OUT1_TAMP;

  if (HAL_RTC_OUTPUT_Enable(output) != HAL_OK)
  {
    return SYSTEM_PERIPHERAL_ERROR;
  }

  if (HAL_RTC_EnableWriteProtection() != HAL_OK)
  {
    return SYSTEM_PERIPHERAL_ERROR;
  }

  /* Enable RTC Domain Write Protection */
  HAL_PWR_EnableRTCDomainWriteProtection();















  /* Enable the interruption for RTC */
  HAL_CORTEX_NVIC_SetPriority(RTC_IRQn, HAL_CORTEX_NVIC_PREEMP_PRIORITY_0, HAL_CORTEX_NVIC_SUB_PRIORITY_0);
  HAL_CORTEX_NVIC_EnableIRQ(RTC_IRQn);

  return SYSTEM_OK;
}

Deinitialization sequence

void HAL_RTC_MspDeInit(RTC_HandleTypeDef* hrtc)
{
  if(hrtc->Instance==RTC)
  {
    /* Peripheral clock disable */
    __HAL_RCC_RTC_DISABLE();
    __HAL_RCC_RTCAPB_CLK_DISABLE();
    __HAL_RCC_RTCAPB_CLKAM_DISABLE();

    /* RTC interrupt DeInit */
    HAL_NVIC_DisableIRQ(RTC_IRQn);
  }
}
void mx_rtc_hal_deinit(void)
{







  /* Disable the interruption for RTC */
  HAL_CORTEX_NVIC_DisableIRQ(RTC_IRQn);
}

IRQ handle function

void RTC_IRQHandler(void)
{
  HAL_RTC_AlarmIRQHandler(&hrtc);
}
void RTC_IRQHandler(void)
{
  HAL_RTC_IRQHandler();
}