1616
1717 #include "i2c_device.h"
1818 #include "mbed_assert.h"
19+ #include "mbed_error.h"
1920 #include "stm32h7xx_ll_rcc.h"
2021
2122 #if DEVICE_I2C
@@ -335,6 +336,71 @@ static uint32_t I2C_ComputeTiming(uint32_t clock_src_freq, uint32_t i2c_freq)
335336
336337 return ret ;
337338}
339+
340+ /**
341+ * @brief Get I2C clock source frequency according I2C instance used.
342+ * @param i2c I2C instance name.
343+ * @retval I2C clock source frequency in Hz.
344+ */
345+ static uint32_t I2C_GetPclk (I2CName i2c )
346+ {
347+ uint32_t clocksource ;
348+ uint32_t pclk = 0 ;
349+ PLL3_ClocksTypeDef pll3_clocks ;
350+
351+ if (i2c == I2C_1 || i2c == I2C_2 || i2c == I2C_3 ) {
352+ clocksource = __HAL_RCC_GET_I2C123_SOURCE ();
353+ switch (clocksource )
354+ {
355+ case RCC_I2C123CLKSOURCE_D2PCLK1 :
356+ pclk = HAL_RCC_GetPCLK1Freq ();
357+ break ;
358+ case RCC_I2C123CLKSOURCE_PLL3 :
359+ HAL_RCCEx_GetPLL3ClockFreq (& pll3_clocks );
360+ pclk = pll3_clocks .PLL3_R_Frequency ;
361+ break ;
362+ case RCC_I2C123CLKSOURCE_HSI :
363+ pclk = HSI_VALUE ;
364+ break ;
365+ case RCC_I2C123CLKSOURCE_CSI :
366+ pclk = CSI_VALUE ;
367+ break ;
368+ default :
369+ // should not happend
370+ error ("I2C123: Invalid clock source" );
371+ break ;
372+ }
373+ }
374+ else if (i2c == I2C_4 ) {
375+ clocksource = __HAL_RCC_GET_I2C4_SOURCE ();
376+ switch (clocksource )
377+ {
378+ case RCC_I2C4CLKSOURCE_D3PCLK1 :
379+ pclk = HAL_RCCEx_GetD3PCLK1Freq ();
380+ break ;
381+ case RCC_I2C4CLKSOURCE_PLL3 :
382+ HAL_RCCEx_GetPLL3ClockFreq (& pll3_clocks );
383+ pclk = pll3_clocks .PLL3_R_Frequency ;
384+ break ;
385+ case RCC_I2C4CLKSOURCE_HSI :
386+ pclk = HSI_VALUE ;
387+ break ;
388+ case RCC_I2C4CLKSOURCE_CSI :
389+ pclk = CSI_VALUE ;
390+ break ;
391+ default :
392+ // should not happend
393+ error ("I2C4: Invalid clock source" );
394+ break ;
395+ }
396+ }
397+ else {
398+ // should not happend
399+ error ("I2C: unknown instance" );
400+ }
401+
402+ return pclk ;
403+ }
338404/**
339405 * @}
340406 */
@@ -347,19 +413,16 @@ static uint32_t I2C_ComputeTiming(uint32_t clock_src_freq, uint32_t i2c_freq)
347413 * @param hz Required I2C clock in Hz.
348414 * @retval I2C timing or 0 in case of error.
349415 */
350- uint32_t get_i2c_timing (int hz )
416+ uint32_t get_i2c_timing (I2CName i2c , int hz )
351417{
352418 uint32_t tim ;
419+ uint32_t pclk ;
353420
354421 I2c_valid_timing_nbr = 0 ;
355422
356- /* we will use D2PCLK1 to calculate I2C timings */
357- MBED_ASSERT (RCC_I2C1CLKSOURCE_D2PCLK1 == __HAL_RCC_GET_I2C1_SOURCE ());
358-
359- LL_RCC_ClocksTypeDef rcc_clocks ;
360- LL_RCC_GetSystemClocksFreq (& rcc_clocks );
423+ pclk = I2C_GetPclk (i2c );
361424
362- tim = I2C_ComputeTiming (rcc_clocks . PCLK1_Frequency , hz );
425+ tim = I2C_ComputeTiming (pclk , hz );
363426
364427 return tim ;
365428}
0 commit comments