1 /**
2 ******************************************************************************
3 * @file stm32n6xx_hal_fdcan.c
4 * @author MCD Application Team
5 * @brief FDCAN HAL module driver.
6 * This file provides firmware functions to manage the following
7 * functionalities of the Flexible DataRate Controller Area Network
8 * (FDCAN) peripheral:
9 * + Initialization and de-initialization functions
10 * + IO operation functions
11 * + Peripheral Configuration and Control functions
12 * + Peripheral State and Error functions
13 ******************************************************************************
14 * @attention
15 *
16 * Copyright (c) 2023 STMicroelectronics.
17 * All rights reserved.
18 *
19 * This software is licensed under terms that can be found in the LICENSE file
20 * in the root directory of this software component.
21 * If no LICENSE file comes with this software, it is provided AS-IS.
22 *
23 ******************************************************************************
24 @verbatim
25 ==============================================================================
26 ##### How to use this driver #####
27 ==============================================================================
28 [..]
29 (#) Initialize the FDCAN peripheral using HAL_FDCAN_Init function.
30
31 (#) If needed , configure the reception filters and optional features using
32 the following configuration functions:
33 (++) HAL_FDCAN_ConfigClockCalibration
34 (++) HAL_FDCAN_ConfigFilter
35 (++) HAL_FDCAN_ConfigGlobalFilter
36 (++) HAL_FDCAN_ConfigExtendedIdMask
37 (++) HAL_FDCAN_ConfigRxFifoOverwrite
38 (++) HAL_FDCAN_ConfigFifoWatermark
39 (++) HAL_FDCAN_ConfigRamWatchdog
40 (++) HAL_FDCAN_ConfigTimestampCounter
41 (++) HAL_FDCAN_EnableTimestampCounter
42 (++) HAL_FDCAN_DisableTimestampCounter
43 (++) HAL_FDCAN_ConfigTimeoutCounter
44 (++) HAL_FDCAN_EnableTimeoutCounter
45 (++) HAL_FDCAN_DisableTimeoutCounter
46 (++) HAL_FDCAN_ConfigTxDelayCompensation
47 (++) HAL_FDCAN_EnableTxDelayCompensation
48 (++) HAL_FDCAN_DisableTxDelayCompensation
49 (++) HAL_FDCAN_EnableISOMode
50 (++) HAL_FDCAN_DisableISOMode
51 (++) HAL_FDCAN_EnableEdgeFiltering
52 (++) HAL_FDCAN_DisableEdgeFiltering
53 (++) HAL_FDCAN_TT_ConfigOperation
54 (++) HAL_FDCAN_TT_ConfigReferenceMessage
55 (++) HAL_FDCAN_TT_ConfigTrigger
56
57 (#) Start the FDCAN module using HAL_FDCAN_Start function. At this level
58 the node is active on the bus: it can send and receive messages.
59
60 (#) The following Tx control functions can only be called when the FDCAN
61 module is started:
62 (++) HAL_FDCAN_AddMessageToTxFifoQ
63 (++) HAL_FDCAN_EnableTxBufferRequest
64 (++) HAL_FDCAN_AbortTxRequest
65
66 (#) After having submitted a Tx request in Tx Fifo or Queue, it is possible to
67 get Tx buffer location used to place the Tx request thanks to
68 HAL_FDCAN_GetLatestTxFifoQRequestBuffer API.
69 It is then possible to abort later on the corresponding Tx Request using
70 HAL_FDCAN_AbortTxRequest API.
71
72 (#) When a message is received into the FDCAN message RAM, it can be
73 retrieved using the HAL_FDCAN_GetRxMessage function.
74
75 (#) Calling the HAL_FDCAN_Stop function stops the FDCAN module by entering
76 it to initialization mode and re-enabling access to configuration
77 registers through the configuration functions listed here above.
78
79 (#) All other control functions can be called any time after initialization
80 phase, no matter if the FDCAN module is started or stopped.
81
82 *** Polling mode operation ***
83 ==============================
84 [..]
85 (#) Reception and transmission states can be monitored via the following
86 functions:
87 (++) HAL_FDCAN_IsRxBufferMessageAvailable
88 (++) HAL_FDCAN_IsTxBufferMessagePending
89 (++) HAL_FDCAN_GetRxFifoFillLevel
90 (++) HAL_FDCAN_GetTxFifoFreeLevel
91
92 *** Interrupt mode operation ***
93 ================================
94 [..]
95 (#) There are two interrupt lines: line 0 and 1.
96 By default, all interrupts are assigned to line 0. Interrupt lines
97 can be configured using HAL_FDCAN_ConfigInterruptLines function.
98
99 (#) Notifications are activated using HAL_FDCAN_ActivateNotification
100 function. Then, the process can be controlled through one of the
101 available user callbacks: HAL_FDCAN_xxxCallback.
102
103 *** Callback registration ***
104 =============================================
105
106 The compilation define USE_HAL_FDCAN_REGISTER_CALLBACKS when set to 1
107 allows the user to configure dynamically the driver callbacks.
108 Use Function HAL_FDCAN_RegisterCallback() or HAL_FDCAN_RegisterXXXCallback()
109 to register an interrupt callback.
110
111 Function HAL_FDCAN_RegisterCallback() allows to register following callbacks:
112 (+) TxFifoEmptyCallback : Tx Fifo Empty Callback.
113 (+) RxBufferNewMessageCallback : Rx Buffer New Message Callback.
114 (+) HighPriorityMessageCallback : High Priority Message Callback.
115 (+) TimestampWraparoundCallback : Timestamp Wraparound Callback.
116 (+) TimeoutOccurredCallback : Timeout Occurred Callback.
117 (+) ErrorCallback : Error Callback.
118 (+) MspInitCallback : FDCAN MspInit.
119 (+) MspDeInitCallback : FDCAN MspDeInit.
120 This function takes as parameters the HAL peripheral handle, the Callback ID
121 and a pointer to the user callback function.
122
123 For specific callbacks ClockCalibrationCallback, TxEventFifoCallback, RxFifo0Callback, RxFifo1Callback,
124 TxBufferCompleteCallback, TxBufferAbortCallback, ErrorStatusCallback, TT_ScheduleSyncCallback, TT_TimeMarkCallback,
125 TT_StopWatchCallback and TT_GlobalTimeCallback, use dedicated register callbacks:
126 respectively HAL_FDCAN_RegisterClockCalibrationCallback(), HAL_FDCAN_RegisterTxEventFifoCallback(),
127 HAL_FDCAN_RegisterRxFifo0Callback(), HAL_FDCAN_RegisterRxFifo1Callback(),
128 HAL_FDCAN_RegisterTxBufferCompleCallback(), HAL_FDCAN_RegisterTxBufferAbortCallback(),
129 HAL_FDCAN_RegisterErrorStatusCallback(), HAL_FDCAN_TT_RegisterScheduleSyncCallback(),
130 HAL_FDCAN_TT_RegisterTimeMarkCallback(), HAL_FDCAN_TT_RegisterStopWatchCallback() and
131 HAL_FDCAN_TT_RegisterGlobalTimeCallback().
132
133 Use function HAL_FDCAN_UnRegisterCallback() to reset a callback to the default
134 weak function.
135 HAL_FDCAN_UnRegisterCallback takes as parameters the HAL peripheral handle,
136 and the Callback ID.
137 This function allows to reset following callbacks:
138 (+) TxFifoEmptyCallback : Tx Fifo Empty Callback.
139 (+) RxBufferNewMessageCallback : Rx Buffer New Message Callback.
140 (+) HighPriorityMessageCallback : High Priority Message Callback.
141 (+) TimestampWraparoundCallback : Timestamp Wraparound Callback.
142 (+) TimeoutOccurredCallback : Timeout Occurred Callback.
143 (+) ErrorCallback : Error Callback.
144 (+) MspInitCallback : FDCAN MspInit.
145 (+) MspDeInitCallback : FDCAN MspDeInit.
146
147 For specific callbacks ClockCalibrationCallback, TxEventFifoCallback, RxFifo0Callback,
148 RxFifo1Callback, TxBufferCompleteCallback, TxBufferAbortCallback, TT_ScheduleSyncCallback,
149 TT_TimeMarkCallback, TT_StopWatchCallback and TT_GlobalTimeCallback, use dedicated
150 register callbacks: respectively HAL_FDCAN_UnRegisterClockCalibrationCallback(),
151 HAL_FDCAN_UnRegisterTxEventFifoCallback(), HAL_FDCAN_UnRegisterRxFifo0Callback(),
152 HAL_FDCAN_UnRegisterRxFifo1Callback(), HAL_FDCAN_UnRegisterTxBufferCompleCallback(),
153 HAL_FDCAN_UnRegisterTxBufferAbortCallback(), HAL_FDCAN_UnRegisterErrorStatusCallback(),
154 HAL_FDCAN_TT_UnRegisterScheduleSyncCallback(), HAL_FDCAN_TT_UnRegisterTimeMarkCallback(),
155 HAL_FDCAN_TT_UnRegisterStopWatchCallback() and HAL_FDCAN_TT_UnRegisterGlobalTimeCallback().
156
157 By default, after the HAL_FDCAN_Init() and when the state is HAL_FDCAN_STATE_RESET,
158 all callbacks are set to the corresponding weak functions:
159 examples HAL_FDCAN_ErrorCallback().
160 Exception done for MspInit and MspDeInit functions that are
161 reset to the legacy weak function in the HAL_FDCAN_Init()/ HAL_FDCAN_DeInit() only when
162 these callbacks are null (not registered beforehand).
163 if not, MspInit or MspDeInit are not null, the HAL_FDCAN_Init()/ HAL_FDCAN_DeInit()
164 keep and use the user MspInit/MspDeInit callbacks (registered beforehand)
165
166 Callbacks can be registered/unregistered in HAL_FDCAN_STATE_READY state only.
167 Exception done MspInit/MspDeInit that can be registered/unregistered
168 in HAL_FDCAN_STATE_READY or HAL_FDCAN_STATE_RESET state,
169 thus registered (user) MspInit/DeInit callbacks can be used during the Init/DeInit.
170 In that case first register the MspInit/MspDeInit user callbacks
171 using HAL_FDCAN_RegisterCallback() before calling HAL_FDCAN_DeInit()
172 or HAL_FDCAN_Init() function.
173
174 When The compilation define USE_HAL_FDCAN_REGISTER_CALLBACKS is set to 0 or
175 not defined, the callback registration feature is not available and all callbacks
176 are set to the corresponding weak functions.
177
178 @endverbatim
179 ******************************************************************************
180 */
181
182 /* Includes ------------------------------------------------------------------*/
183 #include "stm32n6xx_hal.h"
184
185 #if defined(FDCAN1)
186
187 /** @addtogroup STM32N6xx_HAL_Driver
188 * @{
189 */
190
191 /** @defgroup FDCAN FDCAN
192 * @brief FDCAN HAL module driver
193 * @{
194 */
195
196 #ifdef HAL_FDCAN_MODULE_ENABLED
197
198 /* Private typedef -----------------------------------------------------------*/
199 /* Private define ------------------------------------------------------------*/
200 /** @addtogroup FDCAN_Private_Constants
201 * @{
202 */
203 #define FDCAN_TIMEOUT_VALUE 10U
204 #define FDCAN_TIMEOUT_COUNT 50U
205
206 #define FDCAN_TX_EVENT_FIFO_MASK (FDCAN_IR_TEFL | FDCAN_IR_TEFF | FDCAN_IR_TEFW | FDCAN_IR_TEFN)
207 #define FDCAN_RX_FIFO0_MASK (FDCAN_IR_RF0L | FDCAN_IR_RF0F | FDCAN_IR_RF0W | FDCAN_IR_RF0N)
208 #define FDCAN_RX_FIFO1_MASK (FDCAN_IR_RF1L | FDCAN_IR_RF1F | FDCAN_IR_RF1W | FDCAN_IR_RF1N)
209 #define FDCAN_ERROR_MASK (FDCAN_IR_ELO | FDCAN_IR_WDI | FDCAN_IR_PEA | FDCAN_IR_PED | FDCAN_IR_ARA)
210 #define FDCAN_ERROR_STATUS_MASK (FDCAN_IR_EP | FDCAN_IR_EW | FDCAN_IR_BO)
211 #define FDCAN_TT_SCHEDULE_SYNC_MASK (FDCAN_TTIR_SBC | FDCAN_TTIR_SMC | FDCAN_TTIR_CSM | FDCAN_TTIR_SOG)
212 #define FDCAN_TT_TIME_MARK_MASK (FDCAN_TTIR_RTMI | FDCAN_TTIR_TTMI)
213 #define FDCAN_TT_GLOBAL_TIME_MASK (FDCAN_TTIR_GTW | FDCAN_TTIR_GTD)
214 #define FDCAN_TT_DISTURBING_ERROR_MASK (FDCAN_TTIR_GTE | FDCAN_TTIR_TXU | FDCAN_TTIR_TXO | \
215 FDCAN_TTIR_SE1 | FDCAN_TTIR_SE2 | FDCAN_TTIR_ELC)
216 #define FDCAN_TT_FATAL_ERROR_MASK (FDCAN_TTIR_IWT | FDCAN_TTIR_WT | FDCAN_TTIR_AW | FDCAN_TTIR_CER)
217
218 #define FDCAN_ELEMENT_MASK_STDID ((uint32_t)0x1FFC0000U) /* Standard Identifier */
219 #define FDCAN_ELEMENT_MASK_EXTID ((uint32_t)0x1FFFFFFFU) /* Extended Identifier */
220 #define FDCAN_ELEMENT_MASK_RTR ((uint32_t)0x20000000U) /* Remote Transmission Request */
221 #define FDCAN_ELEMENT_MASK_XTD ((uint32_t)0x40000000U) /* Extended Identifier */
222 #define FDCAN_ELEMENT_MASK_ESI ((uint32_t)0x80000000U) /* Error State Indicator */
223 #define FDCAN_ELEMENT_MASK_TS ((uint32_t)0x0000FFFFU) /* Timestamp */
224 #define FDCAN_ELEMENT_MASK_DLC ((uint32_t)0x000F0000U) /* Data Length Code */
225 #define FDCAN_ELEMENT_MASK_BRS ((uint32_t)0x00100000U) /* Bit Rate Switch */
226 #define FDCAN_ELEMENT_MASK_FDF ((uint32_t)0x00200000U) /* FD Format */
227 #define FDCAN_ELEMENT_MASK_EFC ((uint32_t)0x00800000U) /* Event FIFO Control */
228 #define FDCAN_ELEMENT_MASK_MM ((uint32_t)0xFF000000U) /* Message Marker */
229 #define FDCAN_ELEMENT_MASK_FIDX ((uint32_t)0x7F000000U) /* Filter Index */
230 #define FDCAN_ELEMENT_MASK_ANMF ((uint32_t)0x80000000U) /* Accepted Non-matching Frame */
231 #define FDCAN_ELEMENT_MASK_ET ((uint32_t)0x00C00000U) /* Event type */
232
233 #define FDCAN_MESSAGE_RAM_SIZE 0x2800U
234 #define FDCAN_MESSAGE_RAM_END_ADDRESS (SRAMCAN_BASE + FDCAN_MESSAGE_RAM_SIZE - 0x4U) /* Message RAM width is 4 Bytes */
235
236 /**
237 * @}
238 */
239
240 /* Private macro -------------------------------------------------------------*/
241 /* Private variables ---------------------------------------------------------*/
242 /** @addtogroup FDCAN_Private_Variables
243 * @{
244 */
245 static const uint8_t DLCtoBytes[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 12, 16, 20, 24, 32, 48, 64};
246 /**
247 * @}
248 */
249
250 /* Private function prototypes -----------------------------------------------*/
251 /** @addtogroup FDCAN_Private_Functions_Prototypes
252 * @{
253 */
254 static HAL_StatusTypeDef FDCAN_CalcultateRamBlockAddresses(FDCAN_HandleTypeDef *hfdcan);
255 static void FDCAN_CopyMessageToRAM(const FDCAN_HandleTypeDef *hfdcan, const FDCAN_TxHeaderTypeDef *pTxHeader,
256 const uint8_t *pTxData, uint32_t BufferIndex);
257 /**
258 * @}
259 */
260
261 /* Exported functions --------------------------------------------------------*/
262 /** @defgroup FDCAN_Exported_Functions FDCAN Exported Functions
263 * @{
264 */
265
266 /** @defgroup FDCAN_Exported_Functions_Group1 Initialization and de-initialization functions
267 * @brief Initialization and Configuration functions
268 *
269 @verbatim
270 ==============================================================================
271 ##### Initialization and de-initialization functions #####
272 ==============================================================================
273 [..] This section provides functions allowing to:
274 (+) Initialize and configure the FDCAN.
275 (+) De-initialize the FDCAN.
276 (+) Enter FDCAN peripheral in power down mode.
277 (+) Exit power down mode.
278 (+) Register callbacks.
279 (+) Unregister callbacks.
280
281 @endverbatim
282 * @{
283 */
284
285 /**
286 * @brief Initializes the FDCAN peripheral according to the specified
287 * parameters in the FDCAN_InitTypeDef structure.
288 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
289 * the configuration information for the specified FDCAN.
290 * @retval HAL status
291 */
HAL_FDCAN_Init(FDCAN_HandleTypeDef * hfdcan)292 HAL_StatusTypeDef HAL_FDCAN_Init(FDCAN_HandleTypeDef *hfdcan)
293 {
294 uint32_t tickstart;
295 HAL_StatusTypeDef status;
296 const uint32_t CvtEltSize[] = {0, 0, 0, 0, 0, 1, 2, 3, 4, 0, 5, 0, 0, 0, 6, 0, 0, 0, 7};
297
298 /* Check FDCAN handle */
299 if (hfdcan == NULL)
300 {
301 return HAL_ERROR;
302 }
303
304 /* Check FDCAN instance */
305 if (hfdcan->Instance == FDCAN1)
306 {
307 hfdcan->ttcan = (TTCAN_TypeDef *)((uint32_t)hfdcan->Instance + 0x100U);
308 }
309
310 /* Check function parameters */
311 assert_param(IS_FDCAN_ALL_INSTANCE(hfdcan->Instance));
312 assert_param(IS_FDCAN_FRAME_FORMAT(hfdcan->Init.FrameFormat));
313 assert_param(IS_FDCAN_MODE(hfdcan->Init.Mode));
314 assert_param(IS_FUNCTIONAL_STATE(hfdcan->Init.AutoRetransmission));
315 assert_param(IS_FUNCTIONAL_STATE(hfdcan->Init.TransmitPause));
316 assert_param(IS_FUNCTIONAL_STATE(hfdcan->Init.ProtocolException));
317 assert_param(IS_FDCAN_NOMINAL_PRESCALER(hfdcan->Init.NominalPrescaler));
318 assert_param(IS_FDCAN_NOMINAL_SJW(hfdcan->Init.NominalSyncJumpWidth));
319 assert_param(IS_FDCAN_NOMINAL_TSEG1(hfdcan->Init.NominalTimeSeg1));
320 assert_param(IS_FDCAN_NOMINAL_TSEG2(hfdcan->Init.NominalTimeSeg2));
321 if (hfdcan->Init.FrameFormat == FDCAN_FRAME_FD_BRS)
322 {
323 assert_param(IS_FDCAN_DATA_PRESCALER(hfdcan->Init.DataPrescaler));
324 assert_param(IS_FDCAN_DATA_SJW(hfdcan->Init.DataSyncJumpWidth));
325 assert_param(IS_FDCAN_DATA_TSEG1(hfdcan->Init.DataTimeSeg1));
326 assert_param(IS_FDCAN_DATA_TSEG2(hfdcan->Init.DataTimeSeg2));
327 }
328 assert_param(IS_FDCAN_MAX_VALUE(hfdcan->Init.StdFiltersNbr, 128U));
329 assert_param(IS_FDCAN_MAX_VALUE(hfdcan->Init.ExtFiltersNbr, 64U));
330 assert_param(IS_FDCAN_MAX_VALUE(hfdcan->Init.RxFifo0ElmtsNbr, 64U));
331 if (hfdcan->Init.RxFifo0ElmtsNbr > 0U)
332 {
333 assert_param(IS_FDCAN_DATA_SIZE(hfdcan->Init.RxFifo0ElmtSize));
334 }
335 assert_param(IS_FDCAN_MAX_VALUE(hfdcan->Init.RxFifo1ElmtsNbr, 64U));
336 if (hfdcan->Init.RxFifo1ElmtsNbr > 0U)
337 {
338 assert_param(IS_FDCAN_DATA_SIZE(hfdcan->Init.RxFifo1ElmtSize));
339 }
340 assert_param(IS_FDCAN_MAX_VALUE(hfdcan->Init.RxBuffersNbr, 64U));
341 if (hfdcan->Init.RxBuffersNbr > 0U)
342 {
343 assert_param(IS_FDCAN_DATA_SIZE(hfdcan->Init.RxBufferSize));
344 }
345 assert_param(IS_FDCAN_MAX_VALUE(hfdcan->Init.TxEventsNbr, 32U));
346 assert_param(IS_FDCAN_MAX_VALUE((hfdcan->Init.TxBuffersNbr + hfdcan->Init.TxFifoQueueElmtsNbr), 32U));
347 if (hfdcan->Init.TxFifoQueueElmtsNbr > 0U)
348 {
349 assert_param(IS_FDCAN_TX_FIFO_QUEUE_MODE(hfdcan->Init.TxFifoQueueMode));
350 }
351 if ((hfdcan->Init.TxBuffersNbr + hfdcan->Init.TxFifoQueueElmtsNbr) > 0U)
352 {
353 assert_param(IS_FDCAN_DATA_SIZE(hfdcan->Init.TxElmtSize));
354 }
355
356 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
357 if (hfdcan->State == HAL_FDCAN_STATE_RESET)
358 {
359 /* Allocate lock resource and initialize it */
360 hfdcan->Lock = HAL_UNLOCKED;
361
362 /* Reset callbacks to legacy functions */
363 hfdcan->ClockCalibrationCallback = HAL_FDCAN_ClockCalibrationCallback; /* ClockCalibrationCallback */
364 hfdcan->TxEventFifoCallback = HAL_FDCAN_TxEventFifoCallback; /* TxEventFifoCallback */
365 hfdcan->RxFifo0Callback = HAL_FDCAN_RxFifo0Callback; /* RxFifo0Callback */
366 hfdcan->RxFifo1Callback = HAL_FDCAN_RxFifo1Callback; /* RxFifo1Callback */
367 hfdcan->TxFifoEmptyCallback = HAL_FDCAN_TxFifoEmptyCallback; /* TxFifoEmptyCallback */
368 hfdcan->TxBufferCompleteCallback = HAL_FDCAN_TxBufferCompleteCallback; /* TxBufferCompleteCallback */
369 hfdcan->TxBufferAbortCallback = HAL_FDCAN_TxBufferAbortCallback; /* TxBufferAbortCallback */
370 hfdcan->RxBufferNewMessageCallback = HAL_FDCAN_RxBufferNewMessageCallback; /* RxBufferNewMessageCallback */
371 hfdcan->HighPriorityMessageCallback = HAL_FDCAN_HighPriorityMessageCallback; /* HighPriorityMessageCallback */
372 hfdcan->TimestampWraparoundCallback = HAL_FDCAN_TimestampWraparoundCallback; /* TimestampWraparoundCallback */
373 hfdcan->TimeoutOccurredCallback = HAL_FDCAN_TimeoutOccurredCallback; /* TimeoutOccurredCallback */
374 hfdcan->ErrorCallback = HAL_FDCAN_ErrorCallback; /* ErrorCallback */
375 hfdcan->ErrorStatusCallback = HAL_FDCAN_ErrorStatusCallback; /* ErrorStatusCallback */
376 hfdcan->TT_ScheduleSyncCallback = HAL_FDCAN_TT_ScheduleSyncCallback; /* TT_ScheduleSyncCallback */
377 hfdcan->TT_TimeMarkCallback = HAL_FDCAN_TT_TimeMarkCallback; /* TT_TimeMarkCallback */
378 hfdcan->TT_StopWatchCallback = HAL_FDCAN_TT_StopWatchCallback; /* TT_StopWatchCallback */
379 hfdcan->TT_GlobalTimeCallback = HAL_FDCAN_TT_GlobalTimeCallback; /* TT_GlobalTimeCallback */
380
381 if (hfdcan->MspInitCallback == NULL)
382 {
383 hfdcan->MspInitCallback = HAL_FDCAN_MspInit; /* Legacy weak MspInit */
384 }
385
386 /* Init the low level hardware: CLOCK, NVIC */
387 hfdcan->MspInitCallback(hfdcan);
388 }
389 #else
390 if (hfdcan->State == HAL_FDCAN_STATE_RESET)
391 {
392 /* Allocate lock resource and initialize it */
393 hfdcan->Lock = HAL_UNLOCKED;
394
395 /* Init the low level hardware: CLOCK, NVIC */
396 HAL_FDCAN_MspInit(hfdcan);
397 }
398 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
399
400 /* Exit from Sleep mode */
401 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_CSR);
402
403 /* Get tick */
404 tickstart = HAL_GetTick();
405
406 /* Check Sleep mode acknowledge */
407 while ((hfdcan->Instance->CCCR & FDCAN_CCCR_CSA) == FDCAN_CCCR_CSA)
408 {
409 if ((HAL_GetTick() - tickstart) > FDCAN_TIMEOUT_VALUE)
410 {
411 /* Update error code */
412 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
413
414 /* Change FDCAN state */
415 hfdcan->State = HAL_FDCAN_STATE_ERROR;
416
417 return HAL_ERROR;
418 }
419 }
420
421 /* Request initialisation */
422 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_INIT);
423
424 /* Get tick */
425 tickstart = HAL_GetTick();
426
427 /* Wait until the INIT bit into CCCR register is set */
428 while ((hfdcan->Instance->CCCR & FDCAN_CCCR_INIT) == 0U)
429 {
430 /* Check for the Timeout */
431 if ((HAL_GetTick() - tickstart) > FDCAN_TIMEOUT_VALUE)
432 {
433 /* Update error code */
434 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
435
436 /* Change FDCAN state */
437 hfdcan->State = HAL_FDCAN_STATE_ERROR;
438
439 return HAL_ERROR;
440 }
441 }
442
443 /* Enable configuration change */
444 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_CCE);
445
446 /* Set the no automatic retransmission */
447 if (hfdcan->Init.AutoRetransmission == ENABLE)
448 {
449 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_DAR);
450 }
451 else
452 {
453 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_DAR);
454 }
455
456 /* Set the transmit pause feature */
457 if (hfdcan->Init.TransmitPause == ENABLE)
458 {
459 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_TXP);
460 }
461 else
462 {
463 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_TXP);
464 }
465
466 /* Set the Protocol Exception Handling */
467 if (hfdcan->Init.ProtocolException == ENABLE)
468 {
469 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_PXHD);
470 }
471 else
472 {
473 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_PXHD);
474 }
475
476 /* Set FDCAN Frame Format */
477 MODIFY_REG(hfdcan->Instance->CCCR, FDCAN_FRAME_FD_BRS, hfdcan->Init.FrameFormat);
478
479 /* Reset FDCAN Operation Mode */
480 CLEAR_BIT(hfdcan->Instance->CCCR, (FDCAN_CCCR_TEST | FDCAN_CCCR_MON | FDCAN_CCCR_ASM));
481 CLEAR_BIT(hfdcan->Instance->TEST, FDCAN_TEST_LBCK);
482
483 /* Set FDCAN Operating Mode:
484 | Normal | Restricted | Bus | Internal | External
485 | | Operation | Monitoring | LoopBack | LoopBack
486 CCCR.TEST | 0 | 0 | 0 | 1 | 1
487 CCCR.MON | 0 | 0 | 1 | 1 | 0
488 TEST.LBCK | 0 | 0 | 0 | 1 | 1
489 CCCR.ASM | 0 | 1 | 0 | 0 | 0
490 */
491 if (hfdcan->Init.Mode == FDCAN_MODE_RESTRICTED_OPERATION)
492 {
493 /* Enable Restricted Operation mode */
494 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_ASM);
495 }
496 else if (hfdcan->Init.Mode != FDCAN_MODE_NORMAL)
497 {
498 if (hfdcan->Init.Mode != FDCAN_MODE_BUS_MONITORING)
499 {
500 /* Enable write access to TEST register */
501 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_TEST);
502
503 /* Enable LoopBack mode */
504 SET_BIT(hfdcan->Instance->TEST, FDCAN_TEST_LBCK);
505
506 if (hfdcan->Init.Mode == FDCAN_MODE_INTERNAL_LOOPBACK)
507 {
508 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_MON);
509 }
510 }
511 else
512 {
513 /* Enable bus monitoring mode */
514 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_MON);
515 }
516 }
517 else
518 {
519 /* Nothing to do: normal mode */
520 }
521
522 /* Set the nominal bit timing register */
523 hfdcan->Instance->NBTP = ((((uint32_t)hfdcan->Init.NominalSyncJumpWidth - 1U) << FDCAN_NBTP_NSJW_Pos) | \
524 (((uint32_t)hfdcan->Init.NominalTimeSeg1 - 1U) << FDCAN_NBTP_NTSEG1_Pos) | \
525 (((uint32_t)hfdcan->Init.NominalTimeSeg2 - 1U) << FDCAN_NBTP_NTSEG2_Pos) | \
526 (((uint32_t)hfdcan->Init.NominalPrescaler - 1U) << FDCAN_NBTP_NBRP_Pos));
527
528 /* If FD operation with BRS is selected, set the data bit timing register */
529 if (hfdcan->Init.FrameFormat == FDCAN_FRAME_FD_BRS)
530 {
531 hfdcan->Instance->DBTP = ((((uint32_t)hfdcan->Init.DataSyncJumpWidth - 1U) << FDCAN_DBTP_DSJW_Pos) | \
532 (((uint32_t)hfdcan->Init.DataTimeSeg1 - 1U) << FDCAN_DBTP_DTSEG1_Pos) | \
533 (((uint32_t)hfdcan->Init.DataTimeSeg2 - 1U) << FDCAN_DBTP_DTSEG2_Pos) | \
534 (((uint32_t)hfdcan->Init.DataPrescaler - 1U) << FDCAN_DBTP_DBRP_Pos));
535 }
536
537 if (hfdcan->Init.TxFifoQueueElmtsNbr > 0U)
538 {
539 /* Select between Tx FIFO and Tx Queue operation modes */
540 SET_BIT(hfdcan->Instance->TXBC, hfdcan->Init.TxFifoQueueMode);
541 }
542
543 /* Configure Tx element size */
544 if ((hfdcan->Init.TxBuffersNbr + hfdcan->Init.TxFifoQueueElmtsNbr) > 0U)
545 {
546 MODIFY_REG(hfdcan->Instance->TXESC, FDCAN_TXESC_TBDS, CvtEltSize[hfdcan->Init.TxElmtSize]);
547 }
548
549 /* Configure Rx FIFO 0 element size */
550 if (hfdcan->Init.RxFifo0ElmtsNbr > 0U)
551 {
552 MODIFY_REG(hfdcan->Instance->RXESC, FDCAN_RXESC_F0DS,
553 (CvtEltSize[hfdcan->Init.RxFifo0ElmtSize] << FDCAN_RXESC_F0DS_Pos));
554 }
555
556 /* Configure Rx FIFO 1 element size */
557 if (hfdcan->Init.RxFifo1ElmtsNbr > 0U)
558 {
559 MODIFY_REG(hfdcan->Instance->RXESC, FDCAN_RXESC_F1DS,
560 (CvtEltSize[hfdcan->Init.RxFifo1ElmtSize] << FDCAN_RXESC_F1DS_Pos));
561 }
562
563 /* Configure Rx buffer element size */
564 if (hfdcan->Init.RxBuffersNbr > 0U)
565 {
566 MODIFY_REG(hfdcan->Instance->RXESC, FDCAN_RXESC_RBDS,
567 (CvtEltSize[hfdcan->Init.RxBufferSize] << FDCAN_RXESC_RBDS_Pos));
568 }
569
570 /* By default operation mode is set to Event-driven communication.
571 If Time-triggered communication is needed, user should call the
572 HAL_FDCAN_TT_ConfigOperation function just after the HAL_FDCAN_Init */
573 if (hfdcan->Instance == FDCAN1)
574 {
575 CLEAR_BIT(hfdcan->ttcan->TTOCF, FDCAN_TTOCF_OM);
576 }
577
578 /* Initialize the Latest Tx FIFO/Queue request buffer index */
579 hfdcan->LatestTxFifoQRequest = 0U;
580
581 /* Initialize the error code */
582 hfdcan->ErrorCode = HAL_FDCAN_ERROR_NONE;
583
584 /* Initialize the FDCAN state */
585 hfdcan->State = HAL_FDCAN_STATE_READY;
586
587 /* Calculate each RAM block address */
588 status = FDCAN_CalcultateRamBlockAddresses(hfdcan);
589
590 /* Return function status */
591 return status;
592 }
593
594 /**
595 * @brief Deinitializes the FDCAN peripheral registers to their default reset values.
596 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
597 * the configuration information for the specified FDCAN.
598 * @retval HAL status
599 */
HAL_FDCAN_DeInit(FDCAN_HandleTypeDef * hfdcan)600 HAL_StatusTypeDef HAL_FDCAN_DeInit(FDCAN_HandleTypeDef *hfdcan)
601 {
602 /* Check FDCAN handle */
603 if (hfdcan == NULL)
604 {
605 return HAL_ERROR;
606 }
607
608 /* Check function parameters */
609 assert_param(IS_FDCAN_ALL_INSTANCE(hfdcan->Instance));
610
611 /* Stop the FDCAN module: return value is voluntary ignored */
612 (void)HAL_FDCAN_Stop(hfdcan);
613
614 /* Disable Interrupt lines */
615 CLEAR_BIT(hfdcan->Instance->ILE, (FDCAN_INTERRUPT_LINE0 | FDCAN_INTERRUPT_LINE1));
616
617 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
618 if (hfdcan->MspDeInitCallback == NULL)
619 {
620 hfdcan->MspDeInitCallback = HAL_FDCAN_MspDeInit; /* Legacy weak MspDeInit */
621 }
622
623 /* DeInit the low level hardware: CLOCK, NVIC */
624 hfdcan->MspDeInitCallback(hfdcan);
625 #else
626 /* DeInit the low level hardware: CLOCK, NVIC */
627 HAL_FDCAN_MspDeInit(hfdcan);
628 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
629
630 /* Reset the FDCAN ErrorCode */
631 hfdcan->ErrorCode = HAL_FDCAN_ERROR_NONE;
632
633 /* Change FDCAN state */
634 hfdcan->State = HAL_FDCAN_STATE_RESET;
635
636 /* Return function status */
637 return HAL_OK;
638 }
639
640 /**
641 * @brief Initializes the FDCAN MSP.
642 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
643 * the configuration information for the specified FDCAN.
644 * @retval None
645 */
HAL_FDCAN_MspInit(FDCAN_HandleTypeDef * hfdcan)646 __weak void HAL_FDCAN_MspInit(FDCAN_HandleTypeDef *hfdcan)
647 {
648 /* Prevent unused argument(s) compilation warning */
649 UNUSED(hfdcan);
650 /* NOTE: This function Should not be modified, when the callback is needed,
651 the HAL_FDCAN_MspInit could be implemented in the user file
652 */
653 }
654
655 /**
656 * @brief DeInitializes the FDCAN MSP.
657 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
658 * the configuration information for the specified FDCAN.
659 * @retval None
660 */
HAL_FDCAN_MspDeInit(FDCAN_HandleTypeDef * hfdcan)661 __weak void HAL_FDCAN_MspDeInit(FDCAN_HandleTypeDef *hfdcan)
662 {
663 /* Prevent unused argument(s) compilation warning */
664 UNUSED(hfdcan);
665 /* NOTE: This function Should not be modified, when the callback is needed,
666 the HAL_FDCAN_MspDeInit could be implemented in the user file
667 */
668 }
669
670 /**
671 * @brief Enter FDCAN peripheral in sleep mode.
672 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
673 * the configuration information for the specified FDCAN.
674 * @retval HAL status
675 */
HAL_FDCAN_EnterPowerDownMode(FDCAN_HandleTypeDef * hfdcan)676 HAL_StatusTypeDef HAL_FDCAN_EnterPowerDownMode(FDCAN_HandleTypeDef *hfdcan)
677 {
678 uint32_t tickstart;
679
680 /* Request clock stop */
681 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_CSR);
682
683 /* Get tick */
684 tickstart = HAL_GetTick();
685
686 /* Wait until FDCAN is ready for power down */
687 while ((hfdcan->Instance->CCCR & FDCAN_CCCR_CSA) == 0U)
688 {
689 if ((HAL_GetTick() - tickstart) > FDCAN_TIMEOUT_VALUE)
690 {
691 /* Update error code */
692 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
693
694 /* Change FDCAN state */
695 hfdcan->State = HAL_FDCAN_STATE_ERROR;
696
697 return HAL_ERROR;
698 }
699 }
700
701 /* Return function status */
702 return HAL_OK;
703 }
704
705 /**
706 * @brief Exit power down mode.
707 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
708 * the configuration information for the specified FDCAN.
709 * @retval HAL status
710 */
HAL_FDCAN_ExitPowerDownMode(FDCAN_HandleTypeDef * hfdcan)711 HAL_StatusTypeDef HAL_FDCAN_ExitPowerDownMode(FDCAN_HandleTypeDef *hfdcan)
712 {
713 uint32_t tickstart;
714
715 /* Reset clock stop request */
716 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_CSR);
717
718 /* Get tick */
719 tickstart = HAL_GetTick();
720
721 /* Wait until FDCAN exits sleep mode */
722 while ((hfdcan->Instance->CCCR & FDCAN_CCCR_CSA) == FDCAN_CCCR_CSA)
723 {
724 if ((HAL_GetTick() - tickstart) > FDCAN_TIMEOUT_VALUE)
725 {
726 /* Update error code */
727 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
728
729 /* Change FDCAN state */
730 hfdcan->State = HAL_FDCAN_STATE_ERROR;
731
732 return HAL_ERROR;
733 }
734 }
735
736 /* Enter normal operation */
737 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_INIT);
738
739 /* Return function status */
740 return HAL_OK;
741 }
742
743 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
744 /**
745 * @brief Register a FDCAN CallBack.
746 * To be used instead of the weak predefined callback
747 * @param hfdcan pointer to a FDCAN_HandleTypeDef structure that contains
748 * the configuration information for FDCAN module
749 * @param CallbackID ID of the callback to be registered
750 * This parameter can be one of the following values:
751 * @arg @ref HAL_FDCAN_TX_FIFO_EMPTY_CB_ID Tx Fifo Empty callback ID
752 * @arg @ref HAL_FDCAN_RX_BUFFER_NEW_MSG_CB_ID Rx buffer new message callback ID
753 * @arg @ref HAL_FDCAN_HIGH_PRIO_MESSAGE_CB_ID High priority message callback ID
754 * @arg @ref HAL_FDCAN_TIMESTAMP_WRAPAROUND_CB_ID Timestamp wraparound callback ID
755 * @arg @ref HAL_FDCAN_TIMEOUT_OCCURRED_CB_ID Timeout occurred callback ID
756 * @arg @ref HAL_FDCAN_ERROR_CALLBACK_CB_ID Error callback ID
757 * @arg @ref HAL_FDCAN_MSPINIT_CB_ID MspInit callback ID
758 * @arg @ref HAL_FDCAN_MSPDEINIT_CB_ID MspDeInit callback ID
759 * @param pCallback pointer to the Callback function
760 * @retval HAL status
761 */
HAL_FDCAN_RegisterCallback(FDCAN_HandleTypeDef * hfdcan,HAL_FDCAN_CallbackIDTypeDef CallbackID,void (* pCallback)(FDCAN_HandleTypeDef * _hFDCAN))762 HAL_StatusTypeDef HAL_FDCAN_RegisterCallback(FDCAN_HandleTypeDef *hfdcan, HAL_FDCAN_CallbackIDTypeDef CallbackID,
763 void (* pCallback)(FDCAN_HandleTypeDef *_hFDCAN))
764 {
765 HAL_StatusTypeDef status = HAL_OK;
766
767 if (pCallback == NULL)
768 {
769 /* Update the error code */
770 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
771
772 return HAL_ERROR;
773 }
774
775 if (hfdcan->State == HAL_FDCAN_STATE_READY)
776 {
777 switch (CallbackID)
778 {
779 case HAL_FDCAN_TX_FIFO_EMPTY_CB_ID :
780 hfdcan->TxFifoEmptyCallback = pCallback;
781 break;
782
783 case HAL_FDCAN_RX_BUFFER_NEW_MSG_CB_ID :
784 hfdcan->RxBufferNewMessageCallback = pCallback;
785 break;
786
787 case HAL_FDCAN_HIGH_PRIO_MESSAGE_CB_ID :
788 hfdcan->HighPriorityMessageCallback = pCallback;
789 break;
790
791 case HAL_FDCAN_TIMESTAMP_WRAPAROUND_CB_ID :
792 hfdcan->TimestampWraparoundCallback = pCallback;
793 break;
794
795 case HAL_FDCAN_TIMEOUT_OCCURRED_CB_ID :
796 hfdcan->TimeoutOccurredCallback = pCallback;
797 break;
798
799 case HAL_FDCAN_ERROR_CALLBACK_CB_ID :
800 hfdcan->ErrorCallback = pCallback;
801 break;
802
803 case HAL_FDCAN_MSPINIT_CB_ID :
804 hfdcan->MspInitCallback = pCallback;
805 break;
806
807 case HAL_FDCAN_MSPDEINIT_CB_ID :
808 hfdcan->MspDeInitCallback = pCallback;
809 break;
810
811 default :
812 /* Update the error code */
813 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
814
815 /* Return error status */
816 status = HAL_ERROR;
817 break;
818 }
819 }
820 else if (hfdcan->State == HAL_FDCAN_STATE_RESET)
821 {
822 switch (CallbackID)
823 {
824 case HAL_FDCAN_MSPINIT_CB_ID :
825 hfdcan->MspInitCallback = pCallback;
826 break;
827
828 case HAL_FDCAN_MSPDEINIT_CB_ID :
829 hfdcan->MspDeInitCallback = pCallback;
830 break;
831
832 default :
833 /* Update the error code */
834 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
835
836 /* Return error status */
837 status = HAL_ERROR;
838 break;
839 }
840 }
841 else
842 {
843 /* Update the error code */
844 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
845
846 /* Return error status */
847 status = HAL_ERROR;
848 }
849
850 return status;
851 }
852
853 /**
854 * @brief Unregister a FDCAN CallBack.
855 * FDCAN callback is redirected to the weak predefined callback
856 * @param hfdcan pointer to a FDCAN_HandleTypeDef structure that contains
857 * the configuration information for FDCAN module
858 * @param CallbackID ID of the callback to be unregistered
859 * This parameter can be one of the following values:
860 * @arg @ref HAL_FDCAN_TX_FIFO_EMPTY_CB_ID Tx Fifo Empty callback ID
861 * @arg @ref HAL_FDCAN_RX_BUFFER_NEW_MSG_CB_ID Rx buffer new message callback ID
862 * @arg @ref HAL_FDCAN_HIGH_PRIO_MESSAGE_CB_ID High priority message callback ID
863 * @arg @ref HAL_FDCAN_TIMESTAMP_WRAPAROUND_CB_ID Timestamp wraparound callback ID
864 * @arg @ref HAL_FDCAN_TIMEOUT_OCCURRED_CB_ID Timeout occurred callback ID
865 * @arg @ref HAL_FDCAN_ERROR_CALLBACK_CB_ID Error callback ID
866 * @arg @ref HAL_FDCAN_MSPINIT_CB_ID MspInit callback ID
867 * @arg @ref HAL_FDCAN_MSPDEINIT_CB_ID MspDeInit callback ID
868 * @retval HAL status
869 */
HAL_FDCAN_UnRegisterCallback(FDCAN_HandleTypeDef * hfdcan,HAL_FDCAN_CallbackIDTypeDef CallbackID)870 HAL_StatusTypeDef HAL_FDCAN_UnRegisterCallback(FDCAN_HandleTypeDef *hfdcan, HAL_FDCAN_CallbackIDTypeDef CallbackID)
871 {
872 HAL_StatusTypeDef status = HAL_OK;
873
874 if (hfdcan->State == HAL_FDCAN_STATE_READY)
875 {
876 switch (CallbackID)
877 {
878 case HAL_FDCAN_TX_FIFO_EMPTY_CB_ID :
879 hfdcan->TxFifoEmptyCallback = HAL_FDCAN_TxFifoEmptyCallback;
880 break;
881
882 case HAL_FDCAN_RX_BUFFER_NEW_MSG_CB_ID :
883 hfdcan->RxBufferNewMessageCallback = HAL_FDCAN_RxBufferNewMessageCallback;
884 break;
885
886 case HAL_FDCAN_HIGH_PRIO_MESSAGE_CB_ID :
887 hfdcan->HighPriorityMessageCallback = HAL_FDCAN_HighPriorityMessageCallback;
888 break;
889
890 case HAL_FDCAN_TIMESTAMP_WRAPAROUND_CB_ID :
891 hfdcan->TimestampWraparoundCallback = HAL_FDCAN_TimestampWraparoundCallback;
892 break;
893
894 case HAL_FDCAN_TIMEOUT_OCCURRED_CB_ID :
895 hfdcan->TimeoutOccurredCallback = HAL_FDCAN_TimeoutOccurredCallback;
896 break;
897
898 case HAL_FDCAN_ERROR_CALLBACK_CB_ID :
899 hfdcan->ErrorCallback = HAL_FDCAN_ErrorCallback;
900 break;
901
902 case HAL_FDCAN_MSPINIT_CB_ID :
903 hfdcan->MspInitCallback = HAL_FDCAN_MspInit;
904 break;
905
906 case HAL_FDCAN_MSPDEINIT_CB_ID :
907 hfdcan->MspDeInitCallback = HAL_FDCAN_MspDeInit;
908 break;
909
910 default :
911 /* Update the error code */
912 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
913
914 /* Return error status */
915 status = HAL_ERROR;
916 break;
917 }
918 }
919 else if (hfdcan->State == HAL_FDCAN_STATE_RESET)
920 {
921 switch (CallbackID)
922 {
923 case HAL_FDCAN_MSPINIT_CB_ID :
924 hfdcan->MspInitCallback = HAL_FDCAN_MspInit;
925 break;
926
927 case HAL_FDCAN_MSPDEINIT_CB_ID :
928 hfdcan->MspDeInitCallback = HAL_FDCAN_MspDeInit;
929 break;
930
931 default :
932 /* Update the error code */
933 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
934
935 /* Return error status */
936 status = HAL_ERROR;
937 break;
938 }
939 }
940 else
941 {
942 /* Update the error code */
943 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
944
945 /* Return error status */
946 status = HAL_ERROR;
947 }
948
949 return status;
950 }
951
952 /**
953 * @brief Register Clock Calibration FDCAN Callback
954 * To be used instead of the weak HAL_FDCAN_ClockCalibrationCallback() predefined callback
955 * @param hfdcan FDCAN handle
956 * @param pCallback pointer to the Clock Calibration Callback function
957 * @retval HAL status
958 */
HAL_FDCAN_RegisterClockCalibrationCallback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_ClockCalibrationCallbackTypeDef pCallback)959 HAL_StatusTypeDef HAL_FDCAN_RegisterClockCalibrationCallback(FDCAN_HandleTypeDef *hfdcan,
960 pFDCAN_ClockCalibrationCallbackTypeDef pCallback)
961 {
962 HAL_StatusTypeDef status = HAL_OK;
963
964 if (pCallback == NULL)
965 {
966 /* Update the error code */
967 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
968 return HAL_ERROR;
969 }
970
971 if (hfdcan->State == HAL_FDCAN_STATE_READY)
972 {
973 hfdcan->ClockCalibrationCallback = pCallback;
974 }
975 else
976 {
977 /* Update the error code */
978 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
979
980 /* Return error status */
981 status = HAL_ERROR;
982 }
983
984 return status;
985 }
986
987 /**
988 * @brief UnRegister the Clock Calibration FDCAN Callback
989 * Clock Calibration FDCAN Callback is redirected to the weak
990 * HAL_FDCAN_ClockCalibrationCallback() predefined callback
991 * @param hfdcan FDCAN handle
992 * @retval HAL status
993 */
HAL_FDCAN_UnRegisterClockCalibrationCallback(FDCAN_HandleTypeDef * hfdcan)994 HAL_StatusTypeDef HAL_FDCAN_UnRegisterClockCalibrationCallback(FDCAN_HandleTypeDef *hfdcan)
995 {
996 HAL_StatusTypeDef status = HAL_OK;
997
998 if (hfdcan->State == HAL_FDCAN_STATE_READY)
999 {
1000 hfdcan->ClockCalibrationCallback = HAL_FDCAN_ClockCalibrationCallback; /* Legacy weak ClockCalibrationCallback */
1001 }
1002 else
1003 {
1004 /* Update the error code */
1005 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1006
1007 /* Return error status */
1008 status = HAL_ERROR;
1009 }
1010
1011 return status;
1012 }
1013
1014 /**
1015 * @brief Register Tx Event Fifo FDCAN Callback
1016 * To be used instead of the weak HAL_FDCAN_TxEventFifoCallback() predefined callback
1017 * @param hfdcan FDCAN handle
1018 * @param pCallback pointer to the Tx Event Fifo Callback function
1019 * @retval HAL status
1020 */
HAL_FDCAN_RegisterTxEventFifoCallback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_TxEventFifoCallbackTypeDef pCallback)1021 HAL_StatusTypeDef HAL_FDCAN_RegisterTxEventFifoCallback(FDCAN_HandleTypeDef *hfdcan,
1022 pFDCAN_TxEventFifoCallbackTypeDef pCallback)
1023 {
1024 HAL_StatusTypeDef status = HAL_OK;
1025
1026 if (pCallback == NULL)
1027 {
1028 /* Update the error code */
1029 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1030 return HAL_ERROR;
1031 }
1032
1033 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1034 {
1035 hfdcan->TxEventFifoCallback = pCallback;
1036 }
1037 else
1038 {
1039 /* Update the error code */
1040 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1041
1042 /* Return error status */
1043 status = HAL_ERROR;
1044 }
1045
1046 return status;
1047 }
1048
1049 /**
1050 * @brief UnRegister the Tx Event Fifo FDCAN Callback
1051 * Tx Event Fifo FDCAN Callback is redirected to the weak HAL_FDCAN_TxEventFifoCallback() predefined callback
1052 * @param hfdcan FDCAN handle
1053 * @retval HAL status
1054 */
HAL_FDCAN_UnRegisterTxEventFifoCallback(FDCAN_HandleTypeDef * hfdcan)1055 HAL_StatusTypeDef HAL_FDCAN_UnRegisterTxEventFifoCallback(FDCAN_HandleTypeDef *hfdcan)
1056 {
1057 HAL_StatusTypeDef status = HAL_OK;
1058
1059 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1060 {
1061 hfdcan->TxEventFifoCallback = HAL_FDCAN_TxEventFifoCallback; /* Legacy weak TxEventFifoCallback */
1062 }
1063 else
1064 {
1065 /* Update the error code */
1066 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1067
1068 /* Return error status */
1069 status = HAL_ERROR;
1070 }
1071
1072 return status;
1073 }
1074
1075 /**
1076 * @brief Register Rx Fifo 0 FDCAN Callback
1077 * To be used instead of the weak HAL_FDCAN_RxFifo0Callback() predefined callback
1078 * @param hfdcan FDCAN handle
1079 * @param pCallback pointer to the Rx Fifo 0 Callback function
1080 * @retval HAL status
1081 */
HAL_FDCAN_RegisterRxFifo0Callback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_RxFifo0CallbackTypeDef pCallback)1082 HAL_StatusTypeDef HAL_FDCAN_RegisterRxFifo0Callback(FDCAN_HandleTypeDef *hfdcan,
1083 pFDCAN_RxFifo0CallbackTypeDef pCallback)
1084 {
1085 HAL_StatusTypeDef status = HAL_OK;
1086
1087 if (pCallback == NULL)
1088 {
1089 /* Update the error code */
1090 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1091 return HAL_ERROR;
1092 }
1093
1094 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1095 {
1096 hfdcan->RxFifo0Callback = pCallback;
1097 }
1098 else
1099 {
1100 /* Update the error code */
1101 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1102
1103 /* Return error status */
1104 status = HAL_ERROR;
1105 }
1106
1107 return status;
1108 }
1109
1110 /**
1111 * @brief UnRegister the Rx Fifo 0 FDCAN Callback
1112 * Rx Fifo 0 FDCAN Callback is redirected to the weak HAL_FDCAN_RxFifo0Callback() predefined callback
1113 * @param hfdcan FDCAN handle
1114 * @retval HAL status
1115 */
HAL_FDCAN_UnRegisterRxFifo0Callback(FDCAN_HandleTypeDef * hfdcan)1116 HAL_StatusTypeDef HAL_FDCAN_UnRegisterRxFifo0Callback(FDCAN_HandleTypeDef *hfdcan)
1117 {
1118 HAL_StatusTypeDef status = HAL_OK;
1119
1120 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1121 {
1122 hfdcan->RxFifo0Callback = HAL_FDCAN_RxFifo0Callback; /* Legacy weak RxFifo0Callback */
1123 }
1124 else
1125 {
1126 /* Update the error code */
1127 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1128
1129 /* Return error status */
1130 status = HAL_ERROR;
1131 }
1132
1133 return status;
1134 }
1135
1136 /**
1137 * @brief Register Rx Fifo 1 FDCAN Callback
1138 * To be used instead of the weak HAL_FDCAN_RxFifo1Callback() predefined callback
1139 * @param hfdcan FDCAN handle
1140 * @param pCallback pointer to the Rx Fifo 1 Callback function
1141 * @retval HAL status
1142 */
HAL_FDCAN_RegisterRxFifo1Callback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_RxFifo1CallbackTypeDef pCallback)1143 HAL_StatusTypeDef HAL_FDCAN_RegisterRxFifo1Callback(FDCAN_HandleTypeDef *hfdcan,
1144 pFDCAN_RxFifo1CallbackTypeDef pCallback)
1145 {
1146 HAL_StatusTypeDef status = HAL_OK;
1147
1148 if (pCallback == NULL)
1149 {
1150 /* Update the error code */
1151 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1152 return HAL_ERROR;
1153 }
1154
1155 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1156 {
1157 hfdcan->RxFifo1Callback = pCallback;
1158 }
1159 else
1160 {
1161 /* Update the error code */
1162 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1163
1164 /* Return error status */
1165 status = HAL_ERROR;
1166 }
1167
1168 return status;
1169 }
1170
1171 /**
1172 * @brief UnRegister the Rx Fifo 1 FDCAN Callback
1173 * Rx Fifo 1 FDCAN Callback is redirected to the weak HAL_FDCAN_RxFifo1Callback() predefined callback
1174 * @param hfdcan FDCAN handle
1175 * @retval HAL status
1176 */
HAL_FDCAN_UnRegisterRxFifo1Callback(FDCAN_HandleTypeDef * hfdcan)1177 HAL_StatusTypeDef HAL_FDCAN_UnRegisterRxFifo1Callback(FDCAN_HandleTypeDef *hfdcan)
1178 {
1179 HAL_StatusTypeDef status = HAL_OK;
1180
1181 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1182 {
1183 hfdcan->RxFifo1Callback = HAL_FDCAN_RxFifo1Callback; /* Legacy weak RxFifo1Callback */
1184 }
1185 else
1186 {
1187 /* Update the error code */
1188 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1189
1190 /* Return error status */
1191 status = HAL_ERROR;
1192 }
1193
1194 return status;
1195 }
1196
1197 /**
1198 * @brief Register Tx Buffer Complete FDCAN Callback
1199 * To be used instead of the weak HAL_FDCAN_TxBufferCompleteCallback() predefined callback
1200 * @param hfdcan FDCAN handle
1201 * @param pCallback pointer to the Tx Buffer Complete Callback function
1202 * @retval HAL status
1203 */
HAL_FDCAN_RegisterTxBufferCompleteCallback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_TxBufferCompleteCallbackTypeDef pCallback)1204 HAL_StatusTypeDef HAL_FDCAN_RegisterTxBufferCompleteCallback(FDCAN_HandleTypeDef *hfdcan,
1205 pFDCAN_TxBufferCompleteCallbackTypeDef pCallback)
1206 {
1207 HAL_StatusTypeDef status = HAL_OK;
1208
1209 if (pCallback == NULL)
1210 {
1211 /* Update the error code */
1212 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1213 return HAL_ERROR;
1214 }
1215
1216 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1217 {
1218 hfdcan->TxBufferCompleteCallback = pCallback;
1219 }
1220 else
1221 {
1222 /* Update the error code */
1223 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1224
1225 /* Return error status */
1226 status = HAL_ERROR;
1227 }
1228
1229 return status;
1230 }
1231
1232 /**
1233 * @brief UnRegister the Tx Buffer Complete FDCAN Callback
1234 * Tx Buffer Complete FDCAN Callback is redirected to
1235 * the weak HAL_FDCAN_TxBufferCompleteCallback() predefined callback
1236 * @param hfdcan FDCAN handle
1237 * @retval HAL status
1238 */
HAL_FDCAN_UnRegisterTxBufferCompleteCallback(FDCAN_HandleTypeDef * hfdcan)1239 HAL_StatusTypeDef HAL_FDCAN_UnRegisterTxBufferCompleteCallback(FDCAN_HandleTypeDef *hfdcan)
1240 {
1241 HAL_StatusTypeDef status = HAL_OK;
1242
1243 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1244 {
1245 hfdcan->TxBufferCompleteCallback = HAL_FDCAN_TxBufferCompleteCallback; /* Legacy weak TxBufferCompleteCallback */
1246 }
1247 else
1248 {
1249 /* Update the error code */
1250 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1251
1252 /* Return error status */
1253 status = HAL_ERROR;
1254 }
1255
1256 return status;
1257 }
1258
1259 /**
1260 * @brief Register Tx Buffer Abort FDCAN Callback
1261 * To be used instead of the weak HAL_FDCAN_TxBufferAbortCallback() predefined callback
1262 * @param hfdcan FDCAN handle
1263 * @param pCallback pointer to the Tx Buffer Abort Callback function
1264 * @retval HAL status
1265 */
HAL_FDCAN_RegisterTxBufferAbortCallback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_TxBufferAbortCallbackTypeDef pCallback)1266 HAL_StatusTypeDef HAL_FDCAN_RegisterTxBufferAbortCallback(FDCAN_HandleTypeDef *hfdcan,
1267 pFDCAN_TxBufferAbortCallbackTypeDef pCallback)
1268 {
1269 HAL_StatusTypeDef status = HAL_OK;
1270
1271 if (pCallback == NULL)
1272 {
1273 /* Update the error code */
1274 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1275 return HAL_ERROR;
1276 }
1277
1278 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1279 {
1280 hfdcan->TxBufferAbortCallback = pCallback;
1281 }
1282 else
1283 {
1284 /* Update the error code */
1285 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1286
1287 /* Return error status */
1288 status = HAL_ERROR;
1289 }
1290
1291 return status;
1292 }
1293
1294 /**
1295 * @brief UnRegister the Tx Buffer Abort FDCAN Callback
1296 * Tx Buffer Abort FDCAN Callback is redirected to
1297 * the weak HAL_FDCAN_TxBufferAbortCallback() predefined callback
1298 * @param hfdcan FDCAN handle
1299 * @retval HAL status
1300 */
HAL_FDCAN_UnRegisterTxBufferAbortCallback(FDCAN_HandleTypeDef * hfdcan)1301 HAL_StatusTypeDef HAL_FDCAN_UnRegisterTxBufferAbortCallback(FDCAN_HandleTypeDef *hfdcan)
1302 {
1303 HAL_StatusTypeDef status = HAL_OK;
1304
1305 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1306 {
1307 hfdcan->TxBufferAbortCallback = HAL_FDCAN_TxBufferAbortCallback; /* Legacy weak TxBufferAbortCallback */
1308 }
1309 else
1310 {
1311 /* Update the error code */
1312 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1313
1314 /* Return error status */
1315 status = HAL_ERROR;
1316 }
1317
1318 return status;
1319 }
1320
1321 /**
1322 * @brief Register Error Status FDCAN Callback
1323 * To be used instead of the weak HAL_FDCAN_ErrorStatusCallback() predefined callback
1324 * @param hfdcan FDCAN handle
1325 * @param pCallback pointer to the Error Status Callback function
1326 * @retval HAL status
1327 */
HAL_FDCAN_RegisterErrorStatusCallback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_ErrorStatusCallbackTypeDef pCallback)1328 HAL_StatusTypeDef HAL_FDCAN_RegisterErrorStatusCallback(FDCAN_HandleTypeDef *hfdcan,
1329 pFDCAN_ErrorStatusCallbackTypeDef pCallback)
1330 {
1331 HAL_StatusTypeDef status = HAL_OK;
1332
1333 if (pCallback == NULL)
1334 {
1335 /* Update the error code */
1336 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1337 return HAL_ERROR;
1338 }
1339
1340 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1341 {
1342 hfdcan->ErrorStatusCallback = pCallback;
1343 }
1344 else
1345 {
1346 /* Update the error code */
1347 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1348
1349 /* Return error status */
1350 status = HAL_ERROR;
1351 }
1352
1353 return status;
1354 }
1355
1356 /**
1357 * @brief UnRegister the Error Status FDCAN Callback
1358 * Error Status FDCAN Callback is redirected to the weak HAL_FDCAN_ErrorStatusCallback() predefined callback
1359 * @param hfdcan FDCAN handle
1360 * @retval HAL status
1361 */
HAL_FDCAN_UnRegisterErrorStatusCallback(FDCAN_HandleTypeDef * hfdcan)1362 HAL_StatusTypeDef HAL_FDCAN_UnRegisterErrorStatusCallback(FDCAN_HandleTypeDef *hfdcan)
1363 {
1364 HAL_StatusTypeDef status = HAL_OK;
1365
1366 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1367 {
1368 hfdcan->ErrorStatusCallback = HAL_FDCAN_ErrorStatusCallback; /* Legacy weak ErrorStatusCallback */
1369 }
1370 else
1371 {
1372 /* Update the error code */
1373 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1374
1375 /* Return error status */
1376 status = HAL_ERROR;
1377 }
1378
1379 return status;
1380 }
1381
1382 /**
1383 * @brief Register TT Schedule Synchronization FDCAN Callback
1384 * To be used instead of the weak HAL_FDCAN_TT_ScheduleSyncCallback() predefined callback
1385 * @param hfdcan FDCAN handle
1386 * @param pCallback pointer to the TT Schedule Synchronization Callback function
1387 * @retval HAL status
1388 */
HAL_FDCAN_RegisterTTScheduleSyncCallback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_TT_ScheduleSyncCallbackTypeDef pCallback)1389 HAL_StatusTypeDef HAL_FDCAN_RegisterTTScheduleSyncCallback(FDCAN_HandleTypeDef *hfdcan,
1390 pFDCAN_TT_ScheduleSyncCallbackTypeDef pCallback)
1391 {
1392 HAL_StatusTypeDef status = HAL_OK;
1393
1394 if (pCallback == NULL)
1395 {
1396 /* Update the error code */
1397 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1398 return HAL_ERROR;
1399 }
1400
1401 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1402 {
1403 hfdcan->TT_ScheduleSyncCallback = pCallback;
1404 }
1405 else
1406 {
1407 /* Update the error code */
1408 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1409
1410 /* Return error status */
1411 status = HAL_ERROR;
1412 }
1413
1414 return status;
1415 }
1416
1417 /**
1418 * @brief UnRegister the TT Schedule Synchronization FDCAN Callback
1419 * TT Schedule Synchronization Callback is redirected to the weak
1420 * HAL_FDCAN_TT_ScheduleSyncCallback() predefined callback
1421 * @param hfdcan FDCAN handle
1422 * @retval HAL status
1423 */
HAL_FDCAN_UnRegisterTTScheduleSyncCallback(FDCAN_HandleTypeDef * hfdcan)1424 HAL_StatusTypeDef HAL_FDCAN_UnRegisterTTScheduleSyncCallback(FDCAN_HandleTypeDef *hfdcan)
1425 {
1426 HAL_StatusTypeDef status = HAL_OK;
1427
1428 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1429 {
1430 hfdcan->TT_ScheduleSyncCallback = HAL_FDCAN_TT_ScheduleSyncCallback; /* Legacy weak TT_ScheduleSyncCallback */
1431 }
1432 else
1433 {
1434 /* Update the error code */
1435 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1436
1437 /* Return error status */
1438 status = HAL_ERROR;
1439 }
1440
1441 return status;
1442 }
1443
1444 /**
1445 * @brief Register TT Time Mark FDCAN Callback
1446 * To be used instead of the weak HAL_FDCAN_TT_TimeMarkCallback() predefined callback
1447 * @param hfdcan FDCAN handle
1448 * @param pCallback pointer to the TT Time Mark Callback function
1449 * @retval HAL status
1450 */
HAL_FDCAN_RegisterTTTimeMarkCallback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_TT_TimeMarkCallbackTypeDef pCallback)1451 HAL_StatusTypeDef HAL_FDCAN_RegisterTTTimeMarkCallback(FDCAN_HandleTypeDef *hfdcan,
1452 pFDCAN_TT_TimeMarkCallbackTypeDef pCallback)
1453 {
1454 HAL_StatusTypeDef status = HAL_OK;
1455
1456 if (pCallback == NULL)
1457 {
1458 /* Update the error code */
1459 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1460 return HAL_ERROR;
1461 }
1462
1463 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1464 {
1465 hfdcan->TT_TimeMarkCallback = pCallback;
1466 }
1467 else
1468 {
1469 /* Update the error code */
1470 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1471
1472 /* Return error status */
1473 status = HAL_ERROR;
1474 }
1475
1476 return status;
1477 }
1478
1479 /**
1480 * @brief UnRegister the TT Time Mark FDCAN Callback
1481 * TT Time Mark Callback is redirected to the weak HAL_FDCAN_TT_TimeMarkCallback() predefined callback
1482 * @param hfdcan FDCAN handle
1483 * @retval HAL status
1484 */
HAL_FDCAN_UnRegisterTTTimeMarkCallback(FDCAN_HandleTypeDef * hfdcan)1485 HAL_StatusTypeDef HAL_FDCAN_UnRegisterTTTimeMarkCallback(FDCAN_HandleTypeDef *hfdcan)
1486 {
1487 HAL_StatusTypeDef status = HAL_OK;
1488
1489 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1490 {
1491 hfdcan->TT_TimeMarkCallback = HAL_FDCAN_TT_TimeMarkCallback; /* Legacy weak TT_TimeMarkCallback */
1492 }
1493 else
1494 {
1495 /* Update the error code */
1496 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1497
1498 /* Return error status */
1499 status = HAL_ERROR;
1500 }
1501
1502 return status;
1503 }
1504
1505 /**
1506 * @brief Register TT Stop Watch FDCAN Callback
1507 * To be used instead of the weak HAL_FDCAN_TT_StopWatchCallback() predefined callback
1508 * @param hfdcan FDCAN handle
1509 * @param pCallback pointer to the TT Stop Watch Callback function
1510 * @retval HAL status
1511 */
HAL_FDCAN_RegisterTTStopWatchCallback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_TT_StopWatchCallbackTypeDef pCallback)1512 HAL_StatusTypeDef HAL_FDCAN_RegisterTTStopWatchCallback(FDCAN_HandleTypeDef *hfdcan,
1513 pFDCAN_TT_StopWatchCallbackTypeDef pCallback)
1514 {
1515 HAL_StatusTypeDef status = HAL_OK;
1516
1517 if (pCallback == NULL)
1518 {
1519 /* Update the error code */
1520 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1521 return HAL_ERROR;
1522 }
1523
1524 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1525 {
1526 hfdcan->TT_StopWatchCallback = pCallback;
1527 }
1528 else
1529 {
1530 /* Update the error code */
1531 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1532
1533 /* Return error status */
1534 status = HAL_ERROR;
1535 }
1536
1537 return status;
1538 }
1539
1540 /**
1541 * @brief UnRegister the TT Stop Watch FDCAN Callback
1542 * TT Stop Watch Callback is redirected to the weak HAL_FDCAN_TT_StopWatchCallback() predefined callback
1543 * @param hfdcan FDCAN handle
1544 * @retval HAL status
1545 */
HAL_FDCAN_UnRegisterTTStopWatchCallback(FDCAN_HandleTypeDef * hfdcan)1546 HAL_StatusTypeDef HAL_FDCAN_UnRegisterTTStopWatchCallback(FDCAN_HandleTypeDef *hfdcan)
1547 {
1548 HAL_StatusTypeDef status = HAL_OK;
1549
1550 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1551 {
1552 hfdcan->TT_StopWatchCallback = HAL_FDCAN_TT_StopWatchCallback; /* Legacy weak TT_StopWatchCallback */
1553 }
1554 else
1555 {
1556 /* Update the error code */
1557 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1558
1559 /* Return error status */
1560 status = HAL_ERROR;
1561 }
1562
1563 return status;
1564 }
1565
1566 /**
1567 * @brief Register TT Global Time FDCAN Callback
1568 * To be used instead of the weak HAL_FDCAN_TT_GlobalTimeCallback() predefined callback
1569 * @param hfdcan FDCAN handle
1570 * @param pCallback pointer to the TT Global Time Callback function
1571 * @retval HAL status
1572 */
HAL_FDCAN_RegisterTTGlobalTimeCallback(FDCAN_HandleTypeDef * hfdcan,pFDCAN_TT_GlobalTimeCallbackTypeDef pCallback)1573 HAL_StatusTypeDef HAL_FDCAN_RegisterTTGlobalTimeCallback(FDCAN_HandleTypeDef *hfdcan,
1574 pFDCAN_TT_GlobalTimeCallbackTypeDef pCallback)
1575 {
1576 HAL_StatusTypeDef status = HAL_OK;
1577
1578 if (pCallback == NULL)
1579 {
1580 /* Update the error code */
1581 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1582 return HAL_ERROR;
1583 }
1584
1585 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1586 {
1587 hfdcan->TT_GlobalTimeCallback = pCallback;
1588 }
1589 else
1590 {
1591 /* Update the error code */
1592 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1593
1594 /* Return error status */
1595 status = HAL_ERROR;
1596 }
1597
1598 return status;
1599 }
1600
1601 /**
1602 * @brief UnRegister the TT Global Time FDCAN Callback
1603 * TT Global Time Callback is redirected to the weak HAL_FDCAN_TT_GlobalTimeCallback() predefined callback
1604 * @param hfdcan FDCAN handle
1605 * @retval HAL status
1606 */
HAL_FDCAN_UnRegisterTTGlobalTimeCallback(FDCAN_HandleTypeDef * hfdcan)1607 HAL_StatusTypeDef HAL_FDCAN_UnRegisterTTGlobalTimeCallback(FDCAN_HandleTypeDef *hfdcan)
1608 {
1609 HAL_StatusTypeDef status = HAL_OK;
1610
1611 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1612 {
1613 hfdcan->TT_GlobalTimeCallback = HAL_FDCAN_TT_GlobalTimeCallback; /* Legacy weak TT_GlobalTimeCallback */
1614 }
1615 else
1616 {
1617 /* Update the error code */
1618 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_INVALID_CALLBACK;
1619
1620 /* Return error status */
1621 status = HAL_ERROR;
1622 }
1623
1624 return status;
1625 }
1626
1627 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
1628
1629 /**
1630 * @}
1631 */
1632
1633 /** @defgroup FDCAN_Exported_Functions_Group2 Configuration functions
1634 * @brief FDCAN Configuration functions.
1635 *
1636 @verbatim
1637 ==============================================================================
1638 ##### Configuration functions #####
1639 ==============================================================================
1640 [..] This section provides functions allowing to:
1641 (+) HAL_FDCAN_ConfigClockCalibration : Configure the FDCAN clock calibration unit
1642 (+) HAL_FDCAN_GetClockCalibrationState : Get the clock calibration state
1643 (+) HAL_FDCAN_ResetClockCalibrationState : Reset the clock calibration state
1644 (+) HAL_FDCAN_GetClockCalibrationCounter : Get the clock calibration counters values
1645 (+) HAL_FDCAN_ConfigFilter : Configure the FDCAN reception filters
1646 (+) HAL_FDCAN_ConfigGlobalFilter : Configure the FDCAN global filter
1647 (+) HAL_FDCAN_ConfigExtendedIdMask : Configure the extended ID mask
1648 (+) HAL_FDCAN_ConfigRxFifoOverwrite : Configure the Rx FIFO operation mode
1649 (+) HAL_FDCAN_ConfigFifoWatermark : Configure the FIFO watermark
1650 (+) HAL_FDCAN_ConfigRamWatchdog : Configure the RAM watchdog
1651 (+) HAL_FDCAN_ConfigTimestampCounter : Configure the timestamp counter
1652 (+) HAL_FDCAN_EnableTimestampCounter : Enable the timestamp counter
1653 (+) HAL_FDCAN_DisableTimestampCounter : Disable the timestamp counter
1654 (+) HAL_FDCAN_GetTimestampCounter : Get the timestamp counter value
1655 (+) HAL_FDCAN_ResetTimestampCounter : Reset the timestamp counter to zero
1656 (+) HAL_FDCAN_ConfigTimeoutCounter : Configure the timeout counter
1657 (+) HAL_FDCAN_EnableTimeoutCounter : Enable the timeout counter
1658 (+) HAL_FDCAN_DisableTimeoutCounter : Disable the timeout counter
1659 (+) HAL_FDCAN_GetTimeoutCounter : Get the timeout counter value
1660 (+) HAL_FDCAN_ResetTimeoutCounter : Reset the timeout counter to its start value
1661 (+) HAL_FDCAN_ConfigTxDelayCompensation : Configure the transmitter delay compensation
1662 (+) HAL_FDCAN_EnableTxDelayCompensation : Enable the transmitter delay compensation
1663 (+) HAL_FDCAN_DisableTxDelayCompensation : Disable the transmitter delay compensation
1664 (+) HAL_FDCAN_EnableISOMode : Enable ISO 11898-1 protocol mode
1665 (+) HAL_FDCAN_DisableISOMode : Disable ISO 11898-1 protocol mode
1666 (+) HAL_FDCAN_EnableEdgeFiltering : Enable edge filtering during bus integration
1667 (+) HAL_FDCAN_DisableEdgeFiltering : Disable edge filtering during bus integration
1668
1669 @endverbatim
1670 * @{
1671 */
1672
1673 /**
1674 * @brief Configure the FDCAN clock calibration unit according to the specified
1675 * parameters in the FDCAN_ClkCalUnitTypeDef structure.
1676 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
1677 * the configuration information for the specified FDCAN.
1678 * @param sCcuConfig pointer to an FDCAN_ClkCalUnitTypeDef structure that
1679 * contains the clock calibration information
1680 * @retval HAL status
1681 */
HAL_FDCAN_ConfigClockCalibration(FDCAN_HandleTypeDef * hfdcan,const FDCAN_ClkCalUnitTypeDef * sCcuConfig)1682 HAL_StatusTypeDef HAL_FDCAN_ConfigClockCalibration(FDCAN_HandleTypeDef *hfdcan,
1683 const FDCAN_ClkCalUnitTypeDef *sCcuConfig)
1684 {
1685 /* Check function parameters */
1686 assert_param(IS_FDCAN_CLOCK_CALIBRATION(sCcuConfig->ClockCalibration));
1687 if (sCcuConfig->ClockCalibration == FDCAN_CLOCK_CALIBRATION_DISABLE)
1688 {
1689 assert_param(IS_FDCAN_CKDIV(sCcuConfig->ClockDivider));
1690 }
1691 else
1692 {
1693 assert_param(IS_FDCAN_MAX_VALUE(sCcuConfig->MinOscClkPeriods, 0xFFU));
1694 assert_param(IS_FDCAN_CALIBRATION_FIELD_LENGTH(sCcuConfig->CalFieldLength));
1695 assert_param(IS_FDCAN_MIN_VALUE(sCcuConfig->TimeQuantaPerBitTime, 4U));
1696 assert_param(IS_FDCAN_MAX_VALUE(sCcuConfig->TimeQuantaPerBitTime, 0x25U));
1697 assert_param(IS_FDCAN_MAX_VALUE(sCcuConfig->WatchdogStartValue, 0xFFFFU));
1698 }
1699
1700 /* FDCAN1 should be initialized in order to use clock calibration */
1701 if (hfdcan->Instance != FDCAN1)
1702 {
1703 /* Update error code */
1704 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
1705
1706 return HAL_ERROR;
1707 }
1708
1709 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1710 {
1711 if (sCcuConfig->ClockCalibration == FDCAN_CLOCK_CALIBRATION_DISABLE)
1712 {
1713 /* Bypass clock calibration */
1714 SET_BIT(FDCAN_CCU->CCFG, FDCANCCU_CCFG_BCC);
1715
1716 /* Configure clock divider */
1717 MODIFY_REG(FDCAN_CCU->CCFG, FDCANCCU_CCFG_CDIV,
1718 (sCcuConfig->ClockDivider << FDCANCCU_CCFG_CDIV_Pos));
1719 }
1720 else /* sCcuConfig->ClockCalibration == ENABLE */
1721 {
1722 /* Clock calibration unit generates time quanta clock */
1723 CLEAR_BIT(FDCAN_CCU->CCFG, FDCANCCU_CCFG_BCC);
1724
1725 /* Configure clock calibration unit */
1726 MODIFY_REG(FDCAN_CCU->CCFG,
1727 (FDCANCCU_CCFG_TQBT | FDCANCCU_CCFG_CFL | FDCANCCU_CCFG_OCPM),
1728 ((sCcuConfig->TimeQuantaPerBitTime << FDCANCCU_CCFG_TQBT_Pos) |
1729 sCcuConfig->CalFieldLength | (sCcuConfig->MinOscClkPeriods << FDCANCCU_CCFG_OCPM_Pos)));
1730
1731 /* Configure the start value of the calibration watchdog counter */
1732 MODIFY_REG(FDCAN_CCU->CWD, FDCANCCU_CWD_WDC, sCcuConfig->WatchdogStartValue);
1733 }
1734
1735 /* Return function status */
1736 return HAL_OK;
1737 }
1738 else
1739 {
1740 /* Update error code */
1741 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
1742
1743 return HAL_ERROR;
1744 }
1745 }
1746
1747 /**
1748 * @brief Get the clock calibration state.
1749 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
1750 * the configuration information for the specified FDCAN.
1751 * @retval State clock calibration state (can be a value of @arg FDCAN_calibration_state)
1752 */
HAL_FDCAN_GetClockCalibrationState(const FDCAN_HandleTypeDef * hfdcan)1753 uint32_t HAL_FDCAN_GetClockCalibrationState(const FDCAN_HandleTypeDef *hfdcan)
1754 {
1755 /* Prevent unused argument(s) compilation warning */
1756 UNUSED(hfdcan);
1757
1758 return (FDCAN_CCU->CSTAT & FDCANCCU_CSTAT_CALS);
1759 }
1760
1761 /**
1762 * @brief Reset the clock calibration state.
1763 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
1764 * the configuration information for the specified FDCAN.
1765 * @retval HAL status
1766 */
HAL_FDCAN_ResetClockCalibrationState(FDCAN_HandleTypeDef * hfdcan)1767 HAL_StatusTypeDef HAL_FDCAN_ResetClockCalibrationState(FDCAN_HandleTypeDef *hfdcan)
1768 {
1769 /* FDCAN1 should be initialized in order to use clock calibration */
1770 if (hfdcan->Instance != FDCAN1)
1771 {
1772 /* Update error code */
1773 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
1774
1775 return HAL_ERROR;
1776 }
1777
1778 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1779 {
1780 /* Calibration software reset */
1781 SET_BIT(FDCAN_CCU->CCFG, FDCANCCU_CCFG_SWR);
1782
1783 /* Return function status */
1784 return HAL_OK;
1785 }
1786 else
1787 {
1788 /* Update error code */
1789 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
1790
1791 return HAL_ERROR;
1792 }
1793 }
1794
1795 /**
1796 * @brief Get the clock calibration counter value.
1797 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
1798 * the configuration information for the specified FDCAN.
1799 * @param Counter clock calibration counter.
1800 * This parameter can be a value of @arg FDCAN_calibration_counter.
1801 * @retval Value clock calibration counter value
1802 */
HAL_FDCAN_GetClockCalibrationCounter(const FDCAN_HandleTypeDef * hfdcan,uint32_t Counter)1803 uint32_t HAL_FDCAN_GetClockCalibrationCounter(const FDCAN_HandleTypeDef *hfdcan, uint32_t Counter)
1804 {
1805 /* Prevent unused argument(s) compilation warning */
1806 UNUSED(hfdcan);
1807
1808 /* Check function parameters */
1809 assert_param(IS_FDCAN_CALIBRATION_COUNTER(Counter));
1810
1811 if (Counter == FDCAN_CALIB_TIME_QUANTA_COUNTER)
1812 {
1813 return ((FDCAN_CCU->CSTAT & FDCANCCU_CSTAT_TQC) >> FDCANCCU_CSTAT_TQC_Pos);
1814 }
1815 else if (Counter == FDCAN_CALIB_CLOCK_PERIOD_COUNTER)
1816 {
1817 return (FDCAN_CCU->CSTAT & FDCANCCU_CSTAT_OCPC);
1818 }
1819 else /* Counter == FDCAN_CALIB_WATCHDOG_COUNTER */
1820 {
1821 return ((FDCAN_CCU->CWD & FDCANCCU_CWD_WDV) >> FDCANCCU_CWD_WDV_Pos);
1822 }
1823 }
1824
1825 /**
1826 * @brief Configure the FDCAN reception filter according to the specified
1827 * parameters in the FDCAN_FilterTypeDef structure.
1828 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
1829 * the configuration information for the specified FDCAN.
1830 * @param sFilterConfig pointer to an FDCAN_FilterTypeDef structure that
1831 * contains the filter configuration information
1832 * @retval HAL status
1833 */
HAL_FDCAN_ConfigFilter(FDCAN_HandleTypeDef * hfdcan,const FDCAN_FilterTypeDef * sFilterConfig)1834 HAL_StatusTypeDef HAL_FDCAN_ConfigFilter(FDCAN_HandleTypeDef *hfdcan, const FDCAN_FilterTypeDef *sFilterConfig)
1835 {
1836 uint32_t FilterElementW1;
1837 uint32_t FilterElementW2;
1838 uint32_t *FilterAddress;
1839 HAL_FDCAN_StateTypeDef state = hfdcan->State;
1840
1841 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
1842 {
1843 /* Check function parameters */
1844 assert_param(IS_FDCAN_ID_TYPE(sFilterConfig->IdType));
1845 assert_param(IS_FDCAN_FILTER_CFG(sFilterConfig->FilterConfig));
1846 if (sFilterConfig->FilterConfig == FDCAN_FILTER_TO_RXBUFFER)
1847 {
1848 assert_param(IS_FDCAN_MAX_VALUE(sFilterConfig->RxBufferIndex, 63U));
1849 assert_param(IS_FDCAN_MAX_VALUE(sFilterConfig->IsCalibrationMsg, 1U));
1850 }
1851
1852 if (sFilterConfig->IdType == FDCAN_STANDARD_ID)
1853 {
1854 /* Check function parameters */
1855 assert_param(IS_FDCAN_MAX_VALUE(sFilterConfig->FilterIndex, (hfdcan->Init.StdFiltersNbr - 1U)));
1856 assert_param(IS_FDCAN_MAX_VALUE(sFilterConfig->FilterID1, 0x7FFU));
1857 if (sFilterConfig->FilterConfig != FDCAN_FILTER_TO_RXBUFFER)
1858 {
1859 assert_param(IS_FDCAN_MAX_VALUE(sFilterConfig->FilterID2, 0x7FFU));
1860 assert_param(IS_FDCAN_STD_FILTER_TYPE(sFilterConfig->FilterType));
1861 }
1862
1863 /* Build filter element */
1864 if (sFilterConfig->FilterConfig == FDCAN_FILTER_TO_RXBUFFER)
1865 {
1866 FilterElementW1 = ((FDCAN_FILTER_TO_RXBUFFER << 27U) |
1867 (sFilterConfig->FilterID1 << 16U) |
1868 (sFilterConfig->IsCalibrationMsg << 8U) |
1869 sFilterConfig->RxBufferIndex);
1870 }
1871 else
1872 {
1873 FilterElementW1 = ((sFilterConfig->FilterType << 30U) |
1874 (sFilterConfig->FilterConfig << 27U) |
1875 (sFilterConfig->FilterID1 << 16U) |
1876 sFilterConfig->FilterID2);
1877 }
1878
1879 /* Calculate filter address */
1880 FilterAddress = (uint32_t *)(hfdcan->msgRam.StandardFilterSA + (sFilterConfig->FilterIndex * 4U));
1881
1882 /* Write filter element to the message RAM */
1883 *FilterAddress = FilterElementW1;
1884 }
1885 else /* sFilterConfig->IdType == FDCAN_EXTENDED_ID */
1886 {
1887 /* Check function parameters */
1888 assert_param(IS_FDCAN_MAX_VALUE(sFilterConfig->FilterIndex, (hfdcan->Init.ExtFiltersNbr - 1U)));
1889 assert_param(IS_FDCAN_MAX_VALUE(sFilterConfig->FilterID1, 0x1FFFFFFFU));
1890 if (sFilterConfig->FilterConfig != FDCAN_FILTER_TO_RXBUFFER)
1891 {
1892 assert_param(IS_FDCAN_MAX_VALUE(sFilterConfig->FilterID2, 0x1FFFFFFFU));
1893 assert_param(IS_FDCAN_EXT_FILTER_TYPE(sFilterConfig->FilterType));
1894 }
1895
1896 /* Build first word of filter element */
1897 FilterElementW1 = ((sFilterConfig->FilterConfig << 29U) | sFilterConfig->FilterID1);
1898
1899 /* Build second word of filter element */
1900 if (sFilterConfig->FilterConfig == FDCAN_FILTER_TO_RXBUFFER)
1901 {
1902 FilterElementW2 = sFilterConfig->RxBufferIndex;
1903 }
1904 else
1905 {
1906 FilterElementW2 = ((sFilterConfig->FilterType << 30U) | sFilterConfig->FilterID2);
1907 }
1908
1909 /* Calculate filter address */
1910 FilterAddress = (uint32_t *)(hfdcan->msgRam.ExtendedFilterSA + (sFilterConfig->FilterIndex * 4U * 2U));
1911
1912 /* Write filter element to the message RAM */
1913 *FilterAddress = FilterElementW1;
1914 FilterAddress++;
1915 *FilterAddress = FilterElementW2;
1916 }
1917
1918 /* Return function status */
1919 return HAL_OK;
1920 }
1921 else
1922 {
1923 /* Update error code */
1924 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
1925
1926 return HAL_ERROR;
1927 }
1928 }
1929
1930 /**
1931 * @brief Configure the FDCAN global filter.
1932 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
1933 * the configuration information for the specified FDCAN.
1934 * @param NonMatchingStd Defines how received messages with 11-bit IDs that
1935 * do not match any element of the filter list are treated.
1936 * This parameter can be a value of @arg FDCAN_Non_Matching_Frames.
1937 * @param NonMatchingExt Defines how received messages with 29-bit IDs that
1938 * do not match any element of the filter list are treated.
1939 * This parameter can be a value of @arg FDCAN_Non_Matching_Frames.
1940 * @param RejectRemoteStd Filter or reject all the remote 11-bit IDs frames.
1941 * This parameter can be a value of @arg FDCAN_Reject_Remote_Frames.
1942 * @param RejectRemoteExt Filter or reject all the remote 29-bit IDs frames.
1943 * This parameter can be a value of @arg FDCAN_Reject_Remote_Frames.
1944 * @retval HAL status
1945 */
HAL_FDCAN_ConfigGlobalFilter(FDCAN_HandleTypeDef * hfdcan,uint32_t NonMatchingStd,uint32_t NonMatchingExt,uint32_t RejectRemoteStd,uint32_t RejectRemoteExt)1946 HAL_StatusTypeDef HAL_FDCAN_ConfigGlobalFilter(FDCAN_HandleTypeDef *hfdcan,
1947 uint32_t NonMatchingStd,
1948 uint32_t NonMatchingExt,
1949 uint32_t RejectRemoteStd,
1950 uint32_t RejectRemoteExt)
1951 {
1952 /* Check function parameters */
1953 assert_param(IS_FDCAN_NON_MATCHING(NonMatchingStd));
1954 assert_param(IS_FDCAN_NON_MATCHING(NonMatchingExt));
1955 assert_param(IS_FDCAN_REJECT_REMOTE(RejectRemoteStd));
1956 assert_param(IS_FDCAN_REJECT_REMOTE(RejectRemoteExt));
1957
1958 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1959 {
1960 /* Configure global filter */
1961 hfdcan->Instance->GFC = ((NonMatchingStd << FDCAN_GFC_ANFS_Pos) |
1962 (NonMatchingExt << FDCAN_GFC_ANFE_Pos) |
1963 (RejectRemoteStd << FDCAN_GFC_RRFS_Pos) |
1964 (RejectRemoteExt << FDCAN_GFC_RRFE_Pos));
1965
1966 /* Return function status */
1967 return HAL_OK;
1968 }
1969 else
1970 {
1971 /* Update error code */
1972 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
1973
1974 return HAL_ERROR;
1975 }
1976 }
1977
1978 /**
1979 * @brief Configure the extended ID mask.
1980 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
1981 * the configuration information for the specified FDCAN.
1982 * @param Mask Extended ID Mask.
1983 * This parameter must be a number between 0 and 0x1FFFFFFF.
1984 * @retval HAL status
1985 */
HAL_FDCAN_ConfigExtendedIdMask(FDCAN_HandleTypeDef * hfdcan,uint32_t Mask)1986 HAL_StatusTypeDef HAL_FDCAN_ConfigExtendedIdMask(FDCAN_HandleTypeDef *hfdcan, uint32_t Mask)
1987 {
1988 /* Check function parameters */
1989 assert_param(IS_FDCAN_MAX_VALUE(Mask, 0x1FFFFFFFU));
1990
1991 if (hfdcan->State == HAL_FDCAN_STATE_READY)
1992 {
1993 /* Configure the extended ID mask */
1994 hfdcan->Instance->XIDAM = Mask;
1995
1996 /* Return function status */
1997 return HAL_OK;
1998 }
1999 else
2000 {
2001 /* Update error code */
2002 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2003
2004 return HAL_ERROR;
2005 }
2006 }
2007
2008 /**
2009 * @brief Configure the Rx FIFO operation mode.
2010 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2011 * the configuration information for the specified FDCAN.
2012 * @param RxFifo Rx FIFO.
2013 * This parameter can be one of the following values:
2014 * @arg FDCAN_RX_FIFO0: Rx FIFO 0
2015 * @arg FDCAN_RX_FIFO1: Rx FIFO 1
2016 * @param OperationMode operation mode.
2017 * This parameter can be a value of @arg FDCAN_Rx_FIFO_operation_mode.
2018 * @retval HAL status
2019 */
HAL_FDCAN_ConfigRxFifoOverwrite(FDCAN_HandleTypeDef * hfdcan,uint32_t RxFifo,uint32_t OperationMode)2020 HAL_StatusTypeDef HAL_FDCAN_ConfigRxFifoOverwrite(FDCAN_HandleTypeDef *hfdcan, uint32_t RxFifo, uint32_t OperationMode)
2021 {
2022 /* Check function parameters */
2023 assert_param(IS_FDCAN_RX_FIFO(RxFifo));
2024 assert_param(IS_FDCAN_RX_FIFO_MODE(OperationMode));
2025
2026 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2027 {
2028 if (RxFifo == FDCAN_RX_FIFO0)
2029 {
2030 /* Select FIFO 0 Operation Mode */
2031 MODIFY_REG(hfdcan->Instance->RXF0C, FDCAN_RXF0C_F0OM, (OperationMode << FDCAN_RXF0C_F0OM_Pos));
2032 }
2033 else /* RxFifo == FDCAN_RX_FIFO1 */
2034 {
2035 /* Select FIFO 1 Operation Mode */
2036 MODIFY_REG(hfdcan->Instance->RXF1C, FDCAN_RXF1C_F1OM, (OperationMode << FDCAN_RXF1C_F1OM_Pos));
2037 }
2038
2039 /* Return function status */
2040 return HAL_OK;
2041 }
2042 else
2043 {
2044 /* Update error code */
2045 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2046
2047 return HAL_ERROR;
2048 }
2049 }
2050
2051 /**
2052 * @brief Configure the FIFO watermark.
2053 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2054 * the configuration information for the specified FDCAN.
2055 * @param FIFO select the FIFO to be configured.
2056 * This parameter can be a value of @arg FDCAN_FIFO_watermark.
2057 * @param Watermark level for FIFO watermark interrupt.
2058 * This parameter must be a number between:
2059 * - 0 and 32, if FIFO is FDCAN_CFG_TX_EVENT_FIFO
2060 * - 0 and 64, if FIFO is FDCAN_CFG_RX_FIFO0 or FDCAN_CFG_RX_FIFO1
2061 * @retval HAL status
2062 */
HAL_FDCAN_ConfigFifoWatermark(FDCAN_HandleTypeDef * hfdcan,uint32_t FIFO,uint32_t Watermark)2063 HAL_StatusTypeDef HAL_FDCAN_ConfigFifoWatermark(FDCAN_HandleTypeDef *hfdcan, uint32_t FIFO, uint32_t Watermark)
2064 {
2065 /* Check function parameters */
2066 assert_param(IS_FDCAN_FIFO_WATERMARK(FIFO));
2067 if (FIFO == FDCAN_CFG_TX_EVENT_FIFO)
2068 {
2069 assert_param(IS_FDCAN_MAX_VALUE(Watermark, 32U));
2070 }
2071 else /* (FIFO == FDCAN_CFG_RX_FIFO0) || (FIFO == FDCAN_CFG_RX_FIFO1) */
2072 {
2073 assert_param(IS_FDCAN_MAX_VALUE(Watermark, 64U));
2074 }
2075
2076 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2077 {
2078 /* Set the level for FIFO watermark interrupt */
2079 if (FIFO == FDCAN_CFG_TX_EVENT_FIFO)
2080 {
2081 MODIFY_REG(hfdcan->Instance->TXEFC, FDCAN_TXEFC_EFWM, (Watermark << FDCAN_TXEFC_EFWM_Pos));
2082 }
2083 else if (FIFO == FDCAN_CFG_RX_FIFO0)
2084 {
2085 MODIFY_REG(hfdcan->Instance->RXF0C, FDCAN_RXF0C_F0WM, (Watermark << FDCAN_RXF0C_F0WM_Pos));
2086 }
2087 else /* FIFO == FDCAN_CFG_RX_FIFO1 */
2088 {
2089 MODIFY_REG(hfdcan->Instance->RXF1C, FDCAN_RXF1C_F1WM, (Watermark << FDCAN_RXF1C_F1WM_Pos));
2090 }
2091
2092 /* Return function status */
2093 return HAL_OK;
2094 }
2095 else
2096 {
2097 /* Update error code */
2098 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2099
2100 return HAL_ERROR;
2101 }
2102 }
2103
2104 /**
2105 * @brief Configure the RAM watchdog.
2106 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2107 * the configuration information for the specified FDCAN.
2108 * @param CounterStartValue Start value of the Message RAM Watchdog Counter,
2109 * This parameter must be a number between 0x00 and 0xFF,
2110 * with the reset value of 0x00 the counter is disabled.
2111 * @retval HAL status
2112 */
HAL_FDCAN_ConfigRamWatchdog(FDCAN_HandleTypeDef * hfdcan,uint32_t CounterStartValue)2113 HAL_StatusTypeDef HAL_FDCAN_ConfigRamWatchdog(FDCAN_HandleTypeDef *hfdcan, uint32_t CounterStartValue)
2114 {
2115 /* Check function parameters */
2116 assert_param(IS_FDCAN_MAX_VALUE(CounterStartValue, 0xFFU));
2117
2118 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2119 {
2120 /* Configure the RAM watchdog counter start value */
2121 MODIFY_REG(hfdcan->Instance->RWD, FDCAN_RWD_WDC, CounterStartValue);
2122
2123 /* Return function status */
2124 return HAL_OK;
2125 }
2126 else
2127 {
2128 /* Update error code */
2129 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2130
2131 return HAL_ERROR;
2132 }
2133 }
2134
2135 /**
2136 * @brief Configure the timestamp counter.
2137 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2138 * the configuration information for the specified FDCAN.
2139 * @param TimestampPrescaler Timestamp Counter Prescaler.
2140 * This parameter can be a value of @arg FDCAN_Timestamp_Prescaler.
2141 * @retval HAL status
2142 */
HAL_FDCAN_ConfigTimestampCounter(FDCAN_HandleTypeDef * hfdcan,uint32_t TimestampPrescaler)2143 HAL_StatusTypeDef HAL_FDCAN_ConfigTimestampCounter(FDCAN_HandleTypeDef *hfdcan, uint32_t TimestampPrescaler)
2144 {
2145 /* Check function parameters */
2146 assert_param(IS_FDCAN_TIMESTAMP_PRESCALER(TimestampPrescaler));
2147
2148 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2149 {
2150 /* Configure prescaler */
2151 MODIFY_REG(hfdcan->Instance->TSCC, FDCAN_TSCC_TCP, TimestampPrescaler);
2152
2153 /* Return function status */
2154 return HAL_OK;
2155 }
2156 else
2157 {
2158 /* Update error code */
2159 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2160
2161 return HAL_ERROR;
2162 }
2163 }
2164
2165 /**
2166 * @brief Enable the timestamp counter.
2167 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2168 * the configuration information for the specified FDCAN.
2169 * @param TimestampOperation Timestamp counter operation.
2170 * This parameter can be a value of @arg FDCAN_Timestamp.
2171 * @retval HAL status
2172 */
HAL_FDCAN_EnableTimestampCounter(FDCAN_HandleTypeDef * hfdcan,uint32_t TimestampOperation)2173 HAL_StatusTypeDef HAL_FDCAN_EnableTimestampCounter(FDCAN_HandleTypeDef *hfdcan, uint32_t TimestampOperation)
2174 {
2175 /* Check function parameters */
2176 assert_param(IS_FDCAN_TIMESTAMP(TimestampOperation));
2177
2178 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2179 {
2180 /* Enable timestamp counter */
2181 MODIFY_REG(hfdcan->Instance->TSCC, FDCAN_TSCC_TSS, TimestampOperation);
2182
2183 /* Return function status */
2184 return HAL_OK;
2185 }
2186 else
2187 {
2188 /* Update error code */
2189 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2190
2191 return HAL_ERROR;
2192 }
2193 }
2194
2195 /**
2196 * @brief Disable the timestamp counter.
2197 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2198 * the configuration information for the specified FDCAN.
2199 * @retval HAL status
2200 */
HAL_FDCAN_DisableTimestampCounter(FDCAN_HandleTypeDef * hfdcan)2201 HAL_StatusTypeDef HAL_FDCAN_DisableTimestampCounter(FDCAN_HandleTypeDef *hfdcan)
2202 {
2203 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2204 {
2205 /* Disable timestamp counter */
2206 CLEAR_BIT(hfdcan->Instance->TSCC, FDCAN_TSCC_TSS);
2207
2208 /* Return function status */
2209 return HAL_OK;
2210 }
2211 else
2212 {
2213 /* Update error code */
2214 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2215
2216 return HAL_ERROR;
2217 }
2218 }
2219
2220 /**
2221 * @brief Get the timestamp counter value.
2222 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2223 * the configuration information for the specified FDCAN.
2224 * @retval Timestamp counter value
2225 */
HAL_FDCAN_GetTimestampCounter(const FDCAN_HandleTypeDef * hfdcan)2226 uint16_t HAL_FDCAN_GetTimestampCounter(const FDCAN_HandleTypeDef *hfdcan)
2227 {
2228 return (uint16_t)(hfdcan->Instance->TSCV);
2229 }
2230
2231 /**
2232 * @brief Reset the timestamp counter to zero.
2233 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2234 * the configuration information for the specified FDCAN.
2235 * @retval HAL status
2236 */
HAL_FDCAN_ResetTimestampCounter(FDCAN_HandleTypeDef * hfdcan)2237 HAL_StatusTypeDef HAL_FDCAN_ResetTimestampCounter(FDCAN_HandleTypeDef *hfdcan)
2238 {
2239 if ((hfdcan->Instance->TSCC & FDCAN_TSCC_TSS) != FDCAN_TIMESTAMP_EXTERNAL)
2240 {
2241 /* Reset timestamp counter.
2242 Actually any write operation to TSCV clears the counter */
2243 CLEAR_REG(hfdcan->Instance->TSCV);
2244 }
2245 else
2246 {
2247 /* Update error code.
2248 Unable to reset external counter */
2249 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
2250
2251 return HAL_ERROR;
2252 }
2253
2254 /* Return function status */
2255 return HAL_OK;
2256 }
2257
2258 /**
2259 * @brief Configure the timeout counter.
2260 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2261 * the configuration information for the specified FDCAN.
2262 * @param TimeoutOperation Timeout counter operation.
2263 * This parameter can be a value of @arg FDCAN_Timeout_Operation.
2264 * @param TimeoutPeriod Start value of the timeout down-counter.
2265 * This parameter must be a number between 0x0000 and 0xFFFF
2266 * @retval HAL status
2267 */
HAL_FDCAN_ConfigTimeoutCounter(FDCAN_HandleTypeDef * hfdcan,uint32_t TimeoutOperation,uint32_t TimeoutPeriod)2268 HAL_StatusTypeDef HAL_FDCAN_ConfigTimeoutCounter(FDCAN_HandleTypeDef *hfdcan, uint32_t TimeoutOperation,
2269 uint32_t TimeoutPeriod)
2270 {
2271 /* Check function parameters */
2272 assert_param(IS_FDCAN_TIMEOUT(TimeoutOperation));
2273 assert_param(IS_FDCAN_MAX_VALUE(TimeoutPeriod, 0xFFFFU));
2274
2275 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2276 {
2277 /* Select timeout operation and configure period */
2278 MODIFY_REG(hfdcan->Instance->TOCC,
2279 (FDCAN_TOCC_TOS | FDCAN_TOCC_TOP), (TimeoutOperation | (TimeoutPeriod << FDCAN_TOCC_TOP_Pos)));
2280
2281 /* Return function status */
2282 return HAL_OK;
2283 }
2284 else
2285 {
2286 /* Update error code */
2287 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2288
2289 return HAL_ERROR;
2290 }
2291 }
2292
2293 /**
2294 * @brief Enable the timeout counter.
2295 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2296 * the configuration information for the specified FDCAN.
2297 * @retval HAL status
2298 */
HAL_FDCAN_EnableTimeoutCounter(FDCAN_HandleTypeDef * hfdcan)2299 HAL_StatusTypeDef HAL_FDCAN_EnableTimeoutCounter(FDCAN_HandleTypeDef *hfdcan)
2300 {
2301 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2302 {
2303 /* Enable timeout counter */
2304 SET_BIT(hfdcan->Instance->TOCC, FDCAN_TOCC_ETOC);
2305
2306 /* Return function status */
2307 return HAL_OK;
2308 }
2309 else
2310 {
2311 /* Update error code */
2312 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2313
2314 return HAL_ERROR;
2315 }
2316 }
2317
2318 /**
2319 * @brief Disable the timeout counter.
2320 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2321 * the configuration information for the specified FDCAN.
2322 * @retval HAL status
2323 */
HAL_FDCAN_DisableTimeoutCounter(FDCAN_HandleTypeDef * hfdcan)2324 HAL_StatusTypeDef HAL_FDCAN_DisableTimeoutCounter(FDCAN_HandleTypeDef *hfdcan)
2325 {
2326 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2327 {
2328 /* Disable timeout counter */
2329 CLEAR_BIT(hfdcan->Instance->TOCC, FDCAN_TOCC_ETOC);
2330
2331 /* Return function status */
2332 return HAL_OK;
2333 }
2334 else
2335 {
2336 /* Update error code */
2337 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2338
2339 return HAL_ERROR;
2340 }
2341 }
2342
2343 /**
2344 * @brief Get the timeout counter value.
2345 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2346 * the configuration information for the specified FDCAN.
2347 * @retval Timeout counter value
2348 */
HAL_FDCAN_GetTimeoutCounter(const FDCAN_HandleTypeDef * hfdcan)2349 uint16_t HAL_FDCAN_GetTimeoutCounter(const FDCAN_HandleTypeDef *hfdcan)
2350 {
2351 return (uint16_t)(hfdcan->Instance->TOCV);
2352 }
2353
2354 /**
2355 * @brief Reset the timeout counter to its start value.
2356 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2357 * the configuration information for the specified FDCAN.
2358 * @retval HAL status
2359 */
HAL_FDCAN_ResetTimeoutCounter(FDCAN_HandleTypeDef * hfdcan)2360 HAL_StatusTypeDef HAL_FDCAN_ResetTimeoutCounter(FDCAN_HandleTypeDef *hfdcan)
2361 {
2362 if ((hfdcan->Instance->TOCC & FDCAN_TOCC_TOS) == FDCAN_TIMEOUT_CONTINUOUS)
2363 {
2364 /* Reset timeout counter to start value */
2365 CLEAR_REG(hfdcan->Instance->TOCV);
2366
2367 /* Return function status */
2368 return HAL_OK;
2369 }
2370 else
2371 {
2372 /* Update error code.
2373 Unable to reset counter: controlled only by FIFO empty state */
2374 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
2375
2376 return HAL_ERROR;
2377 }
2378 }
2379
2380 /**
2381 * @brief Configure the transmitter delay compensation.
2382 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2383 * the configuration information for the specified FDCAN.
2384 * @param TdcOffset Transmitter Delay Compensation Offset.
2385 * This parameter must be a number between 0x00 and 0x7F.
2386 * @param TdcFilter Transmitter Delay Compensation Filter Window Length.
2387 * This parameter must be a number between 0x00 and 0x7F.
2388 * @retval HAL status
2389 */
HAL_FDCAN_ConfigTxDelayCompensation(FDCAN_HandleTypeDef * hfdcan,uint32_t TdcOffset,uint32_t TdcFilter)2390 HAL_StatusTypeDef HAL_FDCAN_ConfigTxDelayCompensation(FDCAN_HandleTypeDef *hfdcan, uint32_t TdcOffset,
2391 uint32_t TdcFilter)
2392 {
2393 /* Check function parameters */
2394 assert_param(IS_FDCAN_MAX_VALUE(TdcOffset, 0x7FU));
2395 assert_param(IS_FDCAN_MAX_VALUE(TdcFilter, 0x7FU));
2396
2397 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2398 {
2399 /* Configure TDC offset and filter window */
2400 hfdcan->Instance->TDCR = ((TdcFilter << FDCAN_TDCR_TDCF_Pos) | (TdcOffset << FDCAN_TDCR_TDCO_Pos));
2401
2402 /* Return function status */
2403 return HAL_OK;
2404 }
2405 else
2406 {
2407 /* Update error code */
2408 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2409
2410 return HAL_ERROR;
2411 }
2412 }
2413
2414 /**
2415 * @brief Enable the transmitter delay compensation.
2416 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2417 * the configuration information for the specified FDCAN.
2418 * @retval HAL status
2419 */
HAL_FDCAN_EnableTxDelayCompensation(FDCAN_HandleTypeDef * hfdcan)2420 HAL_StatusTypeDef HAL_FDCAN_EnableTxDelayCompensation(FDCAN_HandleTypeDef *hfdcan)
2421 {
2422 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2423 {
2424 /* Enable transmitter delay compensation */
2425 SET_BIT(hfdcan->Instance->DBTP, FDCAN_DBTP_TDC);
2426
2427 /* Return function status */
2428 return HAL_OK;
2429 }
2430 else
2431 {
2432 /* Update error code */
2433 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2434
2435 return HAL_ERROR;
2436 }
2437 }
2438
2439 /**
2440 * @brief Disable the transmitter delay compensation.
2441 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2442 * the configuration information for the specified FDCAN.
2443 * @retval HAL status
2444 */
HAL_FDCAN_DisableTxDelayCompensation(FDCAN_HandleTypeDef * hfdcan)2445 HAL_StatusTypeDef HAL_FDCAN_DisableTxDelayCompensation(FDCAN_HandleTypeDef *hfdcan)
2446 {
2447 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2448 {
2449 /* Disable transmitter delay compensation */
2450 CLEAR_BIT(hfdcan->Instance->DBTP, FDCAN_DBTP_TDC);
2451
2452 /* Return function status */
2453 return HAL_OK;
2454 }
2455 else
2456 {
2457 /* Update error code */
2458 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2459
2460 return HAL_ERROR;
2461 }
2462 }
2463
2464 /**
2465 * @brief Enable ISO 11898-1 protocol mode.
2466 * CAN FD frame format is according to ISO 11898-1 standard.
2467 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2468 * the configuration information for the specified FDCAN.
2469 * @retval HAL status
2470 */
HAL_FDCAN_EnableISOMode(FDCAN_HandleTypeDef * hfdcan)2471 HAL_StatusTypeDef HAL_FDCAN_EnableISOMode(FDCAN_HandleTypeDef *hfdcan)
2472 {
2473 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2474 {
2475 /* Disable Non ISO protocol mode */
2476 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_NISO);
2477
2478 /* Return function status */
2479 return HAL_OK;
2480 }
2481 else
2482 {
2483 /* Update error code */
2484 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2485
2486 return HAL_ERROR;
2487 }
2488 }
2489
2490 /**
2491 * @brief Disable ISO 11898-1 protocol mode.
2492 * CAN FD frame format is according to Bosch CAN FD specification V1.0.
2493 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2494 * the configuration information for the specified FDCAN.
2495 * @retval HAL status
2496 */
HAL_FDCAN_DisableISOMode(FDCAN_HandleTypeDef * hfdcan)2497 HAL_StatusTypeDef HAL_FDCAN_DisableISOMode(FDCAN_HandleTypeDef *hfdcan)
2498 {
2499 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2500 {
2501 /* Enable Non ISO protocol mode */
2502 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_NISO);
2503
2504 /* Return function status */
2505 return HAL_OK;
2506 }
2507 else
2508 {
2509 /* Update error code */
2510 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2511
2512 return HAL_ERROR;
2513 }
2514 }
2515
2516 /**
2517 * @brief Enable edge filtering during bus integration.
2518 * Two consecutive dominant tq are required to detect an edge for hard synchronization.
2519 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2520 * the configuration information for the specified FDCAN.
2521 * @retval HAL status
2522 */
HAL_FDCAN_EnableEdgeFiltering(FDCAN_HandleTypeDef * hfdcan)2523 HAL_StatusTypeDef HAL_FDCAN_EnableEdgeFiltering(FDCAN_HandleTypeDef *hfdcan)
2524 {
2525 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2526 {
2527 /* Enable edge filtering */
2528 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_EFBI);
2529
2530 /* Return function status */
2531 return HAL_OK;
2532 }
2533 else
2534 {
2535 /* Update error code */
2536 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2537
2538 return HAL_ERROR;
2539 }
2540 }
2541
2542 /**
2543 * @brief Disable edge filtering during bus integration.
2544 * One dominant tq is required to detect an edge for hard synchronization.
2545 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2546 * the configuration information for the specified FDCAN.
2547 * @retval HAL status
2548 */
HAL_FDCAN_DisableEdgeFiltering(FDCAN_HandleTypeDef * hfdcan)2549 HAL_StatusTypeDef HAL_FDCAN_DisableEdgeFiltering(FDCAN_HandleTypeDef *hfdcan)
2550 {
2551 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2552 {
2553 /* Disable edge filtering */
2554 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_EFBI);
2555
2556 /* Return function status */
2557 return HAL_OK;
2558 }
2559 else
2560 {
2561 /* Update error code */
2562 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2563
2564 return HAL_ERROR;
2565 }
2566 }
2567
2568 /**
2569 * @}
2570 */
2571
2572 /** @defgroup FDCAN_Exported_Functions_Group3 Control functions
2573 * @brief Control functions
2574 *
2575 @verbatim
2576 ==============================================================================
2577 ##### Control functions #####
2578 ==============================================================================
2579 [..] This section provides functions allowing to:
2580 (+) HAL_FDCAN_Start : Start the FDCAN module
2581 (+) HAL_FDCAN_Stop : Stop the FDCAN module and enable access to configuration registers
2582 (+) HAL_FDCAN_AddMessageToTxFifoQ : Add a message to the Tx FIFO/Queue and activate the corresponding
2583 transmission request
2584 (+) HAL_FDCAN_AddMessageToTxBuffer : Add a message to a dedicated Tx buffer
2585 (+) HAL_FDCAN_EnableTxBufferRequest : Enable transmission request
2586 (+) HAL_FDCAN_GetLatestTxFifoQRequestBuffer : Get Tx buffer index of latest Tx FIFO/Queue request
2587 (+) HAL_FDCAN_AbortTxRequest : Abort transmission request
2588 (+) HAL_FDCAN_GetRxMessage : Get an FDCAN frame from the Rx Buffer/FIFO zone into the
2589 message RAM
2590 (+) HAL_FDCAN_GetTxEvent : Get an FDCAN Tx event from the Tx Event FIFO zone
2591 into the message RAM
2592 (+) HAL_FDCAN_GetHighPriorityMessageStatus : Get high priority message status
2593 (+) HAL_FDCAN_GetProtocolStatus : Get protocol status
2594 (+) HAL_FDCAN_GetErrorCounters : Get error counter values
2595 (+) HAL_FDCAN_IsRxBufferMessageAvailable : Check if a new message is received in the selected Rx buffer
2596 (+) HAL_FDCAN_IsTxBufferMessagePending : Check if a transmission request is pending
2597 on the selected Tx buffer
2598 (+) HAL_FDCAN_GetRxFifoFillLevel : Return Rx FIFO fill level
2599 (+) HAL_FDCAN_GetTxFifoFreeLevel : Return Tx FIFO free level
2600 (+) HAL_FDCAN_IsRestrictedOperationMode : Check if the FDCAN peripheral entered Restricted Operation Mode
2601 (+) HAL_FDCAN_ExitRestrictedOperationMode : Exit Restricted Operation Mode
2602
2603 @endverbatim
2604 * @{
2605 */
2606
2607 /**
2608 * @brief Start the FDCAN module.
2609 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2610 * the configuration information for the specified FDCAN.
2611 * @retval HAL status
2612 */
HAL_FDCAN_Start(FDCAN_HandleTypeDef * hfdcan)2613 HAL_StatusTypeDef HAL_FDCAN_Start(FDCAN_HandleTypeDef *hfdcan)
2614 {
2615 if (hfdcan->State == HAL_FDCAN_STATE_READY)
2616 {
2617 /* Change FDCAN peripheral state */
2618 hfdcan->State = HAL_FDCAN_STATE_BUSY;
2619
2620 /* Request leave initialisation */
2621 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_INIT);
2622
2623 /* Reset the FDCAN ErrorCode */
2624 hfdcan->ErrorCode = HAL_FDCAN_ERROR_NONE;
2625
2626 /* Return function status */
2627 return HAL_OK;
2628 }
2629 else
2630 {
2631 /* Update error code */
2632 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
2633
2634 return HAL_ERROR;
2635 }
2636 }
2637
2638 /**
2639 * @brief Stop the FDCAN module and enable access to configuration registers.
2640 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2641 * the configuration information for the specified FDCAN.
2642 * @retval HAL status
2643 */
HAL_FDCAN_Stop(FDCAN_HandleTypeDef * hfdcan)2644 HAL_StatusTypeDef HAL_FDCAN_Stop(FDCAN_HandleTypeDef *hfdcan)
2645 {
2646 uint32_t Counter = 0U;
2647
2648 if (hfdcan->State == HAL_FDCAN_STATE_BUSY)
2649 {
2650 /* Request initialisation */
2651 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_INIT);
2652
2653 /* Wait until the INIT bit into CCCR register is set */
2654 while ((hfdcan->Instance->CCCR & FDCAN_CCCR_INIT) == 0U)
2655 {
2656 /* Check for the Timeout */
2657 if (Counter > FDCAN_TIMEOUT_COUNT)
2658 {
2659 /* Update error code */
2660 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
2661
2662 /* Change FDCAN state */
2663 hfdcan->State = HAL_FDCAN_STATE_ERROR;
2664
2665 return HAL_ERROR;
2666 }
2667
2668 /* Increment counter */
2669 Counter++;
2670 }
2671
2672 /* Reset counter */
2673 Counter = 0U;
2674
2675 /* Exit from Sleep mode */
2676 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_CSR);
2677
2678 /* Wait until FDCAN exits sleep mode */
2679 while ((hfdcan->Instance->CCCR & FDCAN_CCCR_CSA) == FDCAN_CCCR_CSA)
2680 {
2681 /* Check for the Timeout */
2682 if (Counter > FDCAN_TIMEOUT_COUNT)
2683 {
2684 /* Update error code */
2685 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
2686
2687 /* Change FDCAN state */
2688 hfdcan->State = HAL_FDCAN_STATE_ERROR;
2689
2690 return HAL_ERROR;
2691 }
2692
2693 /* Increment counter */
2694 Counter++;
2695 }
2696
2697 /* Enable configuration change */
2698 SET_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_CCE);
2699
2700 /* Reset Latest Tx FIFO/Queue Request Buffer Index */
2701 hfdcan->LatestTxFifoQRequest = 0U;
2702
2703 /* Change FDCAN peripheral state */
2704 hfdcan->State = HAL_FDCAN_STATE_READY;
2705
2706 /* Return function status */
2707 return HAL_OK;
2708 }
2709 else
2710 {
2711 /* Update error code */
2712 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_STARTED;
2713
2714 return HAL_ERROR;
2715 }
2716 }
2717
2718 /**
2719 * @brief Add a message to the Tx FIFO/Queue and activate the corresponding transmission request
2720 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2721 * the configuration information for the specified FDCAN.
2722 * @param pTxHeader pointer to a FDCAN_TxHeaderTypeDef structure.
2723 * @param pTxData pointer to a buffer containing the payload of the Tx frame.
2724 * @retval HAL status
2725 */
HAL_FDCAN_AddMessageToTxFifoQ(FDCAN_HandleTypeDef * hfdcan,const FDCAN_TxHeaderTypeDef * pTxHeader,const uint8_t * pTxData)2726 HAL_StatusTypeDef HAL_FDCAN_AddMessageToTxFifoQ(FDCAN_HandleTypeDef *hfdcan, const FDCAN_TxHeaderTypeDef *pTxHeader,
2727 const uint8_t *pTxData)
2728 {
2729 uint32_t PutIndex;
2730
2731 /* Check function parameters */
2732 assert_param(IS_FDCAN_ID_TYPE(pTxHeader->IdType));
2733 if (pTxHeader->IdType == FDCAN_STANDARD_ID)
2734 {
2735 assert_param(IS_FDCAN_MAX_VALUE(pTxHeader->Identifier, 0x7FFU));
2736 }
2737 else /* pTxHeader->IdType == FDCAN_EXTENDED_ID */
2738 {
2739 assert_param(IS_FDCAN_MAX_VALUE(pTxHeader->Identifier, 0x1FFFFFFFU));
2740 }
2741 assert_param(IS_FDCAN_FRAME_TYPE(pTxHeader->TxFrameType));
2742 assert_param(IS_FDCAN_DLC(pTxHeader->DataLength));
2743 assert_param(IS_FDCAN_ESI(pTxHeader->ErrorStateIndicator));
2744 assert_param(IS_FDCAN_BRS(pTxHeader->BitRateSwitch));
2745 assert_param(IS_FDCAN_FDF(pTxHeader->FDFormat));
2746 assert_param(IS_FDCAN_EFC(pTxHeader->TxEventFifoControl));
2747 assert_param(IS_FDCAN_MAX_VALUE(pTxHeader->MessageMarker, 0xFFU));
2748
2749 if (hfdcan->State == HAL_FDCAN_STATE_BUSY)
2750 {
2751 /* Check that the Tx FIFO/Queue has an allocated area into the RAM */
2752 if ((hfdcan->Instance->TXBC & FDCAN_TXBC_TFQS) == 0U)
2753 {
2754 /* Update error code */
2755 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
2756
2757 return HAL_ERROR;
2758 }
2759
2760 /* Check that the Tx FIFO/Queue is not full */
2761 if ((hfdcan->Instance->TXFQS & FDCAN_TXFQS_TFQF) != 0U)
2762 {
2763 /* Update error code */
2764 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_FIFO_FULL;
2765
2766 return HAL_ERROR;
2767 }
2768 else
2769 {
2770 /* Retrieve the Tx FIFO PutIndex */
2771 PutIndex = ((hfdcan->Instance->TXFQS & FDCAN_TXFQS_TFQPI) >> FDCAN_TXFQS_TFQPI_Pos);
2772
2773 /* Add the message to the Tx FIFO/Queue */
2774 FDCAN_CopyMessageToRAM(hfdcan, pTxHeader, pTxData, PutIndex);
2775
2776 /* Activate the corresponding transmission request */
2777 hfdcan->Instance->TXBAR = ((uint32_t)1 << PutIndex);
2778
2779 /* Store the Latest Tx FIFO/Queue Request Buffer Index */
2780 hfdcan->LatestTxFifoQRequest = ((uint32_t)1 << PutIndex);
2781 }
2782
2783 /* Return function status */
2784 return HAL_OK;
2785 }
2786 else
2787 {
2788 /* Update error code */
2789 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_STARTED;
2790
2791 return HAL_ERROR;
2792 }
2793 }
2794
2795 /**
2796 * @brief Add a message to a dedicated Tx buffer
2797 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2798 * the configuration information for the specified FDCAN.
2799 * @param pTxHeader pointer to a FDCAN_TxHeaderTypeDef structure.
2800 * @param pTxData pointer to a buffer containing the payload of the Tx frame.
2801 * @param BufferIndex index of the buffer to be configured.
2802 * This parameter can be a value of @arg FDCAN_Tx_location.
2803 * @retval HAL status
2804 */
HAL_FDCAN_AddMessageToTxBuffer(FDCAN_HandleTypeDef * hfdcan,const FDCAN_TxHeaderTypeDef * pTxHeader,const uint8_t * pTxData,uint32_t BufferIndex)2805 HAL_StatusTypeDef HAL_FDCAN_AddMessageToTxBuffer(FDCAN_HandleTypeDef *hfdcan, const FDCAN_TxHeaderTypeDef *pTxHeader,
2806 const uint8_t *pTxData, uint32_t BufferIndex)
2807 {
2808 HAL_FDCAN_StateTypeDef state = hfdcan->State;
2809
2810 /* Check function parameters */
2811 assert_param(IS_FDCAN_ID_TYPE(pTxHeader->IdType));
2812 if (pTxHeader->IdType == FDCAN_STANDARD_ID)
2813 {
2814 assert_param(IS_FDCAN_MAX_VALUE(pTxHeader->Identifier, 0x7FFU));
2815 }
2816 else /* pTxHeader->IdType == FDCAN_EXTENDED_ID */
2817 {
2818 assert_param(IS_FDCAN_MAX_VALUE(pTxHeader->Identifier, 0x1FFFFFFFU));
2819 }
2820 assert_param(IS_FDCAN_FRAME_TYPE(pTxHeader->TxFrameType));
2821 assert_param(IS_FDCAN_DLC(pTxHeader->DataLength));
2822 assert_param(IS_FDCAN_ESI(pTxHeader->ErrorStateIndicator));
2823 assert_param(IS_FDCAN_BRS(pTxHeader->BitRateSwitch));
2824 assert_param(IS_FDCAN_FDF(pTxHeader->FDFormat));
2825 assert_param(IS_FDCAN_EFC(pTxHeader->TxEventFifoControl));
2826 assert_param(IS_FDCAN_MAX_VALUE(pTxHeader->MessageMarker, 0xFFU));
2827 assert_param(IS_FDCAN_TX_LOCATION(BufferIndex));
2828
2829 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
2830 {
2831 /* Check that the selected buffer has an allocated area into the RAM */
2832 if (POSITION_VAL(BufferIndex) >= ((hfdcan->Instance->TXBC & FDCAN_TXBC_NDTB) >> FDCAN_TXBC_NDTB_Pos))
2833 {
2834 /* Update error code */
2835 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
2836
2837 return HAL_ERROR;
2838 }
2839
2840 /* Check that there is no transmission request pending for the selected buffer */
2841 if ((hfdcan->Instance->TXBRP & BufferIndex) != 0U)
2842 {
2843 /* Update error code */
2844 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PENDING;
2845
2846 return HAL_ERROR;
2847 }
2848 else
2849 {
2850 /* Add the message to the Tx buffer */
2851 FDCAN_CopyMessageToRAM(hfdcan, pTxHeader, pTxData, POSITION_VAL(BufferIndex));
2852 }
2853
2854 /* Return function status */
2855 return HAL_OK;
2856 }
2857 else
2858 {
2859 /* Update error code */
2860 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
2861
2862 return HAL_ERROR;
2863 }
2864 }
2865
2866 /**
2867 * @brief Enable transmission request.
2868 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2869 * the configuration information for the specified FDCAN.
2870 * @param BufferIndex buffer index.
2871 * This parameter can be any combination of @arg FDCAN_Tx_location.
2872 * @retval HAL status
2873 */
HAL_FDCAN_EnableTxBufferRequest(FDCAN_HandleTypeDef * hfdcan,uint32_t BufferIndex)2874 HAL_StatusTypeDef HAL_FDCAN_EnableTxBufferRequest(FDCAN_HandleTypeDef *hfdcan, uint32_t BufferIndex)
2875 {
2876 if (hfdcan->State == HAL_FDCAN_STATE_BUSY)
2877 {
2878 /* Add transmission request */
2879 hfdcan->Instance->TXBAR = BufferIndex;
2880
2881 /* Return function status */
2882 return HAL_OK;
2883 }
2884 else
2885 {
2886 /* Update error code */
2887 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_STARTED;
2888
2889 return HAL_ERROR;
2890 }
2891 }
2892
2893 /**
2894 * @brief Get Tx buffer index of latest Tx FIFO/Queue request
2895 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2896 * the configuration information for the specified FDCAN.
2897 * @retval Tx buffer index of last Tx FIFO/Queue request
2898 * - Any value of @arg FDCAN_Tx_location if Tx request has been submitted.
2899 * - 0 if no Tx FIFO/Queue request have been submitted.
2900 */
HAL_FDCAN_GetLatestTxFifoQRequestBuffer(const FDCAN_HandleTypeDef * hfdcan)2901 uint32_t HAL_FDCAN_GetLatestTxFifoQRequestBuffer(const FDCAN_HandleTypeDef *hfdcan)
2902 {
2903 /* Return Last Tx FIFO/Queue Request Buffer */
2904 return hfdcan->LatestTxFifoQRequest;
2905 }
2906
2907 /**
2908 * @brief Abort transmission request
2909 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2910 * the configuration information for the specified FDCAN.
2911 * @param BufferIndex buffer index.
2912 * This parameter can be any combination of @arg FDCAN_Tx_location.
2913 * @retval HAL status
2914 */
HAL_FDCAN_AbortTxRequest(FDCAN_HandleTypeDef * hfdcan,uint32_t BufferIndex)2915 HAL_StatusTypeDef HAL_FDCAN_AbortTxRequest(FDCAN_HandleTypeDef *hfdcan, uint32_t BufferIndex)
2916 {
2917 if (hfdcan->State == HAL_FDCAN_STATE_BUSY)
2918 {
2919 /* Add cancellation request */
2920 hfdcan->Instance->TXBCR = BufferIndex;
2921
2922 /* Return function status */
2923 return HAL_OK;
2924 }
2925 else
2926 {
2927 /* Update error code */
2928 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_STARTED;
2929
2930 return HAL_ERROR;
2931 }
2932 }
2933
2934 /**
2935 * @brief Get an FDCAN frame from the Rx Buffer/FIFO zone into the message RAM.
2936 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
2937 * the configuration information for the specified FDCAN.
2938 * @param RxLocation Location of the received message to be read.
2939 * This parameter can be a value of @arg FDCAN_Rx_location.
2940 * @param pRxHeader pointer to a FDCAN_RxHeaderTypeDef structure.
2941 * @param pRxData pointer to a buffer where the payload of the Rx frame will be stored.
2942 * @retval HAL status
2943 */
HAL_FDCAN_GetRxMessage(FDCAN_HandleTypeDef * hfdcan,uint32_t RxLocation,FDCAN_RxHeaderTypeDef * pRxHeader,uint8_t * pRxData)2944 HAL_StatusTypeDef HAL_FDCAN_GetRxMessage(FDCAN_HandleTypeDef *hfdcan, uint32_t RxLocation,
2945 FDCAN_RxHeaderTypeDef *pRxHeader, uint8_t *pRxData)
2946 {
2947 uint32_t *RxAddress;
2948 uint8_t *pData;
2949 uint32_t ByteCounter;
2950 uint32_t GetIndex = 0;
2951 HAL_FDCAN_StateTypeDef state = hfdcan->State;
2952
2953 if (state == HAL_FDCAN_STATE_BUSY)
2954 {
2955 if (RxLocation == FDCAN_RX_FIFO0) /* Rx element is assigned to the Rx FIFO 0 */
2956 {
2957 /* Check that the Rx FIFO 0 has an allocated area into the RAM */
2958 if ((hfdcan->Instance->RXF0C & FDCAN_RXF0C_F0S) == 0U)
2959 {
2960 /* Update error code */
2961 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
2962
2963 return HAL_ERROR;
2964 }
2965
2966 /* Check that the Rx FIFO 0 is not empty */
2967 if ((hfdcan->Instance->RXF0S & FDCAN_RXF0S_F0FL) == 0U)
2968 {
2969 /* Update error code */
2970 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_FIFO_EMPTY;
2971
2972 return HAL_ERROR;
2973 }
2974 else
2975 {
2976 /* Check that the Rx FIFO 0 is full & overwrite mode is on */
2977 if (((hfdcan->Instance->RXF0S & FDCAN_RXF0S_F0F) >> FDCAN_RXF0S_F0F_Pos) == 1U)
2978 {
2979 if (((hfdcan->Instance->RXF0C & FDCAN_RXF0C_F0OM) >> FDCAN_RXF0C_F0OM_Pos) == FDCAN_RX_FIFO_OVERWRITE)
2980 {
2981 /* When overwrite status is on discard first message in FIFO */
2982 GetIndex = 1U;
2983 }
2984 }
2985
2986 /* Calculate Rx FIFO 0 element index */
2987 GetIndex += ((hfdcan->Instance->RXF0S & FDCAN_RXF0S_F0GI) >> FDCAN_RXF0S_F0GI_Pos);
2988
2989 /* Calculate Rx FIFO 0 element address */
2990 RxAddress = (uint32_t *)(hfdcan->msgRam.RxFIFO0SA + (GetIndex * hfdcan->Init.RxFifo0ElmtSize * 4U));
2991 }
2992 }
2993 else if (RxLocation == FDCAN_RX_FIFO1) /* Rx element is assigned to the Rx FIFO 1 */
2994 {
2995 /* Check that the Rx FIFO 1 has an allocated area into the RAM */
2996 if ((hfdcan->Instance->RXF1C & FDCAN_RXF1C_F1S) == 0U)
2997 {
2998 /* Update error code */
2999 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
3000
3001 return HAL_ERROR;
3002 }
3003
3004 /* Check that the Rx FIFO 1 is not empty */
3005 if ((hfdcan->Instance->RXF1S & FDCAN_RXF1S_F1FL) == 0U)
3006 {
3007 /* Update error code */
3008 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_FIFO_EMPTY;
3009
3010 return HAL_ERROR;
3011 }
3012 else
3013 {
3014 /* Check that the Rx FIFO 1 is full & overwrite mode is on */
3015 if (((hfdcan->Instance->RXF1S & FDCAN_RXF1S_F1F) >> FDCAN_RXF1S_F1F_Pos) == 1U)
3016 {
3017 if (((hfdcan->Instance->RXF1C & FDCAN_RXF1C_F1OM) >> FDCAN_RXF1C_F1OM_Pos) == FDCAN_RX_FIFO_OVERWRITE)
3018 {
3019 /* When overwrite status is on discard first message in FIFO */
3020 GetIndex = 1U;
3021 }
3022 }
3023
3024 /* Calculate Rx FIFO 1 element index */
3025 GetIndex += ((hfdcan->Instance->RXF1S & FDCAN_RXF1S_F1GI) >> FDCAN_RXF1S_F1GI_Pos);
3026
3027 /* Calculate Rx FIFO 1 element address */
3028 RxAddress = (uint32_t *)(hfdcan->msgRam.RxFIFO1SA + (GetIndex * hfdcan->Init.RxFifo1ElmtSize * 4U));
3029 }
3030 }
3031 else /* Rx element is assigned to a dedicated Rx buffer */
3032 {
3033 /* Check that the selected buffer has an allocated area into the RAM */
3034 if (RxLocation >= hfdcan->Init.RxBuffersNbr)
3035 {
3036 /* Update error code */
3037 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
3038
3039 return HAL_ERROR;
3040 }
3041 else
3042 {
3043 /* Calculate Rx buffer address */
3044 RxAddress = (uint32_t *)(hfdcan->msgRam.RxBufferSA + (RxLocation * hfdcan->Init.RxBufferSize * 4U));
3045 }
3046 }
3047
3048 /* Retrieve IdType */
3049 pRxHeader->IdType = *RxAddress & FDCAN_ELEMENT_MASK_XTD;
3050
3051 /* Retrieve Identifier */
3052 if (pRxHeader->IdType == FDCAN_STANDARD_ID) /* Standard ID element */
3053 {
3054 pRxHeader->Identifier = ((*RxAddress & FDCAN_ELEMENT_MASK_STDID) >> 18U);
3055 }
3056 else /* Extended ID element */
3057 {
3058 pRxHeader->Identifier = (*RxAddress & FDCAN_ELEMENT_MASK_EXTID);
3059 }
3060
3061 /* Retrieve RxFrameType */
3062 pRxHeader->RxFrameType = (*RxAddress & FDCAN_ELEMENT_MASK_RTR);
3063
3064 /* Retrieve ErrorStateIndicator */
3065 pRxHeader->ErrorStateIndicator = (*RxAddress & FDCAN_ELEMENT_MASK_ESI);
3066
3067 /* Increment RxAddress pointer to second word of Rx FIFO element */
3068 RxAddress++;
3069
3070 /* Retrieve RxTimestamp */
3071 pRxHeader->RxTimestamp = (*RxAddress & FDCAN_ELEMENT_MASK_TS);
3072
3073 /* Retrieve DataLength */
3074 pRxHeader->DataLength = ((*RxAddress & FDCAN_ELEMENT_MASK_DLC) >> 16U);
3075
3076 /* Retrieve BitRateSwitch */
3077 pRxHeader->BitRateSwitch = (*RxAddress & FDCAN_ELEMENT_MASK_BRS);
3078
3079 /* Retrieve FDFormat */
3080 pRxHeader->FDFormat = (*RxAddress & FDCAN_ELEMENT_MASK_FDF);
3081
3082 /* Retrieve FilterIndex */
3083 pRxHeader->FilterIndex = ((*RxAddress & FDCAN_ELEMENT_MASK_FIDX) >> 24U);
3084
3085 /* Retrieve NonMatchingFrame */
3086 pRxHeader->IsFilterMatchingFrame = ((*RxAddress & FDCAN_ELEMENT_MASK_ANMF) >> 31U);
3087
3088 /* Increment RxAddress pointer to payload of Rx FIFO element */
3089 RxAddress++;
3090
3091 /* Retrieve Rx payload */
3092 pData = (uint8_t *)RxAddress;
3093 for (ByteCounter = 0; ByteCounter < DLCtoBytes[pRxHeader->DataLength]; ByteCounter++)
3094 {
3095 pRxData[ByteCounter] = pData[ByteCounter];
3096 }
3097
3098 if (RxLocation == FDCAN_RX_FIFO0) /* Rx element is assigned to the Rx FIFO 0 */
3099 {
3100 /* Acknowledge the Rx FIFO 0 that the oldest element is read so that it increments the GetIndex */
3101 hfdcan->Instance->RXF0A = GetIndex;
3102 }
3103 else if (RxLocation == FDCAN_RX_FIFO1) /* Rx element is assigned to the Rx FIFO 1 */
3104 {
3105 /* Acknowledge the Rx FIFO 1 that the oldest element is read so that it increments the GetIndex */
3106 hfdcan->Instance->RXF1A = GetIndex;
3107 }
3108 else /* Rx element is assigned to a dedicated Rx buffer */
3109 {
3110 /* Clear the New Data flag of the current Rx buffer */
3111 if (RxLocation < FDCAN_RX_BUFFER32)
3112 {
3113 hfdcan->Instance->NDAT1 = ((uint32_t)1U << RxLocation);
3114 }
3115 else /* FDCAN_RX_BUFFER32 <= RxLocation <= FDCAN_RX_BUFFER63 */
3116 {
3117 hfdcan->Instance->NDAT2 = ((uint32_t)1U << (RxLocation & 0x1FU));
3118 }
3119 }
3120
3121 /* Return function status */
3122 return HAL_OK;
3123 }
3124 else
3125 {
3126 /* Update error code */
3127 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_STARTED;
3128
3129 return HAL_ERROR;
3130 }
3131 }
3132
3133 /**
3134 * @brief Get an FDCAN Tx event from the Tx Event FIFO zone into the message RAM.
3135 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3136 * the configuration information for the specified FDCAN.
3137 * @param pTxEvent pointer to a FDCAN_TxEventFifoTypeDef structure.
3138 * @retval HAL status
3139 */
HAL_FDCAN_GetTxEvent(FDCAN_HandleTypeDef * hfdcan,FDCAN_TxEventFifoTypeDef * pTxEvent)3140 HAL_StatusTypeDef HAL_FDCAN_GetTxEvent(FDCAN_HandleTypeDef *hfdcan, FDCAN_TxEventFifoTypeDef *pTxEvent)
3141 {
3142 uint32_t *TxEventAddress;
3143 uint32_t GetIndex;
3144 HAL_FDCAN_StateTypeDef state = hfdcan->State;
3145
3146 /* Check function parameters */
3147 assert_param(IS_FDCAN_MIN_VALUE(hfdcan->Init.TxEventsNbr, 1U));
3148
3149 if (state == HAL_FDCAN_STATE_BUSY)
3150 {
3151 /* Check that the Tx Event FIFO has an allocated area into the RAM */
3152 if ((hfdcan->Instance->TXEFC & FDCAN_TXEFC_EFS) == 0U)
3153 {
3154 /* Update error code */
3155 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
3156
3157 return HAL_ERROR;
3158 }
3159
3160 /* Check that the Tx event FIFO is not empty */
3161 if ((hfdcan->Instance->TXEFS & FDCAN_TXEFS_EFFL) == 0U)
3162 {
3163 /* Update error code */
3164 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_FIFO_EMPTY;
3165
3166 return HAL_ERROR;
3167 }
3168
3169 /* Calculate Tx event FIFO element address */
3170 GetIndex = ((hfdcan->Instance->TXEFS & FDCAN_TXEFS_EFGI) >> FDCAN_TXEFS_EFGI_Pos);
3171 TxEventAddress = (uint32_t *)(hfdcan->msgRam.TxEventFIFOSA + (GetIndex * 2U * 4U));
3172
3173 /* Retrieve IdType */
3174 pTxEvent->IdType = *TxEventAddress & FDCAN_ELEMENT_MASK_XTD;
3175
3176 /* Retrieve Identifier */
3177 if (pTxEvent->IdType == FDCAN_STANDARD_ID) /* Standard ID element */
3178 {
3179 pTxEvent->Identifier = ((*TxEventAddress & FDCAN_ELEMENT_MASK_STDID) >> 18U);
3180 }
3181 else /* Extended ID element */
3182 {
3183 pTxEvent->Identifier = (*TxEventAddress & FDCAN_ELEMENT_MASK_EXTID);
3184 }
3185
3186 /* Retrieve TxFrameType */
3187 pTxEvent->TxFrameType = (*TxEventAddress & FDCAN_ELEMENT_MASK_RTR);
3188
3189 /* Retrieve ErrorStateIndicator */
3190 pTxEvent->ErrorStateIndicator = (*TxEventAddress & FDCAN_ELEMENT_MASK_ESI);
3191
3192 /* Increment TxEventAddress pointer to second word of Tx Event FIFO element */
3193 TxEventAddress++;
3194
3195 /* Retrieve TxTimestamp */
3196 pTxEvent->TxTimestamp = (*TxEventAddress & FDCAN_ELEMENT_MASK_TS);
3197
3198 /* Retrieve DataLength */
3199 pTxEvent->DataLength = ((*TxEventAddress & FDCAN_ELEMENT_MASK_DLC) >> 16U);
3200
3201 /* Retrieve BitRateSwitch */
3202 pTxEvent->BitRateSwitch = (*TxEventAddress & FDCAN_ELEMENT_MASK_BRS);
3203
3204 /* Retrieve FDFormat */
3205 pTxEvent->FDFormat = (*TxEventAddress & FDCAN_ELEMENT_MASK_FDF);
3206
3207 /* Retrieve EventType */
3208 pTxEvent->EventType = (*TxEventAddress & FDCAN_ELEMENT_MASK_ET);
3209
3210 /* Retrieve MessageMarker */
3211 pTxEvent->MessageMarker = ((*TxEventAddress & FDCAN_ELEMENT_MASK_MM) >> 24U);
3212
3213 /* Acknowledge the Tx Event FIFO that the oldest element is read so that it increments the GetIndex */
3214 hfdcan->Instance->TXEFA = GetIndex;
3215
3216 /* Return function status */
3217 return HAL_OK;
3218 }
3219 else
3220 {
3221 /* Update error code */
3222 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_STARTED;
3223
3224 return HAL_ERROR;
3225 }
3226 }
3227
3228 /**
3229 * @brief Get high priority message status.
3230 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3231 * the configuration information for the specified FDCAN.
3232 * @param HpMsgStatus pointer to an FDCAN_HpMsgStatusTypeDef structure.
3233 * @retval HAL status
3234 */
HAL_FDCAN_GetHighPriorityMessageStatus(const FDCAN_HandleTypeDef * hfdcan,FDCAN_HpMsgStatusTypeDef * HpMsgStatus)3235 HAL_StatusTypeDef HAL_FDCAN_GetHighPriorityMessageStatus(const FDCAN_HandleTypeDef *hfdcan,
3236 FDCAN_HpMsgStatusTypeDef *HpMsgStatus)
3237 {
3238 HpMsgStatus->FilterList = ((hfdcan->Instance->HPMS & FDCAN_HPMS_FLST) >> FDCAN_HPMS_FLST_Pos);
3239 HpMsgStatus->FilterIndex = ((hfdcan->Instance->HPMS & FDCAN_HPMS_FIDX) >> FDCAN_HPMS_FIDX_Pos);
3240 HpMsgStatus->MessageStorage = (hfdcan->Instance->HPMS & FDCAN_HPMS_MSI);
3241 HpMsgStatus->MessageIndex = (hfdcan->Instance->HPMS & FDCAN_HPMS_BIDX);
3242
3243 /* Return function status */
3244 return HAL_OK;
3245 }
3246
3247 /**
3248 * @brief Get protocol status.
3249 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3250 * the configuration information for the specified FDCAN.
3251 * @param ProtocolStatus pointer to an FDCAN_ProtocolStatusTypeDef structure.
3252 * @retval HAL status
3253 */
HAL_FDCAN_GetProtocolStatus(const FDCAN_HandleTypeDef * hfdcan,FDCAN_ProtocolStatusTypeDef * ProtocolStatus)3254 HAL_StatusTypeDef HAL_FDCAN_GetProtocolStatus(const FDCAN_HandleTypeDef *hfdcan,
3255 FDCAN_ProtocolStatusTypeDef *ProtocolStatus)
3256 {
3257 uint32_t StatusReg;
3258
3259 /* Read the protocol status register */
3260 StatusReg = READ_REG(hfdcan->Instance->PSR);
3261
3262 /* Fill the protocol status structure */
3263 ProtocolStatus->LastErrorCode = (StatusReg & FDCAN_PSR_LEC);
3264 ProtocolStatus->DataLastErrorCode = ((StatusReg & FDCAN_PSR_DLEC) >> FDCAN_PSR_DLEC_Pos);
3265 ProtocolStatus->Activity = (StatusReg & FDCAN_PSR_ACT);
3266 ProtocolStatus->ErrorPassive = ((StatusReg & FDCAN_PSR_EP) >> FDCAN_PSR_EP_Pos);
3267 ProtocolStatus->Warning = ((StatusReg & FDCAN_PSR_EW) >> FDCAN_PSR_EW_Pos);
3268 ProtocolStatus->BusOff = ((StatusReg & FDCAN_PSR_BO) >> FDCAN_PSR_BO_Pos);
3269 ProtocolStatus->RxESIflag = ((StatusReg & FDCAN_PSR_RESI) >> FDCAN_PSR_RESI_Pos);
3270 ProtocolStatus->RxBRSflag = ((StatusReg & FDCAN_PSR_RBRS) >> FDCAN_PSR_RBRS_Pos);
3271 ProtocolStatus->RxFDFflag = ((StatusReg & FDCAN_PSR_REDL) >> FDCAN_PSR_REDL_Pos);
3272 ProtocolStatus->ProtocolException = ((StatusReg & FDCAN_PSR_PXE) >> FDCAN_PSR_PXE_Pos);
3273 ProtocolStatus->TDCvalue = ((StatusReg & FDCAN_PSR_TDCV) >> FDCAN_PSR_TDCV_Pos);
3274
3275 /* Return function status */
3276 return HAL_OK;
3277 }
3278
3279 /**
3280 * @brief Get error counter values.
3281 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3282 * the configuration information for the specified FDCAN.
3283 * @param ErrorCounters pointer to an FDCAN_ErrorCountersTypeDef structure.
3284 * @retval HAL status
3285 */
HAL_FDCAN_GetErrorCounters(const FDCAN_HandleTypeDef * hfdcan,FDCAN_ErrorCountersTypeDef * ErrorCounters)3286 HAL_StatusTypeDef HAL_FDCAN_GetErrorCounters(const FDCAN_HandleTypeDef *hfdcan,
3287 FDCAN_ErrorCountersTypeDef *ErrorCounters)
3288 {
3289 uint32_t CountersReg;
3290
3291 /* Read the error counters register */
3292 CountersReg = READ_REG(hfdcan->Instance->ECR);
3293
3294 /* Fill the error counters structure */
3295 ErrorCounters->TxErrorCnt = ((CountersReg & FDCAN_ECR_TEC) >> FDCAN_ECR_TEC_Pos);
3296 ErrorCounters->RxErrorCnt = ((CountersReg & FDCAN_ECR_REC) >> FDCAN_ECR_REC_Pos);
3297 ErrorCounters->RxErrorPassive = ((CountersReg & FDCAN_ECR_RP) >> FDCAN_ECR_RP_Pos);
3298 ErrorCounters->ErrorLogging = ((CountersReg & FDCAN_ECR_CEL) >> FDCAN_ECR_CEL_Pos);
3299
3300 /* Return function status */
3301 return HAL_OK;
3302 }
3303
3304 /**
3305 * @brief Check if a new message is received in the selected Rx buffer.
3306 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3307 * the configuration information for the specified FDCAN.
3308 * @param RxBufferIndex Rx buffer index.
3309 * This parameter must be a number between 0 and 63.
3310 * @retval Status
3311 * - 0 : No new message on RxBufferIndex.
3312 * - 1 : New message received on RxBufferIndex.
3313 */
HAL_FDCAN_IsRxBufferMessageAvailable(FDCAN_HandleTypeDef * hfdcan,uint32_t RxBufferIndex)3314 uint32_t HAL_FDCAN_IsRxBufferMessageAvailable(FDCAN_HandleTypeDef *hfdcan, uint32_t RxBufferIndex)
3315 {
3316 /* Check function parameters */
3317 assert_param(IS_FDCAN_MAX_VALUE(RxBufferIndex, 63U));
3318 uint32_t NewData1 = hfdcan->Instance->NDAT1;
3319 uint32_t NewData2 = hfdcan->Instance->NDAT2;
3320
3321 /* Check new message reception on the selected buffer */
3322 if (((RxBufferIndex < 32U) && ((NewData1 & (uint32_t)((uint32_t)1 << RxBufferIndex)) == 0U)) ||
3323 ((RxBufferIndex >= 32U) && ((NewData2 & (uint32_t)((uint32_t)1 << (RxBufferIndex & 0x1FU))) == 0U)))
3324 {
3325 return 0;
3326 }
3327
3328 /* Clear the New Data flag of the current Rx buffer */
3329 if (RxBufferIndex < 32U)
3330 {
3331 hfdcan->Instance->NDAT1 = ((uint32_t)1 << RxBufferIndex);
3332 }
3333 else /* 32 <= RxBufferIndex <= 63 */
3334 {
3335 hfdcan->Instance->NDAT2 = ((uint32_t)1 << (RxBufferIndex & 0x1FU));
3336 }
3337
3338 return 1;
3339 }
3340
3341 /**
3342 * @brief Check if a transmission request is pending on the selected Tx buffer.
3343 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3344 * the configuration information for the specified FDCAN.
3345 * @param TxBufferIndex Tx buffer index.
3346 * This parameter can be any combination of @arg FDCAN_Tx_location.
3347 * @retval Status
3348 * - 0 : No pending transmission request on TxBufferIndex.
3349 * - 1 : Pending transmission request on TxBufferIndex.
3350 */
HAL_FDCAN_IsTxBufferMessagePending(const FDCAN_HandleTypeDef * hfdcan,uint32_t TxBufferIndex)3351 uint32_t HAL_FDCAN_IsTxBufferMessagePending(const FDCAN_HandleTypeDef *hfdcan, uint32_t TxBufferIndex)
3352 {
3353 /* Check pending transmission request on the selected buffer */
3354 if ((hfdcan->Instance->TXBRP & TxBufferIndex) == 0U)
3355 {
3356 return 0;
3357 }
3358 return 1;
3359 }
3360
3361 /**
3362 * @brief Return Rx FIFO fill level.
3363 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3364 * the configuration information for the specified FDCAN.
3365 * @param RxFifo Rx FIFO.
3366 * This parameter can be one of the following values:
3367 * @arg FDCAN_RX_FIFO0: Rx FIFO 0
3368 * @arg FDCAN_RX_FIFO1: Rx FIFO 1
3369 * @retval Rx FIFO fill level.
3370 */
HAL_FDCAN_GetRxFifoFillLevel(const FDCAN_HandleTypeDef * hfdcan,uint32_t RxFifo)3371 uint32_t HAL_FDCAN_GetRxFifoFillLevel(const FDCAN_HandleTypeDef *hfdcan, uint32_t RxFifo)
3372 {
3373 uint32_t FillLevel;
3374
3375 /* Check function parameters */
3376 assert_param(IS_FDCAN_RX_FIFO(RxFifo));
3377
3378 if (RxFifo == FDCAN_RX_FIFO0)
3379 {
3380 FillLevel = hfdcan->Instance->RXF0S & FDCAN_RXF0S_F0FL;
3381 }
3382 else /* RxFifo == FDCAN_RX_FIFO1 */
3383 {
3384 FillLevel = hfdcan->Instance->RXF1S & FDCAN_RXF1S_F1FL;
3385 }
3386
3387 /* Return Rx FIFO fill level */
3388 return FillLevel;
3389 }
3390
3391 /**
3392 * @brief Return Tx FIFO free level: number of consecutive free Tx FIFO
3393 * elements starting from Tx FIFO GetIndex.
3394 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3395 * the configuration information for the specified FDCAN.
3396 * @retval Tx FIFO free level.
3397 */
HAL_FDCAN_GetTxFifoFreeLevel(const FDCAN_HandleTypeDef * hfdcan)3398 uint32_t HAL_FDCAN_GetTxFifoFreeLevel(const FDCAN_HandleTypeDef *hfdcan)
3399 {
3400 uint32_t FreeLevel;
3401
3402 FreeLevel = hfdcan->Instance->TXFQS & FDCAN_TXFQS_TFFL;
3403
3404 /* Return Tx FIFO free level */
3405 return FreeLevel;
3406 }
3407
3408 /**
3409 * @brief Check if the FDCAN peripheral entered Restricted Operation Mode.
3410 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3411 * the configuration information for the specified FDCAN.
3412 * @retval Status
3413 * - 0 : Normal FDCAN operation.
3414 * - 1 : Restricted Operation Mode active.
3415 */
HAL_FDCAN_IsRestrictedOperationMode(const FDCAN_HandleTypeDef * hfdcan)3416 uint32_t HAL_FDCAN_IsRestrictedOperationMode(const FDCAN_HandleTypeDef *hfdcan)
3417 {
3418 uint32_t OperationMode;
3419
3420 /* Get Operation Mode */
3421 OperationMode = ((hfdcan->Instance->CCCR & FDCAN_CCCR_ASM) >> FDCAN_CCCR_ASM_Pos);
3422
3423 return OperationMode;
3424 }
3425
3426 /**
3427 * @brief Exit Restricted Operation Mode.
3428 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3429 * the configuration information for the specified FDCAN.
3430 * @retval HAL status
3431 */
HAL_FDCAN_ExitRestrictedOperationMode(FDCAN_HandleTypeDef * hfdcan)3432 HAL_StatusTypeDef HAL_FDCAN_ExitRestrictedOperationMode(FDCAN_HandleTypeDef *hfdcan)
3433 {
3434 HAL_FDCAN_StateTypeDef state = hfdcan->State;
3435
3436 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
3437 {
3438 /* Exit Restricted Operation mode */
3439 CLEAR_BIT(hfdcan->Instance->CCCR, FDCAN_CCCR_ASM);
3440
3441 /* Return function status */
3442 return HAL_OK;
3443 }
3444 else
3445 {
3446 /* Update error code */
3447 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
3448
3449 return HAL_ERROR;
3450 }
3451 }
3452
3453 /**
3454 * @}
3455 */
3456
3457 /** @defgroup FDCAN_Exported_Functions_Group4 TT Configuration and control functions
3458 * @brief TT Configuration and control functions
3459 *
3460 @verbatim
3461 ==============================================================================
3462 ##### TT Configuration and control functions #####
3463 ==============================================================================
3464 [..] This section provides functions allowing to:
3465 (+) HAL_FDCAN_TT_ConfigOperation : Initialize TT operation parameters
3466 (+) HAL_FDCAN_TT_ConfigReferenceMessage : Configure the reference message
3467 (+) HAL_FDCAN_TT_ConfigTrigger : Configure the FDCAN trigger
3468 (+) HAL_FDCAN_TT_SetGlobalTime : Schedule global time adjustment
3469 (+) HAL_FDCAN_TT_SetClockSynchronization : Schedule TUR numerator update
3470 (+) HAL_FDCAN_TT_ConfigStopWatch : Configure stop watch source and polarity
3471 (+) HAL_FDCAN_TT_ConfigRegisterTimeMark : Configure register time mark pulse generation
3472 (+) HAL_FDCAN_TT_EnableRegisterTimeMarkPulse : Enable register time mark pulse generation
3473 (+) HAL_FDCAN_TT_DisableRegisterTimeMarkPulse : Disable register time mark pulse generation
3474 (+) HAL_FDCAN_TT_EnableTriggerTimeMarkPulse : Enable trigger time mark pulse generation
3475 (+) HAL_FDCAN_TT_DisableTriggerTimeMarkPulse : Disable trigger time mark pulse generation
3476 (+) HAL_FDCAN_TT_EnableHardwareGapControl : Enable gap control by input pin fdcan1_evt
3477 (+) HAL_FDCAN_TT_DisableHardwareGapControl : Disable gap control by input pin fdcan1_evt
3478 (+) HAL_FDCAN_TT_EnableTimeMarkGapControl : Enable gap control (finish only) by register time mark IT
3479 (+) HAL_FDCAN_TT_DisableTimeMarkGapControl : Disable gap control by register time mark interrupt
3480 (+) HAL_FDCAN_TT_SetNextIsGap : Transmit next reference message with Next_is_Gap = "1"
3481 (+) HAL_FDCAN_TT_SetEndOfGap : Finish a Gap by requesting start of reference message
3482 (+) HAL_FDCAN_TT_ConfigExternalSyncPhase : Configure target phase used for external synchronization
3483 (+) HAL_FDCAN_TT_EnableExternalSynchronization : Synchronize the phase of the FDCAN schedule to an external
3484 schedule
3485 (+) HAL_FDCAN_TT_DisableExternalSynchronization : Disable external schedule synchronization
3486 (+) HAL_FDCAN_TT_GetOperationStatus : Get TT operation status
3487
3488 @endverbatim
3489 * @{
3490 */
3491
3492 /**
3493 * @brief Initialize TT operation parameters.
3494 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3495 * the configuration information for the specified FDCAN.
3496 * @param pTTParams pointer to a FDCAN_TT_ConfigTypeDef structure.
3497 * @retval HAL status
3498 */
HAL_FDCAN_TT_ConfigOperation(FDCAN_HandleTypeDef * hfdcan,const FDCAN_TT_ConfigTypeDef * pTTParams)3499 HAL_StatusTypeDef HAL_FDCAN_TT_ConfigOperation(FDCAN_HandleTypeDef *hfdcan, const FDCAN_TT_ConfigTypeDef *pTTParams)
3500 {
3501 uint32_t tickstart;
3502 uint32_t RAMcounter;
3503 uint32_t StartAddress;
3504
3505 /* Check function parameters */
3506 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
3507 assert_param(IS_FDCAN_TT_TUR_NUMERATOR(pTTParams->TURNumerator));
3508 assert_param(IS_FDCAN_TT_TUR_DENOMINATOR(pTTParams->TURDenominator));
3509 assert_param(IS_FDCAN_TT_TIME_MASTER(pTTParams->TimeMaster));
3510 assert_param(IS_FDCAN_MAX_VALUE(pTTParams->SyncDevLimit, 7U));
3511 assert_param(IS_FDCAN_MAX_VALUE(pTTParams->InitRefTrigOffset, 127U));
3512 assert_param(IS_FDCAN_MAX_VALUE(pTTParams->TriggerMemoryNbr, 64U));
3513 assert_param(IS_FDCAN_TT_CYCLE_START_SYNC(pTTParams->CycleStartSync));
3514 assert_param(IS_FDCAN_TT_STOP_WATCH_TRIGGER(pTTParams->StopWatchTrigSel));
3515 assert_param(IS_FDCAN_TT_EVENT_TRIGGER(pTTParams->EventTrigSel));
3516 if (pTTParams->TimeMaster == FDCAN_TT_POTENTIAL_MASTER)
3517 {
3518 assert_param(IS_FDCAN_TT_BASIC_CYCLES_NUMBER(pTTParams->BasicCyclesNbr));
3519 }
3520 if (pTTParams->OperationMode != FDCAN_TT_COMMUNICATION_LEVEL0)
3521 {
3522 assert_param(IS_FDCAN_TT_OPERATION(pTTParams->GapEnable));
3523 assert_param(IS_FDCAN_MAX_VALUE(pTTParams->AppWdgLimit, 255U));
3524 assert_param(IS_FDCAN_TT_EVENT_TRIGGER_POLARITY(pTTParams->EvtTrigPolarity));
3525 assert_param(IS_FDCAN_TT_TX_ENABLE_WINDOW(pTTParams->TxEnableWindow));
3526 assert_param(IS_FDCAN_MAX_VALUE(pTTParams->ExpTxTrigNbr, 4095U));
3527 }
3528 if (pTTParams->OperationMode != FDCAN_TT_COMMUNICATION_LEVEL1)
3529 {
3530 assert_param(IS_FDCAN_TT_TUR_LEVEL_0_2(pTTParams->TURNumerator, pTTParams->TURDenominator));
3531 assert_param(IS_FDCAN_TT_EXTERNAL_CLK_SYNC(pTTParams->ExternalClkSync));
3532 assert_param(IS_FDCAN_TT_GLOBAL_TIME_FILTERING(pTTParams->GlobalTimeFilter));
3533 assert_param(IS_FDCAN_TT_AUTO_CLK_CALIBRATION(pTTParams->ClockCalibration));
3534 }
3535 else
3536 {
3537 assert_param(IS_FDCAN_TT_TUR_LEVEL_1(pTTParams->TURNumerator, pTTParams->TURDenominator));
3538 }
3539
3540 if (hfdcan->State == HAL_FDCAN_STATE_READY)
3541 {
3542 /* Stop local time in order to enable write access to the other bits of TURCF register */
3543 CLEAR_BIT(hfdcan->ttcan->TURCF, FDCAN_TURCF_ELT);
3544
3545 /* Get tick */
3546 tickstart = HAL_GetTick();
3547
3548 /* Wait until the ELT bit into TURCF register is reset */
3549 while ((hfdcan->ttcan->TURCF & FDCAN_TURCF_ELT) != 0U)
3550 {
3551 /* Check for the Timeout */
3552 if ((HAL_GetTick() - tickstart) > FDCAN_TIMEOUT_VALUE)
3553 {
3554 /* Update error code */
3555 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
3556
3557 /* Change FDCAN state */
3558 hfdcan->State = HAL_FDCAN_STATE_ERROR;
3559
3560 return HAL_ERROR;
3561 }
3562 }
3563
3564 /* Configure TUR (Time Unit Ratio) */
3565 MODIFY_REG(hfdcan->ttcan->TURCF,
3566 (FDCAN_TURCF_NCL | FDCAN_TURCF_DC),
3567 (((pTTParams->TURNumerator - 0x10000U) << FDCAN_TURCF_NCL_Pos) |
3568 (pTTParams->TURDenominator << FDCAN_TURCF_DC_Pos)));
3569
3570 /* Enable local time */
3571 SET_BIT(hfdcan->ttcan->TURCF, FDCAN_TURCF_ELT);
3572
3573 /* Configure TT operation */
3574 MODIFY_REG(hfdcan->ttcan->TTOCF,
3575 (FDCAN_TTOCF_OM | FDCAN_TTOCF_TM | FDCAN_TTOCF_LDSDL | FDCAN_TTOCF_IRTO),
3576 (pTTParams->OperationMode | \
3577 pTTParams->TimeMaster | \
3578 (pTTParams->SyncDevLimit << FDCAN_TTOCF_LDSDL_Pos) | \
3579 (pTTParams->InitRefTrigOffset << FDCAN_TTOCF_IRTO_Pos)));
3580 if (pTTParams->OperationMode != FDCAN_TT_COMMUNICATION_LEVEL0)
3581 {
3582 MODIFY_REG(hfdcan->ttcan->TTOCF,
3583 (FDCAN_TTOCF_GEN | FDCAN_TTOCF_AWL | FDCAN_TTOCF_EVTP),
3584 (pTTParams->GapEnable | \
3585 (pTTParams->AppWdgLimit << FDCAN_TTOCF_AWL_Pos) | \
3586 pTTParams->EvtTrigPolarity));
3587 }
3588 if (pTTParams->OperationMode != FDCAN_TT_COMMUNICATION_LEVEL1)
3589 {
3590 MODIFY_REG(hfdcan->ttcan->TTOCF,
3591 (FDCAN_TTOCF_EECS | FDCAN_TTOCF_EGTF | FDCAN_TTOCF_ECC),
3592 (pTTParams->ExternalClkSync | \
3593 pTTParams->GlobalTimeFilter | \
3594 pTTParams->ClockCalibration));
3595 }
3596
3597 /* Configure system matrix limits */
3598 MODIFY_REG(hfdcan->ttcan->TTMLM, FDCAN_TTMLM_CSS, pTTParams->CycleStartSync);
3599 if (pTTParams->OperationMode != FDCAN_TT_COMMUNICATION_LEVEL0)
3600 {
3601 MODIFY_REG(hfdcan->ttcan->TTMLM,
3602 (FDCAN_TTMLM_TXEW | FDCAN_TTMLM_ENTT),
3603 (((pTTParams->TxEnableWindow - 1U) << FDCAN_TTMLM_TXEW_Pos) |
3604 (pTTParams->ExpTxTrigNbr << FDCAN_TTMLM_ENTT_Pos)));
3605 }
3606 if (pTTParams->TimeMaster == FDCAN_TT_POTENTIAL_MASTER)
3607 {
3608 MODIFY_REG(hfdcan->ttcan->TTMLM, FDCAN_TTMLM_CCM, pTTParams->BasicCyclesNbr);
3609 }
3610
3611 /* Configure input triggers: Stop watch and Event */
3612 MODIFY_REG(hfdcan->ttcan->TTTS,
3613 (FDCAN_TTTS_SWTSEL | FDCAN_TTTS_EVTSEL),
3614 (pTTParams->StopWatchTrigSel | pTTParams->EventTrigSel));
3615
3616 /* Configure trigger memory start address */
3617 StartAddress = (hfdcan->msgRam.EndAddress - SRAMCAN_BASE) / 4U;
3618 MODIFY_REG(hfdcan->ttcan->TTTMC, FDCAN_TTTMC_TMSA, (StartAddress << FDCAN_TTTMC_TMSA_Pos));
3619
3620 /* Trigger memory elements number */
3621 MODIFY_REG(hfdcan->ttcan->TTTMC, FDCAN_TTTMC_TME, (pTTParams->TriggerMemoryNbr << FDCAN_TTTMC_TME_Pos));
3622
3623 /* Recalculate End Address */
3624 hfdcan->msgRam.TTMemorySA = hfdcan->msgRam.EndAddress;
3625 hfdcan->msgRam.EndAddress = hfdcan->msgRam.TTMemorySA + (pTTParams->TriggerMemoryNbr * 2U * 4U);
3626
3627 if (hfdcan->msgRam.EndAddress > FDCAN_MESSAGE_RAM_END_ADDRESS) /* Last address of the Message RAM */
3628 {
3629 /* Update error code.
3630 Message RAM overflow */
3631 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
3632
3633 return HAL_ERROR;
3634 }
3635 else
3636 {
3637 /* Flush the allocated Message RAM area */
3638 for (RAMcounter = hfdcan->msgRam.TTMemorySA; RAMcounter < hfdcan->msgRam.EndAddress; RAMcounter += 4U)
3639 {
3640 *(uint32_t *)(RAMcounter) = 0x00000000;
3641 }
3642 }
3643
3644 /* Return function status */
3645 return HAL_OK;
3646 }
3647 else
3648 {
3649 /* Update error code */
3650 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
3651
3652 return HAL_ERROR;
3653 }
3654 }
3655
3656 /**
3657 * @brief Configure the reference message.
3658 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3659 * the configuration information for the specified FDCAN.
3660 * @param IdType Identifier Type.
3661 * This parameter can be a value of @arg FDCAN_id_type.
3662 * @param Identifier Reference Identifier.
3663 * This parameter must be a number between:
3664 * - 0 and 0x7FF, if IdType is FDCAN_STANDARD_ID
3665 * - 0 and 0x1FFFFFFF, if IdType is FDCAN_EXTENDED_ID
3666 * @param Payload Enable or disable the additional payload.
3667 * This parameter can be a value of @arg FDCAN_TT_Reference_Message_Payload.
3668 * This parameter is ignored in case of time slaves.
3669 * If this parameter is set to FDCAN_TT_REF_MESSAGE_ADD_PAYLOAD, the
3670 * following elements are taken from Tx Buffer 0:
3671 * - MessageMarker
3672 * - TxEventFifoControl
3673 * - DataLength
3674 * - Data Bytes (payload):
3675 * - bytes 2-8, for Level 1
3676 * - bytes 5-8, for Level 0 and Level 2
3677 * @retval HAL status
3678 */
HAL_FDCAN_TT_ConfigReferenceMessage(FDCAN_HandleTypeDef * hfdcan,uint32_t IdType,uint32_t Identifier,uint32_t Payload)3679 HAL_StatusTypeDef HAL_FDCAN_TT_ConfigReferenceMessage(FDCAN_HandleTypeDef *hfdcan, uint32_t IdType,
3680 uint32_t Identifier, uint32_t Payload)
3681 {
3682 /* Check function parameters */
3683 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
3684 assert_param(IS_FDCAN_ID_TYPE(IdType));
3685 if (IdType == FDCAN_STANDARD_ID)
3686 {
3687 assert_param(IS_FDCAN_MAX_VALUE(Identifier, 0x7FFU));
3688 }
3689 else /* IdType == FDCAN_EXTENDED_ID */
3690 {
3691 assert_param(IS_FDCAN_MAX_VALUE(Identifier, 0x1FFFFFFFU));
3692 }
3693 assert_param(IS_FDCAN_TT_REFERENCE_MESSAGE_PAYLOAD(Payload));
3694
3695 if (hfdcan->State == HAL_FDCAN_STATE_READY)
3696 {
3697 /* Configure reference message identifier type, identifier and payload */
3698 if (IdType == FDCAN_EXTENDED_ID)
3699 {
3700 MODIFY_REG(hfdcan->ttcan->TTRMC, (FDCAN_TTRMC_RID | FDCAN_TTRMC_XTD | FDCAN_TTRMC_RMPS),
3701 (Payload | IdType | Identifier));
3702 }
3703 else /* IdType == FDCAN_STANDARD_ID */
3704 {
3705 MODIFY_REG(hfdcan->ttcan->TTRMC, (FDCAN_TTRMC_RID | FDCAN_TTRMC_XTD | FDCAN_TTRMC_RMPS),
3706 (Payload | IdType | (Identifier << 18)));
3707 }
3708
3709 /* Return function status */
3710 return HAL_OK;
3711 }
3712 else
3713 {
3714 /* Update error code */
3715 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
3716
3717 return HAL_ERROR;
3718 }
3719 }
3720
3721 /**
3722 * @brief Configure the FDCAN trigger according to the specified
3723 * parameters in the FDCAN_TriggerTypeDef structure.
3724 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3725 * the configuration information for the specified FDCAN.
3726 * @param sTriggerConfig pointer to an FDCAN_TriggerTypeDef structure that
3727 * contains the trigger configuration information
3728 * @retval HAL status
3729 */
HAL_FDCAN_TT_ConfigTrigger(FDCAN_HandleTypeDef * hfdcan,const FDCAN_TriggerTypeDef * sTriggerConfig)3730 HAL_StatusTypeDef HAL_FDCAN_TT_ConfigTrigger(FDCAN_HandleTypeDef *hfdcan, const FDCAN_TriggerTypeDef *sTriggerConfig)
3731 {
3732 uint32_t CycleCode;
3733 uint32_t MessageNumber;
3734 uint32_t TriggerElementW1;
3735 uint32_t TriggerElementW2;
3736 uint32_t *TriggerAddress;
3737
3738 /* Check function parameters */
3739 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
3740 assert_param(IS_FDCAN_MAX_VALUE(sTriggerConfig->TriggerIndex, 63U));
3741 assert_param(IS_FDCAN_MAX_VALUE(sTriggerConfig->TimeMark, 0xFFFFU));
3742 assert_param(IS_FDCAN_TT_REPEAT_FACTOR(sTriggerConfig->RepeatFactor));
3743 if (sTriggerConfig->RepeatFactor != FDCAN_TT_REPEAT_EVERY_CYCLE)
3744 {
3745 assert_param(IS_FDCAN_MAX_VALUE(sTriggerConfig->StartCycle, (sTriggerConfig->RepeatFactor - 1U)));
3746 }
3747 assert_param(IS_FDCAN_TT_TM_EVENT_INTERNAL(sTriggerConfig->TmEventInt));
3748 assert_param(IS_FDCAN_TT_TM_EVENT_EXTERNAL(sTriggerConfig->TmEventExt));
3749 assert_param(IS_FDCAN_TT_TRIGGER_TYPE(sTriggerConfig->TriggerType));
3750 assert_param(IS_FDCAN_ID_TYPE(sTriggerConfig->FilterType));
3751 if ((sTriggerConfig->TriggerType == FDCAN_TT_TX_TRIGGER_SINGLE) ||
3752 (sTriggerConfig->TriggerType == FDCAN_TT_TX_TRIGGER_CONTINUOUS) ||
3753 (sTriggerConfig->TriggerType == FDCAN_TT_TX_TRIGGER_ARBITRATION) ||
3754 (sTriggerConfig->TriggerType == FDCAN_TT_TX_TRIGGER_MERGED))
3755 {
3756 assert_param(IS_FDCAN_TX_LOCATION(sTriggerConfig->TxBufferIndex));
3757 }
3758 if (sTriggerConfig->TriggerType == FDCAN_TT_RX_TRIGGER)
3759 {
3760 if (sTriggerConfig->FilterType == FDCAN_STANDARD_ID)
3761 {
3762 assert_param(IS_FDCAN_MAX_VALUE(sTriggerConfig->FilterIndex, 63U));
3763 }
3764 else /* sTriggerConfig->FilterType == FDCAN_EXTENDED_ID */
3765 {
3766 assert_param(IS_FDCAN_MAX_VALUE(sTriggerConfig->FilterIndex, 127U));
3767 }
3768 }
3769
3770 if (hfdcan->State == HAL_FDCAN_STATE_READY)
3771 {
3772 /* Calculate cycle code */
3773 if (sTriggerConfig->RepeatFactor == FDCAN_TT_REPEAT_EVERY_CYCLE)
3774 {
3775 CycleCode = FDCAN_TT_REPEAT_EVERY_CYCLE;
3776 }
3777 else /* sTriggerConfig->RepeatFactor != FDCAN_TT_REPEAT_EVERY_CYCLE */
3778 {
3779 CycleCode = sTriggerConfig->RepeatFactor + sTriggerConfig->StartCycle;
3780 }
3781
3782 /* Build first word of trigger element */
3783 TriggerElementW1 = ((sTriggerConfig->TimeMark << 16) | \
3784 (CycleCode << 8) | \
3785 sTriggerConfig->TmEventInt | \
3786 sTriggerConfig->TmEventExt | \
3787 sTriggerConfig->TriggerType);
3788
3789 /* Select message number depending on trigger type (transmission or reception) */
3790 if (sTriggerConfig->TriggerType == FDCAN_TT_RX_TRIGGER)
3791 {
3792 MessageNumber = sTriggerConfig->FilterIndex;
3793 }
3794 else if ((sTriggerConfig->TriggerType == FDCAN_TT_TX_TRIGGER_SINGLE) ||
3795 (sTriggerConfig->TriggerType == FDCAN_TT_TX_TRIGGER_CONTINUOUS) ||
3796 (sTriggerConfig->TriggerType == FDCAN_TT_TX_TRIGGER_ARBITRATION) ||
3797 (sTriggerConfig->TriggerType == FDCAN_TT_TX_TRIGGER_MERGED))
3798 {
3799 MessageNumber = POSITION_VAL(sTriggerConfig->TxBufferIndex);
3800 }
3801 else
3802 {
3803 MessageNumber = 0U;
3804 }
3805
3806 /* Build second word of trigger element */
3807 TriggerElementW2 = ((sTriggerConfig->FilterType >> 7) | (MessageNumber << 16));
3808
3809 /* Calculate trigger address */
3810 TriggerAddress = (uint32_t *)(hfdcan->msgRam.TTMemorySA + (sTriggerConfig->TriggerIndex * 4U * 2U));
3811
3812 /* Write trigger element to the message RAM */
3813 *TriggerAddress = TriggerElementW1;
3814 TriggerAddress++;
3815 *TriggerAddress = TriggerElementW2;
3816
3817 /* Return function status */
3818 return HAL_OK;
3819 }
3820 else
3821 {
3822 /* Update error code */
3823 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_READY;
3824
3825 return HAL_ERROR;
3826 }
3827 }
3828
3829 /**
3830 * @brief Schedule global time adjustment for the next reference message.
3831 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3832 * the configuration information for the specified FDCAN.
3833 * @param TimePreset time preset value.
3834 * This parameter must be a number between:
3835 * - 0x0000 and 0x7FFF, Next_Master_Ref_Mark = Current_Master_Ref_Mark + TimePreset
3836 * or
3837 * - 0x8001 and 0xFFFF, Next_Master_Ref_Mark = Current_Master_Ref_Mark - (0x10000 - TimePreset)
3838 * @retval HAL status
3839 */
HAL_FDCAN_TT_SetGlobalTime(FDCAN_HandleTypeDef * hfdcan,uint32_t TimePreset)3840 HAL_StatusTypeDef HAL_FDCAN_TT_SetGlobalTime(FDCAN_HandleTypeDef *hfdcan, uint32_t TimePreset)
3841 {
3842 uint32_t Counter = 0U;
3843 HAL_FDCAN_StateTypeDef state = hfdcan->State;
3844
3845 /* Check function parameters */
3846 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
3847 assert_param(IS_FDCAN_TT_TIME_PRESET(TimePreset));
3848
3849 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
3850 {
3851 /* Check that the external clock synchronization is enabled */
3852 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_EECS) != FDCAN_TTOCF_EECS)
3853 {
3854 /* Update error code */
3855 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
3856
3857 return HAL_ERROR;
3858 }
3859
3860 /* Check that no global time preset is pending */
3861 if ((hfdcan->ttcan->TTOST & FDCAN_TTOST_WGTD) == FDCAN_TTOST_WGTD)
3862 {
3863 /* Update error code */
3864 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PENDING;
3865
3866 return HAL_ERROR;
3867 }
3868
3869 /* Configure time preset */
3870 MODIFY_REG(hfdcan->ttcan->TTGTP, FDCAN_TTGTP_TP, (TimePreset << FDCAN_TTGTP_TP_Pos));
3871
3872 /* Wait until the LCKC bit into TTOCN register is reset */
3873 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
3874 {
3875 /* Check for the Timeout */
3876 if (Counter > FDCAN_TIMEOUT_COUNT)
3877 {
3878 /* Update error code */
3879 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
3880
3881 /* Change FDCAN state */
3882 hfdcan->State = HAL_FDCAN_STATE_ERROR;
3883
3884 return HAL_ERROR;
3885 }
3886
3887 /* Increment counter */
3888 Counter++;
3889 }
3890
3891 /* Schedule time preset to take effect by the next reference message */
3892 SET_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_SGT);
3893
3894 /* Return function status */
3895 return HAL_OK;
3896 }
3897 else
3898 {
3899 /* Update error code */
3900 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
3901
3902 return HAL_ERROR;
3903 }
3904 }
3905
3906 /**
3907 * @brief Schedule TUR numerator update for the next reference message.
3908 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3909 * the configuration information for the specified FDCAN.
3910 * @param NewTURNumerator new value of the TUR numerator.
3911 * This parameter must be a number between 0x10000 and 0x1FFFF.
3912 * @retval HAL status
3913 */
HAL_FDCAN_TT_SetClockSynchronization(FDCAN_HandleTypeDef * hfdcan,uint32_t NewTURNumerator)3914 HAL_StatusTypeDef HAL_FDCAN_TT_SetClockSynchronization(FDCAN_HandleTypeDef *hfdcan, uint32_t NewTURNumerator)
3915 {
3916 uint32_t Counter = 0U;
3917 HAL_FDCAN_StateTypeDef state = hfdcan->State;
3918
3919 /* Check function parameters */
3920 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
3921 assert_param(IS_FDCAN_TT_TUR_NUMERATOR(NewTURNumerator));
3922
3923 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
3924 {
3925 /* Check that the external clock synchronization is enabled */
3926 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_EECS) != FDCAN_TTOCF_EECS)
3927 {
3928 /* Update error code */
3929 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
3930
3931 return HAL_ERROR;
3932 }
3933
3934 /* Check that no external clock synchronization is pending */
3935 if ((hfdcan->ttcan->TTOST & FDCAN_TTOST_WECS) == FDCAN_TTOST_WECS)
3936 {
3937 /* Update error code */
3938 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PENDING;
3939
3940 return HAL_ERROR;
3941 }
3942
3943 /* Configure new TUR numerator */
3944 MODIFY_REG(hfdcan->ttcan->TURCF, FDCAN_TURCF_NCL, (NewTURNumerator - 0x10000U));
3945
3946 /* Wait until the LCKC bit into TTOCN register is reset */
3947 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
3948 {
3949 /* Check for the Timeout */
3950 if (Counter > FDCAN_TIMEOUT_COUNT)
3951 {
3952 /* Update error code */
3953 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
3954
3955 /* Change FDCAN state */
3956 hfdcan->State = HAL_FDCAN_STATE_ERROR;
3957
3958 return HAL_ERROR;
3959 }
3960
3961 /* Increment counter */
3962 Counter++;
3963 }
3964
3965 /* Schedule TUR numerator update by the next reference message */
3966 SET_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_ECS);
3967
3968 /* Return function status */
3969 return HAL_OK;
3970 }
3971 else
3972 {
3973 /* Update error code */
3974 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
3975
3976 return HAL_ERROR;
3977 }
3978 }
3979
3980 /**
3981 * @brief Configure stop watch source and polarity.
3982 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
3983 * the configuration information for the specified FDCAN.
3984 * @param Source stop watch source.
3985 * This parameter can be a value of @arg FDCAN_TT_stop_watch_source.
3986 * @param Polarity stop watch polarity.
3987 * This parameter can be a value of @arg FDCAN_TT_stop_watch_polarity.
3988 * @retval HAL status
3989 */
HAL_FDCAN_TT_ConfigStopWatch(FDCAN_HandleTypeDef * hfdcan,uint32_t Source,uint32_t Polarity)3990 HAL_StatusTypeDef HAL_FDCAN_TT_ConfigStopWatch(FDCAN_HandleTypeDef *hfdcan, uint32_t Source, uint32_t Polarity)
3991 {
3992 uint32_t Counter = 0U;
3993 HAL_FDCAN_StateTypeDef state = hfdcan->State;
3994
3995 /* Check function parameters */
3996 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
3997 assert_param(IS_FDCAN_TT_STOP_WATCH_SOURCE(Source));
3998 assert_param(IS_FDCAN_TT_STOP_WATCH_POLARITY(Polarity));
3999
4000 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4001 {
4002 /* Wait until the LCKC bit into TTOCN register is reset */
4003 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4004 {
4005 /* Check for the Timeout */
4006 if (Counter > FDCAN_TIMEOUT_COUNT)
4007 {
4008 /* Update error code */
4009 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4010
4011 /* Change FDCAN state */
4012 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4013
4014 return HAL_ERROR;
4015 }
4016
4017 /* Increment counter */
4018 Counter++;
4019 }
4020
4021 /* Select stop watch source and polarity */
4022 MODIFY_REG(hfdcan->ttcan->TTOCN, (FDCAN_TTOCN_SWS | FDCAN_TTOCN_SWP), (Source | Polarity));
4023
4024 /* Return function status */
4025 return HAL_OK;
4026 }
4027 else
4028 {
4029 /* Update error code */
4030 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4031
4032 return HAL_ERROR;
4033 }
4034 }
4035
4036 /**
4037 * @brief Configure register time mark pulse generation.
4038 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4039 * the configuration information for the specified FDCAN.
4040 * @param TimeMarkSource time mark source.
4041 * This parameter can be a value of @arg FDCAN_TT_time_mark_source.
4042 * @param TimeMarkValue time mark value (reference).
4043 * This parameter must be a number between 0 and 0xFFFF.
4044 * @param RepeatFactor repeat factor of the cycle for which the time mark is valid.
4045 * This parameter can be a value of @arg FDCAN_TT_Repeat_Factor.
4046 * @param StartCycle index of the first cycle in which the time mark becomes valid.
4047 * This parameter is ignored if RepeatFactor is set to FDCAN_TT_REPEAT_EVERY_CYCLE.
4048 * This parameter must be a number between 0 and RepeatFactor.
4049 * @retval HAL status
4050 */
HAL_FDCAN_TT_ConfigRegisterTimeMark(FDCAN_HandleTypeDef * hfdcan,uint32_t TimeMarkSource,uint32_t TimeMarkValue,uint32_t RepeatFactor,uint32_t StartCycle)4051 HAL_StatusTypeDef HAL_FDCAN_TT_ConfigRegisterTimeMark(FDCAN_HandleTypeDef *hfdcan,
4052 uint32_t TimeMarkSource, uint32_t TimeMarkValue,
4053 uint32_t RepeatFactor, uint32_t StartCycle)
4054 {
4055 uint32_t Counter = 0U;
4056 uint32_t CycleCode;
4057 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4058
4059 /* Check function parameters */
4060 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4061 assert_param(IS_FDCAN_TT_REGISTER_TIME_MARK_SOURCE(TimeMarkSource));
4062 assert_param(IS_FDCAN_MAX_VALUE(TimeMarkValue, 0xFFFFU));
4063 assert_param(IS_FDCAN_TT_REPEAT_FACTOR(RepeatFactor));
4064 if (RepeatFactor != FDCAN_TT_REPEAT_EVERY_CYCLE)
4065 {
4066 assert_param(IS_FDCAN_MAX_VALUE(StartCycle, (RepeatFactor - 1U)));
4067 }
4068
4069 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4070 {
4071 /* Wait until the LCKC bit into TTOCN register is reset */
4072 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4073 {
4074 /* Check for the Timeout */
4075 if (Counter > FDCAN_TIMEOUT_COUNT)
4076 {
4077 /* Update error code */
4078 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4079
4080 /* Change FDCAN state */
4081 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4082
4083 return HAL_ERROR;
4084 }
4085
4086 /* Increment counter */
4087 Counter++;
4088 }
4089
4090 /* Disable the time mark compare function */
4091 CLEAR_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_TMC);
4092
4093 if (TimeMarkSource != FDCAN_TT_REG_TIMEMARK_DIABLED)
4094 {
4095 /* Calculate cycle code */
4096 if (RepeatFactor == FDCAN_TT_REPEAT_EVERY_CYCLE)
4097 {
4098 CycleCode = FDCAN_TT_REPEAT_EVERY_CYCLE;
4099 }
4100 else /* RepeatFactor != FDCAN_TT_REPEAT_EVERY_CYCLE */
4101 {
4102 CycleCode = RepeatFactor + StartCycle;
4103 }
4104
4105 Counter = 0U;
4106
4107 /* Wait until the LCKM bit into TTTMK register is reset */
4108 while ((hfdcan->ttcan->TTTMK & FDCAN_TTTMK_LCKM) != 0U)
4109 {
4110 /* Check for the Timeout */
4111 if (Counter > FDCAN_TIMEOUT_COUNT)
4112 {
4113 /* Update error code */
4114 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4115
4116 /* Change FDCAN state */
4117 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4118
4119 return HAL_ERROR;
4120 }
4121
4122 /* Increment counter */
4123 Counter++;
4124 }
4125
4126 /* Configure time mark value and cycle code */
4127 hfdcan->ttcan->TTTMK = ((TimeMarkValue << FDCAN_TTTMK_TM_Pos) | (CycleCode << FDCAN_TTTMK_TICC_Pos));
4128
4129 Counter = 0U;
4130
4131 /* Wait until the LCKC bit into TTOCN register is reset */
4132 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4133 {
4134 /* Check for the Timeout */
4135 if (Counter > FDCAN_TIMEOUT_COUNT)
4136 {
4137 /* Update error code */
4138 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4139
4140 /* Change FDCAN state */
4141 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4142
4143 return HAL_ERROR;
4144 }
4145
4146 /* Increment counter */
4147 Counter++;
4148 }
4149
4150 /* Update the register time mark compare source */
4151 MODIFY_REG(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_TMC, TimeMarkSource);
4152 }
4153
4154 /* Return function status */
4155 return HAL_OK;
4156 }
4157 else
4158 {
4159 /* Update error code */
4160 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4161
4162 return HAL_ERROR;
4163 }
4164 }
4165
4166 /**
4167 * @brief Enable register time mark pulse generation.
4168 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4169 * the configuration information for the specified FDCAN.
4170 * @retval HAL status
4171 */
HAL_FDCAN_TT_EnableRegisterTimeMarkPulse(FDCAN_HandleTypeDef * hfdcan)4172 HAL_StatusTypeDef HAL_FDCAN_TT_EnableRegisterTimeMarkPulse(FDCAN_HandleTypeDef *hfdcan)
4173 {
4174 uint32_t Counter = 0U;
4175 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4176
4177 /* Check function parameters */
4178 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4179
4180 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4181 {
4182 /* Wait until the LCKC bit into TTOCN register is reset */
4183 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4184 {
4185 /* Check for the Timeout */
4186 if (Counter > FDCAN_TIMEOUT_COUNT)
4187 {
4188 /* Update error code */
4189 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4190
4191 /* Change FDCAN state */
4192 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4193
4194 return HAL_ERROR;
4195 }
4196
4197 /* Increment counter */
4198 Counter++;
4199 }
4200
4201 /* Enable Register Time Mark Interrupt output on fdcan1_rtp */
4202 SET_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_RTIE);
4203
4204 /* Return function status */
4205 return HAL_OK;
4206 }
4207 else
4208 {
4209 /* Update error code */
4210 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4211
4212 return HAL_ERROR;
4213 }
4214 }
4215
4216 /**
4217 * @brief Disable register time mark pulse generation.
4218 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4219 * the configuration information for the specified FDCAN.
4220 * @retval HAL status
4221 */
HAL_FDCAN_TT_DisableRegisterTimeMarkPulse(FDCAN_HandleTypeDef * hfdcan)4222 HAL_StatusTypeDef HAL_FDCAN_TT_DisableRegisterTimeMarkPulse(FDCAN_HandleTypeDef *hfdcan)
4223 {
4224 uint32_t Counter = 0U;
4225 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4226
4227 /* Check function parameters */
4228 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4229
4230 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4231 {
4232 /* Wait until the LCKC bit into TTOCN register is reset */
4233 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4234 {
4235 /* Check for the Timeout */
4236 if (Counter > FDCAN_TIMEOUT_COUNT)
4237 {
4238 /* Update error code */
4239 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4240
4241 /* Change FDCAN state */
4242 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4243
4244 return HAL_ERROR;
4245 }
4246
4247 /* Increment counter */
4248 Counter++;
4249 }
4250
4251 /* Disable Register Time Mark Interrupt output on fdcan1_rtp */
4252 CLEAR_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_RTIE);
4253
4254 /* Return function status */
4255 return HAL_OK;
4256 }
4257 else
4258 {
4259 /* Update error code */
4260 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4261
4262 return HAL_ERROR;
4263 }
4264 }
4265
4266 /**
4267 * @brief Enable trigger time mark pulse generation.
4268 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4269 * the configuration information for the specified FDCAN.
4270 * @retval HAL status
4271 */
HAL_FDCAN_TT_EnableTriggerTimeMarkPulse(FDCAN_HandleTypeDef * hfdcan)4272 HAL_StatusTypeDef HAL_FDCAN_TT_EnableTriggerTimeMarkPulse(FDCAN_HandleTypeDef *hfdcan)
4273 {
4274 uint32_t Counter = 0U;
4275 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4276
4277 /* Check function parameters */
4278 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4279
4280 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4281 {
4282 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_OM) != FDCAN_TT_COMMUNICATION_LEVEL0)
4283 {
4284 /* Wait until the LCKC bit into TTOCN register is reset */
4285 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4286 {
4287 /* Check for the Timeout */
4288 if (Counter > FDCAN_TIMEOUT_COUNT)
4289 {
4290 /* Update error code */
4291 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4292
4293 /* Change FDCAN state */
4294 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4295
4296 return HAL_ERROR;
4297 }
4298
4299 /* Increment counter */
4300 Counter++;
4301 }
4302
4303 /* Enable Trigger Time Mark Interrupt output on fdcan1_tmp */
4304 SET_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_TTIE);
4305
4306 /* Return function status */
4307 return HAL_OK;
4308 }
4309 else
4310 {
4311 /* Update error code.
4312 Feature not supported for TT Level 0 */
4313 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4314
4315 return HAL_ERROR;
4316 }
4317 }
4318 else
4319 {
4320 /* Update error code */
4321 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4322
4323 return HAL_ERROR;
4324 }
4325 }
4326
4327 /**
4328 * @brief Disable trigger time mark pulse generation.
4329 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4330 * the configuration information for the specified FDCAN.
4331 * @retval HAL status
4332 */
HAL_FDCAN_TT_DisableTriggerTimeMarkPulse(FDCAN_HandleTypeDef * hfdcan)4333 HAL_StatusTypeDef HAL_FDCAN_TT_DisableTriggerTimeMarkPulse(FDCAN_HandleTypeDef *hfdcan)
4334 {
4335 uint32_t Counter = 0U;
4336 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4337
4338 /* Check function parameters */
4339 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4340
4341 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4342 {
4343 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_OM) != FDCAN_TT_COMMUNICATION_LEVEL0)
4344 {
4345 /* Wait until the LCKC bit into TTOCN register is reset */
4346 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4347 {
4348 /* Check for the Timeout */
4349 if (Counter > FDCAN_TIMEOUT_COUNT)
4350 {
4351 /* Update error code */
4352 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4353
4354 /* Change FDCAN state */
4355 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4356
4357 return HAL_ERROR;
4358 }
4359
4360 /* Increment counter */
4361 Counter++;
4362 }
4363
4364 /* Disable Trigger Time Mark Interrupt output on fdcan1_rtp */
4365 CLEAR_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_TTIE);
4366
4367 /* Return function status */
4368 return HAL_OK;
4369 }
4370 else
4371 {
4372 /* Update error code.
4373 Feature not supported for TT Level 0 */
4374 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4375
4376 return HAL_ERROR;
4377 }
4378 }
4379 else
4380 {
4381 /* Update error code */
4382 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4383
4384 return HAL_ERROR;
4385 }
4386 }
4387
4388 /**
4389 * @brief Enable gap control by input pin fdcan1_evt.
4390 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4391 * the configuration information for the specified FDCAN.
4392 * @retval HAL status
4393 */
HAL_FDCAN_TT_EnableHardwareGapControl(FDCAN_HandleTypeDef * hfdcan)4394 HAL_StatusTypeDef HAL_FDCAN_TT_EnableHardwareGapControl(FDCAN_HandleTypeDef *hfdcan)
4395 {
4396 uint32_t Counter = 0U;
4397 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4398
4399 /* Check function parameters */
4400 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4401
4402 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4403 {
4404 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_OM) != FDCAN_TT_COMMUNICATION_LEVEL0)
4405 {
4406 /* Wait until the LCKC bit into TTOCN register is reset */
4407 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4408 {
4409 /* Check for the Timeout */
4410 if (Counter > FDCAN_TIMEOUT_COUNT)
4411 {
4412 /* Update error code */
4413 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4414
4415 /* Change FDCAN state */
4416 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4417
4418 return HAL_ERROR;
4419 }
4420
4421 /* Increment counter */
4422 Counter++;
4423 }
4424
4425 /* Enable gap control by pin fdcan1_evt */
4426 SET_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_GCS);
4427
4428 /* Return function status */
4429 return HAL_OK;
4430 }
4431 else
4432 {
4433 /* Update error code.
4434 Feature not supported for TT Level 0 */
4435 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4436
4437 return HAL_ERROR;
4438 }
4439 }
4440 else
4441 {
4442 /* Update error code */
4443 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4444
4445 return HAL_ERROR;
4446 }
4447 }
4448
4449 /**
4450 * @brief Disable gap control by input pin fdcan1_evt.
4451 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4452 * the configuration information for the specified FDCAN.
4453 * @retval HAL status
4454 */
HAL_FDCAN_TT_DisableHardwareGapControl(FDCAN_HandleTypeDef * hfdcan)4455 HAL_StatusTypeDef HAL_FDCAN_TT_DisableHardwareGapControl(FDCAN_HandleTypeDef *hfdcan)
4456 {
4457 uint32_t Counter = 0U;
4458 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4459
4460 /* Check function parameters */
4461 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4462
4463 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4464 {
4465 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_OM) != FDCAN_TT_COMMUNICATION_LEVEL0)
4466 {
4467 /* Wait until the LCKC bit into TTOCN register is reset */
4468 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4469 {
4470 /* Check for the Timeout */
4471 if (Counter > FDCAN_TIMEOUT_COUNT)
4472 {
4473 /* Update error code */
4474 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4475
4476 /* Change FDCAN state */
4477 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4478
4479 return HAL_ERROR;
4480 }
4481
4482 /* Increment counter */
4483 Counter++;
4484 }
4485
4486 /* Disable gap control by pin fdcan1_evt */
4487 CLEAR_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_GCS);
4488
4489 /* Return function status */
4490 return HAL_OK;
4491 }
4492 else
4493 {
4494 /* Update error code.
4495 Feature not supported for TT Level 0 */
4496 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4497
4498 return HAL_ERROR;
4499 }
4500 }
4501 else
4502 {
4503 /* Update error code */
4504 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4505
4506 return HAL_ERROR;
4507 }
4508 }
4509
4510 /**
4511 * @brief Enable gap control (finish only) by register time mark interrupt.
4512 * The next register time mark interrupt (TTIR.RTMI = "1") will finish
4513 * the Gap and start the reference message.
4514 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4515 * the configuration information for the specified FDCAN.
4516 * @retval HAL status
4517 */
HAL_FDCAN_TT_EnableTimeMarkGapControl(FDCAN_HandleTypeDef * hfdcan)4518 HAL_StatusTypeDef HAL_FDCAN_TT_EnableTimeMarkGapControl(FDCAN_HandleTypeDef *hfdcan)
4519 {
4520 uint32_t Counter = 0U;
4521 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4522
4523 /* Check function parameters */
4524 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4525
4526 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4527 {
4528 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_OM) != FDCAN_TT_COMMUNICATION_LEVEL0)
4529 {
4530 /* Wait until the LCKC bit into TTOCN register is reset */
4531 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4532 {
4533 /* Check for the Timeout */
4534 if (Counter > FDCAN_TIMEOUT_COUNT)
4535 {
4536 /* Update error code */
4537 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4538
4539 /* Change FDCAN state */
4540 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4541
4542 return HAL_ERROR;
4543 }
4544
4545 /* Increment counter */
4546 Counter++;
4547 }
4548
4549 /* Enable gap control by register time mark interrupt */
4550 SET_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_TMG);
4551
4552 /* Return function status */
4553 return HAL_OK;
4554 }
4555 else
4556 {
4557 /* Update error code.
4558 Feature not supported for TT Level 0 */
4559 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4560
4561 return HAL_ERROR;
4562 }
4563 }
4564 else
4565 {
4566 /* Update error code */
4567 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4568
4569 return HAL_ERROR;
4570 }
4571 }
4572
4573 /**
4574 * @brief Disable gap control by register time mark interrupt.
4575 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4576 * the configuration information for the specified FDCAN.
4577 * @retval HAL status
4578 */
HAL_FDCAN_TT_DisableTimeMarkGapControl(FDCAN_HandleTypeDef * hfdcan)4579 HAL_StatusTypeDef HAL_FDCAN_TT_DisableTimeMarkGapControl(FDCAN_HandleTypeDef *hfdcan)
4580 {
4581 uint32_t Counter = 0U;
4582 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4583
4584 /* Check function parameters */
4585 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4586
4587 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4588 {
4589 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_OM) != FDCAN_TT_COMMUNICATION_LEVEL0)
4590 {
4591 /* Wait until the LCKC bit into TTOCN register is reset */
4592 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4593 {
4594 /* Check for the Timeout */
4595 if (Counter > FDCAN_TIMEOUT_COUNT)
4596 {
4597 /* Update error code */
4598 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4599
4600 /* Change FDCAN state */
4601 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4602
4603 return HAL_ERROR;
4604 }
4605
4606 /* Increment counter */
4607 Counter++;
4608 }
4609
4610 /* Disable gap control by register time mark interrupt */
4611 CLEAR_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_TMG);
4612
4613 /* Return function status */
4614 return HAL_OK;
4615 }
4616 else
4617 {
4618 /* Update error code.
4619 Feature not supported for TT Level 0 */
4620 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4621
4622 return HAL_ERROR;
4623 }
4624 }
4625 else
4626 {
4627 /* Update error code */
4628 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4629
4630 return HAL_ERROR;
4631 }
4632 }
4633
4634 /**
4635 * @brief Transmit next reference message with Next_is_Gap = "1".
4636 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4637 * the configuration information for the specified FDCAN.
4638 * @retval HAL status
4639 */
HAL_FDCAN_TT_SetNextIsGap(FDCAN_HandleTypeDef * hfdcan)4640 HAL_StatusTypeDef HAL_FDCAN_TT_SetNextIsGap(FDCAN_HandleTypeDef *hfdcan)
4641 {
4642 uint32_t Counter = 0U;
4643 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4644
4645 /* Check function parameters */
4646 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4647
4648 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4649 {
4650 /* Check that the node is configured for external event-synchronized TT operation */
4651 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_GEN) != FDCAN_TTOCF_GEN)
4652 {
4653 /* Update error code */
4654 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4655
4656 return HAL_ERROR;
4657 }
4658
4659 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_OM) != FDCAN_TT_COMMUNICATION_LEVEL0)
4660 {
4661 /* Wait until the LCKC bit into TTOCN register is reset */
4662 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4663 {
4664 /* Check for the Timeout */
4665 if (Counter > FDCAN_TIMEOUT_COUNT)
4666 {
4667 /* Update error code */
4668 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4669
4670 /* Change FDCAN state */
4671 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4672
4673 return HAL_ERROR;
4674 }
4675
4676 /* Increment counter */
4677 Counter++;
4678 }
4679
4680 /* Set Next is Gap */
4681 SET_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_NIG);
4682
4683 /* Return function status */
4684 return HAL_OK;
4685 }
4686 else
4687 {
4688 /* Update error code.
4689 Feature not supported for TT Level 0 */
4690 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4691
4692 return HAL_ERROR;
4693 }
4694 }
4695 else
4696 {
4697 /* Update error code */
4698 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4699
4700 return HAL_ERROR;
4701 }
4702 }
4703
4704 /**
4705 * @brief Finish a Gap by requesting start of reference message.
4706 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4707 * the configuration information for the specified FDCAN.
4708 * @retval HAL status
4709 */
HAL_FDCAN_TT_SetEndOfGap(FDCAN_HandleTypeDef * hfdcan)4710 HAL_StatusTypeDef HAL_FDCAN_TT_SetEndOfGap(FDCAN_HandleTypeDef *hfdcan)
4711 {
4712 uint32_t Counter = 0U;
4713 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4714
4715 /* Check function parameters */
4716 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4717
4718 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4719 {
4720 /* Check that the node is configured for external event-synchronized TT operation */
4721 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_GEN) != FDCAN_TTOCF_GEN)
4722 {
4723 /* Update error code */
4724 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4725
4726 return HAL_ERROR;
4727 }
4728
4729 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_OM) != FDCAN_TT_COMMUNICATION_LEVEL0)
4730 {
4731 /* Wait until the LCKC bit into TTOCN register is reset */
4732 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4733 {
4734 /* Check for the Timeout */
4735 if (Counter > FDCAN_TIMEOUT_COUNT)
4736 {
4737 /* Update error code */
4738 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4739
4740 /* Change FDCAN state */
4741 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4742
4743 return HAL_ERROR;
4744 }
4745
4746 /* Increment counter */
4747 Counter++;
4748 }
4749
4750 /* Set Finish Gap */
4751 SET_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_FGP);
4752
4753 /* Return function status */
4754 return HAL_OK;
4755 }
4756 else
4757 {
4758 /* Update error code.
4759 Feature not supported for TT Level 0 */
4760 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_SUPPORTED;
4761
4762 return HAL_ERROR;
4763 }
4764 }
4765 else
4766 {
4767 /* Update error code */
4768 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4769
4770 return HAL_ERROR;
4771 }
4772 }
4773
4774 /**
4775 * @brief Configure target phase used for external synchronization by event
4776 * trigger input pin fdcan1_evt.
4777 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4778 * the configuration information for the specified FDCAN.
4779 * @param TargetPhase defines target value of cycle time when a rising edge
4780 * of fdcan1_evt is expected.
4781 * This parameter must be a number between 0 and 0xFFFF.
4782 * @retval HAL status
4783 */
HAL_FDCAN_TT_ConfigExternalSyncPhase(FDCAN_HandleTypeDef * hfdcan,uint32_t TargetPhase)4784 HAL_StatusTypeDef HAL_FDCAN_TT_ConfigExternalSyncPhase(FDCAN_HandleTypeDef *hfdcan, uint32_t TargetPhase)
4785 {
4786 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4787
4788 /* Check function parameters */
4789 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4790 assert_param(IS_FDCAN_MAX_VALUE(TargetPhase, 0xFFFFU));
4791
4792 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4793 {
4794 /* Check that no external schedule synchronization is pending */
4795 if ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_ESCN) == FDCAN_TTOCN_ESCN)
4796 {
4797 /* Update error code */
4798 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PENDING;
4799
4800 return HAL_ERROR;
4801 }
4802
4803 /* Configure cycle time target phase */
4804 MODIFY_REG(hfdcan->ttcan->TTGTP, FDCAN_TTGTP_CTP, (TargetPhase << FDCAN_TTGTP_CTP_Pos));
4805
4806 /* Return function status */
4807 return HAL_OK;
4808 }
4809 else
4810 {
4811 /* Update error code */
4812 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4813
4814 return HAL_ERROR;
4815 }
4816 }
4817
4818 /**
4819 * @brief Synchronize the phase of the FDCAN schedule to an external schedule
4820 * using event trigger input pin fdcan1_evt.
4821 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4822 * the configuration information for the specified FDCAN.
4823 * @retval HAL status
4824 */
HAL_FDCAN_TT_EnableExternalSynchronization(FDCAN_HandleTypeDef * hfdcan)4825 HAL_StatusTypeDef HAL_FDCAN_TT_EnableExternalSynchronization(FDCAN_HandleTypeDef *hfdcan)
4826 {
4827 uint32_t Counter = 0U;
4828 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4829
4830 /* Check function parameters */
4831 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4832
4833 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4834 {
4835 /* Wait until the LCKC bit into TTOCN register is reset */
4836 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4837 {
4838 /* Check for the Timeout */
4839 if (Counter > FDCAN_TIMEOUT_COUNT)
4840 {
4841 /* Update error code */
4842 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4843
4844 /* Change FDCAN state */
4845 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4846
4847 return HAL_ERROR;
4848 }
4849
4850 /* Increment counter */
4851 Counter++;
4852 }
4853
4854 /* Enable external synchronization */
4855 SET_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_ESCN);
4856
4857 /* Return function status */
4858 return HAL_OK;
4859 }
4860 else
4861 {
4862 /* Update error code */
4863 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4864
4865 return HAL_ERROR;
4866 }
4867 }
4868
4869 /**
4870 * @brief Disable external schedule synchronization.
4871 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4872 * the configuration information for the specified FDCAN.
4873 * @retval HAL status
4874 */
HAL_FDCAN_TT_DisableExternalSynchronization(FDCAN_HandleTypeDef * hfdcan)4875 HAL_StatusTypeDef HAL_FDCAN_TT_DisableExternalSynchronization(FDCAN_HandleTypeDef *hfdcan)
4876 {
4877 uint32_t Counter = 0U;
4878 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4879
4880 /* Check function parameters */
4881 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4882
4883 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
4884 {
4885 /* Wait until the LCKC bit into TTOCN register is reset */
4886 while ((hfdcan->ttcan->TTOCN & FDCAN_TTOCN_LCKC) != 0U)
4887 {
4888 /* Check for the Timeout */
4889 if (Counter > FDCAN_TIMEOUT_COUNT)
4890 {
4891 /* Update error code */
4892 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_TIMEOUT;
4893
4894 /* Change FDCAN state */
4895 hfdcan->State = HAL_FDCAN_STATE_ERROR;
4896
4897 return HAL_ERROR;
4898 }
4899
4900 /* Increment counter */
4901 Counter++;
4902 }
4903
4904 /* Disable external synchronization */
4905 CLEAR_BIT(hfdcan->ttcan->TTOCN, FDCAN_TTOCN_ESCN);
4906
4907 /* Return function status */
4908 return HAL_OK;
4909 }
4910 else
4911 {
4912 /* Update error code */
4913 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
4914
4915 return HAL_ERROR;
4916 }
4917 }
4918
4919 /**
4920 * @brief Get TT operation status.
4921 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4922 * the configuration information for the specified FDCAN.
4923 * @param TTOpStatus pointer to an FDCAN_TTOperationStatusTypeDef structure.
4924 * @retval HAL status
4925 */
HAL_FDCAN_TT_GetOperationStatus(const FDCAN_HandleTypeDef * hfdcan,FDCAN_TTOperationStatusTypeDef * TTOpStatus)4926 HAL_StatusTypeDef HAL_FDCAN_TT_GetOperationStatus(const FDCAN_HandleTypeDef *hfdcan,
4927 FDCAN_TTOperationStatusTypeDef *TTOpStatus)
4928 {
4929 uint32_t TTStatusReg;
4930
4931 /* Check function parameters */
4932 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
4933
4934 /* Read the TT operation status register */
4935 TTStatusReg = READ_REG(hfdcan->ttcan->TTOST);
4936
4937 /* Fill the TT operation status structure */
4938 TTOpStatus->ErrorLevel = (TTStatusReg & FDCAN_TTOST_EL);
4939 TTOpStatus->MasterState = (TTStatusReg & FDCAN_TTOST_MS);
4940 TTOpStatus->SyncState = (TTStatusReg & FDCAN_TTOST_SYS);
4941 TTOpStatus->GTimeQuality = ((TTStatusReg & FDCAN_TTOST_QGTP) >> FDCAN_TTOST_QGTP_Pos);
4942 TTOpStatus->ClockQuality = ((TTStatusReg & FDCAN_TTOST_QCS) >> FDCAN_TTOST_QCS_Pos);
4943 TTOpStatus->RefTrigOffset = ((TTStatusReg & FDCAN_TTOST_RTO) >> FDCAN_TTOST_RTO_Pos);
4944 TTOpStatus->GTimeDiscPending = ((TTStatusReg & FDCAN_TTOST_WGTD) >> FDCAN_TTOST_WGTD_Pos);
4945 TTOpStatus->GapFinished = ((TTStatusReg & FDCAN_TTOST_GFI) >> FDCAN_TTOST_GFI_Pos);
4946 TTOpStatus->MasterPriority = ((TTStatusReg & FDCAN_TTOST_TMP) >> FDCAN_TTOST_TMP_Pos);
4947 TTOpStatus->GapStarted = ((TTStatusReg & FDCAN_TTOST_GSI) >> FDCAN_TTOST_GSI_Pos);
4948 TTOpStatus->WaitForEvt = ((TTStatusReg & FDCAN_TTOST_WFE) >> FDCAN_TTOST_WFE_Pos);
4949 TTOpStatus->AppWdgEvt = ((TTStatusReg & FDCAN_TTOST_AWE) >> FDCAN_TTOST_AWE_Pos);
4950 TTOpStatus->ECSPending = ((TTStatusReg & FDCAN_TTOST_WECS) >> FDCAN_TTOST_WECS_Pos);
4951 TTOpStatus->PhaseLock = ((TTStatusReg & FDCAN_TTOST_SPL) >> FDCAN_TTOST_SPL_Pos);
4952
4953 /* Return function status */
4954 return HAL_OK;
4955 }
4956
4957 /**
4958 * @}
4959 */
4960
4961 /** @defgroup FDCAN_Exported_Functions_Group5 Interrupts management
4962 * @brief Interrupts management
4963 *
4964 @verbatim
4965 ==============================================================================
4966 ##### Interrupts management #####
4967 ==============================================================================
4968 [..] This section provides functions allowing to:
4969 (+) HAL_FDCAN_ConfigInterruptLines : Assign interrupts to either Interrupt line 0 or 1
4970 (+) HAL_FDCAN_TT_ConfigInterruptLines : Assign TT interrupts to either Interrupt line 0 or 1
4971 (+) HAL_FDCAN_ActivateNotification : Enable interrupts
4972 (+) HAL_FDCAN_DeactivateNotification : Disable interrupts
4973 (+) HAL_FDCAN_TT_ActivateNotification : Enable TT interrupts
4974 (+) HAL_FDCAN_TT_DeactivateNotification : Disable TT interrupts
4975 (+) HAL_FDCAN_IRQHandler : Handles FDCAN interrupt request
4976
4977 @endverbatim
4978 * @{
4979 */
4980
4981 /**
4982 * @brief Assign interrupts to either Interrupt line 0 or 1.
4983 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
4984 * the configuration information for the specified FDCAN.
4985 * @param ITList indicates which interrupts will be assigned to the selected interrupt line.
4986 * This parameter can be any combination of @arg FDCAN_Interrupts.
4987 * @param InterruptLine Interrupt line.
4988 * This parameter can be a value of @arg FDCAN_Interrupt_Line.
4989 * @retval HAL status
4990 */
HAL_FDCAN_ConfigInterruptLines(FDCAN_HandleTypeDef * hfdcan,uint32_t ITList,uint32_t InterruptLine)4991 HAL_StatusTypeDef HAL_FDCAN_ConfigInterruptLines(FDCAN_HandleTypeDef *hfdcan, uint32_t ITList, uint32_t InterruptLine)
4992 {
4993 HAL_FDCAN_StateTypeDef state = hfdcan->State;
4994
4995 /* Check function parameters */
4996 assert_param(IS_FDCAN_IT(ITList));
4997 assert_param(IS_FDCAN_IT_LINE(InterruptLine));
4998
4999 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
5000 {
5001 /* Assign list of interrupts to the selected line */
5002 if (InterruptLine == FDCAN_INTERRUPT_LINE0)
5003 {
5004 CLEAR_BIT(hfdcan->Instance->ILS, ITList);
5005 }
5006 else /* InterruptLine == FDCAN_INTERRUPT_LINE1 */
5007 {
5008 SET_BIT(hfdcan->Instance->ILS, ITList);
5009 }
5010
5011 /* Return function status */
5012 return HAL_OK;
5013 }
5014 else
5015 {
5016 /* Update error code */
5017 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
5018
5019 return HAL_ERROR;
5020 }
5021 }
5022
5023 /**
5024 * @brief Assign TT interrupts to either Interrupt line 0 or 1.
5025 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5026 * the configuration information for the specified FDCAN.
5027 * @param TTITList indicates which interrupts will be assigned to the selected interrupt line.
5028 * This parameter can be any combination of @arg FDCAN_TTInterrupts.
5029 * @param InterruptLine Interrupt line.
5030 * This parameter can be a value of @arg FDCAN_Interrupt_Line.
5031 * @retval HAL status
5032 */
HAL_FDCAN_TT_ConfigInterruptLines(FDCAN_HandleTypeDef * hfdcan,uint32_t TTITList,uint32_t InterruptLine)5033 HAL_StatusTypeDef HAL_FDCAN_TT_ConfigInterruptLines(FDCAN_HandleTypeDef *hfdcan, uint32_t TTITList,
5034 uint32_t InterruptLine)
5035 {
5036 HAL_FDCAN_StateTypeDef state = hfdcan->State;
5037
5038 /* Check function parameters */
5039 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
5040 assert_param(IS_FDCAN_TT_IT(TTITList));
5041 assert_param(IS_FDCAN_IT_LINE(InterruptLine));
5042
5043 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
5044 {
5045 /* Assign list of interrupts to the selected line */
5046 if (InterruptLine == FDCAN_INTERRUPT_LINE0)
5047 {
5048 CLEAR_BIT(hfdcan->ttcan->TTILS, TTITList);
5049 }
5050 else /* InterruptLine == FDCAN_INTERRUPT_LINE1 */
5051 {
5052 SET_BIT(hfdcan->ttcan->TTILS, TTITList);
5053 }
5054
5055 /* Return function status */
5056 return HAL_OK;
5057 }
5058 else
5059 {
5060 /* Update error code */
5061 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
5062
5063 return HAL_ERROR;
5064 }
5065 }
5066
5067 /**
5068 * @brief Enable interrupts.
5069 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5070 * the configuration information for the specified FDCAN.
5071 * @param ActiveITs indicates which interrupts will be enabled.
5072 * This parameter can be any combination of @arg FDCAN_Interrupts.
5073 * @param BufferIndexes Tx Buffer Indexes.
5074 * This parameter can be any combination of @arg FDCAN_Tx_location.
5075 * This parameter is ignored if ActiveITs does not include one of the following:
5076 * - FDCAN_IT_TX_COMPLETE
5077 * - FDCAN_IT_TX_ABORT_COMPLETE
5078 * @retval HAL status
5079 */
HAL_FDCAN_ActivateNotification(FDCAN_HandleTypeDef * hfdcan,uint32_t ActiveITs,uint32_t BufferIndexes)5080 HAL_StatusTypeDef HAL_FDCAN_ActivateNotification(FDCAN_HandleTypeDef *hfdcan, uint32_t ActiveITs,
5081 uint32_t BufferIndexes)
5082 {
5083 HAL_FDCAN_StateTypeDef state = hfdcan->State;
5084
5085 /* Check function parameters */
5086 assert_param(IS_FDCAN_IT(ActiveITs));
5087
5088 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
5089 {
5090 /* Enable Interrupt lines */
5091 if ((ActiveITs & hfdcan->Instance->ILS) == 0U)
5092 {
5093 /* Enable Interrupt line 0 */
5094 SET_BIT(hfdcan->Instance->ILE, FDCAN_INTERRUPT_LINE0);
5095 }
5096 else if ((ActiveITs & hfdcan->Instance->ILS) == ActiveITs)
5097 {
5098 /* Enable Interrupt line 1 */
5099 SET_BIT(hfdcan->Instance->ILE, FDCAN_INTERRUPT_LINE1);
5100 }
5101 else
5102 {
5103 /* Enable Interrupt lines 0 and 1 */
5104 hfdcan->Instance->ILE = (FDCAN_INTERRUPT_LINE0 | FDCAN_INTERRUPT_LINE1);
5105 }
5106
5107 if ((ActiveITs & FDCAN_IT_TX_COMPLETE) != 0U)
5108 {
5109 /* Enable Tx Buffer Transmission Interrupt to set TC flag in IR register,
5110 but interrupt will only occur if TC is enabled in IE register */
5111 SET_BIT(hfdcan->Instance->TXBTIE, BufferIndexes);
5112 }
5113
5114 if ((ActiveITs & FDCAN_IT_TX_ABORT_COMPLETE) != 0U)
5115 {
5116 /* Enable Tx Buffer Cancellation Finished Interrupt to set TCF flag in IR register,
5117 but interrupt will only occur if TCF is enabled in IE register */
5118 SET_BIT(hfdcan->Instance->TXBCIE, BufferIndexes);
5119 }
5120
5121 /* Enable the selected interrupts */
5122 __HAL_FDCAN_ENABLE_IT(hfdcan, ActiveITs);
5123
5124 /* Return function status */
5125 return HAL_OK;
5126 }
5127 else
5128 {
5129 /* Update error code */
5130 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
5131
5132 return HAL_ERROR;
5133 }
5134 }
5135
5136 /**
5137 * @brief Disable interrupts.
5138 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5139 * the configuration information for the specified FDCAN.
5140 * @param InactiveITs indicates which interrupts will be disabled.
5141 * This parameter can be any combination of @arg FDCAN_Interrupts.
5142 * @retval HAL status
5143 */
HAL_FDCAN_DeactivateNotification(FDCAN_HandleTypeDef * hfdcan,uint32_t InactiveITs)5144 HAL_StatusTypeDef HAL_FDCAN_DeactivateNotification(FDCAN_HandleTypeDef *hfdcan, uint32_t InactiveITs)
5145 {
5146 uint32_t ITLineSelection;
5147 HAL_FDCAN_StateTypeDef state = hfdcan->State;
5148
5149 /* Check function parameters */
5150 assert_param(IS_FDCAN_IT(InactiveITs));
5151
5152 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
5153 {
5154 /* Disable the selected interrupts */
5155 __HAL_FDCAN_DISABLE_IT(hfdcan, InactiveITs);
5156
5157 if ((InactiveITs & FDCAN_IT_TX_COMPLETE) != 0U)
5158 {
5159 /* Disable Tx Buffer Transmission Interrupts */
5160 CLEAR_REG(hfdcan->Instance->TXBTIE);
5161 }
5162
5163 if ((InactiveITs & FDCAN_IT_TX_ABORT_COMPLETE) != 0U)
5164 {
5165 /* Disable Tx Buffer Cancellation Finished Interrupt */
5166 CLEAR_REG(hfdcan->Instance->TXBCIE);
5167 }
5168
5169 ITLineSelection = hfdcan->Instance->ILS;
5170
5171 if ((hfdcan->Instance->IE | ITLineSelection) == ITLineSelection)
5172 {
5173 /* Disable Interrupt line 0 */
5174 CLEAR_BIT(hfdcan->Instance->ILE, FDCAN_INTERRUPT_LINE0);
5175 }
5176
5177 if ((hfdcan->Instance->IE & ITLineSelection) == 0U)
5178 {
5179 /* Disable Interrupt line 1 */
5180 CLEAR_BIT(hfdcan->Instance->ILE, FDCAN_INTERRUPT_LINE1);
5181 }
5182
5183 /* Return function status */
5184 return HAL_OK;
5185 }
5186 else
5187 {
5188 /* Update error code */
5189 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
5190
5191 return HAL_ERROR;
5192 }
5193 }
5194
5195 /**
5196 * @brief Enable TT interrupts.
5197 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5198 * the configuration information for the specified FDCAN.
5199 * @param ActiveTTITs indicates which TT interrupts will be enabled.
5200 * This parameter can be any combination of @arg FDCAN_TTInterrupts.
5201 * @retval HAL status
5202 */
HAL_FDCAN_TT_ActivateNotification(FDCAN_HandleTypeDef * hfdcan,uint32_t ActiveTTITs)5203 HAL_StatusTypeDef HAL_FDCAN_TT_ActivateNotification(FDCAN_HandleTypeDef *hfdcan, uint32_t ActiveTTITs)
5204 {
5205 HAL_FDCAN_StateTypeDef state = hfdcan->State;
5206
5207 /* Check function parameters */
5208 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
5209 assert_param(IS_FDCAN_TT_IT(ActiveTTITs));
5210
5211 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
5212 {
5213 /* Enable Interrupt lines */
5214 if ((ActiveTTITs & hfdcan->ttcan->TTILS) == 0U)
5215 {
5216 /* Enable Interrupt line 0 */
5217 SET_BIT(hfdcan->Instance->ILE, FDCAN_INTERRUPT_LINE0);
5218 }
5219 else if ((ActiveTTITs & hfdcan->ttcan->TTILS) == ActiveTTITs)
5220 {
5221 /* Enable Interrupt line 1 */
5222 SET_BIT(hfdcan->Instance->ILE, FDCAN_INTERRUPT_LINE1);
5223 }
5224 else
5225 {
5226 /* Enable Interrupt lines 0 and 1 */
5227 hfdcan->Instance->ILE = (FDCAN_INTERRUPT_LINE0 | FDCAN_INTERRUPT_LINE1);
5228 }
5229
5230 /* Enable the selected TT interrupts */
5231 __HAL_FDCAN_TT_ENABLE_IT(hfdcan, ActiveTTITs);
5232
5233 /* Return function status */
5234 return HAL_OK;
5235 }
5236 else
5237 {
5238 /* Update error code */
5239 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
5240
5241 return HAL_ERROR;
5242 }
5243 }
5244
5245 /**
5246 * @brief Disable TT interrupts.
5247 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5248 * the configuration information for the specified FDCAN.
5249 * @param InactiveTTITs indicates which TT interrupts will be disabled.
5250 * This parameter can be any combination of @arg FDCAN_TTInterrupts.
5251 * @retval HAL status
5252 */
HAL_FDCAN_TT_DeactivateNotification(FDCAN_HandleTypeDef * hfdcan,uint32_t InactiveTTITs)5253 HAL_StatusTypeDef HAL_FDCAN_TT_DeactivateNotification(FDCAN_HandleTypeDef *hfdcan, uint32_t InactiveTTITs)
5254 {
5255 uint32_t ITLineSelection;
5256 HAL_FDCAN_StateTypeDef state = hfdcan->State;
5257
5258 /* Check function parameters */
5259 assert_param(IS_FDCAN_TT_INSTANCE(hfdcan->Instance));
5260 assert_param(IS_FDCAN_TT_IT(InactiveTTITs));
5261
5262 if ((state == HAL_FDCAN_STATE_READY) || (state == HAL_FDCAN_STATE_BUSY))
5263 {
5264 /* Disable the selected TT interrupts */
5265 __HAL_FDCAN_TT_DISABLE_IT(hfdcan, InactiveTTITs);
5266
5267 ITLineSelection = hfdcan->ttcan->TTILS;
5268
5269 if ((hfdcan->ttcan->TTIE | ITLineSelection) == ITLineSelection)
5270 {
5271 /* Disable Interrupt line 0 */
5272 CLEAR_BIT(hfdcan->Instance->ILE, FDCAN_INTERRUPT_LINE0);
5273 }
5274
5275 if ((hfdcan->ttcan->TTIE & ITLineSelection) == 0U)
5276 {
5277 /* Disable interrupt line 1 */
5278 CLEAR_BIT(hfdcan->Instance->ILE, FDCAN_INTERRUPT_LINE1);
5279 }
5280
5281 /* Return function status */
5282 return HAL_OK;
5283 }
5284 else
5285 {
5286 /* Update error code */
5287 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_NOT_INITIALIZED;
5288
5289 return HAL_ERROR;
5290 }
5291 }
5292
5293 /**
5294 * @brief Handles FDCAN interrupt request.
5295 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5296 * the configuration information for the specified FDCAN.
5297 * @retval HAL status
5298 */
HAL_FDCAN_IRQHandler(FDCAN_HandleTypeDef * hfdcan)5299 void HAL_FDCAN_IRQHandler(FDCAN_HandleTypeDef *hfdcan)
5300 {
5301 uint32_t ClkCalibrationITs;
5302 uint32_t TxEventFifoITs;
5303 uint32_t RxFifo0ITs;
5304 uint32_t RxFifo1ITs;
5305 uint32_t Errors;
5306 uint32_t ErrorStatusITs;
5307 uint32_t TransmittedBuffers;
5308 uint32_t AbortedBuffers;
5309 uint32_t TTSchedSyncITs;
5310 uint32_t TTTimeMarkITs;
5311 uint32_t TTGlobTimeITs;
5312 uint32_t TTDistErrors;
5313 uint32_t TTFatalErrors;
5314 uint32_t SWTime;
5315 uint32_t SWCycleCount;
5316 uint32_t itsourceIE;
5317 uint32_t itsourceTTIE;
5318 uint32_t itflagIR;
5319 uint32_t itflagTTIR;
5320
5321 ClkCalibrationITs = (FDCAN_CCU->IR << 30);
5322 ClkCalibrationITs &= (FDCAN_CCU->IE << 30);
5323 TxEventFifoITs = hfdcan->Instance->IR & FDCAN_TX_EVENT_FIFO_MASK;
5324 TxEventFifoITs &= hfdcan->Instance->IE;
5325 RxFifo0ITs = hfdcan->Instance->IR & FDCAN_RX_FIFO0_MASK;
5326 RxFifo0ITs &= hfdcan->Instance->IE;
5327 RxFifo1ITs = hfdcan->Instance->IR & FDCAN_RX_FIFO1_MASK;
5328 RxFifo1ITs &= hfdcan->Instance->IE;
5329 Errors = hfdcan->Instance->IR & FDCAN_ERROR_MASK;
5330 Errors &= hfdcan->Instance->IE;
5331 ErrorStatusITs = hfdcan->Instance->IR & FDCAN_ERROR_STATUS_MASK;
5332 ErrorStatusITs &= hfdcan->Instance->IE;
5333 itsourceIE = hfdcan->Instance->IE;
5334 itflagIR = hfdcan->Instance->IR;
5335
5336 /* High Priority Message interrupt management *******************************/
5337 if (FDCAN_CHECK_IT_SOURCE(itsourceIE, FDCAN_IT_RX_HIGH_PRIORITY_MSG) != RESET)
5338 {
5339 if (FDCAN_CHECK_FLAG(itflagIR, FDCAN_FLAG_RX_HIGH_PRIORITY_MSG) != RESET)
5340 {
5341 /* Clear the High Priority Message flag */
5342 __HAL_FDCAN_CLEAR_FLAG(hfdcan, FDCAN_FLAG_RX_HIGH_PRIORITY_MSG);
5343
5344 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5345 /* Call registered callback*/
5346 hfdcan->HighPriorityMessageCallback(hfdcan);
5347 #else
5348 /* High Priority Message Callback */
5349 HAL_FDCAN_HighPriorityMessageCallback(hfdcan);
5350 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5351 }
5352 }
5353
5354 /* Transmission Abort interrupt management **********************************/
5355 if (FDCAN_CHECK_IT_SOURCE(itsourceIE, FDCAN_IT_TX_ABORT_COMPLETE) != RESET)
5356 {
5357 if (FDCAN_CHECK_FLAG(itflagIR, FDCAN_FLAG_TX_ABORT_COMPLETE) != RESET)
5358 {
5359 /* List of aborted monitored buffers */
5360 AbortedBuffers = hfdcan->Instance->TXBCF;
5361 AbortedBuffers &= hfdcan->Instance->TXBCIE;
5362
5363 /* Clear the Transmission Cancellation flag */
5364 __HAL_FDCAN_CLEAR_FLAG(hfdcan, FDCAN_FLAG_TX_ABORT_COMPLETE);
5365
5366 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5367 /* Call registered callback*/
5368 hfdcan->TxBufferAbortCallback(hfdcan, AbortedBuffers);
5369 #else
5370 /* Transmission Cancellation Callback */
5371 HAL_FDCAN_TxBufferAbortCallback(hfdcan, AbortedBuffers);
5372 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5373 }
5374 }
5375
5376 /* Clock calibration unit interrupts management *****************************/
5377 if (ClkCalibrationITs != 0U)
5378 {
5379 /* Clear the Clock Calibration flags */
5380 __HAL_FDCAN_CLEAR_FLAG(hfdcan, ClkCalibrationITs);
5381
5382 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5383 /* Call registered callback*/
5384 hfdcan->ClockCalibrationCallback(hfdcan, ClkCalibrationITs);
5385 #else
5386 /* Clock Calibration Callback */
5387 HAL_FDCAN_ClockCalibrationCallback(hfdcan, ClkCalibrationITs);
5388 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5389 }
5390
5391 /* Tx event FIFO interrupts management **************************************/
5392 if (TxEventFifoITs != 0U)
5393 {
5394 /* Clear the Tx Event FIFO flags */
5395 __HAL_FDCAN_CLEAR_FLAG(hfdcan, TxEventFifoITs);
5396
5397 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5398 /* Call registered callback*/
5399 hfdcan->TxEventFifoCallback(hfdcan, TxEventFifoITs);
5400 #else
5401 /* Tx Event FIFO Callback */
5402 HAL_FDCAN_TxEventFifoCallback(hfdcan, TxEventFifoITs);
5403 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5404 }
5405
5406 /* Rx FIFO 0 interrupts management ******************************************/
5407 if (RxFifo0ITs != 0U)
5408 {
5409 /* Clear the Rx FIFO 0 flags */
5410 __HAL_FDCAN_CLEAR_FLAG(hfdcan, RxFifo0ITs);
5411
5412 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5413 /* Call registered callback*/
5414 hfdcan->RxFifo0Callback(hfdcan, RxFifo0ITs);
5415 #else
5416 /* Rx FIFO 0 Callback */
5417 HAL_FDCAN_RxFifo0Callback(hfdcan, RxFifo0ITs);
5418 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5419 }
5420
5421 /* Rx FIFO 1 interrupts management ******************************************/
5422 if (RxFifo1ITs != 0U)
5423 {
5424 /* Clear the Rx FIFO 1 flags */
5425 __HAL_FDCAN_CLEAR_FLAG(hfdcan, RxFifo1ITs);
5426
5427 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5428 /* Call registered callback*/
5429 hfdcan->RxFifo1Callback(hfdcan, RxFifo1ITs);
5430 #else
5431 /* Rx FIFO 1 Callback */
5432 HAL_FDCAN_RxFifo1Callback(hfdcan, RxFifo1ITs);
5433 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5434 }
5435
5436 /* Tx FIFO empty interrupt management ***************************************/
5437 if (FDCAN_CHECK_IT_SOURCE(itsourceIE, FDCAN_IT_TX_FIFO_EMPTY) != RESET)
5438 {
5439 if (FDCAN_CHECK_FLAG(itflagIR, FDCAN_FLAG_TX_FIFO_EMPTY) != RESET)
5440 {
5441 /* Clear the Tx FIFO empty flag */
5442 __HAL_FDCAN_CLEAR_FLAG(hfdcan, FDCAN_FLAG_TX_FIFO_EMPTY);
5443
5444 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5445 /* Call registered callback*/
5446 hfdcan->TxFifoEmptyCallback(hfdcan);
5447 #else
5448 /* Tx FIFO empty Callback */
5449 HAL_FDCAN_TxFifoEmptyCallback(hfdcan);
5450 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5451 }
5452 }
5453
5454 /* Transmission Complete interrupt management *******************************/
5455 if (FDCAN_CHECK_IT_SOURCE(itsourceIE, FDCAN_IT_TX_COMPLETE) != RESET)
5456 {
5457 if (FDCAN_CHECK_FLAG(itflagIR, FDCAN_FLAG_TX_COMPLETE) != RESET)
5458 {
5459 /* List of transmitted monitored buffers */
5460 TransmittedBuffers = hfdcan->Instance->TXBTO;
5461 TransmittedBuffers &= hfdcan->Instance->TXBTIE;
5462
5463 /* Clear the Transmission Complete flag */
5464 __HAL_FDCAN_CLEAR_FLAG(hfdcan, FDCAN_FLAG_TX_COMPLETE);
5465
5466 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5467 /* Call registered callback*/
5468 hfdcan->TxBufferCompleteCallback(hfdcan, TransmittedBuffers);
5469 #else
5470 /* Transmission Complete Callback */
5471 HAL_FDCAN_TxBufferCompleteCallback(hfdcan, TransmittedBuffers);
5472 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5473 }
5474 }
5475
5476 /* Rx Buffer New Message interrupt management *******************************/
5477 if (FDCAN_CHECK_IT_SOURCE(itsourceIE, FDCAN_IT_RX_BUFFER_NEW_MESSAGE) != RESET)
5478 {
5479 if (FDCAN_CHECK_FLAG(itflagIR, FDCAN_FLAG_RX_BUFFER_NEW_MESSAGE) != RESET)
5480 {
5481 /* Clear the Rx Buffer New Message flag */
5482 __HAL_FDCAN_CLEAR_FLAG(hfdcan, FDCAN_FLAG_RX_BUFFER_NEW_MESSAGE);
5483
5484 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5485 /* Call registered callback*/
5486 hfdcan->RxBufferNewMessageCallback(hfdcan);
5487 #else
5488 /* Rx Buffer New Message Callback */
5489 HAL_FDCAN_RxBufferNewMessageCallback(hfdcan);
5490 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5491 }
5492 }
5493
5494 /* Timestamp Wraparound interrupt management ********************************/
5495 if (FDCAN_CHECK_IT_SOURCE(itsourceIE, FDCAN_IT_TIMESTAMP_WRAPAROUND) != RESET)
5496 {
5497 if (FDCAN_CHECK_FLAG(itflagIR, FDCAN_FLAG_TIMESTAMP_WRAPAROUND) != RESET)
5498 {
5499 /* Clear the Timestamp Wraparound flag */
5500 __HAL_FDCAN_CLEAR_FLAG(hfdcan, FDCAN_FLAG_TIMESTAMP_WRAPAROUND);
5501
5502 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5503 /* Call registered callback*/
5504 hfdcan->TimestampWraparoundCallback(hfdcan);
5505 #else
5506 /* Timestamp Wraparound Callback */
5507 HAL_FDCAN_TimestampWraparoundCallback(hfdcan);
5508 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5509 }
5510 }
5511
5512 /* Timeout Occurred interrupt management ************************************/
5513 if (FDCAN_CHECK_IT_SOURCE(itsourceIE, FDCAN_IT_TIMEOUT_OCCURRED) != RESET)
5514 {
5515 if (FDCAN_CHECK_FLAG(itflagIR, FDCAN_FLAG_TIMEOUT_OCCURRED) != RESET)
5516 {
5517 /* Clear the Timeout Occurred flag */
5518 __HAL_FDCAN_CLEAR_FLAG(hfdcan, FDCAN_FLAG_TIMEOUT_OCCURRED);
5519
5520 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5521 /* Call registered callback*/
5522 hfdcan->TimeoutOccurredCallback(hfdcan);
5523 #else
5524 /* Timeout Occurred Callback */
5525 HAL_FDCAN_TimeoutOccurredCallback(hfdcan);
5526 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5527 }
5528 }
5529
5530 /* Message RAM access failure interrupt management **************************/
5531 if (FDCAN_CHECK_IT_SOURCE(itsourceIE, FDCAN_IT_RAM_ACCESS_FAILURE) != RESET)
5532 {
5533 if (FDCAN_CHECK_FLAG(itflagIR, FDCAN_FLAG_RAM_ACCESS_FAILURE) != RESET)
5534 {
5535 /* Clear the Message RAM access failure flag */
5536 __HAL_FDCAN_CLEAR_FLAG(hfdcan, FDCAN_FLAG_RAM_ACCESS_FAILURE);
5537
5538 /* Update error code */
5539 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_RAM_ACCESS;
5540 }
5541 }
5542
5543 /* Error Status interrupts management ***************************************/
5544 if (ErrorStatusITs != 0U)
5545 {
5546 /* Clear the Error flags */
5547 __HAL_FDCAN_CLEAR_FLAG(hfdcan, ErrorStatusITs);
5548
5549 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5550 /* Call registered callback*/
5551 hfdcan->ErrorStatusCallback(hfdcan, ErrorStatusITs);
5552 #else
5553 /* Error Status Callback */
5554 HAL_FDCAN_ErrorStatusCallback(hfdcan, ErrorStatusITs);
5555 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5556 }
5557
5558 /* Error interrupts management **********************************************/
5559 if (Errors != 0U)
5560 {
5561 /* Clear the Error flags */
5562 __HAL_FDCAN_CLEAR_FLAG(hfdcan, Errors);
5563
5564 /* Update error code */
5565 hfdcan->ErrorCode |= Errors;
5566 }
5567
5568 if (hfdcan->Instance == FDCAN1)
5569 {
5570 if ((hfdcan->ttcan->TTOCF & FDCAN_TTOCF_OM) != 0U)
5571 {
5572 TTSchedSyncITs = hfdcan->ttcan->TTIR & FDCAN_TT_SCHEDULE_SYNC_MASK;
5573 TTSchedSyncITs &= hfdcan->ttcan->TTIE;
5574 TTTimeMarkITs = hfdcan->ttcan->TTIR & FDCAN_TT_TIME_MARK_MASK;
5575 TTTimeMarkITs &= hfdcan->ttcan->TTIE;
5576 TTGlobTimeITs = hfdcan->ttcan->TTIR & FDCAN_TT_GLOBAL_TIME_MASK;
5577 TTGlobTimeITs &= hfdcan->ttcan->TTIE;
5578 TTDistErrors = hfdcan->ttcan->TTIR & FDCAN_TT_DISTURBING_ERROR_MASK;
5579 TTDistErrors &= hfdcan->ttcan->TTIE;
5580 TTFatalErrors = hfdcan->ttcan->TTIR & FDCAN_TT_FATAL_ERROR_MASK;
5581 TTFatalErrors &= hfdcan->ttcan->TTIE;
5582 itsourceTTIE = hfdcan->ttcan->TTIE;
5583 itflagTTIR = hfdcan->ttcan->TTIR;
5584
5585 /* TT Schedule Synchronization interrupts management **********************/
5586 if (TTSchedSyncITs != 0U)
5587 {
5588 /* Clear the TT Schedule Synchronization flags */
5589 __HAL_FDCAN_TT_CLEAR_FLAG(hfdcan, TTSchedSyncITs);
5590
5591 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5592 /* Call registered callback*/
5593 hfdcan->TT_ScheduleSyncCallback(hfdcan, TTSchedSyncITs);
5594 #else
5595 /* TT Schedule Synchronization Callback */
5596 HAL_FDCAN_TT_ScheduleSyncCallback(hfdcan, TTSchedSyncITs);
5597 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5598 }
5599
5600 /* TT Time Mark interrupts management *************************************/
5601 if (TTTimeMarkITs != 0U)
5602 {
5603 /* Clear the TT Time Mark flags */
5604 __HAL_FDCAN_TT_CLEAR_FLAG(hfdcan, TTTimeMarkITs);
5605
5606 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5607 /* Call registered callback*/
5608 hfdcan->TT_TimeMarkCallback(hfdcan, TTTimeMarkITs);
5609 #else
5610 /* TT Time Mark Callback */
5611 HAL_FDCAN_TT_TimeMarkCallback(hfdcan, TTTimeMarkITs);
5612 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5613 }
5614
5615 /* TT Stop Watch interrupt management *************************************/
5616 if (FDCAN_CHECK_IT_SOURCE(itsourceTTIE, FDCAN_TT_IT_STOP_WATCH) != RESET)
5617 {
5618 if (FDCAN_CHECK_FLAG(itflagTTIR, FDCAN_TT_FLAG_STOP_WATCH) != RESET)
5619 {
5620 /* Retrieve Stop watch Time and Cycle count */
5621 SWTime = ((hfdcan->ttcan->TTCPT & FDCAN_TTCPT_SWV) >> FDCAN_TTCPT_SWV_Pos);
5622 SWCycleCount = ((hfdcan->ttcan->TTCPT & FDCAN_TTCPT_CCV) >> FDCAN_TTCPT_CCV_Pos);
5623
5624 /* Clear the TT Stop Watch flag */
5625 __HAL_FDCAN_TT_CLEAR_FLAG(hfdcan, FDCAN_TT_FLAG_STOP_WATCH);
5626
5627 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5628 /* Call registered callback*/
5629 hfdcan->TT_StopWatchCallback(hfdcan, SWTime, SWCycleCount);
5630 #else
5631 /* TT Stop Watch Callback */
5632 HAL_FDCAN_TT_StopWatchCallback(hfdcan, SWTime, SWCycleCount);
5633 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5634 }
5635 }
5636
5637 /* TT Global Time interrupts management ***********************************/
5638 if (TTGlobTimeITs != 0U)
5639 {
5640 /* Clear the TT Global Time flags */
5641 __HAL_FDCAN_TT_CLEAR_FLAG(hfdcan, TTGlobTimeITs);
5642
5643 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5644 /* Call registered callback*/
5645 hfdcan->TT_GlobalTimeCallback(hfdcan, TTGlobTimeITs);
5646 #else
5647 /* TT Global Time Callback */
5648 HAL_FDCAN_TT_GlobalTimeCallback(hfdcan, TTGlobTimeITs);
5649 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5650 }
5651
5652 /* TT Disturbing Error interrupts management ******************************/
5653 if (TTDistErrors != 0U)
5654 {
5655 /* Clear the TT Disturbing Error flags */
5656 __HAL_FDCAN_TT_CLEAR_FLAG(hfdcan, TTDistErrors);
5657
5658 /* Update error code */
5659 hfdcan->ErrorCode |= TTDistErrors;
5660 }
5661
5662 /* TT Fatal Error interrupts management ***********************************/
5663 if (TTFatalErrors != 0U)
5664 {
5665 /* Clear the TT Fatal Error flags */
5666 __HAL_FDCAN_TT_CLEAR_FLAG(hfdcan, TTFatalErrors);
5667
5668 /* Update error code */
5669 hfdcan->ErrorCode |= TTFatalErrors;
5670 }
5671 }
5672 }
5673
5674 if (hfdcan->ErrorCode != HAL_FDCAN_ERROR_NONE)
5675 {
5676 #if USE_HAL_FDCAN_REGISTER_CALLBACKS == 1
5677 /* Call registered callback*/
5678 hfdcan->ErrorCallback(hfdcan);
5679 #else
5680 /* Error Callback */
5681 HAL_FDCAN_ErrorCallback(hfdcan);
5682 #endif /* USE_HAL_FDCAN_REGISTER_CALLBACKS */
5683 }
5684 }
5685
5686 /**
5687 * @}
5688 */
5689
5690 /** @defgroup FDCAN_Exported_Functions_Group6 Callback functions
5691 * @brief FDCAN Callback functions
5692 *
5693 @verbatim
5694 ==============================================================================
5695 ##### Callback functions #####
5696 ==============================================================================
5697 [..]
5698 This subsection provides the following callback functions:
5699 (+) HAL_FDCAN_ClockCalibrationCallback
5700 (+) HAL_FDCAN_TxEventFifoCallback
5701 (+) HAL_FDCAN_RxFifo0Callback
5702 (+) HAL_FDCAN_RxFifo1Callback
5703 (+) HAL_FDCAN_TxFifoEmptyCallback
5704 (+) HAL_FDCAN_TxBufferCompleteCallback
5705 (+) HAL_FDCAN_TxBufferAbortCallback
5706 (+) HAL_FDCAN_RxBufferNewMessageCallback
5707 (+) HAL_FDCAN_HighPriorityMessageCallback
5708 (+) HAL_FDCAN_TimestampWraparoundCallback
5709 (+) HAL_FDCAN_TimeoutOccurredCallback
5710 (+) HAL_FDCAN_ErrorCallback
5711 (+) HAL_FDCAN_ErrorStatusCallback
5712 (+) HAL_FDCAN_TT_ScheduleSyncCallback
5713 (+) HAL_FDCAN_TT_TimeMarkCallback
5714 (+) HAL_FDCAN_TT_StopWatchCallback
5715 (+) HAL_FDCAN_TT_GlobalTimeCallback
5716
5717 @endverbatim
5718 * @{
5719 */
5720
5721 /**
5722 * @brief Clock Calibration callback.
5723 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5724 * the configuration information for the specified FDCAN.
5725 * @param ClkCalibrationITs indicates which Clock Calibration interrupts are signaled.
5726 * This parameter can be any combination of @arg FDCAN_Clock_Calibration_Interrupts.
5727 * @retval None
5728 */
HAL_FDCAN_ClockCalibrationCallback(FDCAN_HandleTypeDef * hfdcan,uint32_t ClkCalibrationITs)5729 __weak void HAL_FDCAN_ClockCalibrationCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t ClkCalibrationITs)
5730 {
5731 /* Prevent unused argument(s) compilation warning */
5732 UNUSED(hfdcan);
5733 UNUSED(ClkCalibrationITs);
5734
5735 /* NOTE: This function Should not be modified, when the callback is needed,
5736 the HAL_FDCAN_ClockCalibrationCallback could be implemented in the user file
5737 */
5738 }
5739
5740 /**
5741 * @brief Tx Event callback.
5742 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5743 * the configuration information for the specified FDCAN.
5744 * @param TxEventFifoITs indicates which Tx Event FIFO interrupts are signaled.
5745 * This parameter can be any combination of @arg FDCAN_Tx_Event_Fifo_Interrupts.
5746 * @retval None
5747 */
HAL_FDCAN_TxEventFifoCallback(FDCAN_HandleTypeDef * hfdcan,uint32_t TxEventFifoITs)5748 __weak void HAL_FDCAN_TxEventFifoCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t TxEventFifoITs)
5749 {
5750 /* Prevent unused argument(s) compilation warning */
5751 UNUSED(hfdcan);
5752 UNUSED(TxEventFifoITs);
5753
5754 /* NOTE: This function Should not be modified, when the callback is needed,
5755 the HAL_FDCAN_TxEventFifoCallback could be implemented in the user file
5756 */
5757 }
5758
5759 /**
5760 * @brief Rx FIFO 0 callback.
5761 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5762 * the configuration information for the specified FDCAN.
5763 * @param RxFifo0ITs indicates which Rx FIFO 0 interrupts are signaled.
5764 * This parameter can be any combination of @arg FDCAN_Rx_Fifo0_Interrupts.
5765 * @retval None
5766 */
HAL_FDCAN_RxFifo0Callback(FDCAN_HandleTypeDef * hfdcan,uint32_t RxFifo0ITs)5767 __weak void HAL_FDCAN_RxFifo0Callback(FDCAN_HandleTypeDef *hfdcan, uint32_t RxFifo0ITs)
5768 {
5769 /* Prevent unused argument(s) compilation warning */
5770 UNUSED(hfdcan);
5771 UNUSED(RxFifo0ITs);
5772
5773 /* NOTE: This function Should not be modified, when the callback is needed,
5774 the HAL_FDCAN_RxFifo0Callback could be implemented in the user file
5775 */
5776 }
5777
5778 /**
5779 * @brief Rx FIFO 1 callback.
5780 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5781 * the configuration information for the specified FDCAN.
5782 * @param RxFifo1ITs indicates which Rx FIFO 1 interrupts are signaled.
5783 * This parameter can be any combination of @arg FDCAN_Rx_Fifo1_Interrupts.
5784 * @retval None
5785 */
HAL_FDCAN_RxFifo1Callback(FDCAN_HandleTypeDef * hfdcan,uint32_t RxFifo1ITs)5786 __weak void HAL_FDCAN_RxFifo1Callback(FDCAN_HandleTypeDef *hfdcan, uint32_t RxFifo1ITs)
5787 {
5788 /* Prevent unused argument(s) compilation warning */
5789 UNUSED(hfdcan);
5790 UNUSED(RxFifo1ITs);
5791
5792 /* NOTE: This function Should not be modified, when the callback is needed,
5793 the HAL_FDCAN_RxFifo1Callback could be implemented in the user file
5794 */
5795 }
5796
5797 /**
5798 * @brief Tx FIFO Empty callback.
5799 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5800 * the configuration information for the specified FDCAN.
5801 * @retval None
5802 */
HAL_FDCAN_TxFifoEmptyCallback(FDCAN_HandleTypeDef * hfdcan)5803 __weak void HAL_FDCAN_TxFifoEmptyCallback(FDCAN_HandleTypeDef *hfdcan)
5804 {
5805 /* Prevent unused argument(s) compilation warning */
5806 UNUSED(hfdcan);
5807
5808 /* NOTE: This function Should not be modified, when the callback is needed,
5809 the HAL_FDCAN_TxFifoEmptyCallback could be implemented in the user file
5810 */
5811 }
5812
5813 /**
5814 * @brief Transmission Complete callback.
5815 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5816 * the configuration information for the specified FDCAN.
5817 * @param BufferIndexes Indexes of the transmitted buffers.
5818 * This parameter can be any combination of @arg FDCAN_Tx_location.
5819 * @retval None
5820 */
HAL_FDCAN_TxBufferCompleteCallback(FDCAN_HandleTypeDef * hfdcan,uint32_t BufferIndexes)5821 __weak void HAL_FDCAN_TxBufferCompleteCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t BufferIndexes)
5822 {
5823 /* Prevent unused argument(s) compilation warning */
5824 UNUSED(hfdcan);
5825 UNUSED(BufferIndexes);
5826
5827 /* NOTE: This function Should not be modified, when the callback is needed,
5828 the HAL_FDCAN_TxBufferCompleteCallback could be implemented in the user file
5829 */
5830 }
5831
5832 /**
5833 * @brief Transmission Cancellation callback.
5834 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5835 * the configuration information for the specified FDCAN.
5836 * @param BufferIndexes Indexes of the aborted buffers.
5837 * This parameter can be any combination of @arg FDCAN_Tx_location.
5838 * @retval None
5839 */
HAL_FDCAN_TxBufferAbortCallback(FDCAN_HandleTypeDef * hfdcan,uint32_t BufferIndexes)5840 __weak void HAL_FDCAN_TxBufferAbortCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t BufferIndexes)
5841 {
5842 /* Prevent unused argument(s) compilation warning */
5843 UNUSED(hfdcan);
5844 UNUSED(BufferIndexes);
5845
5846 /* NOTE: This function Should not be modified, when the callback is needed,
5847 the HAL_FDCAN_TxBufferAbortCallback could be implemented in the user file
5848 */
5849 }
5850
5851 /**
5852 * @brief Rx Buffer New Message callback.
5853 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5854 * the configuration information for the specified FDCAN.
5855 * @retval None
5856 */
HAL_FDCAN_RxBufferNewMessageCallback(FDCAN_HandleTypeDef * hfdcan)5857 __weak void HAL_FDCAN_RxBufferNewMessageCallback(FDCAN_HandleTypeDef *hfdcan)
5858 {
5859 /* Prevent unused argument(s) compilation warning */
5860 UNUSED(hfdcan);
5861
5862 /* NOTE: This function Should not be modified, when the callback is needed,
5863 the HAL_FDCAN_RxBufferNewMessageCallback could be implemented in the user file
5864 */
5865 }
5866
5867 /**
5868 * @brief Timestamp Wraparound callback.
5869 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5870 * the configuration information for the specified FDCAN.
5871 * @retval None
5872 */
HAL_FDCAN_TimestampWraparoundCallback(FDCAN_HandleTypeDef * hfdcan)5873 __weak void HAL_FDCAN_TimestampWraparoundCallback(FDCAN_HandleTypeDef *hfdcan)
5874 {
5875 /* Prevent unused argument(s) compilation warning */
5876 UNUSED(hfdcan);
5877
5878 /* NOTE: This function Should not be modified, when the callback is needed,
5879 the HAL_FDCAN_TimestampWraparoundCallback could be implemented in the user file
5880 */
5881 }
5882
5883 /**
5884 * @brief Timeout Occurred callback.
5885 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5886 * the configuration information for the specified FDCAN.
5887 * @retval None
5888 */
HAL_FDCAN_TimeoutOccurredCallback(FDCAN_HandleTypeDef * hfdcan)5889 __weak void HAL_FDCAN_TimeoutOccurredCallback(FDCAN_HandleTypeDef *hfdcan)
5890 {
5891 /* Prevent unused argument(s) compilation warning */
5892 UNUSED(hfdcan);
5893
5894 /* NOTE: This function Should not be modified, when the callback is needed,
5895 the HAL_FDCAN_TimeoutOccurredCallback could be implemented in the user file
5896 */
5897 }
5898
5899 /**
5900 * @brief High Priority Message callback.
5901 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5902 * the configuration information for the specified FDCAN.
5903 * @retval None
5904 */
HAL_FDCAN_HighPriorityMessageCallback(FDCAN_HandleTypeDef * hfdcan)5905 __weak void HAL_FDCAN_HighPriorityMessageCallback(FDCAN_HandleTypeDef *hfdcan)
5906 {
5907 /* Prevent unused argument(s) compilation warning */
5908 UNUSED(hfdcan);
5909
5910 /* NOTE: This function Should not be modified, when the callback is needed,
5911 the HAL_FDCAN_HighPriorityMessageCallback could be implemented in the user file
5912 */
5913 }
5914
5915 /**
5916 * @brief Error callback.
5917 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5918 * the configuration information for the specified FDCAN.
5919 * @retval None
5920 */
HAL_FDCAN_ErrorCallback(FDCAN_HandleTypeDef * hfdcan)5921 __weak void HAL_FDCAN_ErrorCallback(FDCAN_HandleTypeDef *hfdcan)
5922 {
5923 /* Prevent unused argument(s) compilation warning */
5924 UNUSED(hfdcan);
5925
5926 /* NOTE: This function Should not be modified, when the callback is needed,
5927 the HAL_FDCAN_ErrorCallback could be implemented in the user file
5928 */
5929 }
5930
5931 /**
5932 * @brief Error status callback.
5933 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5934 * the configuration information for the specified FDCAN.
5935 * @param ErrorStatusITs indicates which Error Status interrupts are signaled.
5936 * This parameter can be any combination of @arg FDCAN_Error_Status_Interrupts.
5937 * @retval None
5938 */
HAL_FDCAN_ErrorStatusCallback(FDCAN_HandleTypeDef * hfdcan,uint32_t ErrorStatusITs)5939 __weak void HAL_FDCAN_ErrorStatusCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t ErrorStatusITs)
5940 {
5941 /* Prevent unused argument(s) compilation warning */
5942 UNUSED(hfdcan);
5943 UNUSED(ErrorStatusITs);
5944
5945 /* NOTE: This function Should not be modified, when the callback is needed,
5946 the HAL_FDCAN_ErrorStatusCallback could be implemented in the user file
5947 */
5948 }
5949
5950 /**
5951 * @brief TT Schedule Synchronization callback.
5952 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5953 * the configuration information for the specified FDCAN.
5954 * @param TTSchedSyncITs indicates which TT Schedule Synchronization interrupts are signaled.
5955 * This parameter can be any combination of @arg FDCAN_TTScheduleSynchronization_Interrupts.
5956 * @retval None
5957 */
HAL_FDCAN_TT_ScheduleSyncCallback(FDCAN_HandleTypeDef * hfdcan,uint32_t TTSchedSyncITs)5958 __weak void HAL_FDCAN_TT_ScheduleSyncCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t TTSchedSyncITs)
5959 {
5960 /* Prevent unused argument(s) compilation warning */
5961 UNUSED(hfdcan);
5962 UNUSED(TTSchedSyncITs);
5963
5964 /* NOTE: This function Should not be modified, when the callback is needed,
5965 the HAL_FDCAN_TT_ScheduleSyncCallback could be implemented in the user file
5966 */
5967 }
5968
5969 /**
5970 * @brief TT Time Mark callback.
5971 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5972 * the configuration information for the specified FDCAN.
5973 * @param TTTimeMarkITs indicates which TT Schedule Synchronization interrupts are signaled.
5974 * This parameter can be any combination of @arg FDCAN_TTTimeMark_Interrupts.
5975 * @retval None
5976 */
HAL_FDCAN_TT_TimeMarkCallback(FDCAN_HandleTypeDef * hfdcan,uint32_t TTTimeMarkITs)5977 __weak void HAL_FDCAN_TT_TimeMarkCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t TTTimeMarkITs)
5978 {
5979 /* Prevent unused argument(s) compilation warning */
5980 UNUSED(hfdcan);
5981 UNUSED(TTTimeMarkITs);
5982
5983 /* NOTE: This function Should not be modified, when the callback is needed,
5984 the HAL_FDCAN_TT_TimeMarkCallback could be implemented in the user file
5985 */
5986 }
5987
5988 /**
5989 * @brief TT Stop Watch callback.
5990 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
5991 * the configuration information for the specified FDCAN.
5992 * @param SWTime Time Value captured at the Stop Watch Trigger pin (fdcan1_swt) falling/rising
5993 * edge (as configured via HAL_FDCAN_TTConfigStopWatch).
5994 * This parameter is a number between 0 and 0xFFFF.
5995 * @param SWCycleCount Cycle count value captured together with SWTime.
5996 * This parameter is a number between 0 and 0x3F.
5997 * @retval None
5998 */
HAL_FDCAN_TT_StopWatchCallback(FDCAN_HandleTypeDef * hfdcan,uint32_t SWTime,uint32_t SWCycleCount)5999 __weak void HAL_FDCAN_TT_StopWatchCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t SWTime, uint32_t SWCycleCount)
6000 {
6001 /* Prevent unused argument(s) compilation warning */
6002 UNUSED(hfdcan);
6003 UNUSED(SWTime);
6004 UNUSED(SWCycleCount);
6005
6006 /* NOTE: This function Should not be modified, when the callback is needed,
6007 the HAL_FDCAN_TT_StopWatchCallback could be implemented in the user file
6008 */
6009 }
6010
6011 /**
6012 * @brief TT Global Time callback.
6013 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
6014 * the configuration information for the specified FDCAN.
6015 * @param TTGlobTimeITs indicates which TT Global Time interrupts are signaled.
6016 * This parameter can be any combination of @arg FDCAN_TTGlobalTime_Interrupts.
6017 * @retval None
6018 */
HAL_FDCAN_TT_GlobalTimeCallback(FDCAN_HandleTypeDef * hfdcan,uint32_t TTGlobTimeITs)6019 __weak void HAL_FDCAN_TT_GlobalTimeCallback(FDCAN_HandleTypeDef *hfdcan, uint32_t TTGlobTimeITs)
6020 {
6021 /* Prevent unused argument(s) compilation warning */
6022 UNUSED(hfdcan);
6023 UNUSED(TTGlobTimeITs);
6024
6025 /* NOTE: This function Should not be modified, when the callback is needed,
6026 the HAL_FDCAN_TT_GlobalTimeCallback could be implemented in the user file
6027 */
6028 }
6029
6030 /**
6031 * @}
6032 */
6033
6034 /** @defgroup FDCAN_Exported_Functions_Group7 Peripheral State functions
6035 * @brief FDCAN Peripheral State functions
6036 *
6037 @verbatim
6038 ==============================================================================
6039 ##### Peripheral State functions #####
6040 ==============================================================================
6041 [..]
6042 This subsection provides functions allowing to :
6043 (+) HAL_FDCAN_GetState() : Return the FDCAN state.
6044 (+) HAL_FDCAN_GetError() : Return the FDCAN error code if any.
6045
6046 @endverbatim
6047 * @{
6048 */
6049 /**
6050 * @brief Return the FDCAN state
6051 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
6052 * the configuration information for the specified FDCAN.
6053 * @retval HAL state
6054 */
HAL_FDCAN_GetState(const FDCAN_HandleTypeDef * hfdcan)6055 HAL_FDCAN_StateTypeDef HAL_FDCAN_GetState(const FDCAN_HandleTypeDef *hfdcan)
6056 {
6057 /* Return FDCAN state */
6058 return hfdcan->State;
6059 }
6060
6061 /**
6062 * @brief Return the FDCAN error code
6063 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
6064 * the configuration information for the specified FDCAN.
6065 * @retval FDCAN Error Code
6066 */
HAL_FDCAN_GetError(const FDCAN_HandleTypeDef * hfdcan)6067 uint32_t HAL_FDCAN_GetError(const FDCAN_HandleTypeDef *hfdcan)
6068 {
6069 /* Return FDCAN error code */
6070 return hfdcan->ErrorCode;
6071 }
6072
6073 /**
6074 * @}
6075 */
6076
6077 /**
6078 * @}
6079 */
6080
6081 /** @defgroup FDCAN_Private_Functions FDCAN Private Functions
6082 * @{
6083 */
6084
6085 /**
6086 * @brief Calculate each RAM block start address and size
6087 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
6088 * the configuration information for the specified FDCAN.
6089 * @retval HAL status
6090 */
FDCAN_CalcultateRamBlockAddresses(FDCAN_HandleTypeDef * hfdcan)6091 static HAL_StatusTypeDef FDCAN_CalcultateRamBlockAddresses(FDCAN_HandleTypeDef *hfdcan)
6092 {
6093 uint32_t RAMcounter;
6094 uint32_t StartAddress;
6095
6096 StartAddress = hfdcan->Init.MessageRAMOffset;
6097
6098 /* Standard filter list start address */
6099 MODIFY_REG(hfdcan->Instance->SIDFC, FDCAN_SIDFC_FLSSA, (StartAddress << FDCAN_SIDFC_FLSSA_Pos));
6100
6101 /* Standard filter elements number */
6102 MODIFY_REG(hfdcan->Instance->SIDFC, FDCAN_SIDFC_LSS, (hfdcan->Init.StdFiltersNbr << FDCAN_SIDFC_LSS_Pos));
6103
6104 /* Extended filter list start address */
6105 StartAddress += hfdcan->Init.StdFiltersNbr;
6106 MODIFY_REG(hfdcan->Instance->XIDFC, FDCAN_XIDFC_FLESA, (StartAddress << FDCAN_XIDFC_FLESA_Pos));
6107
6108 /* Extended filter elements number */
6109 MODIFY_REG(hfdcan->Instance->XIDFC, FDCAN_XIDFC_LSE, (hfdcan->Init.ExtFiltersNbr << FDCAN_XIDFC_LSE_Pos));
6110
6111 /* Rx FIFO 0 start address */
6112 StartAddress += (hfdcan->Init.ExtFiltersNbr * 2U);
6113 MODIFY_REG(hfdcan->Instance->RXF0C, FDCAN_RXF0C_F0SA, (StartAddress << FDCAN_RXF0C_F0SA_Pos));
6114
6115 /* Rx FIFO 0 elements number */
6116 MODIFY_REG(hfdcan->Instance->RXF0C, FDCAN_RXF0C_F0S, (hfdcan->Init.RxFifo0ElmtsNbr << FDCAN_RXF0C_F0S_Pos));
6117
6118 /* Rx FIFO 1 start address */
6119 StartAddress += (hfdcan->Init.RxFifo0ElmtsNbr * hfdcan->Init.RxFifo0ElmtSize);
6120 MODIFY_REG(hfdcan->Instance->RXF1C, FDCAN_RXF1C_F1SA, (StartAddress << FDCAN_RXF1C_F1SA_Pos));
6121
6122 /* Rx FIFO 1 elements number */
6123 MODIFY_REG(hfdcan->Instance->RXF1C, FDCAN_RXF1C_F1S, (hfdcan->Init.RxFifo1ElmtsNbr << FDCAN_RXF1C_F1S_Pos));
6124
6125 /* Rx buffer list start address */
6126 StartAddress += (hfdcan->Init.RxFifo1ElmtsNbr * hfdcan->Init.RxFifo1ElmtSize);
6127 MODIFY_REG(hfdcan->Instance->RXBC, FDCAN_RXBC_RBSA, (StartAddress << FDCAN_RXBC_RBSA_Pos));
6128
6129 /* Tx event FIFO start address */
6130 StartAddress += (hfdcan->Init.RxBuffersNbr * hfdcan->Init.RxBufferSize);
6131 MODIFY_REG(hfdcan->Instance->TXEFC, FDCAN_TXEFC_EFSA, (StartAddress << FDCAN_TXEFC_EFSA_Pos));
6132
6133 /* Tx event FIFO elements number */
6134 MODIFY_REG(hfdcan->Instance->TXEFC, FDCAN_TXEFC_EFS, (hfdcan->Init.TxEventsNbr << FDCAN_TXEFC_EFS_Pos));
6135
6136 /* Tx buffer list start address */
6137 StartAddress += (hfdcan->Init.TxEventsNbr * 2U);
6138 MODIFY_REG(hfdcan->Instance->TXBC, FDCAN_TXBC_TBSA, (StartAddress << FDCAN_TXBC_TBSA_Pos));
6139
6140 /* Dedicated Tx buffers number */
6141 MODIFY_REG(hfdcan->Instance->TXBC, FDCAN_TXBC_NDTB, (hfdcan->Init.TxBuffersNbr << FDCAN_TXBC_NDTB_Pos));
6142
6143 /* Tx FIFO/queue elements number */
6144 MODIFY_REG(hfdcan->Instance->TXBC, FDCAN_TXBC_TFQS, (hfdcan->Init.TxFifoQueueElmtsNbr << FDCAN_TXBC_TFQS_Pos));
6145
6146 hfdcan->msgRam.StandardFilterSA = SRAMCAN_BASE + (hfdcan->Init.MessageRAMOffset * 4U);
6147 hfdcan->msgRam.ExtendedFilterSA = hfdcan->msgRam.StandardFilterSA + (hfdcan->Init.StdFiltersNbr * 4U);
6148 hfdcan->msgRam.RxFIFO0SA = hfdcan->msgRam.ExtendedFilterSA + (hfdcan->Init.ExtFiltersNbr * 2U * 4U);
6149 hfdcan->msgRam.RxFIFO1SA = hfdcan->msgRam.RxFIFO0SA +
6150 (hfdcan->Init.RxFifo0ElmtsNbr * hfdcan->Init.RxFifo0ElmtSize * 4U);
6151 hfdcan->msgRam.RxBufferSA = hfdcan->msgRam.RxFIFO1SA +
6152 (hfdcan->Init.RxFifo1ElmtsNbr * hfdcan->Init.RxFifo1ElmtSize * 4U);
6153 hfdcan->msgRam.TxEventFIFOSA = hfdcan->msgRam.RxBufferSA +
6154 (hfdcan->Init.RxBuffersNbr * hfdcan->Init.RxBufferSize * 4U);
6155 hfdcan->msgRam.TxBufferSA = hfdcan->msgRam.TxEventFIFOSA + (hfdcan->Init.TxEventsNbr * 2U * 4U);
6156 hfdcan->msgRam.TxFIFOQSA = hfdcan->msgRam.TxBufferSA + (hfdcan->Init.TxBuffersNbr * hfdcan->Init.TxElmtSize * 4U);
6157
6158 hfdcan->msgRam.EndAddress = hfdcan->msgRam.TxFIFOQSA +
6159 (hfdcan->Init.TxFifoQueueElmtsNbr * hfdcan->Init.TxElmtSize * 4U);
6160
6161 if (hfdcan->msgRam.EndAddress > FDCAN_MESSAGE_RAM_END_ADDRESS) /* Last address of the Message RAM */
6162 {
6163 /* Update error code.
6164 Message RAM overflow */
6165 hfdcan->ErrorCode |= HAL_FDCAN_ERROR_PARAM;
6166
6167 /* Change FDCAN state */
6168 hfdcan->State = HAL_FDCAN_STATE_ERROR;
6169
6170 return HAL_ERROR;
6171 }
6172 else
6173 {
6174 /* Flush the allocated Message RAM area */
6175 for (RAMcounter = hfdcan->msgRam.StandardFilterSA; RAMcounter < hfdcan->msgRam.EndAddress; RAMcounter += 4U)
6176 {
6177 *(uint32_t *)(RAMcounter) = 0x00000000;
6178 }
6179 }
6180
6181 /* Return function status */
6182 return HAL_OK;
6183 }
6184
6185 /**
6186 * @brief Copy Tx message to the message RAM.
6187 * @param hfdcan pointer to an FDCAN_HandleTypeDef structure that contains
6188 * the configuration information for the specified FDCAN.
6189 * @param pTxHeader pointer to a FDCAN_TxHeaderTypeDef structure.
6190 * @param pTxData pointer to a buffer containing the payload of the Tx frame.
6191 * @param BufferIndex index of the buffer to be configured.
6192 * @retval none
6193 */
FDCAN_CopyMessageToRAM(const FDCAN_HandleTypeDef * hfdcan,const FDCAN_TxHeaderTypeDef * pTxHeader,const uint8_t * pTxData,uint32_t BufferIndex)6194 static void FDCAN_CopyMessageToRAM(const FDCAN_HandleTypeDef *hfdcan, const FDCAN_TxHeaderTypeDef *pTxHeader,
6195 const uint8_t *pTxData, uint32_t BufferIndex)
6196 {
6197 uint32_t TxElementW1;
6198 uint32_t TxElementW2;
6199 uint32_t *TxAddress;
6200 uint32_t ByteCounter;
6201
6202 /* Build first word of Tx header element */
6203 if (pTxHeader->IdType == FDCAN_STANDARD_ID)
6204 {
6205 TxElementW1 = (pTxHeader->ErrorStateIndicator |
6206 FDCAN_STANDARD_ID |
6207 pTxHeader->TxFrameType |
6208 (pTxHeader->Identifier << 18U));
6209 }
6210 else /* pTxHeader->IdType == FDCAN_EXTENDED_ID */
6211 {
6212 TxElementW1 = (pTxHeader->ErrorStateIndicator |
6213 FDCAN_EXTENDED_ID |
6214 pTxHeader->TxFrameType |
6215 pTxHeader->Identifier);
6216 }
6217
6218 /* Build second word of Tx header element */
6219 TxElementW2 = ((pTxHeader->MessageMarker << 24U) |
6220 pTxHeader->TxEventFifoControl |
6221 pTxHeader->FDFormat |
6222 pTxHeader->BitRateSwitch |
6223 (pTxHeader->DataLength << 16U));
6224
6225 /* Calculate Tx element address */
6226 TxAddress = (uint32_t *)(hfdcan->msgRam.TxBufferSA + (BufferIndex * hfdcan->Init.TxElmtSize * 4U));
6227
6228 /* Write Tx element header to the message RAM */
6229 *TxAddress = TxElementW1;
6230 TxAddress++;
6231 *TxAddress = TxElementW2;
6232 TxAddress++;
6233
6234 /* Write Tx payload to the message RAM */
6235 for (ByteCounter = 0; ByteCounter < DLCtoBytes[pTxHeader->DataLength]; ByteCounter += 4U)
6236 {
6237 *TxAddress = (((uint32_t)pTxData[ByteCounter + 3U] << 24U) |
6238 ((uint32_t)pTxData[ByteCounter + 2U] << 16U) |
6239 ((uint32_t)pTxData[ByteCounter + 1U] << 8U) |
6240 (uint32_t)pTxData[ByteCounter]);
6241 TxAddress++;
6242 }
6243 }
6244
6245 /**
6246 * @}
6247 */
6248 #endif /* HAL_FDCAN_MODULE_ENABLED */
6249 /**
6250 * @}
6251 */
6252
6253 /**
6254 * @}
6255 */
6256
6257 #endif /* FDCAN1 */
6258