1 /**
2   ******************************************************************************
3   * @file    stm32wb0x_ll_rtc.c
4   * @author  MCD Application Team
5   * @brief   RTC LL module driver.
6   ******************************************************************************
7   * @attention
8   *
9   * Copyright (c) 2024 STMicroelectronics.
10   * All rights reserved.
11   *
12   * This software is licensed under terms that can be found in the LICENSE file
13   * in the root directory of this software component.
14   * If no LICENSE file comes with this software, it is provided AS-IS.
15   *
16   ******************************************************************************
17   */
18 #if defined(USE_FULL_LL_DRIVER)
19 
20 /* Includes ------------------------------------------------------------------*/
21 #include "stm32wb0x_ll_rtc.h"
22 #include "stm32wb0x_ll_cortex.h"
23 #ifdef  USE_FULL_ASSERT
24 #include "stm32_assert.h"
25 #else
26 #define assert_param(expr) ((void)0U)
27 #endif
28 
29 /** @addtogroup STM32WB0x_LL_Driver
30   * @{
31   */
32 
33 #if defined(RTC)
34 
35 /** @addtogroup RTC_LL
36   * @{
37   */
38 
39 /* Private types -------------------------------------------------------------*/
40 /* Private variables ---------------------------------------------------------*/
41 /* Private constants ---------------------------------------------------------*/
42 /** @addtogroup RTC_LL_Private_Constants
43   * @{
44   */
45 /* Default values used for prescaler */
46 #define RTC_ASYNCH_PRESC_DEFAULT     0x0000007FU
47 #define RTC_SYNCH_PRESC_DEFAULT      0x000000FFU
48 
49 /* Values used for timeout */
50 #define RTC_INITMODE_TIMEOUT         1000U /* 1s when tick set to 1ms */
51 #define RTC_SYNCHRO_TIMEOUT          1000U /* 1s when tick set to 1ms */
52 /**
53   * @}
54   */
55 
56 /* Private macros ------------------------------------------------------------*/
57 /** @addtogroup RTC_LL_Private_Macros
58   * @{
59   */
60 
61 #define IS_LL_RTC_HOURFORMAT(__VALUE__) (((__VALUE__) == LL_RTC_HOURFORMAT_24HOUR) \
62                                       || ((__VALUE__) == LL_RTC_HOURFORMAT_AMPM))
63 
64 #define IS_LL_RTC_ASYNCH_PREDIV(__VALUE__)   ((__VALUE__) <= 0x7FU)
65 
66 #define IS_LL_RTC_SYNCH_PREDIV(__VALUE__)    ((__VALUE__) <= 0x7FFFU)
67 
68 #define IS_LL_RTC_FORMAT(__VALUE__) (((__VALUE__) == LL_RTC_FORMAT_BIN) \
69                                   || ((__VALUE__) == LL_RTC_FORMAT_BCD))
70 
71 #define IS_LL_RTC_TIME_FORMAT(__VALUE__) (((__VALUE__) == LL_RTC_TIME_FORMAT_AM_OR_24) \
72                                        || ((__VALUE__) == LL_RTC_TIME_FORMAT_PM))
73 
74 #define IS_LL_RTC_HOUR12(__HOUR__)            (((__HOUR__) > 0U) && ((__HOUR__) <= 12U))
75 #define IS_LL_RTC_HOUR24(__HOUR__)            ((__HOUR__) <= 23U)
76 #define IS_LL_RTC_MINUTES(__MINUTES__)        ((__MINUTES__) <= 59U)
77 #define IS_LL_RTC_SECONDS(__SECONDS__)        ((__SECONDS__) <= 59U)
78 
79 #define IS_LL_RTC_WEEKDAY(__VALUE__) (((__VALUE__) == LL_RTC_WEEKDAY_MONDAY) \
80                                    || ((__VALUE__) == LL_RTC_WEEKDAY_TUESDAY) \
81                                    || ((__VALUE__) == LL_RTC_WEEKDAY_WEDNESDAY) \
82                                    || ((__VALUE__) == LL_RTC_WEEKDAY_THURSDAY) \
83                                    || ((__VALUE__) == LL_RTC_WEEKDAY_FRIDAY) \
84                                    || ((__VALUE__) == LL_RTC_WEEKDAY_SATURDAY) \
85                                    || ((__VALUE__) == LL_RTC_WEEKDAY_SUNDAY))
86 
87 #define IS_LL_RTC_DAY(__DAY__)     (((__DAY__) >= 1U) && ((__DAY__) <= 31U))
88 
89 #define IS_LL_RTC_MONTH(__MONTH__) (((__MONTH__) >= 1U) && ((__MONTH__) <= 12U))
90 
91 #define IS_LL_RTC_YEAR(__YEAR__)   ((__YEAR__) <= 99U)
92 
93 #define IS_LL_RTC_ALMA_MASK(__VALUE__) (((__VALUE__) == LL_RTC_ALMA_MASK_NONE) \
94                                      || ((__VALUE__) == LL_RTC_ALMA_MASK_DATEWEEKDAY) \
95                                      || ((__VALUE__) == LL_RTC_ALMA_MASK_HOURS) \
96                                      || ((__VALUE__) == LL_RTC_ALMA_MASK_MINUTES) \
97                                      || ((__VALUE__) == LL_RTC_ALMA_MASK_SECONDS) \
98                                      || ((__VALUE__) == LL_RTC_ALMA_MASK_ALL))
99 
100 #define IS_LL_RTC_ALMA_DATE_WEEKDAY_SEL(__SEL__) (((__SEL__) == LL_RTC_ALMA_DATEWEEKDAYSEL_DATE) || \
101                                                   ((__SEL__) == LL_RTC_ALMA_DATEWEEKDAYSEL_WEEKDAY))
102 
103 /**
104   * @}
105   */
106 /* Private function prototypes -----------------------------------------------*/
107 /* Exported functions --------------------------------------------------------*/
108 /** @addtogroup RTC_LL_Exported_Functions
109   * @{
110   */
111 
112 /** @addtogroup RTC_LL_EF_Init
113   * @{
114   */
115 
116 /**
117   * @brief  De-Initializes the RTC registers to their default reset values.
118   * @note   This function does not reset the RTC Clock source and RTC Backup Data
119   *         registers.
120   * @param  RTCx RTC Instance
121   * @retval An ErrorStatus enumeration value:
122   *          - SUCCESS: RTC registers are de-initialized
123   *          - ERROR: RTC registers are not de-initialized
124   */
LL_RTC_DeInit(RTC_TypeDef * RTCx)125 ErrorStatus LL_RTC_DeInit(RTC_TypeDef *RTCx)
126 {
127   ErrorStatus status = ERROR;
128 
129   /* Check the parameter */
130   assert_param(IS_RTC_ALL_INSTANCE(RTCx));
131 
132   /* Disable the write protection for RTC registers */
133   LL_RTC_DisableWriteProtection(RTCx);
134 
135   /* Set Initialization mode */
136   if (LL_RTC_EnterInitMode(RTCx) != ERROR)
137   {
138     /* Reset TR, DR and CR registers */
139     LL_RTC_WriteReg(RTCx, TR,       0x00000000U);
140     LL_RTC_WriteReg(RTCx, WUTR,     RTC_WUTR_WUT);
141     LL_RTC_WriteReg(RTCx, DR,      (RTC_DR_WDU_0 | RTC_DR_MU_0 | RTC_DR_DU_0));
142 
143     /* Reset All CR bits except CR[2:0] */
144     LL_RTC_WriteReg(RTCx, CR, (LL_RTC_ReadReg(RTCx, CR) & RTC_CR_WUCKSEL));
145 
146     LL_RTC_WriteReg(RTCx, PRER,    (RTC_PRER_PREDIV_A | RTC_SYNCH_PRESC_DEFAULT));
147     LL_RTC_WriteReg(RTCx, ALRMAR,   0x00000000U);
148     LL_RTC_WriteReg(RTCx, CALR,     0x00000000U);
149     LL_RTC_WriteReg(RTCx, SHIFTR,   0x00000000U);
150     LL_RTC_WriteReg(RTCx, ALRMASSR, 0x00000000U);
151 
152     /* Reset ISR register and exit initialization mode */
153     LL_RTC_WriteReg(RTCx, ISR,      0x00000000U);
154 
155     /* Wait till the RTC RSF flag is set */
156     status = LL_RTC_WaitForSynchro(RTCx);
157   }
158 
159   /* Enable the write protection for RTC registers */
160   LL_RTC_EnableWriteProtection(RTCx);
161 
162   return status;
163 }
164 
165 /**
166   * @brief  Initializes the RTC registers according to the specified parameters
167   *         in RTC_InitStruct.
168   * @param  RTCx RTC Instance
169   * @param  RTC_InitStruct pointer to a @ref LL_RTC_InitTypeDef structure that contains
170   *         the configuration information for the RTC peripheral.
171   * @note   The RTC Prescaler register is write protected and can be written in
172   *         initialization mode only.
173   * @retval An ErrorStatus enumeration value:
174   *          - SUCCESS: RTC registers are initialized
175   *          - ERROR: RTC registers are not initialized
176   */
LL_RTC_Init(RTC_TypeDef * RTCx,LL_RTC_InitTypeDef * RTC_InitStruct)177 ErrorStatus LL_RTC_Init(RTC_TypeDef *RTCx, LL_RTC_InitTypeDef *RTC_InitStruct)
178 {
179   ErrorStatus status = ERROR;
180 
181   /* Check the parameters */
182   assert_param(IS_RTC_ALL_INSTANCE(RTCx));
183   assert_param(IS_LL_RTC_HOURFORMAT(RTC_InitStruct->HourFormat));
184   assert_param(IS_LL_RTC_ASYNCH_PREDIV(RTC_InitStruct->AsynchPrescaler));
185   assert_param(IS_LL_RTC_SYNCH_PREDIV(RTC_InitStruct->SynchPrescaler));
186 
187   /* Disable the write protection for RTC registers */
188   LL_RTC_DisableWriteProtection(RTCx);
189 
190   /* Set Initialization mode */
191   if (LL_RTC_EnterInitMode(RTCx) != ERROR)
192   {
193     /* Set Hour Format */
194     LL_RTC_SetHourFormat(RTCx, RTC_InitStruct->HourFormat);
195 
196     /* Configure Synchronous and Asynchronous prescaler factor */
197     LL_RTC_SetSynchPrescaler(RTCx, RTC_InitStruct->SynchPrescaler);
198     LL_RTC_SetAsynchPrescaler(RTCx, RTC_InitStruct->AsynchPrescaler);
199 
200     /* Exit Initialization mode */
201     LL_RTC_DisableInitMode(RTCx);
202 
203     status = SUCCESS;
204   }
205   /* Enable the write protection for RTC registers */
206   LL_RTC_EnableWriteProtection(RTCx);
207 
208   return status;
209 }
210 
211 /**
212   * @brief  Set each @ref LL_RTC_InitTypeDef field to default value.
213   * @param  RTC_InitStruct pointer to a @ref LL_RTC_InitTypeDef structure which will be initialized.
214   * @retval None
215   */
LL_RTC_StructInit(LL_RTC_InitTypeDef * RTC_InitStruct)216 void LL_RTC_StructInit(LL_RTC_InitTypeDef *RTC_InitStruct)
217 {
218   /* Set RTC_InitStruct fields to default values */
219   RTC_InitStruct->HourFormat      = LL_RTC_HOURFORMAT_24HOUR;
220   RTC_InitStruct->AsynchPrescaler = RTC_ASYNCH_PRESC_DEFAULT;
221   RTC_InitStruct->SynchPrescaler  = RTC_SYNCH_PRESC_DEFAULT;
222 }
223 
224 /**
225   * @brief  Set the RTC current time.
226   * @param  RTCx RTC Instance
227   * @param  RTC_Format This parameter can be one of the following values:
228   *         @arg @ref LL_RTC_FORMAT_BIN
229   *         @arg @ref LL_RTC_FORMAT_BCD
230   * @param  RTC_TimeStruct pointer to a RTC_TimeTypeDef structure that contains
231   *                        the time configuration information for the RTC.
232   * @retval An ErrorStatus enumeration value:
233   *          - SUCCESS: RTC Time register is configured
234   *          - ERROR: RTC Time register is not configured
235   */
LL_RTC_TIME_Init(RTC_TypeDef * RTCx,uint32_t RTC_Format,LL_RTC_TimeTypeDef * RTC_TimeStruct)236 ErrorStatus LL_RTC_TIME_Init(RTC_TypeDef *RTCx, uint32_t RTC_Format, LL_RTC_TimeTypeDef *RTC_TimeStruct)
237 {
238   ErrorStatus status = ERROR;
239 
240   /* Check the parameters */
241   assert_param(IS_RTC_ALL_INSTANCE(RTCx));
242   assert_param(IS_LL_RTC_FORMAT(RTC_Format));
243 
244   if (RTC_Format == LL_RTC_FORMAT_BIN)
245   {
246     if (LL_RTC_GetHourFormat(RTCx) != LL_RTC_HOURFORMAT_24HOUR)
247     {
248       assert_param(IS_LL_RTC_HOUR12(RTC_TimeStruct->Hours));
249       assert_param(IS_LL_RTC_TIME_FORMAT(RTC_TimeStruct->TimeFormat));
250     }
251     else
252     {
253       RTC_TimeStruct->TimeFormat = 0x00U;
254       assert_param(IS_LL_RTC_HOUR24(RTC_TimeStruct->Hours));
255     }
256     assert_param(IS_LL_RTC_MINUTES(RTC_TimeStruct->Minutes));
257     assert_param(IS_LL_RTC_SECONDS(RTC_TimeStruct->Seconds));
258   }
259   else
260   {
261     if (LL_RTC_GetHourFormat(RTCx) != LL_RTC_HOURFORMAT_24HOUR)
262     {
263       assert_param(IS_LL_RTC_HOUR12(__LL_RTC_CONVERT_BCD2BIN(RTC_TimeStruct->Hours)));
264       assert_param(IS_LL_RTC_TIME_FORMAT(RTC_TimeStruct->TimeFormat));
265     }
266     else
267     {
268       RTC_TimeStruct->TimeFormat = 0x00U;
269       assert_param(IS_LL_RTC_HOUR24(__LL_RTC_CONVERT_BCD2BIN(RTC_TimeStruct->Hours)));
270     }
271     assert_param(IS_LL_RTC_MINUTES(__LL_RTC_CONVERT_BCD2BIN(RTC_TimeStruct->Minutes)));
272     assert_param(IS_LL_RTC_SECONDS(__LL_RTC_CONVERT_BCD2BIN(RTC_TimeStruct->Seconds)));
273   }
274 
275   /* Disable the write protection for RTC registers */
276   LL_RTC_DisableWriteProtection(RTCx);
277 
278   /* Set Initialization mode */
279   if (LL_RTC_EnterInitMode(RTCx) != ERROR)
280   {
281     /* Check the input parameters format */
282     if (RTC_Format != LL_RTC_FORMAT_BIN)
283     {
284       LL_RTC_TIME_Config(RTCx, RTC_TimeStruct->TimeFormat, RTC_TimeStruct->Hours,
285                          RTC_TimeStruct->Minutes, RTC_TimeStruct->Seconds);
286     }
287     else
288     {
289       LL_RTC_TIME_Config(RTCx, RTC_TimeStruct->TimeFormat, __LL_RTC_CONVERT_BIN2BCD(RTC_TimeStruct->Hours),
290                          __LL_RTC_CONVERT_BIN2BCD(RTC_TimeStruct->Minutes),
291                          __LL_RTC_CONVERT_BIN2BCD(RTC_TimeStruct->Seconds));
292     }
293 
294     /* Exit Initialization mode */
295     LL_RTC_DisableInitMode(RTCx);
296 
297     /* If  RTC_CR_BYPSHAD bit = 0, wait for synchro else this check is not needed */
298     if (LL_RTC_IsShadowRegBypassEnabled(RTCx) == 0U)
299     {
300       status = LL_RTC_WaitForSynchro(RTCx);
301     }
302     else
303     {
304       status = SUCCESS;
305     }
306   }
307   /* Enable the write protection for RTC registers */
308   LL_RTC_EnableWriteProtection(RTCx);
309 
310   return status;
311 }
312 
313 /**
314   * @brief  Set each @ref LL_RTC_TimeTypeDef field to default value (Time = 00h:00min:00sec).
315   * @param  RTC_TimeStruct pointer to a @ref LL_RTC_TimeTypeDef structure which will be initialized.
316   * @retval None
317   */
LL_RTC_TIME_StructInit(LL_RTC_TimeTypeDef * RTC_TimeStruct)318 void LL_RTC_TIME_StructInit(LL_RTC_TimeTypeDef *RTC_TimeStruct)
319 {
320   /* Time = 00h:00min:00sec */
321   RTC_TimeStruct->TimeFormat = LL_RTC_TIME_FORMAT_AM_OR_24;
322   RTC_TimeStruct->Hours      = 0U;
323   RTC_TimeStruct->Minutes    = 0U;
324   RTC_TimeStruct->Seconds    = 0U;
325 }
326 
327 /**
328   * @brief  Set the RTC current date.
329   * @param  RTCx RTC Instance
330   * @param  RTC_Format This parameter can be one of the following values:
331   *         @arg @ref LL_RTC_FORMAT_BIN
332   *         @arg @ref LL_RTC_FORMAT_BCD
333   * @param  RTC_DateStruct pointer to a RTC_DateTypeDef structure that contains
334   *                         the date configuration information for the RTC.
335   * @retval An ErrorStatus enumeration value:
336   *          - SUCCESS: RTC Day register is configured
337   *          - ERROR: RTC Day register is not configured
338   */
LL_RTC_DATE_Init(RTC_TypeDef * RTCx,uint32_t RTC_Format,LL_RTC_DateTypeDef * RTC_DateStruct)339 ErrorStatus LL_RTC_DATE_Init(RTC_TypeDef *RTCx, uint32_t RTC_Format, LL_RTC_DateTypeDef *RTC_DateStruct)
340 {
341   ErrorStatus status = ERROR;
342 
343   /* Check the parameters */
344   assert_param(IS_RTC_ALL_INSTANCE(RTCx));
345   assert_param(IS_LL_RTC_FORMAT(RTC_Format));
346 
347   if ((RTC_Format == LL_RTC_FORMAT_BIN) && ((RTC_DateStruct->Month & 0x10U) == 0x10U))
348   {
349     RTC_DateStruct->Month = (uint8_t)(RTC_DateStruct->Month & (uint8_t)~(0x10U)) + 0x0AU;
350   }
351   if (RTC_Format == LL_RTC_FORMAT_BIN)
352   {
353     assert_param(IS_LL_RTC_YEAR(RTC_DateStruct->Year));
354     assert_param(IS_LL_RTC_MONTH(RTC_DateStruct->Month));
355     assert_param(IS_LL_RTC_DAY(RTC_DateStruct->Day));
356   }
357   else
358   {
359     assert_param(IS_LL_RTC_YEAR(__LL_RTC_CONVERT_BCD2BIN(RTC_DateStruct->Year)));
360     assert_param(IS_LL_RTC_MONTH(__LL_RTC_CONVERT_BCD2BIN(RTC_DateStruct->Month)));
361     assert_param(IS_LL_RTC_DAY(__LL_RTC_CONVERT_BCD2BIN(RTC_DateStruct->Day)));
362   }
363   assert_param(IS_LL_RTC_WEEKDAY(RTC_DateStruct->WeekDay));
364 
365   /* Disable the write protection for RTC registers */
366   LL_RTC_DisableWriteProtection(RTCx);
367 
368   /* Set Initialization mode */
369   if (LL_RTC_EnterInitMode(RTCx) != ERROR)
370   {
371     /* Check the input parameters format */
372     if (RTC_Format != LL_RTC_FORMAT_BIN)
373     {
374       LL_RTC_DATE_Config(RTCx, RTC_DateStruct->WeekDay, RTC_DateStruct->Day, RTC_DateStruct->Month, RTC_DateStruct->Year);
375     }
376     else
377     {
378       LL_RTC_DATE_Config(RTCx, RTC_DateStruct->WeekDay, __LL_RTC_CONVERT_BIN2BCD(RTC_DateStruct->Day),
379                          __LL_RTC_CONVERT_BIN2BCD(RTC_DateStruct->Month), __LL_RTC_CONVERT_BIN2BCD(RTC_DateStruct->Year));
380     }
381 
382     /* Exit Initialization mode */
383     LL_RTC_DisableInitMode(RTCx);
384 
385     /* If  RTC_CR_BYPSHAD bit = 0, wait for synchro else this check is not needed */
386     if (LL_RTC_IsShadowRegBypassEnabled(RTCx) == 0U)
387     {
388       status = LL_RTC_WaitForSynchro(RTCx);
389     }
390     else
391     {
392       status = SUCCESS;
393     }
394   }
395   /* Enable the write protection for RTC registers */
396   LL_RTC_EnableWriteProtection(RTCx);
397 
398   return status;
399 }
400 
401 /**
402   * @brief  Set each @ref LL_RTC_DateTypeDef field to default value (date = Monday, January 01 xx00)
403   * @param  RTC_DateStruct pointer to a @ref LL_RTC_DateTypeDef structure which will be initialized.
404   * @retval None
405   */
LL_RTC_DATE_StructInit(LL_RTC_DateTypeDef * RTC_DateStruct)406 void LL_RTC_DATE_StructInit(LL_RTC_DateTypeDef *RTC_DateStruct)
407 {
408   /* Monday, January 01 xx00 */
409   RTC_DateStruct->WeekDay = LL_RTC_WEEKDAY_MONDAY;
410   RTC_DateStruct->Day     = 1U;
411   RTC_DateStruct->Month   = LL_RTC_MONTH_JANUARY;
412   RTC_DateStruct->Year    = 0U;
413 }
414 
415 /**
416   * @brief  Set the RTC Alarm A.
417   * @note   The Alarm register can only be written when the corresponding Alarm
418   *         is disabled (Use @ref LL_RTC_ALMA_Disable function).
419   * @param  RTCx RTC Instance
420   * @param  RTC_Format This parameter can be one of the following values:
421   *         @arg @ref LL_RTC_FORMAT_BIN
422   *         @arg @ref LL_RTC_FORMAT_BCD
423   * @param  RTC_AlarmStruct pointer to a @ref LL_RTC_AlarmTypeDef structure that
424   *                         contains the alarm configuration parameters.
425   * @retval An ErrorStatus enumeration value:
426   *          - SUCCESS: ALARMA registers are configured
427   *          - ERROR: ALARMA registers are not configured
428   */
LL_RTC_ALMA_Init(RTC_TypeDef * RTCx,uint32_t RTC_Format,LL_RTC_AlarmTypeDef * RTC_AlarmStruct)429 ErrorStatus LL_RTC_ALMA_Init(RTC_TypeDef *RTCx, uint32_t RTC_Format, LL_RTC_AlarmTypeDef *RTC_AlarmStruct)
430 {
431   /* Check the parameters */
432   assert_param(IS_RTC_ALL_INSTANCE(RTCx));
433   assert_param(IS_LL_RTC_FORMAT(RTC_Format));
434   assert_param(IS_LL_RTC_ALMA_MASK(RTC_AlarmStruct->AlarmMask));
435   assert_param(IS_LL_RTC_ALMA_DATE_WEEKDAY_SEL(RTC_AlarmStruct->AlarmDateWeekDaySel));
436 
437   if (RTC_Format == LL_RTC_FORMAT_BIN)
438   {
439     if (LL_RTC_GetHourFormat(RTCx) != LL_RTC_HOURFORMAT_24HOUR)
440     {
441       assert_param(IS_LL_RTC_HOUR12(RTC_AlarmStruct->AlarmTime.Hours));
442       assert_param(IS_LL_RTC_TIME_FORMAT(RTC_AlarmStruct->AlarmTime.TimeFormat));
443     }
444     else
445     {
446       RTC_AlarmStruct->AlarmTime.TimeFormat = 0x00U;
447       assert_param(IS_LL_RTC_HOUR24(RTC_AlarmStruct->AlarmTime.Hours));
448     }
449     assert_param(IS_LL_RTC_MINUTES(RTC_AlarmStruct->AlarmTime.Minutes));
450     assert_param(IS_LL_RTC_SECONDS(RTC_AlarmStruct->AlarmTime.Seconds));
451 
452     if (RTC_AlarmStruct->AlarmDateWeekDaySel == LL_RTC_ALMA_DATEWEEKDAYSEL_DATE)
453     {
454       assert_param(IS_LL_RTC_DAY(RTC_AlarmStruct->AlarmDateWeekDay));
455     }
456     else
457     {
458       assert_param(IS_LL_RTC_WEEKDAY(RTC_AlarmStruct->AlarmDateWeekDay));
459     }
460   }
461   else
462   {
463     if (LL_RTC_GetHourFormat(RTCx) != LL_RTC_HOURFORMAT_24HOUR)
464     {
465       assert_param(IS_LL_RTC_HOUR12(__LL_RTC_CONVERT_BCD2BIN(RTC_AlarmStruct->AlarmTime.Hours)));
466       assert_param(IS_LL_RTC_TIME_FORMAT(RTC_AlarmStruct->AlarmTime.TimeFormat));
467     }
468     else
469     {
470       RTC_AlarmStruct->AlarmTime.TimeFormat = 0x00U;
471       assert_param(IS_LL_RTC_HOUR24(__LL_RTC_CONVERT_BCD2BIN(RTC_AlarmStruct->AlarmTime.Hours)));
472     }
473 
474     assert_param(IS_LL_RTC_MINUTES(__LL_RTC_CONVERT_BCD2BIN(RTC_AlarmStruct->AlarmTime.Minutes)));
475     assert_param(IS_LL_RTC_SECONDS(__LL_RTC_CONVERT_BCD2BIN(RTC_AlarmStruct->AlarmTime.Seconds)));
476 
477     if (RTC_AlarmStruct->AlarmDateWeekDaySel == LL_RTC_ALMA_DATEWEEKDAYSEL_DATE)
478     {
479       assert_param(IS_LL_RTC_DAY(__LL_RTC_CONVERT_BCD2BIN(RTC_AlarmStruct->AlarmDateWeekDay)));
480     }
481     else
482     {
483       assert_param(IS_LL_RTC_WEEKDAY(__LL_RTC_CONVERT_BCD2BIN(RTC_AlarmStruct->AlarmDateWeekDay)));
484     }
485   }
486 
487   /* Disable the write protection for RTC registers */
488   LL_RTC_DisableWriteProtection(RTCx);
489 
490   /* Select weekday selection */
491   if (RTC_AlarmStruct->AlarmDateWeekDaySel == LL_RTC_ALMA_DATEWEEKDAYSEL_DATE)
492   {
493     /* Set the date for ALARM */
494     LL_RTC_ALMA_DisableWeekday(RTCx);
495     if (RTC_Format != LL_RTC_FORMAT_BIN)
496     {
497       LL_RTC_ALMA_SetDay(RTCx, RTC_AlarmStruct->AlarmDateWeekDay);
498     }
499     else
500     {
501       LL_RTC_ALMA_SetDay(RTCx, __LL_RTC_CONVERT_BIN2BCD(RTC_AlarmStruct->AlarmDateWeekDay));
502     }
503   }
504   else
505   {
506     /* Set the week day for ALARM */
507     LL_RTC_ALMA_EnableWeekday(RTCx);
508     LL_RTC_ALMA_SetWeekDay(RTCx, RTC_AlarmStruct->AlarmDateWeekDay);
509   }
510 
511   /* Configure the Alarm register */
512   if (RTC_Format != LL_RTC_FORMAT_BIN)
513   {
514     LL_RTC_ALMA_ConfigTime(RTCx, RTC_AlarmStruct->AlarmTime.TimeFormat, RTC_AlarmStruct->AlarmTime.Hours,
515                            RTC_AlarmStruct->AlarmTime.Minutes, RTC_AlarmStruct->AlarmTime.Seconds);
516   }
517   else
518   {
519     LL_RTC_ALMA_ConfigTime(RTCx, RTC_AlarmStruct->AlarmTime.TimeFormat,
520                            __LL_RTC_CONVERT_BIN2BCD(RTC_AlarmStruct->AlarmTime.Hours),
521                            __LL_RTC_CONVERT_BIN2BCD(RTC_AlarmStruct->AlarmTime.Minutes),
522                            __LL_RTC_CONVERT_BIN2BCD(RTC_AlarmStruct->AlarmTime.Seconds));
523   }
524   /* Set ALARM mask */
525   LL_RTC_ALMA_SetMask(RTCx, RTC_AlarmStruct->AlarmMask);
526 
527   /* Enable the write protection for RTC registers */
528   LL_RTC_EnableWriteProtection(RTCx);
529 
530   return SUCCESS;
531 }
532 
533 /**
534   * @brief  Set each @ref LL_RTC_AlarmTypeDef of ALARMA field to default value (Time = 00h:00mn:00sec /
535   *         Day = 1st day of the month/Mask = all fields are masked).
536   * @param  RTC_AlarmStruct pointer to a @ref LL_RTC_AlarmTypeDef structure which will be initialized.
537   * @retval None
538   */
LL_RTC_ALMA_StructInit(LL_RTC_AlarmTypeDef * RTC_AlarmStruct)539 void LL_RTC_ALMA_StructInit(LL_RTC_AlarmTypeDef *RTC_AlarmStruct)
540 {
541   /* Alarm Time Settings : Time = 00h:00mn:00sec */
542   RTC_AlarmStruct->AlarmTime.TimeFormat = LL_RTC_ALMA_TIME_FORMAT_AM;
543   RTC_AlarmStruct->AlarmTime.Hours      = 0U;
544   RTC_AlarmStruct->AlarmTime.Minutes    = 0U;
545   RTC_AlarmStruct->AlarmTime.Seconds    = 0U;
546 
547   /* Alarm Day Settings : Day = 1st day of the month */
548   RTC_AlarmStruct->AlarmDateWeekDaySel = LL_RTC_ALMA_DATEWEEKDAYSEL_DATE;
549   RTC_AlarmStruct->AlarmDateWeekDay    = 1U;
550 
551   /* Alarm Masks Settings : Mask =  all fields are not masked */
552   RTC_AlarmStruct->AlarmMask           = LL_RTC_ALMA_MASK_NONE;
553 }
554 
555 /**
556   * @brief  Enters the RTC Initialization mode.
557   * @note   The RTC Initialization mode is write protected, use the
558   *         @ref LL_RTC_DisableWriteProtection before calling this function.
559   * @param  RTCx RTC Instance
560   * @retval An ErrorStatus enumeration value:
561   *          - SUCCESS: RTC is in Init mode
562   *          - ERROR: RTC is not in Init mode
563   */
LL_RTC_EnterInitMode(RTC_TypeDef * RTCx)564 ErrorStatus LL_RTC_EnterInitMode(RTC_TypeDef *RTCx)
565 {
566   __IO uint32_t timeout = RTC_INITMODE_TIMEOUT;
567   ErrorStatus status = SUCCESS;
568   uint32_t tmp = 0U;
569 
570   /* Check the parameter */
571   assert_param(IS_RTC_ALL_INSTANCE(RTCx));
572 
573   /* Check if the Initialization mode is set */
574   if (LL_RTC_IsActiveFlag_INIT(RTCx) == 0U)
575   {
576     /* Set the Initialization mode */
577     LL_RTC_EnableInitMode(RTCx);
578 
579     /* Wait till RTC is in INIT state and if Time out is reached exit */
580     tmp = LL_RTC_IsActiveFlag_INIT(RTCx);
581     while ((timeout != 0U) && (tmp != 1U))
582     {
583       if (LL_SYSTICK_IsActiveCounterFlag() == 1U)
584       {
585         timeout --;
586       }
587       tmp = LL_RTC_IsActiveFlag_INIT(RTCx);
588       if (timeout == 0U)
589       {
590         status = ERROR;
591       }
592     }
593   }
594   return status;
595 }
596 
597 /**
598   * @brief  Exit the RTC Initialization mode.
599   * @note   When the initialization sequence is complete, the calendar restarts
600   *         counting after 4 RTCCLK cycles.
601   * @note   The RTC Initialization mode is write protected, use the
602   *         @ref LL_RTC_DisableWriteProtection before calling this function.
603   * @param  RTCx RTC Instance
604   * @retval An ErrorStatus enumeration value:
605   *          - SUCCESS: RTC exited from in Init mode
606   *          - ERROR: Not applicable
607   */
LL_RTC_ExitInitMode(RTC_TypeDef * RTCx)608 ErrorStatus LL_RTC_ExitInitMode(RTC_TypeDef *RTCx)
609 {
610   /* Check the parameter */
611   assert_param(IS_RTC_ALL_INSTANCE(RTCx));
612 
613   /* Disable initialization mode */
614   LL_RTC_DisableInitMode(RTCx);
615 
616   return SUCCESS;
617 }
618 
619 /**
620   * @brief  Waits until the RTC Time and Day registers (RTC_TR and RTC_DR) are
621   *         synchronized with RTC APB clock.
622   * @note   The RTC Resynchronization mode is write protected, use the
623   *         @ref LL_RTC_DisableWriteProtection before calling this function.
624   * @note   To read the calendar through the shadow registers after calendar
625   *         initialization, calendar update or after wakeup from low power modes
626   *         the software must first clear the RSF flag.
627   *         The software must then wait until it is set again before reading
628   *         the calendar, which means that the calendar registers have been
629   *         correctly copied into the RTC_TR and RTC_DR shadow registers.
630   * @param  RTCx RTC Instance
631   * @retval An ErrorStatus enumeration value:
632   *          - SUCCESS: RTC registers are synchronised
633   *          - ERROR: RTC registers are not synchronised
634   */
LL_RTC_WaitForSynchro(RTC_TypeDef * RTCx)635 ErrorStatus LL_RTC_WaitForSynchro(RTC_TypeDef *RTCx)
636 {
637   __IO uint32_t timeout = RTC_SYNCHRO_TIMEOUT;
638   ErrorStatus status = SUCCESS;
639   uint32_t tmp = 0U;
640 
641   /* Check the parameter */
642   assert_param(IS_RTC_ALL_INSTANCE(RTCx));
643 
644   /* Clear RSF flag */
645   LL_RTC_ClearFlag_RS(RTCx);
646 
647   /* Wait the registers to be synchronised */
648   tmp = LL_RTC_IsActiveFlag_RS(RTCx);
649   while ((timeout != 0U) && (tmp != 1U))
650   {
651     if (LL_SYSTICK_IsActiveCounterFlag() == 1U)
652     {
653       timeout--;
654     }
655     tmp = LL_RTC_IsActiveFlag_RS(RTCx);
656     if (timeout == 0U)
657     {
658       status = ERROR;
659     }
660   }
661 
662   return (status);
663 }
664 
665 /**
666   * @}
667   */
668 
669 /**
670   * @}
671   */
672 
673 /**
674   * @}
675   */
676 
677 #endif /* defined(RTC) */
678 
679 /**
680   * @}
681   */
682 
683 #endif /* USE_FULL_LL_DRIVER */
684