1 /**
2   ******************************************************************************
3   * @file    stm32h7rsxx_hal_rcc.c
4   * @author  MCD Application Team
5   * @brief   RCC HAL module driver.
6   *          This file provides firmware functions to manage the following
7   *          functionalities of the Reset and Clock Control (RCC) peripheral:
8   *           + Initialization and de-initialization functions
9   *           + Peripheral Control functions
10   *
11   ******************************************************************************
12   * @attention
13   *
14   * Copyright (c) 2022 STMicroelectronics.
15   * All rights reserved.
16   *
17   * This software is licensed under terms that can be found in the LICENSE file
18   * in the root directory of this software component.
19   * If no LICENSE file comes with this software, it is provided AS-IS.
20   *
21   ******************************************************************************
22   @verbatim
23   ==============================================================================
24                       ##### RCC specific features #####
25   ==============================================================================
26     [..]
27       After reset the device is running from Internal High Speed oscillator
28       (HSI 64MHz) with Flash 0 wait state,and all peripherals are off except
29       internal SRAM, Flash, JTAG and PWR
30       (+) There is no pre-scaler on High speed (AHB) and Low speed (APB) buses;
31           all peripherals mapped on these buses are running at HSI speed.
32       (+) The clock for all peripherals is switched off, except the SRAM and FLASH.
33       (+) All GPIOs are in analogue mode , except the JTAG pins which
34           are assigned to be used for debug purpose.
35 
36     [..]
37       Once the device started from reset, the user application has to:
38       (+) Configure the clock source to be used to drive the System clock
39           (if the application needs higher frequency/performance)
40       (+) Configure the System clock frequency and Flash settings
41       (+) Configure the AHB and APB buses pre-scalers
42       (+) Enable the clock for the peripheral(s) to be used
43       (+) Configure the clock kernel source(s) for peripherals which clocks are not
44           derived from the System clock through :RCC_D1CCIPR,RCC_D2CCIP1R,RCC_D2CCIP2R
45           and RCC_D3CCIPR registers
46 
47                       ##### RCC Limitations #####
48   ==============================================================================
49     [..]
50       A delay between an RCC peripheral clock enable and the effective peripheral
51       enabling should be taken into account in order to manage the peripheral read/write
52       from/to registers.
53       (+) This delay depends on the peripheral mapping.
54       (+) If peripheral is mapped on AHB: the delay is 2 AHB clock cycle
55           after the clock enable bit is set on the hardware register
56       (+) If peripheral is mapped on APB: the delay is 2 APB clock cycle
57           after the clock enable bit is set on the hardware register
58 
59     [..]
60       Implemented Workaround:
61       (+) For AHB & APB peripherals, a dummy read to the peripheral register has been
62           inserted in each __HAL_RCC_PPP_CLK_ENABLE() macro.
63 
64   @endverbatim
65   */
66 
67 /* Includes ------------------------------------------------------------------*/
68 #include "stm32h7rsxx_hal.h"
69 
70 /** @addtogroup STM32H7RSxx_HAL_Driver
71   * @{
72   */
73 
74 /** @defgroup RCC  RCC
75   * @brief RCC HAL module driver
76   * @{
77   */
78 
79 #ifdef HAL_RCC_MODULE_ENABLED
80 
81 /* Private typedef -----------------------------------------------------------*/
82 /* Private defines -----------------------------------------------------------*/
83 /** @defgroup RCC_Private_Constants RCC Private Constants
84   * @{
85   */
86 #define RCC_CSI_TIMEOUT_VALUE         1U        /* 1 ms */
87 #define RCC_HSI_TIMEOUT_VALUE         1U        /* 1 ms */
88 #define RCC_HSI48_TIMEOUT_VALUE       1U        /* 1 ms */
89 #define RCC_HSE_TIMEOUT_VALUE         HSE_STARTUP_TIMEOUT
90 #define RCC_LSI_TIMEOUT_VALUE         1U        /* 1 ms */
91 #define RCC_CLOCKSWITCH_TIMEOUT_VALUE 5000U     /* 5 s  */
92 #define RCC_PLL_FRAC_WAIT_VALUE       1U        /* PLL Fractional part waiting time before new latch enable : 1 ms */
93 #define RCC_PLL_INPUTRANGE0_FREQMAX   2000000U  /* 2 MHz is maximum frequency for VCO input range 0 */
94 #define RCC_PLL_INPUTRANGE1_FREQMAX   4000000U  /* 4 MHz is maximum frequency for VCO input range 1 */
95 #define RCC_PLL_INPUTRANGE2_FREQMAX   8000000U  /* 8 MHz is maximum frequency for VCO input range 2 */
96 
97 #define RCC_PLL1_CONFIG               0U
98 #define RCC_PLL2_CONFIG               1U
99 #define RCC_PLL3_CONFIG               2U
100 /**
101   * @}
102   */
103 
104 /* Private macros ------------------------------------------------------------*/
105 /** @defgroup RCC_Private_Macros RCC Private Macros
106   * @{
107   */
108 #define RCC_GET_MCO_GPIO_PIN(__RCC_MCOx__)   ((__RCC_MCOx__) & GPIO_PIN_MASK)
109 
110 #define RCC_GET_MCO_GPIO_AF(__RCC_MCOx__)    (((__RCC_MCOx__) & RCC_MCO_GPIOAF_MASK) >> RCC_MCO_GPIOAF_POS)
111 
112 #define RCC_GET_MCO_GPIO_INDEX(__RCC_MCOx__) (((__RCC_MCOx__) & RCC_MCO_GPIOPORT_MASK) >> RCC_MCO_GPIOPORT_POS)
113 
114 #define RCC_GET_MCO_GPIO_PORT(__RCC_MCOx__)  (GPIOA_BASE + ((0x00000400UL) * RCC_GET_MCO_GPIO_INDEX((__RCC_MCOx__))))
115 
116 /**
117   * @}
118   */
119 
120 /* Private variables ---------------------------------------------------------*/
121 /** @defgroup RCC_Private_Variables Private Variables
122   * @{
123   */
124 /**
125   * @}
126   */
127 
128 /* Private function prototypes -----------------------------------------------*/
129 /** @defgroup RCC_Private_Functions RCC Private Functions
130   * @{
131   */
132 static uint32_t RCC_PLL1_GetVCOOutputFreq(void);
133 static uint32_t RCC_PLL2_GetVCOOutputFreq(void);
134 static uint32_t RCC_PLL3_GetVCOOutputFreq(void);
135 static HAL_StatusTypeDef RCC_PLL_Config(uint32_t PLLnumber, const RCC_PLLInitTypeDef *pPLLInit);
136 /**
137   * @}
138   */
139 
140 /* Exported functions --------------------------------------------------------*/
141 
142 /** @defgroup RCC_Exported_Functions RCC Exported Functions
143   * @{
144   */
145 
146 /** @defgroup RCC_Exported_Functions_Group1 Initialization and de-initialization functions
147   *  @brief    Initialization and Configuration functions
148   *
149 @verbatim
150  ===============================================================================
151            ##### Initialization and de-initialization functions #####
152  ===============================================================================
153     [..]
154       This section provides functions allowing to configure the internal/external oscillators
155       (HSE, HSI, LSE,CSI, LSI,HSI48, PLL, CSS and MCO) and the System buses clocks (SYSCLK, AHB3, AHB1
156        AHB2,AHB4,APB3, APB1L, APB1H, APB2, and APB4).
157 
158     [..] Internal/external clock and PLL configuration
159          (#) HSI (high-speed internal), 64 MHz factory-trimmed RC used directly or through
160              the PLL as System clock source.
161          (#) CSI is a low-power RC oscillator which can be used directly as system clock, peripheral
162              clock, or PLL input.But even with frequency calibration, is less accurate than an
163              external crystal oscillator or ceramic resonator.
164          (#) LSI (low-speed internal), 32 KHz low consumption RC used as IWDG and/or RTC
165              clock source.
166 
167          (#) HSE (high-speed external), 4 to 48 MHz crystal oscillator used directly or
168              through the PLL as System clock source. Can be used also as RTC clock source.
169 
170          (#) LSE (low-speed external), 32 KHz oscillator used as RTC clock source.
171 
172          (#) PLL , The RCC features three independent PLLs (clocked by HSI , HSE or CSI),
173              featuring three different output clocks and able  to work either in integer or Fractional mode.
174            (++) A main PLL, PLL1, which is generally used to provide clocks to the CPU
175                 and to some peripherals.
176            (++) Two dedicated PLLs, PLL2 and PLL3, which are used to generate the kernel clock for peripherals.
177 
178 
179          (#) CSS (Clock security system), once enabled and if a HSE clock failure occurs
180             (HSE used directly or through PLL as System clock source), the System clock
181              is automatically switched to HSI and an interrupt is generated if enabled.
182              The interrupt is linked to the Cortex-M NMI (Non-Mask-able Interrupt)
183              exception vector.
184 
185          (#) MCO1 (micro controller clock output), used to output HSI, LSE, HSE, PLL1(PLL1_Q)
186              or HSI48 clock (through a configurable pre-scaler) on PA8 pin.
187 
188          (#) MCO2 (micro controller clock output), used to output HSE, PLL2(PLL2_P), SYSCLK,
189              LSI, CSI, or PLL1(PLL1_P) clock (through a configurable pre-scaler) on PC9 pin.
190 
191     [..] System, AHB and APB buses clocks configuration
192          (#) Several clock sources can be used to drive the System clock (SYSCLK): CSI,HSI,
193              HSE and PLL.
194              The AHB clock (HCLK) is derived from System core clock through configurable
195              pre-scaler and used to clock the CPU, memory and peripherals mapped
196              on AHB and APB bus of the 3 Domains (D1, D2, D3)* through configurable pre-scalers
197              and used to clock the peripherals mapped on these buses. You can use
198              "HAL_RCC_GetSysClockFreq()" function to retrieve system clock frequency.
199 
200          -@- All the peripheral clocks are derived from the System clock (SYSCLK) except those
201              with dual clock domain where kernel source clock could be selected through
202              RCC_D1CCIPR,RCC_D2CCIP1R,RCC_D2CCIP2R and RCC_D3CCIPR registers.
203 
204      (*) : 2 Domains (CD and SRD) for stm32h7a3xx and stm32h7b3xx family lines.
205 @endverbatim
206   * @{
207   */
208 
209 /**
210   * @brief  Resets the RCC clock configuration to the default reset state.
211   * @note   The default reset state of the clock configuration is given below:
212   *            - HSI ON and used as system clock source
213   *            - HSE, PLL1, PLL2 and PLL3 OFF
214   *            - AHB, APB Bus pre-scaler set to 1.
215   *            - CSS, MCO1 and MCO2 OFF
216   *            - All interrupts disabled
217   * @note   This function doesn't modify the configuration of the
218   *            - Peripheral clocks
219   *            - LSI, LSE and RTC clocks
220   * @note   In case the FMC or XSPI clock protection have been set, it must be disabled
221   *         prior to calling this API.
222   * @retval HAL status
223   */
HAL_RCC_DeInit(void)224 HAL_StatusTypeDef HAL_RCC_DeInit(void)
225 {
226   uint32_t tickstart;
227 
228   /* Get Start Tick */
229   tickstart = HAL_GetTick();
230 
231   /* Set HSION bit */
232   SET_BIT(RCC->CR, RCC_CR_HSION);
233 
234   /* Wait till HSI is ready */
235   while (READ_BIT(RCC->CR, RCC_CR_HSIRDY) == 0U)
236   {
237     if ((HAL_GetTick() - tickstart) > RCC_HSI_TIMEOUT_VALUE)
238     {
239       return HAL_TIMEOUT;
240     }
241   }
242 
243   /* Set HSITRIM[6:0] bits to the reset value */
244   SET_BIT(RCC->HSICFGR, RCC_HSICFGR_HSITRIM_6);
245 
246   if (HAL_RCC_GetHCLKFreq() > HSI_VALUE)
247   {
248     /* Reset CFGR register (HSI is selected as system clock source) */
249     CLEAR_REG(RCC->CFGR);
250 
251     /* Update the SystemCoreClock and SystemD2Clock global variables */
252     SystemCoreClock = HSI_VALUE;
253 
254     /* Adapt Systick interrupt period */
255     if (HAL_InitTick(uwTickPrio) != HAL_OK)
256     {
257       return HAL_ERROR;
258     }
259 
260     /* Get Start Tick */
261     tickstart = HAL_GetTick();
262 
263     /* Wait till clock switch is ready */
264     while (READ_BIT(RCC->CFGR, RCC_CFGR_SWS) != 0U)
265     {
266       if ((HAL_GetTick() - tickstart) > RCC_CLOCKSWITCH_TIMEOUT_VALUE)
267       {
268         return HAL_TIMEOUT;
269       }
270     }
271 
272     /* Reduce flash latency */
273     __HAL_FLASH_SET_LATENCY(FLASH_LATENCY_1);
274   }
275   else
276   {
277     /* Increase flash latency */
278     __HAL_FLASH_SET_LATENCY(FLASH_LATENCY_1);
279 
280     /* Reset CFGR register (HSI is selected as system clock source) */
281     CLEAR_REG(RCC->CFGR);
282 
283     /* Adapt Systick interrupt period */
284     if (HAL_InitTick(uwTickPrio) != HAL_OK)
285     {
286       return HAL_ERROR;
287     }
288 
289     /* Get Start Tick */
290     tickstart = HAL_GetTick();
291 
292     /* Wait till clock switch is ready */
293     while (READ_BIT(RCC->CFGR, RCC_CFGR_SWS) != 0U)
294     {
295       if ((HAL_GetTick() - tickstart) > RCC_CLOCKSWITCH_TIMEOUT_VALUE)
296       {
297         return HAL_TIMEOUT;
298       }
299     }
300   }
301 
302 
303   /* Get Start Tick */
304   tickstart = HAL_GetTick();
305 
306   /* Reset CSION, CSIKERON, HSEON, HSI48ON, HSECSSON, HSIDIV bits */
307   CLEAR_BIT(RCC->CR, RCC_CR_HSEON | RCC_CR_HSIKERON | RCC_CR_HSIDIV |  RCC_CR_CSION | RCC_CR_CSIKERON  \
308             | RCC_CR_HSI48ON | RCC_CR_HSECSSON);
309 
310   /* Wait till HSE is disabled */
311   while (READ_BIT(RCC->CR, RCC_CR_HSERDY) != 0U)
312   {
313     if ((HAL_GetTick() - tickstart) > RCC_HSE_TIMEOUT_VALUE)
314     {
315       return HAL_TIMEOUT;
316     }
317   }
318 
319   /* Get Start Tick */
320   tickstart = HAL_GetTick();
321 
322   /* Clear PLLON bit */
323   CLEAR_BIT(RCC->CR, RCC_CR_PLL1ON);
324 
325   /* Wait till PLL is disabled */
326   while (READ_BIT(RCC->CR, RCC_CR_PLL1RDY) != 0U)
327   {
328     if ((HAL_GetTick() - tickstart) > RCC_PLL_TIMEOUT_VALUE)
329     {
330       return HAL_TIMEOUT;
331     }
332   }
333 
334   /* Get Start Tick */
335   tickstart = HAL_GetTick();
336 
337   /* Reset PLL2ON bit */
338   CLEAR_BIT(RCC->CR, RCC_CR_PLL2ON);
339 
340   /* Wait till PLL2 is disabled */
341   while (READ_BIT(RCC->CR, RCC_CR_PLL2RDY) != 0U)
342   {
343     if ((HAL_GetTick() - tickstart) > RCC_PLL_TIMEOUT_VALUE)
344     {
345       return HAL_TIMEOUT;
346     }
347   }
348 
349   /* Get Start Tick */
350   tickstart = HAL_GetTick();
351 
352   /* Reset PLL3 bit */
353   CLEAR_BIT(RCC->CR, RCC_CR_PLL3ON);
354 
355   /* Wait till PLL3 is disabled */
356   while (READ_BIT(RCC->CR, RCC_CR_PLL3RDY) != 0U)
357   {
358     if ((HAL_GetTick() - tickstart) > RCC_PLL_TIMEOUT_VALUE)
359     {
360       return HAL_TIMEOUT;
361     }
362   }
363 
364   /* Reset CDCFGR register */
365   CLEAR_REG(RCC->CDCFGR);
366 
367   /* Reset BMCFGR register */
368   CLEAR_REG(RCC->BMCFGR);
369 
370   /* Reset APBCFGR register */
371   CLEAR_REG(RCC->APBCFGR);
372 
373   /* Reset PLLCKSELR register to default value */
374   WRITE_REG(RCC->PLLCKSELR, 0x02020200U);
375 
376   /* Reset PLLCFGR register */
377   CLEAR_REG(RCC->PLLCFGR);
378 
379   /* Reset PLL1DIVR1 register to default value */
380   WRITE_REG(RCC->PLL1DIVR1, 0x01010280U);
381 
382   /* Reset PLL1DIVR2 register to default value */
383   WRITE_REG(RCC->PLL1DIVR2, 0x00000101U);
384 
385   /* Reset PLL1FRACR register */
386   CLEAR_REG(RCC->PLL1FRACR);
387 
388   /* Reset PLL2DIVR1 register to default value */
389   WRITE_REG(RCC->PLL2DIVR1, 0x01010280U);
390 
391   /* Reset PLL2DIVR2 register to default value */
392   WRITE_REG(RCC->PLL2DIVR2, 0x00000101U);
393 
394   /* Reset PLL2FRACR register */
395   CLEAR_REG(RCC->PLL2FRACR);
396 
397   /* Reset PLL3DIVR1 register to default value */
398   WRITE_REG(RCC->PLL3DIVR1, 0x01010280U);
399 
400   /* Reset PLL3DIVR2 register to default value */
401   WRITE_REG(RCC->PLL3DIVR2, 0x00000101U);
402 
403   /* Reset PLL3FRACR register */
404   CLEAR_REG(RCC->PLL3FRACR);
405 
406   /* Reset HSEBYP bit */
407   CLEAR_BIT(RCC->CR, RCC_CR_HSEBYP);
408 
409   /* Disable all interrupts */
410   CLEAR_REG(RCC->CIER);
411 
412   /* Clear all interrupts flags */
413   WRITE_REG(RCC->CICR, 0xFFFFFFFFU);
414 
415   /* Reset all RSR flags */
416   SET_BIT(RCC->RSR, RCC_RSR_RMVF);
417 
418   return HAL_OK;
419 }
420 
421 /**
422   * @brief  Initializes the RCC Oscillators according to the specified parameters in the
423   *         RCC_OscInitTypeDef.
424   * @param  RCC_OscInitStruct: pointer to an RCC_OscInitTypeDef structure that
425   *         contains the configuration information for the RCC Oscillators.
426   * @note   The PLL is not disabled when used as system clock.
427   * @note   Transitions LSE Bypass to LSE On and LSE On to LSE Bypass are not
428   *         supported by this function. User should request a transition to LSE Off
429   *         first and then LSE On or LSE Bypass.
430   * @note   Transition HSE Bypass to HSE On and HSE On to HSE Bypass are not
431   *         supported by this function. User should request a transition to HSE Off
432   *         first and then HSE On or HSE Bypass.
433   * @retval HAL status
434   */
HAL_RCC_OscConfig(RCC_OscInitTypeDef * RCC_OscInitStruct)435 HAL_StatusTypeDef HAL_RCC_OscConfig(RCC_OscInitTypeDef  *RCC_OscInitStruct)
436 {
437   uint32_t tickstart;
438   uint32_t sysclksrc;
439   uint32_t pllsrc;
440   uint32_t pllrdy;
441   uint32_t tmpreg1;
442 
443   /* Check Null pointer */
444   if (RCC_OscInitStruct == NULL)
445   {
446     return HAL_ERROR;
447   }
448 
449   /* Check the parameters */
450   assert_param(IS_RCC_OSCILLATORTYPE(RCC_OscInitStruct->OscillatorType));
451 
452   sysclksrc = __HAL_RCC_GET_SYSCLK_SOURCE();
453   pllsrc = __HAL_RCC_GET_PLL_OSCSOURCE();
454   pllrdy = RCC->CR & (RCC_CR_PLL1RDY | RCC_CR_PLL2RDY | RCC_CR_PLL3RDY);
455 
456   /*------------------------------- HSE Configuration ------------------------*/
457   if (((RCC_OscInitStruct->OscillatorType) & RCC_OSCILLATORTYPE_HSE) == RCC_OSCILLATORTYPE_HSE)
458   {
459     /* Check the parameters */
460     assert_param(IS_RCC_HSE(RCC_OscInitStruct->HSEState));
461 
462     /* When the HSE is used as system clock or clock source for PLL in these cases HSE will not disabled */
463     if ((sysclksrc == RCC_SYSCLKSOURCE_STATUS_HSE) ||
464         ((pllrdy != 0U) && (pllsrc == RCC_PLLSOURCE_HSE)))
465     {
466       if (RCC_OscInitStruct->HSEState == RCC_HSE_OFF)
467       {
468         return HAL_ERROR;
469       }
470     }
471     else
472     {
473       /* Set the new HSE configuration ---------------------------------------*/
474       __HAL_RCC_HSE_CONFIG(RCC_OscInitStruct->HSEState);
475 
476       /* Get Start Tick*/
477       tickstart = HAL_GetTick();
478 
479       /* Check the HSE State */
480       if (RCC_OscInitStruct->HSEState != RCC_HSE_OFF)
481       {
482         /* Wait till HSE is ready */
483         while (READ_BIT(RCC->CR, RCC_CR_HSERDY) == 0U)
484         {
485           if ((HAL_GetTick() - tickstart) > RCC_HSE_TIMEOUT_VALUE)
486           {
487             return HAL_TIMEOUT;
488           }
489         }
490       }
491       else
492       {
493         /* Wait till HSE is disabled */
494         while (READ_BIT(RCC->CR, RCC_CR_HSERDY) != 0U)
495         {
496           if ((HAL_GetTick() - tickstart) > RCC_HSE_TIMEOUT_VALUE)
497           {
498             return HAL_TIMEOUT;
499           }
500         }
501       }
502     }
503   }
504   /*----------------------------- HSI Configuration --------------------------*/
505   if (((RCC_OscInitStruct->OscillatorType) & RCC_OSCILLATORTYPE_HSI) == RCC_OSCILLATORTYPE_HSI)
506   {
507     /* Check the parameters */
508     assert_param(IS_RCC_HSI(RCC_OscInitStruct->HSIState));
509     assert_param(IS_RCC_HSICALIBRATION_VALUE(RCC_OscInitStruct->HSICalibrationValue));
510 
511     /* Check if HSI is used as system clock or as PLL1 source when PLL1 is selected as system clock */
512     if ((sysclksrc == RCC_SYSCLKSOURCE_STATUS_HSI) ||
513         ((pllrdy != 0U) && (pllsrc == RCC_PLLSOURCE_HSI)))
514     {
515       /* When HSI is used as system clock it will not be disabled */
516       if (RCC_OscInitStruct->HSIState == RCC_HSI_OFF)
517       {
518         return HAL_ERROR;
519       }
520       /* Otherwise, calibration is allowed, divider update also unless used for any enabled PLL */
521       else
522       {
523         /* HSI must not be used as reference clock for any enabled PLL clock source */
524         tmpreg1 = (RCC->CR & RCC_CR_HSIDIV);
525         if ((pllsrc == RCC_PLLSOURCE_HSI) && (pllrdy != 0U) && \
526             (tmpreg1 != RCC_OscInitStruct->HSIDiv))
527         {
528           return HAL_ERROR;
529         }
530 
531         assert_param(IS_RCC_HSIDIV(RCC_OscInitStruct->HSIDiv));
532 
533         /* Set the Internal High Speed oscillator new divider */
534         __HAL_RCC_HSI_CONFIG(RCC_HSI_ON | RCC_OscInitStruct->HSIDiv);
535 
536         if (sysclksrc == RCC_SYSCLKSOURCE_STATUS_HSI)
537         {
538           SystemCoreClock = (HSI_VALUE / (1UL << ((READ_BIT(RCC->CR, RCC_CR_HSIDIV)) >> RCC_CR_HSIDIV_Pos)));
539         }
540         /* Adapt Systick interrupt period */
541         if (HAL_InitTick(uwTickPrio) != HAL_OK)
542         {
543           return HAL_ERROR;
544         }
545       }
546       /* Adjusts the Internal High Speed oscillator (HSI) calibration value.*/
547       __HAL_RCC_HSI_CALIBRATIONVALUE_ADJUST(RCC_OscInitStruct->HSICalibrationValue);
548     }
549     else
550     {
551       /* Check the HSI State */
552       if (RCC_OscInitStruct->HSIState != RCC_HSI_OFF)
553       {
554         /* Enable the Internal High Speed oscillator */
555         __HAL_RCC_HSI_CONFIG(RCC_OscInitStruct->HSIState | RCC_OscInitStruct->HSIDiv);
556 
557         /* Adjusts the Internal High Speed oscillator (HSI) calibration value.*/
558         __HAL_RCC_HSI_CALIBRATIONVALUE_ADJUST(RCC_OscInitStruct->HSICalibrationValue);
559 
560         /* Get Start Tick*/
561         tickstart = HAL_GetTick();
562 
563         /* Wait till HSI is ready */
564         while (READ_BIT(RCC->CR, RCC_CR_HSIRDY) == 0U)
565         {
566           if ((HAL_GetTick() - tickstart) > RCC_HSI_TIMEOUT_VALUE)
567           {
568             return HAL_TIMEOUT;
569           }
570         }
571       }
572       else
573       {
574         /* Disable the Internal High Speed oscillator (HSI). */
575         __HAL_RCC_HSI_DISABLE();
576 
577         /* Get Start Tick*/
578         tickstart = HAL_GetTick();
579 
580         /* Wait till HSI is disabled */
581         while (READ_BIT(RCC->CR, RCC_CR_HSIRDY) != 0U)
582         {
583           if ((HAL_GetTick() - tickstart) > RCC_HSI_TIMEOUT_VALUE)
584           {
585             return HAL_TIMEOUT;
586           }
587         }
588       }
589     }
590   }
591   /*----------------------------- CSI Configuration --------------------------*/
592   if (((RCC_OscInitStruct->OscillatorType) & RCC_OSCILLATORTYPE_CSI) == RCC_OSCILLATORTYPE_CSI)
593   {
594     /* Check the parameters */
595     assert_param(IS_RCC_CSI(RCC_OscInitStruct->CSIState));
596 
597     /* When the CSI is used as system clock it will not disabled */
598     if ((sysclksrc == RCC_SYSCLKSOURCE_STATUS_CSI) ||
599         ((pllrdy != 0U) && (pllsrc == RCC_PLLSOURCE_CSI)))
600     {
601       /* When CSI is used as system clock it will not disabled */
602       if (RCC_OscInitStruct->CSIState == RCC_CSI_OFF)
603       {
604         return HAL_ERROR;
605       }
606     }
607     else
608     {
609       /* Check the CSI State */
610       if ((RCC_OscInitStruct->CSIState) != RCC_CSI_OFF)
611       {
612         /* Enable the Internal High Speed oscillator (CSI). */
613         __HAL_RCC_CSI_ENABLE();
614 
615         /* Get Start Tick*/
616         tickstart = HAL_GetTick();
617 
618         /* Wait till CSI is ready */
619         while (READ_BIT(RCC->CR, RCC_CR_CSIRDY) == 0U)
620         {
621           if ((HAL_GetTick() - tickstart) > RCC_CSI_TIMEOUT_VALUE)
622           {
623             return HAL_TIMEOUT;
624           }
625         }
626       }
627       else
628       {
629         /* Disable the Internal High Speed oscillator (CSI). */
630         __HAL_RCC_CSI_DISABLE();
631 
632         /* Get Start Tick*/
633         tickstart = HAL_GetTick();
634 
635         /* Wait till CSI is disabled */
636         while (READ_BIT(RCC->CR, RCC_CR_CSIRDY) != 0U)
637         {
638           if ((HAL_GetTick() - tickstart) > RCC_CSI_TIMEOUT_VALUE)
639           {
640             return HAL_TIMEOUT;
641           }
642         }
643       }
644     }
645   }
646   /*------------------------------ LSI Configuration -------------------------*/
647   if (((RCC_OscInitStruct->OscillatorType) & RCC_OSCILLATORTYPE_LSI) == RCC_OSCILLATORTYPE_LSI)
648   {
649     /* Check the parameters */
650     assert_param(IS_RCC_LSI(RCC_OscInitStruct->LSIState));
651 
652     /* Check the LSI State */
653     if ((RCC_OscInitStruct->LSIState) != RCC_LSI_OFF)
654     {
655       /* Enable the Internal Low Speed oscillator (LSI). */
656       __HAL_RCC_LSI_ENABLE();
657 
658       /* Get Start Tick*/
659       tickstart = HAL_GetTick();
660 
661       /* Wait till LSI is ready */
662       while (READ_BIT(RCC->CSR, RCC_CSR_LSIRDY) == 0U)
663       {
664         if ((HAL_GetTick() - tickstart) > RCC_LSI_TIMEOUT_VALUE)
665         {
666           return HAL_TIMEOUT;
667         }
668       }
669     }
670     else
671     {
672       /* Disable the Internal Low Speed oscillator (LSI). */
673       __HAL_RCC_LSI_DISABLE();
674 
675       /* Get Start Tick*/
676       tickstart = HAL_GetTick();
677 
678       /* Wait till LSI is ready */
679       while (READ_BIT(RCC->CSR, RCC_CSR_LSIRDY) != 0U)
680       {
681         if ((HAL_GetTick() - tickstart) > RCC_LSI_TIMEOUT_VALUE)
682         {
683           return HAL_TIMEOUT;
684         }
685       }
686     }
687   }
688 
689   /*------------------------------ HSI48 Configuration -------------------------*/
690   if (((RCC_OscInitStruct->OscillatorType) & RCC_OSCILLATORTYPE_HSI48) == RCC_OSCILLATORTYPE_HSI48)
691   {
692     /* Check the parameters */
693     assert_param(IS_RCC_HSI48(RCC_OscInitStruct->HSI48State));
694 
695     /* Check the HSI48 State */
696     if ((RCC_OscInitStruct->HSI48State) != RCC_HSI48_OFF)
697     {
698       /* Enable the Internal Low Speed oscillator (HSI48). */
699       __HAL_RCC_HSI48_ENABLE();
700 
701       /* Get time-out */
702       tickstart = HAL_GetTick();
703 
704       /* Wait till HSI48 is ready */
705       while (READ_BIT(RCC->CR, RCC_CR_HSI48RDY) == 0U)
706       {
707         if ((HAL_GetTick() - tickstart) > RCC_HSI48_TIMEOUT_VALUE)
708         {
709           return HAL_TIMEOUT;
710         }
711       }
712     }
713     else
714     {
715       /* Disable the Internal Low Speed oscillator (HSI48). */
716       __HAL_RCC_HSI48_DISABLE();
717 
718       /* Get time-out */
719       tickstart = HAL_GetTick();
720 
721       /* Wait till HSI48 is ready */
722       while (READ_BIT(RCC->CR, RCC_CR_HSI48RDY) != 0U)
723       {
724         if ((HAL_GetTick() - tickstart) > RCC_HSI48_TIMEOUT_VALUE)
725         {
726           return HAL_TIMEOUT;
727         }
728       }
729     }
730   }
731   /*------------------------------ LSE Configuration -------------------------*/
732   if (((RCC_OscInitStruct->OscillatorType) & RCC_OSCILLATORTYPE_LSE) == RCC_OSCILLATORTYPE_LSE)
733   {
734     /* Check the parameters */
735     assert_param(IS_RCC_LSE(RCC_OscInitStruct->LSEState));
736 
737     /* Enable write access to Backup domain */
738     PWR->CR1 |= PWR_CR1_DBP;
739 
740     /* Set the new LSE configuration -----------------------------------------*/
741     __HAL_RCC_LSE_CONFIG(RCC_OscInitStruct->LSEState);
742     /* Check the LSE State */
743     if ((RCC_OscInitStruct->LSEState) != RCC_LSE_OFF)
744     {
745       /* Get Start Tick*/
746       tickstart = HAL_GetTick();
747 
748       /* Wait till LSE is ready */
749       while (READ_BIT(RCC->BDCR, RCC_BDCR_LSERDY) == 0U)
750       {
751         if ((HAL_GetTick() - tickstart) > RCC_LSE_TIMEOUT_VALUE)
752         {
753           return HAL_TIMEOUT;
754         }
755       }
756     }
757     else
758     {
759       /* Get Start Tick*/
760       tickstart = HAL_GetTick();
761 
762       /* Wait till LSE is disabled */
763       while (READ_BIT(RCC->BDCR, RCC_BDCR_LSERDY) != 0U)
764       {
765         if ((HAL_GetTick() - tickstart) > RCC_LSE_TIMEOUT_VALUE)
766         {
767           return HAL_TIMEOUT;
768         }
769       }
770     }
771   }
772 
773   /*-------------------------------- PLL1 Configuration ----------------------*/
774   /* Check the parameters */
775   assert_param(IS_RCC_PLL(RCC_OscInitStruct->PLL1.PLLState));
776 
777   if (RCC_OscInitStruct->PLL1.PLLState != RCC_PLL_NONE)
778   {
779     /* Check if the PLL is used as system clock or not */
780     if (sysclksrc == RCC_SYSCLKSOURCE_STATUS_PLLCLK)
781     {
782       /* No PLL off possible */
783       if (RCC_OscInitStruct->PLL1.PLLState == RCC_PLL_OFF)
784       {
785         return HAL_ERROR;
786       }
787       else
788       {
789         /* Check if only fractional part needs to be updated  */
790         tmpreg1 = ((RCC->PLL1FRACR & RCC_PLL1FRACR_FRACN) >> RCC_PLL1FRACR_FRACN_Pos);
791 
792         if (RCC_OscInitStruct->PLL1.PLLFractional != tmpreg1)
793         {
794           assert_param(IS_RCC_PLLFRACN_VALUE(RCC_OscInitStruct->PLL1.PLLFractional));
795 
796           /* Disable PLL1FRACLE */
797           __HAL_RCC_PLL1_FRACN_DISABLE();
798 
799           /* Get Start Tick*/
800           tickstart = HAL_GetTick();
801 
802           /* Wait at least 2 CK_REF (PLL input source divided by M) period to make sure next latched value will be taken into account. */
803           while ((HAL_GetTick() - tickstart) < RCC_PLL_FRAC_WAIT_VALUE)
804           {
805             /* Do nothing */
806           }
807 
808           /* Configure PLL1FRACN */
809           __HAL_RCC_PLL1_FRACN_CONFIG(RCC_OscInitStruct->PLL1.PLLFractional);
810 
811           /* Enable PLL1FRACLE to latch new value . */
812           __HAL_RCC_PLL1_FRACN_ENABLE();
813         }
814       }
815     }
816     else
817     {
818       /* Initialize PLL1T to 1 to use common PLL initialization function */
819       RCC_OscInitStruct->PLL1.PLLT = 1U;
820       if (RCC_PLL_Config(RCC_PLL1_CONFIG, &(RCC_OscInitStruct->PLL1)) != HAL_OK)
821       {
822         return HAL_ERROR;
823       }
824     }
825   }
826 
827   /*-------------------------------- PLL2 Configuration ----------------------*/
828   /* Check the parameters */
829   assert_param(IS_RCC_PLL(RCC_OscInitStruct->PLL2.PLLState));
830 
831   if (RCC_OscInitStruct->PLL2.PLLState != RCC_PLL_NONE)
832   {
833     if (RCC_PLL_Config(RCC_PLL2_CONFIG, &(RCC_OscInitStruct->PLL2)) != HAL_OK)
834     {
835       return HAL_ERROR;
836     }
837   }
838 
839   /*-------------------------------- PLL3 Configuration ----------------------*/
840   /* Check the parameters */
841   assert_param(IS_RCC_PLL(RCC_OscInitStruct->PLL3.PLLState));
842 
843   if (RCC_OscInitStruct->PLL3.PLLState != RCC_PLL_NONE)
844   {
845     /* Initialize PLL3T to 1 to use common PLL initialization function */
846     RCC_OscInitStruct->PLL3.PLLT = 1U;
847     if (RCC_PLL_Config(RCC_PLL3_CONFIG, &(RCC_OscInitStruct->PLL3)) != HAL_OK)
848     {
849       return HAL_ERROR;
850     }
851   }
852 
853   return HAL_OK;
854 }
855 
856 /**
857   * @brief  Initializes the CPU, AHB and APB buses clocks according to the specified
858   *         parameters in the RCC_ClkInitStruct.
859   * @param  RCC_ClkInitStruct: pointer to an RCC_OscInitTypeDef structure that
860   *         contains the configuration information for the RCC peripheral.
861   * @param  FLatency: FLASH Latency, this parameter depend on device selected
862   *
863   * @note   The SystemCoreClock CMSIS variable is used to store System Core Clock Frequency
864   *         and updated by HAL_InitTick() function called within this function
865   *
866   * @note   The HSI is used (enabled by hardware) as system clock source after
867   *         start-up from Reset, wake-up from STOP and STANDBY mode, or in case
868   *         of failure of the HSE used directly or indirectly as system clock
869   *         (if the Clock Security System CSS is enabled).
870   *
871   * @note   A switch from one clock source to another occurs only if the target
872   *         clock source is ready (clock stable after start-up delay or PLL locked).
873   *         If a clock source which is not yet ready is selected, the switch will
874   *         occur when the clock source will be ready.
875   *         You can use HAL_RCC_GetClockConfig() function to know which clock is
876   *         currently used as system clock source.
877   * @note   Depending on the device voltage range, the software has to set correctly
878   *         D1CPRE[3:0] bits to ensure that  Domain1 core clock not exceed the maximum allowed frequency
879   *         (for more details refer to section above "Initialization/de-initialization functions")
880   * @retval None
881   */
HAL_RCC_ClockConfig(const RCC_ClkInitTypeDef * RCC_ClkInitStruct,uint32_t FLatency)882 HAL_StatusTypeDef HAL_RCC_ClockConfig(const RCC_ClkInitTypeDef  *RCC_ClkInitStruct, uint32_t FLatency)
883 {
884   HAL_StatusTypeDef halstatus;
885   uint32_t tickstart;
886 
887   /* Check Null pointer */
888   if (RCC_ClkInitStruct == NULL)
889   {
890     return HAL_ERROR;
891   }
892 
893   /* Check the parameters */
894   assert_param(IS_RCC_CLOCKTYPE(RCC_ClkInitStruct->ClockType));
895   assert_param(IS_FLASH_LATENCY(FLatency));
896 
897   /* To correctly read data from FLASH memory, the number of wait states (LATENCY)
898     must be correctly programmed according to the frequency of the CPU clock
899     (HCLK) and the supply voltage of the device. */
900 
901   /* Increasing the CPU frequency */
902   if (FLatency > __HAL_FLASH_GET_LATENCY())
903   {
904     /* Program the new number of wait states to the LATENCY bits in the FLASH_ACR register */
905     __HAL_FLASH_SET_LATENCY(FLatency);
906 
907     /* Check that the new number of wait states is taken into account to access the Flash
908     memory by reading the FLASH_ACR register */
909     if (__HAL_FLASH_GET_LATENCY() != FLatency)
910     {
911       return HAL_ERROR;
912     }
913 
914   }
915 
916   /* Increasing the BUS frequency divider ? */
917 
918   /*-------------------------- PCLK1 Configuration ---------------------------*/
919   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_PCLK1) == RCC_CLOCKTYPE_PCLK1)
920   {
921     assert_param(IS_RCC_PCLK1(RCC_ClkInitStruct->APB1CLKDivider));
922     if ((RCC_ClkInitStruct->APB1CLKDivider) > (RCC->APBCFGR & RCC_APBCFGR_PPRE1))
923     {
924       MODIFY_REG(RCC->APBCFGR, RCC_APBCFGR_PPRE1, (RCC_ClkInitStruct->APB1CLKDivider));
925     }
926   }
927 
928   /*-------------------------- PCLK2 Configuration ---------------------------*/
929   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_PCLK2) == RCC_CLOCKTYPE_PCLK2)
930   {
931     assert_param(IS_RCC_PCLK2(RCC_ClkInitStruct->APB2CLKDivider));
932     if ((RCC_ClkInitStruct->APB2CLKDivider) > (RCC->APBCFGR & RCC_APBCFGR_PPRE2))
933     {
934       MODIFY_REG(RCC->APBCFGR, RCC_APBCFGR_PPRE2, (RCC_ClkInitStruct->APB2CLKDivider));
935     }
936   }
937 
938   /*-------------------------- PCLK4 Configuration ---------------------------*/
939   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_PCLK4) == RCC_CLOCKTYPE_PCLK4)
940   {
941     assert_param(IS_RCC_PCLK4(RCC_ClkInitStruct->APB4CLKDivider));
942     if ((RCC_ClkInitStruct->APB4CLKDivider) > (RCC->APBCFGR & RCC_APBCFGR_PPRE4))
943     {
944       MODIFY_REG(RCC->APBCFGR, RCC_APBCFGR_PPRE4, (RCC_ClkInitStruct->APB4CLKDivider));
945     }
946   }
947 
948   /*-------------------------- PCLK5 Configuration ---------------------------*/
949   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_PCLK5) == RCC_CLOCKTYPE_PCLK5)
950   {
951     assert_param(IS_RCC_PCLK5(RCC_ClkInitStruct->APB5CLKDivider));
952     if ((RCC_ClkInitStruct->APB5CLKDivider) > (RCC->APBCFGR & RCC_APBCFGR_PPRE5))
953     {
954       MODIFY_REG(RCC->APBCFGR, RCC_APBCFGR_PPRE5, (RCC_ClkInitStruct->APB5CLKDivider));
955     }
956   }
957 
958   /*-------------------------- HCLK Configuration --------------------------*/
959   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_HCLK) == RCC_CLOCKTYPE_HCLK)
960   {
961     assert_param(IS_RCC_HCLK(RCC_ClkInitStruct->AHBCLKDivider));
962     if ((RCC_ClkInitStruct->AHBCLKDivider) > (RCC->BMCFGR & RCC_BMCFGR_BMPRE))
963     {
964       /* Set the new HCLK clock divider */
965       MODIFY_REG(RCC->BMCFGR, RCC_BMCFGR_BMPRE, RCC_ClkInitStruct->AHBCLKDivider);
966     }
967   }
968 
969   /*------------------------- SYSCLK Configuration -------------------------*/
970   if ((RCC_ClkInitStruct->ClockType & RCC_CLOCKTYPE_SYSCLK) == RCC_CLOCKTYPE_SYSCLK)
971   {
972     assert_param(IS_RCC_SYSCLKSOURCE(RCC_ClkInitStruct->SYSCLKSource));
973     assert_param(IS_RCC_SYSCLK(RCC_ClkInitStruct->SYSCLKDivider));
974     MODIFY_REG(RCC->CDCFGR, RCC_CDCFGR_CPRE, RCC_ClkInitStruct->SYSCLKDivider);
975 
976     /* HSE is selected as System Clock Source */
977     if (RCC_ClkInitStruct->SYSCLKSource == RCC_SYSCLKSOURCE_HSE)
978     {
979       /* Check the HSE ready flag */
980       if (READ_BIT(RCC->CR, RCC_CR_HSERDY) == 0U)
981       {
982         return HAL_ERROR;
983       }
984     }
985     /* PLL is selected as System Clock Source */
986     else if (RCC_ClkInitStruct->SYSCLKSource == RCC_SYSCLKSOURCE_PLLCLK)
987     {
988       /* Check the PLL ready flag */
989       if (READ_BIT(RCC->CR, RCC_CR_PLL1RDY) == 0U)
990       {
991         return HAL_ERROR;
992       }
993     }
994     /* CSI is selected as System Clock Source */
995     else if (RCC_ClkInitStruct->SYSCLKSource == RCC_SYSCLKSOURCE_CSI)
996     {
997       /* Check the PLL ready flag */
998       if (READ_BIT(RCC->CR, RCC_CR_CSIRDY) == 0U)
999       {
1000         return HAL_ERROR;
1001       }
1002     }
1003     /* HSI is selected as System Clock Source */
1004     else
1005     {
1006       /* Check the HSI ready flag */
1007       if (READ_BIT(RCC->CR, RCC_CR_HSIRDY) == 0U)
1008       {
1009         return HAL_ERROR;
1010       }
1011     }
1012     MODIFY_REG(RCC->CFGR, RCC_CFGR_SW, RCC_ClkInitStruct->SYSCLKSource);
1013 
1014     /* Get Start Tick*/
1015     tickstart = HAL_GetTick();
1016 
1017     while (__HAL_RCC_GET_SYSCLK_SOURCE() != (RCC_ClkInitStruct->SYSCLKSource << RCC_CFGR_SWS_Pos))
1018     {
1019       if ((HAL_GetTick() - tickstart) > RCC_CLOCKSWITCH_TIMEOUT_VALUE)
1020       {
1021         return HAL_TIMEOUT;
1022       }
1023     }
1024   }
1025 
1026   /* Decreasing the BUS frequency divider ? */
1027 
1028   /*-------------------------- HCLK Configuration --------------------------*/
1029   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_HCLK) == RCC_CLOCKTYPE_HCLK)
1030   {
1031     assert_param(IS_RCC_HCLK(RCC_ClkInitStruct->AHBCLKDivider));
1032     if ((RCC_ClkInitStruct->AHBCLKDivider) < (RCC->BMCFGR & RCC_BMCFGR_BMPRE))
1033     {
1034       /* Set the new HCLK clock divider */
1035       MODIFY_REG(RCC->BMCFGR, RCC_BMCFGR_BMPRE, RCC_ClkInitStruct->AHBCLKDivider);
1036     }
1037   }
1038 
1039   /* Decreasing the number of wait states because of lower CPU frequency */
1040   if (FLatency < __HAL_FLASH_GET_LATENCY())
1041   {
1042     /* Program the new number of wait states to the LATENCY bits in the FLASH_ACR register */
1043     __HAL_FLASH_SET_LATENCY(FLatency);
1044 
1045     /* Check that the new number of wait states is taken into account to access the Flash
1046     memory by reading the FLASH_ACR register */
1047     if (__HAL_FLASH_GET_LATENCY() != FLatency)
1048     {
1049       return HAL_ERROR;
1050     }
1051   }
1052 
1053   /*-------------------------- PCLK1 Configuration ---------------------------*/
1054   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_PCLK1) == RCC_CLOCKTYPE_PCLK1)
1055   {
1056     assert_param(IS_RCC_PCLK1(RCC_ClkInitStruct->APB1CLKDivider));
1057     if ((RCC_ClkInitStruct->APB1CLKDivider) < (RCC->APBCFGR & RCC_APBCFGR_PPRE1))
1058     {
1059       MODIFY_REG(RCC->APBCFGR, RCC_APBCFGR_PPRE1, (RCC_ClkInitStruct->APB1CLKDivider));
1060     }
1061   }
1062 
1063   /*-------------------------- PCLK2 Configuration ---------------------------*/
1064   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_PCLK2) == RCC_CLOCKTYPE_PCLK2)
1065   {
1066     assert_param(IS_RCC_PCLK2(RCC_ClkInitStruct->APB2CLKDivider));
1067     if ((RCC_ClkInitStruct->APB2CLKDivider) < (RCC->APBCFGR & RCC_APBCFGR_PPRE2))
1068     {
1069       MODIFY_REG(RCC->APBCFGR, RCC_APBCFGR_PPRE2, (RCC_ClkInitStruct->APB2CLKDivider));
1070     }
1071   }
1072 
1073   /*-------------------------- PCLK4 Configuration ---------------------------*/
1074   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_PCLK4) == RCC_CLOCKTYPE_PCLK4)
1075   {
1076     assert_param(IS_RCC_PCLK4(RCC_ClkInitStruct->APB4CLKDivider));
1077     if ((RCC_ClkInitStruct->APB4CLKDivider) < (RCC->APBCFGR & RCC_APBCFGR_PPRE4))
1078     {
1079       MODIFY_REG(RCC->APBCFGR, RCC_APBCFGR_PPRE4, (RCC_ClkInitStruct->APB4CLKDivider));
1080     }
1081   }
1082 
1083   /*-------------------------- PCLK5 Configuration ---------------------------*/
1084   if (((RCC_ClkInitStruct->ClockType) & RCC_CLOCKTYPE_PCLK5) == RCC_CLOCKTYPE_PCLK5)
1085   {
1086     assert_param(IS_RCC_PCLK5(RCC_ClkInitStruct->APB5CLKDivider));
1087     if ((RCC_ClkInitStruct->APB5CLKDivider) < (RCC->APBCFGR & RCC_APBCFGR_PPRE5))
1088     {
1089       MODIFY_REG(RCC->APBCFGR, RCC_APBCFGR_PPRE5, (RCC_ClkInitStruct->APB5CLKDivider));
1090     }
1091   }
1092 
1093   /* Update the SystemCoreClock global variable with the System CPU clock */
1094   SystemCoreClock = HAL_RCC_GetSysClockFreq();
1095 
1096   /* Configure the source of time base considering new system clocks settings*/
1097   halstatus = HAL_InitTick(uwTickPrio);
1098 
1099   return halstatus;
1100 }
1101 
1102 /**
1103   * @}
1104   */
1105 
1106 /** @defgroup RCC_Group2 Peripheral Control functions
1107   *  @brief   RCC clocks control functions
1108   *
1109 @verbatim
1110  ===============================================================================
1111                       ##### Peripheral Control functions #####
1112  ===============================================================================
1113     [..]
1114     This subsection provides a set of functions allowing to control the RCC Clocks
1115     frequencies.
1116 
1117 @endverbatim
1118   * @{
1119   */
1120 
1121 /**
1122   * @brief  Selects the clock source to output on MCO1 pin(PA8) or on MCO2 pin(PC9).
1123   * @note   PA8/PC9 should be configured in alternate function mode.
1124   * @param  RCC_MCOx specifies the output direction for the clock source.
1125   *          This parameter can be one of the following values:
1126   *            @arg RCC_MCO1_PA8 Clock source to output on MCO1 pin(PA8).
1127   *            @arg RCC_MCO2_PC9 Clock source to output on MCO2 pin(PC9).
1128   * @param  RCC_MCOSource specifies the clock source to output.
1129   *          This parameter can be one of the following values:
1130   *            @arg RCC_MCO1SOURCE_HSI HSI clock selected as MCO1 source
1131   *            @arg RCC_MCO1SOURCE_LSE LSE clock selected as MCO1 source
1132   *            @arg RCC_MCO1SOURCE_HSE HSE clock selected as MCO1 source
1133   *            @arg RCC_MCO1SOURCE_PLL1Q:  PLL1Q clock selected as MCO1 source
1134   *            @arg RCC_MCO1SOURCE_HSI48 HSI48 (48MHZ) selected as MCO1 source
1135   *            @arg RCC_MCO2SOURCE_SYSCLK System clock (SYSCLK) selected as MCO2 source
1136   *            @arg RCC_MCO2SOURCE_PLL2PCLK PLL2P clock selected as MCO2 source
1137   *            @arg RCC_MCO2SOURCE_HSE HSE clock selected as MCO2 source
1138   *            @arg RCC_MCO2SOURCE_PLL1P  PLL1P clock selected as MCO2 source
1139   *            @arg RCC_MCO2SOURCE_CSI  CSI clock selected as MCO2 source
1140   *            @arg RCC_MCO2SOURCE_LSI  LSI clock selected as MCO2 source
1141   * @param  RCC_MCODiv: specifies the MCOx pre-scaler.
1142   *          This parameter can be one of the following values:
1143   *            @arg RCC_MCODIV_1 up to RCC_MCODIV_15  : divider applied to MCOx clock
1144   * @retval None
1145   */
HAL_RCC_MCOConfig(uint32_t RCC_MCOx,uint32_t RCC_MCOSource,uint32_t RCC_MCODiv)1146 void HAL_RCC_MCOConfig(uint32_t RCC_MCOx, uint32_t RCC_MCOSource, uint32_t RCC_MCODiv)
1147 {
1148 #if defined(HAL_GPIO_MODULE_ENABLED)
1149   GPIO_InitTypeDef GPIO_InitStruct;
1150   uint32_t mcoindex;
1151   uint32_t mco_gpio_index;
1152   GPIO_TypeDef *mco_gpio_port;
1153 
1154   /* Check the parameters */
1155   assert_param(IS_RCC_MCO(RCC_MCOx));
1156 
1157   /* Common GPIO init parameters */
1158   GPIO_InitStruct.Mode      = GPIO_MODE_AF_PP;
1159   GPIO_InitStruct.Speed     = GPIO_SPEED_FREQ_VERY_HIGH;
1160   GPIO_InitStruct.Pull      = GPIO_NOPULL;
1161 
1162   /* Get MCOx selection */
1163   mcoindex = RCC_MCOx & RCC_MCO_INDEX_MASK;
1164 
1165   /* Get MCOx GPIO Port */
1166   mco_gpio_port = (GPIO_TypeDef *) RCC_GET_MCO_GPIO_PORT(RCC_MCOx);
1167 
1168   /* MCOx Clock Enable */
1169   mco_gpio_index = RCC_GET_MCO_GPIO_INDEX(RCC_MCOx);
1170   SET_BIT(RCC->AHB4ENR, (1UL << mco_gpio_index));
1171 
1172   /* Configure the MCOx pin in alternate function mode */
1173   GPIO_InitStruct.Pin = RCC_GET_MCO_GPIO_PIN(RCC_MCOx);
1174   GPIO_InitStruct.Alternate = RCC_GET_MCO_GPIO_AF(RCC_MCOx);
1175   HAL_GPIO_Init(mco_gpio_port, &GPIO_InitStruct);
1176 
1177   if (mcoindex == RCC_MCO1_INDEX)
1178   {
1179     assert_param(IS_RCC_MCODIV(RCC_MCODiv));
1180     assert_param(IS_RCC_MCO1SOURCE(RCC_MCOSource));
1181     /* Mask MCOSEL[] and MCOPRE[] bits then set MCO clock source and prescaler */
1182     MODIFY_REG(RCC->CFGR, (RCC_CFGR_MCO1SEL | RCC_CFGR_MCO1PRE), (RCC_MCOSource | RCC_MCODiv));
1183   }
1184   else if (mcoindex == RCC_MCO2_INDEX)
1185   {
1186     assert_param(IS_RCC_MCODIV(RCC_MCODiv));
1187     assert_param(IS_RCC_MCO2SOURCE(RCC_MCOSource));
1188     /* Mask MCOSEL[] and MCOPRE[] bits then set MCO clock source and prescaler */
1189     MODIFY_REG(RCC->CFGR, (RCC_CFGR_MCO2SEL | RCC_CFGR_MCO2PRE), (RCC_MCOSource | (RCC_MCODiv << 7)));
1190   }
1191   else
1192   {
1193     /* Do nothing */
1194   }
1195 
1196 #endif /* HAL_GPIO_MODULE_ENABLED */
1197 }
1198 
1199 /**
1200   * @brief  Enables the Clock Security System.
1201   * @note   If a failure is detected on the HSE oscillator clock, this oscillator
1202   *         is automatically disabled and an interrupt is generated to inform the
1203   *         software about the failure (Clock Security System Interrupt, CSSI),
1204   *         allowing the MCU to perform rescue operations. The CSSI is linked to
1205   *         the Cortex-M NMI (Non-Mask-able Interrupt) exception vector.
1206   * @retval None
1207   */
HAL_RCC_EnableCSS(void)1208 void HAL_RCC_EnableCSS(void)
1209 {
1210   SET_BIT(RCC->CR, RCC_CR_HSECSSON);
1211 }
1212 
1213 /**
1214   * @brief  Disables the Clock Security System.
1215   * @retval None
1216   */
HAL_RCC_DisableCSS(void)1217 void HAL_RCC_DisableCSS(void)
1218 {
1219   CLEAR_BIT(RCC->CR, RCC_CR_HSECSSON);
1220 }
1221 
1222 /**
1223   * @brief  Returns the SYSCLK frequency
1224   *
1225   * @note   The system frequency computed by this function is not the real
1226   *         frequency in the chip. It is calculated based on the predefined
1227   *         constant and the selected clock source:
1228   * @note     If SYSCLK source is CSI, function returns values based on CSI_VALUE(*)
1229   * @note     If SYSCLK source is HSI, function returns values based on HSI_VALUE(**)
1230   * @note     If SYSCLK source is HSE, function returns values based on HSE_VALUE(***)
1231   * @note     If SYSCLK source is PLL, function returns values based on CSI_VALUE(*),
1232   *           HSI_VALUE(**) or HSE_VALUE(***) multiplied/divided by the PLL factors.
1233   * @note     (*) CSI_VALUE is a constant defined in stm32h7rsxx_hal_conf.h file (default value
1234   *               4 MHz) but the real value may vary depending on the variations
1235   *               in voltage and temperature.
1236   * @note     (**) HSI_VALUE is a constant defined in stm32h7rsxx_hal_conf.h file (default value
1237   *               64 MHz) but the real value may vary depending on the variations
1238   *               in voltage and temperature.
1239   * @note     (***) HSE_VALUE is a constant defined in stm32h7rsxx_hal_conf.h file (default value
1240   *                24 MHz), user has to ensure that HSE_VALUE is same as the real
1241   *                frequency of the crystal used. Otherwise, this function may
1242   *                have wrong result.
1243   *
1244   * @note   The result of this function could be not correct when using fractional
1245   *         value for HSE crystal.
1246   *
1247   * @note   This function can be used by the user application to compute the
1248   *         baud rate for the communication peripherals or configure other parameters.
1249   *
1250   * @note   Each time SYSCLK changes, this function must be called to update the
1251   *         right SYSCLK value. Otherwise, any configuration based on this function will be incorrect.
1252   *
1253   *
1254   * @retval SYSCLK frequency
1255   */
HAL_RCC_GetSysClockFreq(void)1256 uint32_t HAL_RCC_GetSysClockFreq(void)
1257 {
1258   uint32_t pllp, pllsource, pllm, pllfracen, hsivalue;
1259   float_t fracn1, pllvco;
1260   uint32_t sysclockfreq, prescaler;
1261 
1262   /* Get SYSCLK source -------------------------------------------------------*/
1263 
1264   switch (RCC->CFGR & RCC_CFGR_SWS)
1265   {
1266     case RCC_SYSCLKSOURCE_STATUS_HSI:  /* HSI used as system clock source */
1267 
1268       if (READ_BIT(RCC->CR, RCC_CR_HSIDIVF) != 0U)
1269       {
1270         sysclockfreq = (uint32_t)(HSI_VALUE >> (__HAL_RCC_GET_HSI_DIVIDER() >> RCC_CR_HSIDIV_Pos));
1271       }
1272       else
1273       {
1274         /* Can't retrieve HSIDIV value */
1275         sysclockfreq = 0U;
1276       }
1277 
1278       break;
1279 
1280     case RCC_SYSCLKSOURCE_STATUS_CSI:  /* CSI used as system clock  source */
1281       sysclockfreq = CSI_VALUE;
1282       break;
1283 
1284     case RCC_SYSCLKSOURCE_STATUS_HSE:  /* HSE used as system clock  source */
1285       sysclockfreq = HSE_VALUE;
1286       break;
1287 
1288     case RCC_SYSCLKSOURCE_STATUS_PLLCLK:  /* PLL1 used as system clock  source */
1289 
1290       /* PLL_VCO = (HSE_VALUE or HSI_VALUE or CSI_VALUE/ PLLM) * PLLN
1291       SYSCLK = PLL_VCO / PLLR
1292       */
1293       pllsource = (RCC->PLLCKSELR & RCC_PLLCKSELR_PLLSRC);
1294       pllm = ((RCC->PLLCKSELR & RCC_PLLCKSELR_DIVM1) >> RCC_PLLCKSELR_DIVM1_Pos)  ;
1295       pllfracen = ((RCC-> PLLCFGR & RCC_PLLCFGR_PLL1FRACEN) >> RCC_PLLCFGR_PLL1FRACEN_Pos);
1296       fracn1 = (float_t)(uint32_t)(pllfracen * ((RCC->PLL1FRACR & RCC_PLL1FRACR_FRACN) >> 3));
1297 
1298       if (pllm != 0U)
1299       {
1300         switch (pllsource)
1301         {
1302           case RCC_PLLSOURCE_HSI:  /* HSI used as PLL clock source */
1303 
1304             if (READ_BIT(RCC->CR, RCC_CR_HSIDIVF) != 0U)
1305             {
1306               hsivalue = (HSI_VALUE >> (__HAL_RCC_GET_HSI_DIVIDER() >> RCC_CR_HSIDIV_Pos));
1307               pllvco = ((float_t)hsivalue / (float_t)pllm) * ((float_t)(uint32_t)(RCC->PLL1DIVR1 & RCC_PLL1DIVR1_DIVN) + (fracn1 / (float_t)0x2000) + (float_t)1);
1308             }
1309             else
1310             {
1311               /* Can't retrieve HSIDIV value */
1312               pllvco = (float_t)0;
1313             }
1314             break;
1315 
1316           case RCC_PLLSOURCE_CSI:  /* CSI used as PLL clock source */
1317             pllvco = ((float_t)CSI_VALUE / (float_t)pllm) * ((float_t)(uint32_t)(RCC->PLL1DIVR1 & RCC_PLL1DIVR1_DIVN) + (fracn1 / (float_t)0x2000) + (float_t)1);
1318             break;
1319 
1320           case RCC_PLLSOURCE_HSE:  /* HSE used as PLL clock source */
1321             pllvco = ((float_t)HSE_VALUE / (float_t)pllm) * ((float_t)(uint32_t)(RCC->PLL1DIVR1 & RCC_PLL1DIVR1_DIVN) + (fracn1 / (float_t)0x2000) + (float_t)1);
1322             break;
1323 
1324           default:
1325             pllvco = ((float_t)CSI_VALUE / (float_t)pllm) * ((float_t)(uint32_t)(RCC->PLL1DIVR1 & RCC_PLL1DIVR1_DIVN) + (fracn1 / (float_t)0x2000) + (float_t)1);
1326             break;
1327         }
1328         pllp = (((RCC->PLL1DIVR1 & RCC_PLL1DIVR1_DIVP) >> RCC_PLL1DIVR1_DIVP_Pos) + 1U) ;
1329         sysclockfreq = (uint32_t)(float_t)(pllvco / (float_t)pllp);
1330       }
1331       else
1332       {
1333         sysclockfreq = 0U;
1334       }
1335       break;
1336 
1337     default:
1338       sysclockfreq = CSI_VALUE;
1339       break;
1340   }
1341 
1342   prescaler = RCC->CDCFGR & RCC_CDCFGR_CPRE;
1343   if (prescaler >= 8U)
1344   {
1345     sysclockfreq = sysclockfreq >> (prescaler - RCC_CDCFGR_CPRE_3 + 1U);
1346   }
1347 
1348   return sysclockfreq;
1349 }
1350 
1351 
1352 /**
1353   * @brief  Return the HCLK frequency.
1354   * @retval HCLK frequency in Hz
1355   */
HAL_RCC_GetHCLKFreq(void)1356 uint32_t HAL_RCC_GetHCLKFreq(void)
1357 {
1358   uint32_t clock, prescaler;
1359   const uint8_t AHBPrescTable[8] = {1U, 2U, 3U, 4U, 6U, 7U, 8U, 9U};
1360 
1361   /* SysClk */
1362   clock = HAL_RCC_GetSysClockFreq();
1363   /* Bus matrix divider */
1364   prescaler = (RCC->BMCFGR & RCC_BMCFGR_BMPRE) >> RCC_BMCFGR_BMPRE_Pos;
1365   if (prescaler >= 8U)
1366   {
1367     clock = clock >> AHBPrescTable[prescaler - 8U];
1368   }
1369   return (clock);
1370 }
1371 
1372 /**
1373   * @brief  Return the PCLK1 frequency.
1374   * @note   Each time PCLK1 changes, this function must be called to update the
1375   *         right PCLK1 value. Otherwise, any configuration based on this function will be incorrect.
1376   * @retval PCLK1 frequency in Hz
1377   */
HAL_RCC_GetPCLK1Freq(void)1378 uint32_t HAL_RCC_GetPCLK1Freq(void)
1379 {
1380   uint32_t clock, prescaler;
1381   /* Get HCLK source and compute PCLK1 frequency ---------------------------*/
1382   clock = HAL_RCC_GetHCLKFreq();
1383   /* APB1 prescaler */
1384   prescaler = (RCC->APBCFGR & RCC_APBCFGR_PPRE1) >> RCC_APBCFGR_PPRE1_Pos;
1385   if (prescaler >= 4U)
1386   {
1387     clock = clock >> (prescaler - 3U);
1388   }
1389   return (clock);
1390 }
1391 
1392 /**
1393   * @brief  Return the PCLK2 frequency.
1394   * @note   Each time PCLK2 changes, this function must be called to update the
1395   *         right PCLK2 value. Otherwise, any configuration based on this function will be incorrect.
1396   * @retval PCLK2 frequency in Hz
1397   */
HAL_RCC_GetPCLK2Freq(void)1398 uint32_t HAL_RCC_GetPCLK2Freq(void)
1399 {
1400   uint32_t clock, prescaler;
1401   /* Get HCLK source and compute PCLK2 frequency ---------------------------*/
1402   clock = HAL_RCC_GetHCLKFreq();
1403   /* APB2 prescaler */
1404   prescaler = (RCC->APBCFGR & RCC_APBCFGR_PPRE2) >> RCC_APBCFGR_PPRE2_Pos;
1405   if (prescaler >= 4U)
1406   {
1407     clock = clock >> (prescaler - 3U);
1408   }
1409   return (clock);
1410 }
1411 
1412 /**
1413   * @brief  Return the PCLK4 frequency.
1414   * @note   Each time PCLK4 changes, this function must be called to update the
1415   *         right PCLK4 value. Otherwise, any configuration based on this function will be incorrect.
1416   * @retval PCLK4 frequency in Hz
1417   */
HAL_RCC_GetPCLK4Freq(void)1418 uint32_t HAL_RCC_GetPCLK4Freq(void)
1419 {
1420   uint32_t clock, prescaler;
1421   /* Get HCLK source and compute PCLK4 frequency ---------------------------*/
1422   clock = HAL_RCC_GetHCLKFreq();
1423   /* APB4 prescaler */
1424   prescaler = (RCC->APBCFGR & RCC_APBCFGR_PPRE4) >> RCC_APBCFGR_PPRE4_Pos;
1425   if (prescaler >= 4U)
1426   {
1427     clock = clock >> (prescaler - 3U);
1428   }
1429   return (clock);
1430 }
1431 
1432 /**
1433   * @brief  Return the PCLK5 frequency.
1434   * @note   Each time PCLK5 changes, this function must be called to update the
1435   *         right PCLK5 value. Otherwise, any configuration based on this function will be incorrect.
1436   * @retval PCLK5 frequency in Hz
1437   */
HAL_RCC_GetPCLK5Freq(void)1438 uint32_t HAL_RCC_GetPCLK5Freq(void)
1439 {
1440   uint32_t clock, prescaler;
1441   /* Get HCLK source and compute PCLK5 frequency ---------------------------*/
1442   clock = HAL_RCC_GetHCLKFreq();
1443   /* APB5 prescaler */
1444   prescaler = (RCC->APBCFGR & RCC_APBCFGR_PPRE5) >> RCC_APBCFGR_PPRE5_Pos;
1445   if (prescaler >= 4U)
1446   {
1447     clock = clock >> (prescaler - 3U);
1448   }
1449   return (clock);
1450 }
1451 
1452 /**
1453   * @brief  Return the PLL1P frequency.
1454   * @retval PLL1P frequency in Hz
1455   */
HAL_RCC_GetPLL1PFreq(void)1456 uint32_t HAL_RCC_GetPLL1PFreq(void)
1457 {
1458   uint32_t pllp;
1459 
1460   /* PLL1P divider */
1461   pllp = ((RCC->PLL1DIVR1 & RCC_PLL1DIVR1_DIVP) >> RCC_PLL1DIVR1_DIVP_Pos) + 1U;
1462 
1463   /* Compute VCO output frequency and return PLL1P one */
1464   return ((uint32_t)RCC_PLL1_GetVCOOutputFreq() / pllp);
1465 }
1466 
1467 /**
1468   * @brief  Return the PLL1Q frequency.
1469   * @retval PLL1Q frequency in Hz
1470   */
HAL_RCC_GetPLL1QFreq(void)1471 uint32_t HAL_RCC_GetPLL1QFreq(void)
1472 {
1473   uint32_t pllq;
1474 
1475   /* PLL1Q divider */
1476   pllq = ((RCC->PLL1DIVR1 & RCC_PLL1DIVR1_DIVQ) >> RCC_PLL1DIVR1_DIVQ_Pos) + 1U;
1477 
1478   /* Compute VCO output frequency and return PLL1Q one */
1479   return ((uint32_t)RCC_PLL1_GetVCOOutputFreq() / pllq);
1480 }
1481 
1482 /**
1483   * @brief  Return the PLL1R frequency.
1484   * @retval PLL1R frequency in Hz
1485   */
HAL_RCC_GetPLL1RFreq(void)1486 uint32_t HAL_RCC_GetPLL1RFreq(void)
1487 {
1488   uint32_t pllr;
1489 
1490   /* PLL1R divider */
1491   pllr = ((RCC->PLL1DIVR1 & RCC_PLL1DIVR1_DIVR) >> RCC_PLL1DIVR1_DIVR_Pos) + 1U;
1492 
1493   /* Compute VCO output frequency and return PLL1R one */
1494   return ((uint32_t)RCC_PLL1_GetVCOOutputFreq() / pllr);
1495 }
1496 
1497 /**
1498   * @brief  Return the PLL1S frequency.
1499   * @retval PLL1S frequency in Hz
1500   */
HAL_RCC_GetPLL1SFreq(void)1501 uint32_t HAL_RCC_GetPLL1SFreq(void)
1502 {
1503   uint32_t plls;
1504 
1505   /* PLL1S divider */
1506   plls = ((RCC->PLL1DIVR2 & RCC_PLL1DIVR2_DIVS) >> RCC_PLL1DIVR2_DIVS_Pos) + 1U;
1507 
1508   /* Compute VCO output frequency and return PLL1S one */
1509   return ((uint32_t)RCC_PLL1_GetVCOOutputFreq() / plls);
1510 }
1511 
1512 /**
1513   * @brief  Return the PLL2P frequency.
1514   * @retval PLL2P frequency in Hz
1515   */
HAL_RCC_GetPLL2PFreq(void)1516 uint32_t HAL_RCC_GetPLL2PFreq(void)
1517 {
1518   uint32_t pllp;
1519 
1520   /* PLL2P divider */
1521   pllp = ((RCC->PLL2DIVR1 & RCC_PLL2DIVR1_DIVP) >> RCC_PLL2DIVR1_DIVP_Pos) + 1U;
1522 
1523   /* Compute VCO output frequency and return PLL2P one */
1524   return ((uint32_t)RCC_PLL2_GetVCOOutputFreq() / pllp);
1525 }
1526 
1527 /**
1528   * @brief  Return the PLL2Q frequency.
1529   * @retval PLL2Q frequency in Hz
1530   */
HAL_RCC_GetPLL2QFreq(void)1531 uint32_t HAL_RCC_GetPLL2QFreq(void)
1532 {
1533   uint32_t pllq;
1534 
1535   /* PLL2Q divider */
1536   pllq = ((RCC->PLL2DIVR1 & RCC_PLL2DIVR1_DIVQ) >> RCC_PLL2DIVR1_DIVQ_Pos) + 1U;
1537 
1538   /* Compute VCO output frequency and return PLL2Q one */
1539   return ((uint32_t)RCC_PLL2_GetVCOOutputFreq() / pllq);
1540 }
1541 
1542 /**
1543   * @brief  Return the PLL2R frequency.
1544   * @retval PLL2R frequency in Hz
1545   */
HAL_RCC_GetPLL2RFreq(void)1546 uint32_t HAL_RCC_GetPLL2RFreq(void)
1547 {
1548   uint32_t pllr;
1549 
1550   /* PLL2R divider */
1551   pllr = ((RCC->PLL2DIVR1 & RCC_PLL2DIVR1_DIVR) >> RCC_PLL2DIVR1_DIVR_Pos) + 1U;
1552 
1553   /* Compute VCO output frequency and return PLL2R one */
1554   return ((uint32_t)RCC_PLL2_GetVCOOutputFreq() / pllr);
1555 }
1556 
1557 /**
1558   * @brief  Return the PLL2S frequency.
1559   * @retval PLL2S frequency in Hz
1560   */
HAL_RCC_GetPLL2SFreq(void)1561 uint32_t HAL_RCC_GetPLL2SFreq(void)
1562 {
1563   uint32_t plls;
1564 
1565   /* PLL2S divider */
1566   plls = ((RCC->PLL2DIVR2 & RCC_PLL2DIVR2_DIVS) >> RCC_PLL2DIVR2_DIVS_Pos) + 1U;
1567 
1568   /* Compute VCO output frequency and return PLL2R one */
1569   return ((uint32_t)RCC_PLL2_GetVCOOutputFreq() / plls);
1570 }
1571 
1572 /**
1573   * @brief  Return the PLL2T frequency.
1574   * @retval PLL2T frequency in Hz
1575   */
HAL_RCC_GetPLL2TFreq(void)1576 uint32_t HAL_RCC_GetPLL2TFreq(void)
1577 {
1578   uint32_t pllt;
1579 
1580   /* PLL2T divider */
1581   pllt = ((RCC->PLL2DIVR2 & RCC_PLL2DIVR2_DIVT) >> RCC_PLL2DIVR2_DIVT_Pos) + 1U;
1582 
1583   /* Compute VCO output frequency and return PLL2T one */
1584   return ((uint32_t)RCC_PLL2_GetVCOOutputFreq() / pllt);
1585 }
1586 
1587 /**
1588   * @brief  Return the PLL3P frequency.
1589   * @retval PLL3P frequency in Hz
1590   */
HAL_RCC_GetPLL3PFreq(void)1591 uint32_t HAL_RCC_GetPLL3PFreq(void)
1592 {
1593   uint32_t pllp;
1594 
1595   /* PLL3P divider */
1596   pllp = ((RCC->PLL3DIVR1 & RCC_PLL3DIVR1_DIVP) >> RCC_PLL3DIVR1_DIVP_Pos) + 1U;
1597 
1598   /* Compute VCO output frequency and return PLL3P one */
1599   return ((uint32_t)RCC_PLL3_GetVCOOutputFreq() / pllp);
1600 }
1601 
1602 /**
1603   * @brief  Return the PLL3Q frequency.
1604   * @retval PLL3Q frequency in Hz
1605   */
HAL_RCC_GetPLL3QFreq(void)1606 uint32_t HAL_RCC_GetPLL3QFreq(void)
1607 {
1608   uint32_t pllq;
1609 
1610   /* PLL3Q divider */
1611   pllq = ((RCC->PLL3DIVR1 & RCC_PLL3DIVR1_DIVQ) >> RCC_PLL3DIVR1_DIVQ_Pos) + 1U;
1612 
1613   /* Compute VCO output frequency and return PLL3Q one */
1614   return ((uint32_t)RCC_PLL3_GetVCOOutputFreq() / pllq);
1615 }
1616 
1617 /**
1618   * @brief  Return the PLL3R frequency.
1619   * @retval PLL3R frequency in Hz
1620   */
HAL_RCC_GetPLL3RFreq(void)1621 uint32_t HAL_RCC_GetPLL3RFreq(void)
1622 {
1623   uint32_t pllr;
1624 
1625   /* PLL3R divider */
1626   pllr = ((RCC->PLL3DIVR1 & RCC_PLL3DIVR1_DIVR) >> RCC_PLL3DIVR1_DIVR_Pos) + 1U;
1627 
1628   /* Compute VCO output frequency and return PLL3R one */
1629   return ((uint32_t)RCC_PLL3_GetVCOOutputFreq() / pllr);
1630 }
1631 
1632 /**
1633   * @brief  Return the PLL3S frequency.
1634   * @retval PLL3S frequency in Hz
1635   */
HAL_RCC_GetPLL3SFreq(void)1636 uint32_t HAL_RCC_GetPLL3SFreq(void)
1637 {
1638   uint32_t plls;
1639 
1640   /* PLL3S divider */
1641   plls = ((RCC->PLL3DIVR2 & RCC_PLL3DIVR2_DIVS) >> RCC_PLL3DIVR2_DIVS_Pos) + 1U;
1642 
1643   /* Compute VCO output frequency and return PLL3S one */
1644   return ((uint32_t)RCC_PLL3_GetVCOOutputFreq() / plls);
1645 }
1646 
1647 /**
1648   * @brief  Configures the RCC_OscInitStruct according to the internal
1649   * RCC configuration registers.
1650   * @param  RCC_OscInitStruct: pointer to an RCC_OscInitTypeDef structure that
1651   * will be configured.
1652   * @retval None
1653   */
HAL_RCC_GetOscConfig(RCC_OscInitTypeDef * RCC_OscInitStruct)1654 void HAL_RCC_GetOscConfig(RCC_OscInitTypeDef  *RCC_OscInitStruct)
1655 {
1656 
1657   uint32_t regvalue;
1658   uint32_t mask;
1659 
1660   /* Check the parameters */
1661   assert_param(RCC_OscInitStruct != (void *)NULL);
1662 
1663   /* Set all possible values for the Oscillator type parameter ---------------*/
1664   RCC_OscInitStruct->OscillatorType = RCC_OSCILLATORTYPE_HSE | RCC_OSCILLATORTYPE_HSI | RCC_OSCILLATORTYPE_CSI | \
1665                                       RCC_OSCILLATORTYPE_LSE | RCC_OSCILLATORTYPE_LSI | RCC_OSCILLATORTYPE_HSI48;
1666 
1667   /* Get Backup Domain register  */
1668   regvalue = RCC->BDCR;
1669 
1670   /* Get the LSE configuration -----------------------------------------------*/
1671   mask = (RCC_BDCR_LSEBYP | RCC_BDCR_LSEEXT | RCC_BDCR_LSEON);
1672   RCC_OscInitStruct->LSEState = (regvalue & mask);
1673 
1674   /* Get RCC clock control and status register */
1675   regvalue = RCC->CSR;
1676 
1677   /* Get the LSI configuration -----------------------------------------------*/
1678   mask = RCC_CSR_LSION;
1679   RCC_OscInitStruct->LSIState = (regvalue & mask);
1680 
1681   /* Get Control register */
1682   regvalue = RCC->CR;
1683 
1684   /* Get the HSE configuration -----------------------------------------------*/
1685   mask = (RCC_CR_HSEBYP | RCC_CR_HSEEXT | RCC_CR_HSEON);
1686   RCC_OscInitStruct->HSEState = (regvalue & mask);
1687 
1688   /* Get the HSI configuration -----------------------------------------------*/
1689   mask = RCC_CR_HSION;
1690   RCC_OscInitStruct->HSIState = (regvalue & mask);
1691   RCC_OscInitStruct->HSIDiv = (regvalue & RCC_CR_HSIDIV);
1692   RCC_OscInitStruct->HSICalibrationValue = ((RCC->HSICFGR & RCC_HSICFGR_HSITRIM) >> RCC_HSICFGR_HSITRIM_Pos);
1693 
1694   /* Get the HSI48 configuration ---------------------------------------------*/
1695   mask = RCC_CR_HSI48ON;
1696   RCC_OscInitStruct->HSI48State = (regvalue & mask);
1697 
1698   /* Get the CSI configuration -----------------------------------------------*/
1699   mask = RCC_CR_CSION;
1700   RCC_OscInitStruct->CSIState = (regvalue & mask);
1701 
1702   /* Get the PLL1 configuration -----------------------------------------------*/
1703   if ((regvalue & RCC_CR_PLL1ON) == RCC_CR_PLL1ON)
1704   {
1705     RCC_OscInitStruct->PLL1.PLLState = RCC_PLL_ON;
1706   }
1707   else
1708   {
1709     RCC_OscInitStruct->PLL1.PLLState = RCC_PLL_OFF;
1710   }
1711 
1712   /* Get PLL1 configuration register */
1713   regvalue = RCC->PLLCKSELR;
1714   RCC_OscInitStruct->PLL1.PLLSource = (regvalue & RCC_PLLCKSELR_PLLSRC);
1715   RCC_OscInitStruct->PLL1.PLLM = ((regvalue & RCC_PLLCKSELR_DIVM1) >> RCC_PLLCKSELR_DIVM1_Pos);
1716 
1717   /* Check if fractional part is enable */
1718   regvalue = RCC->PLLCFGR;
1719   if ((regvalue & RCC_PLLCFGR_PLL1FRACEN) != 0x00u)
1720   {
1721     regvalue = (((RCC->PLL1FRACR & RCC_PLL1FRACR_FRACN) >> RCC_PLL1FRACR_FRACN_Pos));
1722   }
1723   else
1724   {
1725     regvalue = 0;
1726   }
1727   RCC_OscInitStruct->PLL1.PLLFractional = regvalue;
1728 
1729   /* Get PLL1 dividers register */
1730   regvalue = RCC->PLL1DIVR1;
1731   RCC_OscInitStruct->PLL1.PLLN = ((regvalue & RCC_PLL1DIVR1_DIVN) + 1U);
1732   RCC_OscInitStruct->PLL1.PLLR = (((regvalue & RCC_PLL1DIVR1_DIVR) >> RCC_PLL1DIVR1_DIVR_Pos) + 1U);
1733   RCC_OscInitStruct->PLL1.PLLP = (((regvalue & RCC_PLL1DIVR1_DIVP) >> RCC_PLL1DIVR1_DIVP_Pos) + 1U);
1734   RCC_OscInitStruct->PLL1.PLLQ = (((regvalue & RCC_PLL1DIVR1_DIVQ) >> RCC_PLL1DIVR1_DIVQ_Pos) + 1U);
1735   regvalue = RCC->PLL1DIVR2;
1736   RCC_OscInitStruct->PLL1.PLLS = (((regvalue & RCC_PLL1DIVR2_DIVS) >> RCC_PLL1DIVR2_DIVS_Pos) + 1U);
1737   RCC_OscInitStruct->PLL1.PLLT = 0;
1738 
1739   /* Get the PLL2 configuration -----------------------------------------------*/
1740   /* Get Control register */
1741   regvalue = RCC->CR;
1742   if ((regvalue & RCC_CR_PLL2ON) == RCC_CR_PLL2ON)
1743   {
1744     RCC_OscInitStruct->PLL2.PLLState = RCC_PLL_ON;
1745   }
1746   else
1747   {
1748     RCC_OscInitStruct->PLL2.PLLState = RCC_PLL_OFF;
1749   }
1750 
1751   /* Get PLL2 configuration register */
1752   regvalue = RCC->PLLCKSELR;
1753   RCC_OscInitStruct->PLL2.PLLSource = (regvalue & RCC_PLLCKSELR_PLLSRC);
1754   RCC_OscInitStruct->PLL2.PLLM = ((regvalue & RCC_PLLCKSELR_DIVM2) >> RCC_PLLCKSELR_DIVM2_Pos);
1755 
1756   /* Check if fractional part is enable */
1757   regvalue = RCC->PLLCFGR;
1758   if ((regvalue & RCC_PLLCFGR_PLL2FRACEN) != 0x00u)
1759   {
1760     regvalue = (((RCC->PLL2FRACR & RCC_PLL2FRACR_FRACN) >> RCC_PLL2FRACR_FRACN_Pos));
1761   }
1762   else
1763   {
1764     regvalue = 0;
1765   }
1766   RCC_OscInitStruct->PLL2.PLLFractional = regvalue;
1767 
1768   /* Get PLL2 dividers register */
1769   regvalue = RCC->PLL2DIVR1;
1770   RCC_OscInitStruct->PLL2.PLLN = ((regvalue & RCC_PLL2DIVR1_DIVN) + 1U);
1771   RCC_OscInitStruct->PLL2.PLLR = (((regvalue & RCC_PLL2DIVR1_DIVR) >> RCC_PLL2DIVR1_DIVR_Pos) + 1U);
1772   RCC_OscInitStruct->PLL2.PLLP = (((regvalue & RCC_PLL2DIVR1_DIVP) >> RCC_PLL2DIVR1_DIVP_Pos) + 1U);
1773   RCC_OscInitStruct->PLL2.PLLQ = (((regvalue & RCC_PLL2DIVR1_DIVQ) >> RCC_PLL2DIVR1_DIVQ_Pos) + 1U);
1774   regvalue = RCC->PLL2DIVR2;
1775   RCC_OscInitStruct->PLL2.PLLS = (((regvalue & RCC_PLL2DIVR2_DIVS) >> RCC_PLL2DIVR2_DIVS_Pos) + 1U);
1776   RCC_OscInitStruct->PLL2.PLLT = (((regvalue & RCC_PLL2DIVR2_DIVT) >> RCC_PLL2DIVR2_DIVT_Pos) + 1U);
1777 
1778   /* Get the PLL3 configuration -----------------------------------------------*/
1779   /* Get Control register */
1780   regvalue = RCC->CR;
1781   if ((regvalue & RCC_CR_PLL3ON) == RCC_CR_PLL3ON)
1782   {
1783     RCC_OscInitStruct->PLL3.PLLState = RCC_PLL_ON;
1784   }
1785   else
1786   {
1787     RCC_OscInitStruct->PLL3.PLLState = RCC_PLL_OFF;
1788   }
1789 
1790   /* Get PLL3 configuration register */
1791   regvalue = RCC->PLLCKSELR;
1792   RCC_OscInitStruct->PLL3.PLLSource = (regvalue & RCC_PLLCKSELR_PLLSRC);
1793   RCC_OscInitStruct->PLL3.PLLM = ((regvalue & RCC_PLLCKSELR_DIVM3) >> RCC_PLLCKSELR_DIVM3_Pos);
1794 
1795 
1796   /* Check if fractional part is enable */
1797   regvalue = RCC->PLLCFGR;
1798   if ((regvalue & RCC_PLLCFGR_PLL3FRACEN) != 0x00u)
1799   {
1800     regvalue = (((RCC->PLL3FRACR & RCC_PLL3FRACR_FRACN) >> RCC_PLL3FRACR_FRACN_Pos));
1801   }
1802   else
1803   {
1804     regvalue = 0;
1805   }
1806   RCC_OscInitStruct->PLL3.PLLFractional = regvalue;
1807 
1808   /* Get PLL3 dividers register */
1809   regvalue = RCC->PLL3DIVR1;
1810   RCC_OscInitStruct->PLL3.PLLN = ((regvalue & RCC_PLL3DIVR1_DIVN) + 1U);
1811   RCC_OscInitStruct->PLL3.PLLR = (((regvalue & RCC_PLL3DIVR1_DIVR) >> RCC_PLL3DIVR1_DIVR_Pos) + 1U);
1812   RCC_OscInitStruct->PLL3.PLLP = (((regvalue & RCC_PLL3DIVR1_DIVP) >> RCC_PLL3DIVR1_DIVP_Pos) + 1U);
1813   RCC_OscInitStruct->PLL3.PLLQ = (((regvalue & RCC_PLL3DIVR1_DIVQ) >> RCC_PLL3DIVR1_DIVQ_Pos) + 1U);
1814   regvalue = RCC->PLL3DIVR2;
1815   RCC_OscInitStruct->PLL3.PLLS = (((regvalue & RCC_PLL3DIVR2_DIVS) >> RCC_PLL3DIVR2_DIVS_Pos) + 1U);
1816   RCC_OscInitStruct->PLL3.PLLT = 0;
1817 
1818 }
1819 
1820 /**
1821   * @brief  Configures the RCC_ClkInitStruct according to the internal
1822   * RCC configuration registers.
1823   * @param  RCC_ClkInitStruct: pointer to an RCC_ClkInitTypeDef structure that
1824   * will be configured.
1825   * @param  pFLatency: Pointer on the Flash Latency.
1826   * @retval None
1827   */
HAL_RCC_GetClockConfig(RCC_ClkInitTypeDef * RCC_ClkInitStruct,uint32_t * pFLatency)1828 void HAL_RCC_GetClockConfig(RCC_ClkInitTypeDef  *RCC_ClkInitStruct, uint32_t *pFLatency)
1829 {
1830   /* Set all possible values for the Clock type parameter --------------------*/
1831   RCC_ClkInitStruct->ClockType = RCC_CLOCKTYPE_SYSCLK | RCC_CLOCKTYPE_HCLK  | \
1832                                  RCC_CLOCKTYPE_PCLK1  | RCC_CLOCKTYPE_PCLK2 | \
1833                                  RCC_CLOCKTYPE_PCLK4  | RCC_CLOCKTYPE_PCLK5;
1834 
1835   /* Get the SYSCLK source ---------------------------------------------------*/
1836   RCC_ClkInitStruct->SYSCLKSource = READ_BIT(RCC->CFGR, RCC_CFGR_SW);
1837 
1838   /* Get the SYSCLK configuration---------------------------------------------*/
1839   RCC_ClkInitStruct->SYSCLKDivider = READ_BIT(RCC->CDCFGR, RCC_CDCFGR_CPRE);
1840 
1841   /* Get the HCLK configuration ----------------------------------------------*/
1842   RCC_ClkInitStruct->AHBCLKDivider = READ_BIT(RCC->BMCFGR, RCC_BMCFGR_BMPRE);
1843 
1844   /* Get the APB1 configuration ----------------------------------------------*/
1845   RCC_ClkInitStruct->APB1CLKDivider = READ_BIT(RCC->APBCFGR, RCC_APBCFGR_PPRE1);
1846 
1847   /* Get the APB2 configuration ----------------------------------------------*/
1848   RCC_ClkInitStruct->APB2CLKDivider = READ_BIT(RCC->APBCFGR, RCC_APBCFGR_PPRE2);
1849 
1850   /* Get the APB4 configuration ----------------------------------------------*/
1851   RCC_ClkInitStruct->APB4CLKDivider = READ_BIT(RCC->APBCFGR, RCC_APBCFGR_PPRE4);
1852 
1853   /* Get the APB5 configuration ----------------------------------------------*/
1854   RCC_ClkInitStruct->APB5CLKDivider = READ_BIT(RCC->APBCFGR, RCC_APBCFGR_PPRE5);
1855 
1856   /* Get the Flash Wait State (Latency) configuration ------------------------*/
1857   *pFLatency = __HAL_FLASH_GET_LATENCY();
1858 }
1859 
1860 /**
1861   * @brief This function handles the RCC HSE CSS interrupt request.
1862   * @note This API should be called under the NMI_Handler().
1863   * @retval None
1864   */
HAL_RCC_NMI_IRQHandler(void)1865 void HAL_RCC_NMI_IRQHandler(void)
1866 {
1867   /* Check RCC HSECSSF interrupt flag  */
1868   if (__HAL_RCC_GET_IT(RCC_IT_HSECSS))
1869   {
1870     /* Clear RCC HSE CSS pending bit */
1871     __HAL_RCC_CLEAR_IT(RCC_IT_HSECSS);
1872 
1873     /* RCC HSE Clock Security System interrupt user callback */
1874     HAL_RCC_HSECSSCallback();
1875   }
1876 }
1877 
1878 /**
1879   * @brief  RCC HSE Clock Security System interrupt callback
1880   * @retval none
1881   */
HAL_RCC_HSECSSCallback(void)1882 __weak void HAL_RCC_HSECSSCallback(void)
1883 {
1884   /* NOTE : This function should not be modified, when the callback is needed,
1885             the HAL_RCC_HSECSSCallback could be implemented in the user file
1886    */
1887 }
1888 
1889 /**
1890   * @brief  RCC LSE Clock Security System interrupt callback
1891   * @retval none
1892   */
HAL_RCC_LSECSSCallback(void)1893 __weak void HAL_RCC_LSECSSCallback(void)
1894 {
1895   /* NOTE : This function should not be modified, when the callback is needed,
1896             the HAL_RCC_LSECSSCallback could be implemented in the user file
1897    */
1898 }
1899 
1900 /**
1901   * @brief  Get and clear reset flags
1902   * @note   Once reset flags are retrieved, this API is clearing them in order
1903   *         to isolate next reset reason.
1904   * @retval can be a combination of @ref RCC_Reset_Flag
1905   */
HAL_RCC_GetResetSource(void)1906 uint32_t HAL_RCC_GetResetSource(void)
1907 {
1908   uint32_t reset;
1909 
1910   /* Get all reset flags */
1911   reset = RCC->RSR & RCC_RESET_FLAG_ALL;
1912 
1913   /* Clear Reset flags */
1914   RCC->RSR |= RCC_RSR_RMVF;
1915 
1916   return reset;
1917 }
1918 
1919 /**
1920   * @}
1921   */
1922 
1923 /* Private functions ---------------------------------------------------------*/
1924 /** @addtogroup RCC_Private_Functions
1925   * @{
1926   */
1927 
1928 /**
1929   * @brief  Configure the requested PLL
1930   * @param  PLLnumber PLL number to configure
1931   * @param  pPLLInit Pointer to an RCC_PLLInitTypeDef structure that
1932   *                  contains the configuration parameters.
1933   * @note   PLL is temporary disabled to apply new parameters
1934   *
1935   * @retval HAL status
1936   */
RCC_PLL_Config(uint32_t PLLnumber,const RCC_PLLInitTypeDef * pPLLInit)1937 static HAL_StatusTypeDef RCC_PLL_Config(uint32_t PLLnumber, const RCC_PLLInitTypeDef *pPLLInit)
1938 {
1939   __IO uint32_t *p_rcc_pll_divr1_reg;
1940   __IO uint32_t *p_rcc_pll_divr2_reg;
1941   __IO uint32_t *p_rcc_pll_fracr_reg;
1942   HAL_StatusTypeDef ret = HAL_OK;
1943   uint32_t tickstart;
1944   uint32_t pllsrc;
1945   uint32_t pllvco;
1946 
1947   p_rcc_pll_divr1_reg = &(RCC->PLL1DIVR1) + (((uint32_t)0x02) * PLLnumber);
1948   p_rcc_pll_divr2_reg = &(RCC->PLL1DIVR2) + (((uint32_t)0x01) * PLLnumber);
1949 
1950   /* Disable the post-dividers */
1951   CLEAR_BIT(RCC->PLLCFGR, (RCC_PLLCFGR_PLL1PEN | RCC_PLLCFGR_PLL1QEN | RCC_PLLCFGR_PLL1REN | RCC_PLLCFGR_PLL1SEN |
1952                            0x00000200U) /* Hardcoded because no definition in CMSIS */
1953             << ((RCC_PLLCFGR_PLL2PEN_Pos - RCC_PLLCFGR_PLL1PEN_Pos)*PLLnumber));
1954 
1955   /* Ensure PLLx is disabled */
1956   CLEAR_BIT(RCC->CR, RCC_CR_PLL1ON << ((RCC_CR_PLL2ON_Pos - RCC_CR_PLL1ON_Pos)*PLLnumber));
1957 
1958   /* Get Start Tick*/
1959   tickstart = HAL_GetTick();
1960 
1961   /* Wait till PLLx is disabled */
1962   while (READ_BIT(RCC->CR, (RCC_CR_PLL1RDY << ((RCC_CR_PLL2RDY_Pos - RCC_CR_PLL1RDY_Pos)*PLLnumber))) != 0U)
1963   {
1964     if ((HAL_GetTick() - tickstart) > RCC_PLL_TIMEOUT_VALUE)
1965     {
1966       return HAL_TIMEOUT;
1967     }
1968   }
1969 
1970   if (pPLLInit->PLLState == RCC_PLL_ON)
1971   {
1972     /* Check the parameters */
1973     assert_param(IS_RCC_PLLSOURCE(pPLLInit->PLLSource));
1974     assert_param(IS_RCC_PLLM_VALUE(pPLLInit->PLLM));
1975     assert_param(IS_RCC_PLLN_VALUE(pPLLInit->PLLN));
1976     assert_param(IS_RCC_PLLP_VALUE(pPLLInit->PLLP));
1977     assert_param(IS_RCC_PLLQ_VALUE(pPLLInit->PLLQ));
1978     assert_param(IS_RCC_PLLR_VALUE(pPLLInit->PLLR));
1979     assert_param(IS_RCC_PLLS_VALUE(pPLLInit->PLLS));
1980     assert_param(IS_RCC_PLLT_VALUE(pPLLInit->PLLT));
1981 
1982     pllsrc = pPLLInit->PLLSource;
1983 
1984     /* Compute VCO input frequency and define range accordingly. First check clock source frequency */
1985     if (pllsrc == RCC_PLLSOURCE_HSI)
1986     {
1987       /* Clock source is HSI or HSI/HSIDIV */
1988       pllvco = HSI_VALUE >> ((RCC->CR & RCC_CR_HSIDIV) >> RCC_CR_HSIDIV_Pos);
1989     }
1990     else if (pllsrc == RCC_PLLSOURCE_HSE)
1991     {
1992       /* Clock source is HSE */
1993       pllvco = HSE_VALUE;
1994     }
1995     else
1996     {
1997       /* Clock source is CSI */
1998       pllvco = CSI_VALUE;
1999     }
2000 
2001     /* Compute VCO input frequency depending on M divider */
2002     pllvco = (pllvco / pPLLInit->PLLM);
2003     assert_param(IS_RCC_PLL_VCOINPUTFREQ(pllvco));
2004 
2005     if (pllvco >= RCC_PLL_INPUTRANGE2_FREQMAX)
2006     {
2007       pllvco = RCC_PLL_VCOINPUT_RANGE3 | RCC_PLL_VCO_HIGH;
2008     }
2009     else if (pllvco >= RCC_PLL_INPUTRANGE1_FREQMAX)
2010     {
2011       pllvco = RCC_PLL_VCOINPUT_RANGE2 | RCC_PLL_VCO_HIGH;
2012     }
2013     else if (pllvco >= RCC_PLL_INPUTRANGE0_FREQMAX)
2014     {
2015       pllvco = RCC_PLL_VCOINPUT_RANGE1 | RCC_PLL_VCO_HIGH;
2016     }
2017     else
2018     {
2019       pllvco = RCC_PLL_VCOINPUT_RANGE0 | RCC_PLL_VCO_LOW;
2020     }
2021 
2022     pllvco = (pllvco << ((RCC_PLLCFGR_PLL2RGE_Pos - RCC_PLLCFGR_PLL1RGE_Pos) * PLLnumber));
2023 
2024     /* Configure PLL source and PLLM divider */
2025     MODIFY_REG(RCC->PLLCKSELR, (RCC_PLLCKSELR_PLLSRC | (RCC_PLLCKSELR_DIVM1 << ((RCC_PLLCKSELR_DIVM2_Pos - RCC_PLLCKSELR_DIVM1_Pos)*PLLnumber))), \
2026                pllsrc | (pPLLInit->PLLM << (RCC_PLLCKSELR_DIVM1_Pos + ((RCC_PLLCKSELR_DIVM2_Pos - RCC_PLLCKSELR_DIVM1_Pos)*PLLnumber))));
2027 
2028     if ((RCC->PLLCKSELR & RCC_PLLCKSELR_PLLSRC) != pllsrc)
2029     {
2030       /* There is another PLL activated with another source */
2031       return HAL_ERROR;
2032     }
2033 
2034     /* Configure VCO input range, VCO selection and clear FRACEN */
2035     MODIFY_REG(RCC->PLLCFGR, (RCC_PLLCFGR_PLL1RGE | RCC_PLLCFGR_PLL1VCOSEL | RCC_PLLCFGR_PLL1FRACEN) << (((RCC_PLLCFGR_PLL2RGE_Pos - RCC_PLLCFGR_PLL1RGE_Pos)*PLLnumber)), \
2036                pllvco);
2037 
2038     /* Configure PLLN, PLLP, PLLQ, PLLR, PLLS and PLLT dividers */
2039     WRITE_REG(*p_rcc_pll_divr1_reg, ((pPLLInit->PLLN - 1U) |
2040                                      ((pPLLInit->PLLP - 1U) << RCC_PLL1DIVR1_DIVP_Pos) |
2041                                      ((pPLLInit->PLLQ - 1U) << RCC_PLL1DIVR1_DIVQ_Pos) |
2042                                      ((pPLLInit->PLLR - 1U) << RCC_PLL1DIVR1_DIVR_Pos)));
2043     WRITE_REG(*p_rcc_pll_divr2_reg, ((pPLLInit->PLLS - 1U) |
2044                                      ((pPLLInit->PLLT - 1U) << RCC_PLL2DIVR2_DIVT_Pos)));
2045 
2046     if (PLLnumber == RCC_PLL1_CONFIG)
2047     {
2048       SET_BIT(RCC->PLLCFGR, RCC_PLLCFGR_PLL1PEN);
2049     }
2050 
2051     if (pPLLInit->PLLFractional != 0U)
2052     {
2053       assert_param(IS_RCC_PLLFRACN_VALUE(pPLLInit->PLLFractional));
2054 
2055       p_rcc_pll_fracr_reg = &(RCC->PLL1FRACR) + (((uint32_t)0x02) * PLLnumber);
2056 
2057       /* Configure PLLFRACN */
2058       MODIFY_REG(*p_rcc_pll_fracr_reg, RCC_PLL1FRACR_FRACN, pPLLInit->PLLFractional << RCC_PLL1FRACR_FRACN_Pos);
2059 
2060       /* Enable PLLFRACLE */
2061       SET_BIT(RCC->PLLCFGR, RCC_PLLCFGR_PLL1FRACEN << ((RCC_PLLCFGR_PLL2FRACEN_Pos - RCC_PLLCFGR_PLL1FRACEN_Pos)*PLLnumber));
2062     }
2063 
2064     /* Enable the PLLx */
2065     SET_BIT(RCC->CR, RCC_CR_PLL1ON << ((RCC_CR_PLL2ON_Pos - RCC_CR_PLL1ON_Pos)*PLLnumber));
2066 
2067     /* Get Start Tick*/
2068     tickstart = HAL_GetTick();
2069 
2070     /* Wait till PLLx is ready */
2071     while (READ_BIT(RCC->CR, RCC_CR_PLL1RDY << ((RCC_CR_PLL2RDY_Pos - RCC_CR_PLL1RDY_Pos)*PLLnumber)) == 0U)
2072     {
2073       if ((HAL_GetTick() - tickstart) > RCC_PLL_TIMEOUT_VALUE)
2074       {
2075         return HAL_TIMEOUT;
2076       }
2077     }
2078   }
2079   else
2080   {
2081     /* Disable outputs to save power when PLLx is off */
2082     MODIFY_REG(RCC->PLLCKSELR, ((RCC_PLLCKSELR_DIVM1 << (RCC_PLLCKSELR_DIVM1_Pos + ((RCC_PLLCKSELR_DIVM2_Pos - RCC_PLLCKSELR_DIVM1_Pos)*PLLnumber)))
2083                                 | RCC_PLLCKSELR_PLLSRC), RCC_PLLSOURCE_NONE);
2084   }
2085 
2086   return ret;
2087 }
2088 
2089 /**
2090   * @brief  Compute PLL1 VCO output frequency
2091   * @retval Value of PLL1 VCO output frequency
2092   */
RCC_PLL1_GetVCOOutputFreq(void)2093 static uint32_t RCC_PLL1_GetVCOOutputFreq(void)
2094 {
2095   uint32_t tmpreg1;
2096   uint32_t tmpreg2;
2097   uint32_t pllsrc;
2098   uint32_t pllm;
2099   uint32_t plln;
2100   uint32_t pllfracn;
2101   float_t frequency;
2102 
2103   /* Get PLL1 CFGR and DIVR register values */
2104   tmpreg1 = RCC->PLLCKSELR;
2105   tmpreg2 = RCC->PLL1DIVR1;
2106 
2107   /* Retrieve PLL1 multiplication factor and divider */
2108   pllm = (tmpreg1 & RCC_PLLCKSELR_DIVM1) >> RCC_PLLCKSELR_DIVM1_Pos;
2109   plln = (tmpreg2 & RCC_PLL1DIVR1_DIVN) + 1U;
2110 
2111   if (pllm == 0U)
2112   {
2113     /* Prescaler disabled */
2114     return 0U;
2115   }
2116 
2117   /* Check if fractional part is enable */
2118   if ((tmpreg1 & RCC_PLLCFGR_PLL1FRACEN) != 0U)
2119   {
2120     pllfracn = (RCC->PLL1FRACR & RCC_PLL1FRACR_FRACN) >> RCC_PLL1FRACR_FRACN_Pos;
2121   }
2122   else
2123   {
2124     pllfracn = 0U;
2125   }
2126 
2127   /* determine PLL source */
2128   switch (tmpreg1 & RCC_PLLCKSELR_PLLSRC)
2129   {
2130     /* HSI used as PLL1 clock source */
2131     case RCC_PLLSOURCE_HSI:
2132       if (READ_BIT(RCC->CR, RCC_CR_HSIDIVF) != 0U)
2133       {
2134         pllsrc = HSI_VALUE >> ((RCC->CR & RCC_CR_HSIDIV) >> RCC_CR_HSIDIV_Pos);
2135       }
2136       else
2137       {
2138         /* Can't retrieve HSIDIV value */
2139         pllsrc = 0U;
2140       }
2141       break;
2142 
2143     /* HSE used as PLL1 clock source */
2144     case RCC_PLLSOURCE_HSE:
2145       pllsrc = HSE_VALUE;
2146       break;
2147 
2148     /* CSI used as PLL1 clock source */
2149     case RCC_PLLSOURCE_CSI:
2150       pllsrc = CSI_VALUE;
2151       break;
2152 
2153     default:
2154       pllsrc = 0U;
2155       break;
2156   }
2157 
2158   /* Compute VCO output frequency */
2159   frequency = ((float_t)pllsrc / (float_t)pllm) * ((float_t)plln + ((float_t)pllfracn / (float_t)0x2000U));
2160 
2161   return (uint32_t)frequency;
2162 }
2163 
2164 /**
2165   * @brief  Compute PLL2 VCO output frequency
2166   * @retval Value of PLL2 VCO output frequency
2167   */
RCC_PLL2_GetVCOOutputFreq(void)2168 static uint32_t RCC_PLL2_GetVCOOutputFreq(void)
2169 {
2170   uint32_t tmpreg1;
2171   uint32_t tmpreg2;
2172   uint32_t pllsrc;
2173   uint32_t pllm;
2174   uint32_t plln;
2175   uint32_t pllfracn;
2176   float_t frequency;
2177 
2178   /* Get PLL2 CFGR and DIVR register values */
2179   tmpreg1 = RCC->PLLCKSELR;
2180   tmpreg2 = RCC->PLL2DIVR1;
2181 
2182   /* Retrieve PLL2 multiplication factor and divider */
2183   pllm = (tmpreg1 & RCC_PLLCKSELR_DIVM2) >> RCC_PLLCKSELR_DIVM2_Pos;
2184   plln = (tmpreg2 & RCC_PLL2DIVR1_DIVN) + 1U;
2185 
2186   if (pllm == 0U)
2187   {
2188     /* Prescaler disabled */
2189     return 0U;
2190   }
2191 
2192   /* Check if fractional part is enable */
2193   if ((tmpreg1 & RCC_PLLCFGR_PLL2FRACEN) != 0U)
2194   {
2195     pllfracn = (RCC->PLL2FRACR & RCC_PLL2FRACR_FRACN) >> RCC_PLL2FRACR_FRACN_Pos;
2196   }
2197   else
2198   {
2199     pllfracn = 0U;
2200   }
2201 
2202   /* determine PLL source */
2203   switch (tmpreg1 & RCC_PLLCKSELR_PLLSRC)
2204   {
2205     /* HSI used as PLL2 clock source */
2206     case RCC_PLLSOURCE_HSI:
2207       if (READ_BIT(RCC->CR, RCC_CR_HSIDIVF) != 0U)
2208       {
2209         pllsrc = HSI_VALUE >> ((RCC->CR & RCC_CR_HSIDIV) >> RCC_CR_HSIDIV_Pos);
2210       }
2211       else
2212       {
2213         /* Can't retrieve HSIDIV value */
2214         pllsrc = 0U;
2215       }
2216       break;
2217 
2218     /* HSE used as PLL2 clock source */
2219     case RCC_PLLSOURCE_HSE:
2220       pllsrc = HSE_VALUE;
2221       break;
2222 
2223     /* CSI used as PLL2 clock source */
2224     case RCC_PLLSOURCE_CSI:
2225       pllsrc = CSI_VALUE;
2226       break;
2227 
2228     default:
2229       pllsrc = 0U;
2230       break;
2231   }
2232 
2233   /* Compute VCO output frequency */
2234   frequency = ((float_t)pllsrc / (float_t)pllm) * ((float_t)plln + ((float_t)pllfracn / (float_t)0x2000U));
2235 
2236   return (uint32_t)frequency;
2237 }
2238 
2239 /**
2240   * @brief  Compute PLL3 VCO output frequency
2241   * @retval Value of PLL3 VCO output frequency
2242   */
RCC_PLL3_GetVCOOutputFreq(void)2243 static uint32_t RCC_PLL3_GetVCOOutputFreq(void)
2244 {
2245   uint32_t tmpreg1;
2246   uint32_t tmpreg2;
2247   uint32_t pllsrc;
2248   uint32_t pllm;
2249   uint32_t plln;
2250   uint32_t pllfracn;
2251   float_t frequency;
2252 
2253   /* Get PLL3 CFGR and DIVR register values */
2254   tmpreg1 = RCC->PLLCKSELR;
2255   tmpreg2 = RCC->PLL3DIVR1;
2256 
2257   /* Retrieve PLL3 multiplication factor and divider */
2258   pllm = (tmpreg1 & RCC_PLLCKSELR_DIVM3) >> RCC_PLLCKSELR_DIVM3_Pos;
2259   plln = (tmpreg2 & RCC_PLL3DIVR1_DIVN) + 1U;
2260 
2261   if (pllm == 0U)
2262   {
2263     /* Prescaler disabled */
2264     return 0U;
2265   }
2266 
2267   /* Check if fractional part is enable */
2268   if ((tmpreg1 & RCC_PLLCFGR_PLL3FRACEN) != 0U)
2269   {
2270     pllfracn = (RCC->PLL3FRACR & RCC_PLL3FRACR_FRACN) >> RCC_PLL3FRACR_FRACN_Pos;
2271   }
2272   else
2273   {
2274     pllfracn = 0U;
2275   }
2276 
2277   /* determine PLL source */
2278   switch (tmpreg1 & RCC_PLLCKSELR_PLLSRC)
2279   {
2280     /* HSI used as PLL3 clock source */
2281     case RCC_PLLSOURCE_HSI:
2282       if (READ_BIT(RCC->CR, RCC_CR_HSIDIVF) != 0U)
2283       {
2284         pllsrc = HSI_VALUE >> ((RCC->CR & RCC_CR_HSIDIV) >> RCC_CR_HSIDIV_Pos);
2285       }
2286       else
2287       {
2288         /* Can't retrieve HSIDIV value */
2289         pllsrc = 0U;
2290       }
2291       break;
2292 
2293     /* HSE used as PLL3 clock source */
2294     case RCC_PLLSOURCE_HSE:
2295       pllsrc = HSE_VALUE;
2296       break;
2297 
2298     /* CSI used as PLL3 clock source */
2299     case RCC_PLLSOURCE_CSI:
2300       pllsrc = CSI_VALUE;
2301       break;
2302 
2303     default:
2304       pllsrc = 0U;
2305       break;
2306   }
2307 
2308   /* Compute VCO output frequency */
2309   frequency = ((float_t)pllsrc / (float_t)pllm) * ((float_t)plln + ((float_t)pllfracn / (float_t)0x2000U));
2310 
2311   return (uint32_t)frequency;
2312 }
2313 
2314 /**
2315   * @}
2316   */
2317 
2318 /**
2319   * @}
2320   */
2321 #endif /* HAL_RCC_MODULE_ENABLED */
2322 
2323 /**
2324   * @}
2325   */
2326 
2327 /**
2328   * @}
2329   */
2330