Skip to content

Commit 35c9e7a

Browse files
Use HAL function for FDCAN_CLK-calculation
- Thanks to @jeromecoutant for showing the HAL funtion - Added #ifdef guard to FDCAN2/3 handler functions
1 parent 08ce2f2 commit 35c9e7a

File tree

1 file changed

+29
-59
lines changed

1 file changed

+29
-59
lines changed

targets/TARGET_STM/can_api.c

Lines changed: 29 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -57,62 +57,6 @@ int can_internal_init(can_t *obj)
5757
return 1;
5858
}
5959

60-
61-
/** Calculate the fdcan-core-clk value for accurate calculation of the quantum timing
62-
*
63-
* !Attention Not all bitrates can be covered with all fdcan-core-clk values. When a clk
64-
* does not work for the desired bitrate, change system_clock settings for PLLQ
65-
*
66-
* !Attention For now, PCLK is not supported (PLLQ is selected always anyways)
67-
*
68-
* @returns
69-
* core_frequency when successful
70-
* -1 when error / not supported
71-
*/
72-
static int _can_get_core_frequency( void )
73-
{
74-
int clk_sel = (RCC->CCIPR & RCC_CCIPR_FDCANSEL_Msk) >> RCC_CCIPR_FDCANSEL_Pos;
75-
76-
switch (clk_sel){
77-
case 0: //! HSE clock selected as FDCAN clock
78-
{
79-
return HSE_VALUE;
80-
}
81-
case 1: //! PLL "Q" clock selected as FDCAN clock
82-
{
83-
int pll_source_clk;
84-
85-
int pll_source = (RCC->PLLCFGR & RCC_PLLCFGR_PLLSRC_Msk);
86-
if (pll_source == RCC_PLLCFGR_PLLSRC_HSE){
87-
pll_source_clk = HSE_VALUE;
88-
} else if (pll_source == RCC_PLLCFGR_PLLSRC_HSI){
89-
pll_source_clk = HSI_VALUE;
90-
} else {
91-
MBED_ERROR(
92-
MBED_MAKE_ERROR(MBED_MODULE_DRIVER_CAN, MBED_ERROR_CODE_CONFIG_UNSUPPORTED),
93-
"PLL source must be HSI or HSE");
94-
return -1;
95-
}
96-
97-
int pllm = ((RCC->PLLCFGR & RCC_PLLCFGR_PLLM_Msk) >> RCC_PLLCFGR_PLLM_Pos) + 1;
98-
int plln = (RCC->PLLCFGR & RCC_PLLCFGR_PLLN_Msk) >> RCC_PLLCFGR_PLLN_Pos;
99-
int pllq = ((RCC->PLLCFGR & RCC_PLLCFGR_PLLQ_Msk) >> RCC_PLLCFGR_PLLQ_Pos) + 1;
100-
pllq = pllq * 2;
101-
int fdcan_freq = ((pll_source_clk / pllm) * plln) / pllq;
102-
103-
return fdcan_freq;
104-
}
105-
case 2: //! PCLK Clk selected as FDCAN clock
106-
case 3:
107-
default:
108-
MBED_ERROR(
109-
MBED_MAKE_ERROR(MBED_MODULE_DRIVER_CAN, MBED_ERROR_CODE_CONFIG_UNSUPPORTED),
110-
"Wrong clk_source configuration");
111-
return -1;
112-
}
113-
}
114-
115-
11660
#if STATIC_PINMAP_READY
11761
#define CAN_INIT_FREQ_DIRECT can_init_freq_direct
11862
void can_init_freq_direct(can_t *obj, const can_pinmap_t *pinmap, int hz)
@@ -180,7 +124,16 @@ static void _can_init_freq_direct(can_t *obj, const can_pinmap_t *pinmap, int hz
180124
Synchronization_Jump_width | 30 tq | <nsjw> = <nts2>
181125
*/
182126

183-
int ntq = _can_get_core_frequency() / hz;
127+
// !Attention Not all bitrates can be covered with all fdcan-core-clk values. When a clk
128+
// does not work for the desired bitrate, change system_clock settings for FDCAN_CLK
129+
// (default FDCAN_CLK is PLLQ)
130+
#ifdef TARGET_STM32G4
131+
int ntq = HAL_RCCEx_GetPeriphCLKFreq(RCC_PERIPHCLK_FDCAN) / hz;
132+
#else
133+
// STM32H7 doesn't support yet HAL_RCCEx_GetPeriphCLKFreq for FDCAN
134+
// Internal ST ticket 92465
135+
int ntq = 10000000 / hz;
136+
#endif
184137

185138
obj->CanHandle.Init.FrameFormat = FDCAN_FRAME_CLASSIC;
186139
obj->CanHandle.Init.Mode = FDCAN_MODE_NORMAL;
@@ -310,8 +263,21 @@ int can_frequency(can_t *obj, int f)
310263
error("HAL_FDCAN_Stop error\n");
311264
}
312265

313-
/* See can_init_freq function for calculation details */
314-
int ntq = _can_get_core_frequency() / f;
266+
267+
/* See can_init_freq function for calculation details
268+
*
269+
* !Attention Not all bitrates can be covered with all fdcan-core-clk values. When a clk
270+
* does not work for the desired bitrate, change system_clock settings for FDCAN_CLK
271+
* (default FDCAN_CLK is PLLQ)
272+
*/
273+
#ifdef TARGET_STM32G4
274+
int ntq = HAL_RCCEx_GetPeriphCLKFreq(RCC_PERIPHCLK_FDCAN) / f;
275+
#else
276+
// STM32H7 doesn't support yet HAL_RCCEx_GetPeriphCLKFreq for FDCAN
277+
// Internal ST ticket 92465
278+
int ntq = 10000000 / hz;
279+
#endif
280+
315281
obj->CanHandle.Init.NominalTimeSeg1 = ntq * 0.75; // Phase_segment_1
316282
obj->CanHandle.Init.NominalTimeSeg2 = ntq - 1 - obj->CanHandle.Init.NominalTimeSeg1; // Phase_segment_2
317283
obj->CanHandle.Init.NominalSyncJumpWidth = obj->CanHandle.Init.NominalTimeSeg2; // Synchronization_Jump_width
@@ -563,6 +529,7 @@ void FDCAN1_IT1_IRQHandler(void)
563529
can_irq(CAN_1, 0);
564530
}
565531

532+
#if defined(FDCAN2_BASE)
566533
void FDCAN2_IT0_IRQHandler(void)
567534
{
568535
can_irq(CAN_2, 1);
@@ -572,7 +539,9 @@ void FDCAN2_IT1_IRQHandler(void)
572539
{
573540
can_irq(CAN_2, 1);
574541
}
542+
#endif //FDCAN2_BASE
575543

544+
#if defined(FDCAN3_BASE)
576545
void FDCAN3_IT0_IRQHandler(void)
577546
{
578547
can_irq(CAN_3, 2);
@@ -582,6 +551,7 @@ void FDCAN3_IT1_IRQHandler(void)
582551
{
583552
can_irq(CAN_3, 2);
584553
}
554+
#endif //FDCAN3_BASE
585555

586556

587557
// TODO Add other interrupts ?

0 commit comments

Comments
 (0)