Skip to content

Commit e699310

Browse files
Fix FDCan Stuff (#392)
Co-authored-by: Caio DaSilva <dasilva.cai@northeastern.edu>
1 parent 06e8138 commit e699310

2 files changed

Lines changed: 49 additions & 5 deletions

File tree

platforms/stm32h563/include/fdcan.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,8 @@ HAL_StatusTypeDef can_init(can_t *can, FDCAN_HandleTypeDef *hcan);
2828
HAL_StatusTypeDef can_send_msg(can_t *can, can_msg_t *msg);
2929
HAL_StatusTypeDef can_add_filter_standard(can_t *can, uint16_t can_ids[2]);
3030
HAL_StatusTypeDef can_add_filter_extended(can_t *can, uint32_t can_ids[2]);
31+
bool can_is_bus_off(can_t *can);
32+
HAL_StatusTypeDef can_recover_bus_off(can_t *can);
3133

3234
// clang-format on
3335
#endif // FDCAN_H

platforms/stm32h563/src/fdcan.c

Lines changed: 47 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -13,19 +13,31 @@ HAL_StatusTypeDef can_init(can_t *can, FDCAN_HandleTypeDef *hcan)
1313
can->extended_filter_index = 0;
1414
can->hcan = hcan;
1515

16-
/* Config interrupts */
16+
/* Config incoming message interrupt. */
1717
HAL_StatusTypeDef status = HAL_FDCAN_ConfigInterruptLines(can->hcan, FDCAN_IT_RX_FIFO0_NEW_MESSAGE, FDCAN_INTERRUPT_LINE0);
1818
if (status != HAL_OK)
1919
{
20-
printf("[fdcan.c/can_init()] ERROR: Failed to run HAL_FDCAN_ConfigInterruptLines() (Status: %d).\n", status);
20+
printf("[fdcan.c/can_init()] ERROR: Failed to run HAL_FDCAN_ConfigInterruptLines(can->hcan, FDCAN_IT_RX_FIFO0_NEW_MESSAGE, FDCAN_INTERRUPT_LINE0); (Status: %d).\n", status);
2121
return status;
2222
}
23-
24-
/* Activate interrupt notifications */
2523
status = HAL_FDCAN_ActivateNotification(can->hcan, FDCAN_IT_RX_FIFO0_NEW_MESSAGE, 0);
2624
if (status != HAL_OK)
2725
{
28-
printf("[fdcan.c/can_init()] ERROR: Failed to run HAL_FDCAN_ActivateNotification() (Status: %d).\n", status);
26+
printf("[fdcan.c/can_init()] ERROR: Failed to run HAL_FDCAN_ActivateNotification(can->hcan, FDCAN_IT_RX_FIFO0_NEW_MESSAGE, 0); (Status: %d).\n", status);
27+
return status;
28+
}
29+
30+
/* Config BusOff interrupt. */
31+
status = HAL_FDCAN_ConfigInterruptLines(can->hcan, FDCAN_IT_BUS_OFF, FDCAN_INTERRUPT_LINE1);
32+
if (status != HAL_OK)
33+
{
34+
printf("[fdcan.c/can_init()] ERROR: Failed to run HAL_FDCAN_ConfigInterruptLines(can->hcan, FDCAN_IT_BUS_OFF, FDCAN_INTERRUPT_LINE1); (Status: %d).\n", status);
35+
return status;
36+
}
37+
status = HAL_FDCAN_ActivateNotification(can->hcan, FDCAN_IT_BUS_OFF, 1);
38+
if (status != HAL_OK)
39+
{
40+
printf("[fdcan.c/can_init()] ERROR: Failed to run HAL_FDCAN_ActivateNotification(can->hcan, FDCAN_IT_BUS_OFF, 1); (Status: %d).\n", status);
2941
return status;
3042
}
3143

@@ -101,6 +113,36 @@ HAL_StatusTypeDef can_add_filter_extended(can_t *can, uint32_t can_ids[2])
101113
return status;
102114
}
103115

116+
/* Returns true if the CAN node is in bus-off state. */
117+
bool can_is_bus_off(can_t *can) {
118+
FDCAN_ProtocolStatusTypeDef status;
119+
HAL_FDCAN_GetProtocolStatus(can->hcan, &status);
120+
return (bool)status.BusOff;
121+
}
122+
123+
/* Recovers from bus-off by stopping and restarting the FDCAN peripheral.
124+
Filters survive Stop/Start but notifications do not, so RX FIFO interrupt is re-enabled. */
125+
HAL_StatusTypeDef can_recover_bus_off(can_t *can) {
126+
HAL_StatusTypeDef status = HAL_FDCAN_Stop(can->hcan);
127+
if (status != HAL_OK) {
128+
printf("[fdcan.c/can_recover_bus_off()] ERROR: HAL_FDCAN_Stop() failed (Status: %d).\n", status);
129+
return status;
130+
}
131+
132+
status = HAL_FDCAN_Start(can->hcan);
133+
if (status != HAL_OK) {
134+
printf("[fdcan.c/can_recover_bus_off()] ERROR: HAL_FDCAN_Start() failed (Status: %d).\n", status);
135+
return status;
136+
}
137+
138+
status = HAL_FDCAN_ActivateNotification(can->hcan, FDCAN_IT_RX_FIFO0_NEW_MESSAGE, 0);
139+
if (status != HAL_OK) {
140+
printf("[fdcan.c/can_recover_bus_off()] ERROR: HAL_FDCAN_ActivateNotification() failed (Status: %d).\n", status);
141+
}
142+
143+
return status;
144+
}
145+
104146
/* Sends a CAN message. */
105147
HAL_StatusTypeDef can_send_msg(can_t *can, can_msg_t *msg)
106148
{

0 commit comments

Comments
 (0)