diff --git a/os/hal/include/can.h b/os/hal/include/can.h index 9fd9a09ca..fe4386089 100644 --- a/os/hal/include/can.h +++ b/os/hal/include/can.h @@ -38,23 +38,23 @@ /** * @brief Errors rate warning. */ -#define CAN_LIMIT_WARNING 1 +#define CAN_LIMIT_WARNING 1U /** * @brief Errors rate error. */ -#define CAN_LIMIT_ERROR 2 +#define CAN_LIMIT_ERROR 2U /** * @brief Bus off condition reached. */ -#define CAN_BUS_OFF_ERROR 4 +#define CAN_BUS_OFF_ERROR 4U /** * @brief Framing error of some kind on the CAN bus. */ -#define CAN_FRAMING_ERROR 8 +#define CAN_FRAMING_ERROR 8U /** * @brief Overflow in receive queue. */ -#define CAN_OVERFLOW_ERROR 16 +#define CAN_OVERFLOW_ERROR 16U /** @} */ /** @@ -113,7 +113,7 @@ typedef enum { /** * @brief Converts a mailbox index to a bit mask. */ -#define CAN_MAILBOX_TO_MASK(mbx) (1 << ((mbx) - 1)) +#define CAN_MAILBOX_TO_MASK(mbx) (1U << ((mbx) - 1U)) /** @} */ /*===========================================================================*/ diff --git a/os/hal/ports/STM32/LLD/CANv1/can_lld.c b/os/hal/ports/STM32/LLD/CANv1/can_lld.c index 7bca76d8e..485a08c79 100644 --- a/os/hal/ports/STM32/LLD/CANv1/can_lld.c +++ b/os/hal/ports/STM32/LLD/CANv1/can_lld.c @@ -142,12 +142,50 @@ static void can_lld_set_filters(uint32_t can2sb, * @notapi */ static void can_lld_tx_handler(CANDriver *canp) { + uint32_t tsr; + eventflags_t flags; - /* No more events until a message is transmitted.*/ - canp->can->TSR = CAN_TSR_RQCP0 | CAN_TSR_RQCP1 | CAN_TSR_RQCP2; + /* Clearing IRQ sources.*/ + tsr = canp->can->TSR; + canp->can->TSR = tsr; + + /* Flags to be signaled through the TX event source.*/ + flags = 0U; + + /* Checking mailbox 0.*/ + if ((tsr & CAN_TSR_RQCP0) != 0U) { + if ((tsr & (CAN_TSR_ALST0 | CAN_TSR_TERR0)) != 0U) { + flags |= CAN_MAILBOX_TO_MASK(1U) << 16U; + } + else { + flags |= CAN_MAILBOX_TO_MASK(1U); + } + } + + /* Checking mailbox 1.*/ + if ((tsr & CAN_TSR_RQCP1) != 0U) { + if ((tsr & (CAN_TSR_ALST1 | CAN_TSR_TERR1)) != 0U) { + flags |= CAN_MAILBOX_TO_MASK(2U) << 16U; + } + else { + flags |= CAN_MAILBOX_TO_MASK(2U); + } + } + + /* Checking mailbox 2.*/ + if ((tsr & CAN_TSR_RQCP2) != 0U) { + if ((tsr & (CAN_TSR_ALST2 | CAN_TSR_TERR2)) != 0U) { + flags |= CAN_MAILBOX_TO_MASK(3U) << 16U; + } + else { + flags |= CAN_MAILBOX_TO_MASK(3U); + } + } + + /* Signaling flags and waking up threads waiting for a transmission slot.*/ osalSysLockFromISR(); osalThreadDequeueAllI(&canp->txqueue, MSG_OK); - osalEventBroadcastFlagsI(&canp->txempty_event, CAN_MAILBOX_TO_MASK(1)); + osalEventBroadcastFlagsI(&canp->txempty_event, flags); osalSysUnlockFromISR(); } @@ -167,7 +205,7 @@ static void can_lld_rx0_handler(CANDriver *canp) { canp->can->IER &= ~CAN_IER_FMPIE0; osalSysLockFromISR(); osalThreadDequeueAllI(&canp->rxqueue, MSG_OK); - osalEventBroadcastFlagsI(&canp->rxfull_event, CAN_MAILBOX_TO_MASK(1)); + osalEventBroadcastFlagsI(&canp->rxfull_event, CAN_MAILBOX_TO_MASK(1U)); osalSysUnlockFromISR(); } if ((rf0r & CAN_RF0R_FOVR0) > 0) { @@ -195,7 +233,7 @@ static void can_lld_rx1_handler(CANDriver *canp) { canp->can->IER &= ~CAN_IER_FMPIE1; osalSysLockFromISR(); osalThreadDequeueAllI(&canp->rxqueue, MSG_OK); - osalEventBroadcastFlagsI(&canp->rxfull_event, CAN_MAILBOX_TO_MASK(2)); + osalEventBroadcastFlagsI(&canp->rxfull_event, CAN_MAILBOX_TO_MASK(2U)); osalSysUnlockFromISR(); } if ((rf1r & CAN_RF1R_FOVR1) > 0) { diff --git a/os/hal/ports/STM32/LLD/CANv1/can_lld.h b/os/hal/ports/STM32/LLD/CANv1/can_lld.h index 6297449c6..4a288cf3e 100644 --- a/os/hal/ports/STM32/LLD/CANv1/can_lld.h +++ b/os/hal/ports/STM32/LLD/CANv1/can_lld.h @@ -282,7 +282,7 @@ typedef struct { * until the received frames queue has been completely emptied. It * is not broadcasted for each received frame. It is * responsibility of the application to empty the queue by - * repeatedly invoking @p chReceive() when listening to this event. + * repeatedly invoking @p canReceive() when listening to this event. * This behavior minimizes the interrupt served by the system * because CAN traffic. * @note The flags associated to the listeners will indicate which @@ -293,13 +293,17 @@ typedef struct { * @brief One or more transmission mailbox become available. * @note The flags associated to the listeners will indicate which * transmit mailboxes become empty. + * @note The upper 16 bits are transmission error flags associated + * to the transmit mailboxes. * */ event_source_t txempty_event; /** * @brief A CAN bus error happened. - * @note The flags associated to the listeners will indicate the - * error(s) that have occurred. + * @note The flags associated to the listeners will indicate that + * receive error(s) have occurred. + * @note In this implementation the upper 16 bits are filled with the + * unprocessed content of the ESR register. */ event_source_t error_event; #if CAN_USE_SLEEP_MODE || defined (__DOXYGEN__) diff --git a/os/hal/ports/STM32/STM32L4xx/stm32_registry.h b/os/hal/ports/STM32/STM32L4xx/stm32_registry.h index 4c684760d..95bb46a10 100644 --- a/os/hal/ports/STM32/STM32L4xx/stm32_registry.h +++ b/os/hal/ports/STM32/STM32L4xx/stm32_registry.h @@ -61,6 +61,14 @@ #define STM32_HAS_CAN1 TRUE #define STM32_HAS_CAN2 FALSE #define STM32_CAN_MAX_FILTERS 14 +#define STM32_CAN1_TX_HANDLER Vector8C +#define STM32_CAN1_RX0_HANDLER Vector90 +#define STM32_CAN1_RX1_HANDLER Vector94 +#define STM32_CAN1_SCE_HANDLER Vector98 +#define STM32_CAN1_TX_NUMBER 19 +#define STM32_CAN1_RX0_NUMBER 20 +#define STM32_CAN1_RX1_NUMBER 21 +#define STM32_CAN1_SCE_NUMBER 22 /* DAC attributes.*/ #define STM32_HAS_DAC1_CH1 TRUE diff --git a/testhal/STM32/STM32L4xx/CAN/debug/STM32L4xx-CAN (OpenOCD, Flash and Run).launch b/testhal/STM32/STM32L4xx/CAN/debug/STM32L4xx-CAN (OpenOCD, Flash and Run).launch index 30b653f3f..f3fc038e1 100644 --- a/testhal/STM32/STM32L4xx/CAN/debug/STM32L4xx-CAN (OpenOCD, Flash and Run).launch +++ b/testhal/STM32/STM32L4xx/CAN/debug/STM32L4xx-CAN (OpenOCD, Flash and Run).launch @@ -33,7 +33,7 @@ - +