From 6fe547114d89cae6a83a92599828479270f4541b Mon Sep 17 00:00:00 2001 From: Yuan Yu Date: Wed, 20 Aug 2025 10:20:21 +0800 Subject: [PATCH] refactor(twai): Optimize the TWAI frame parsing function and separate frame header and data parsing logic --- components/hal/esp32/include/hal/twai_ll.h | 50 +++++++++++-------- components/hal/esp32c3/include/hal/twai_ll.h | 50 +++++++++++-------- components/hal/esp32c6/include/hal/twai_ll.h | 50 +++++++++++-------- components/hal/esp32h2/include/hal/twai_ll.h | 50 +++++++++++-------- components/hal/esp32h21/include/hal/twai_ll.h | 50 +++++++++++-------- components/hal/esp32p4/include/hal/twai_ll.h | 50 +++++++++++-------- components/hal/esp32s2/include/hal/twai_ll.h | 50 +++++++++++-------- components/hal/esp32s3/include/hal/twai_ll.h | 50 +++++++++++-------- components/hal/twai_hal_sja1000.c | 8 +-- 9 files changed, 236 insertions(+), 172 deletions(-) diff --git a/components/hal/esp32/include/hal/twai_ll.h b/components/hal/esp32/include/hal/twai_ll.h index 26585c7995..59a0513d7e 100644 --- a/components/hal/esp32/include/hal/twai_ll.h +++ b/components/hal/esp32/include/hal/twai_ll.h @@ -702,7 +702,7 @@ static inline void twai_ll_set_tx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t * @param hw Start address of the TWAI registers * @param rx_frame Pointer to store formatted frame * - * @note Call twai_ll_parse_frame_buffer() to parse the formatted frame + * @note Call twai_hal_parse_frame() to parse the formatted frame */ __attribute__((always_inline)) static inline void twai_ll_get_rx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t *rx_frame) @@ -776,47 +776,55 @@ static inline bool twai_ll_frame_is_ext_format(twai_ll_frame_buffer_t *rx_frame) } /** - * @brief Parse formatted TWAI frame (RX Buffer Layout) into its constituent contents + * @brief Parse formatted TWAI frame header (RX Buffer Layout) into twai_frame_header_t * * @param[in] rx_frame Pointer to formatted frame - * @param[out] id 11 or 29bit ID - * @param[out] dlc Data length code - * @param[out] data Data. Left over bytes set to 0. - * @param[out] format Type of TWAI frame + * @param[out] header Pointer to frame header structure */ __attribute__((always_inline)) -static inline void twai_ll_parse_frame_buffer(twai_ll_frame_buffer_t *rx_frame, uint32_t *id, uint8_t *dlc, - uint8_t *data, uint32_t buf_sz, uint32_t *flags) +static inline void twai_ll_parse_frame_header(const twai_ll_frame_buffer_t *rx_frame, twai_frame_header_t *header) { - //Copy frame information - *dlc = rx_frame->dlc; - uint32_t flags_temp = 0; - flags_temp |= (rx_frame->frame_format) ? TWAI_MSG_FLAG_EXTD : 0; - flags_temp |= (rx_frame->rtr) ? TWAI_MSG_FLAG_RTR : 0; - flags_temp |= (rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_MSG_FLAG_DLC_NON_COMP : 0; - *flags = flags_temp; + // Copy frame information + header->dlc = rx_frame->dlc; + header->ide = rx_frame->frame_format; + header->rtr = rx_frame->rtr; + header->fdf = 0; + header->brs = 0; + header->esi = 0; + header->timestamp = 0; - //Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required + // Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required if (rx_frame->frame_format) { uint32_t id_temp = 0; for (int i = 0; i < 4; i++) { id_temp |= rx_frame->extended.id[i] << (8 * i); } id_temp = HAL_SWAP32(id_temp) >> 3; //((byte[i] << 8*(3-i)) >> 3) - *id = id_temp & TWAI_EXTD_ID_MASK; + header->id = id_temp & TWAI_EXTD_ID_MASK; } else { uint32_t id_temp = 0; for (int i = 0; i < 2; i++) { id_temp |= rx_frame->standard.id[i] << (8 * i); } id_temp = HAL_SWAP16(id_temp) >> 5; //((byte[i] << 8*(1-i)) >> 5) - *id = id_temp & TWAI_STD_ID_MASK; + header->id = id_temp & TWAI_STD_ID_MASK; } +} - uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; - //Only copy data if the frame is a data frame (i.e. not a remote frame) +/** + * @brief Parse formatted TWAI frame data (RX Buffer Layout) into data buffer + * + * @param[in] rx_frame Pointer to formatted frame + * @param[out] data Pointer to data buffer + * @param[in] data_len_limit The data length limit, if less than frame data length, over length data will be dropped + */ +__attribute__((always_inline)) +static inline void twai_ll_parse_frame_data(const twai_ll_frame_buffer_t *rx_frame, uint8_t *data, uint8_t data_len_limit) +{ + const uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; + // Only copy data if the frame is a data frame (i.e. not a remote frame) int data_length = (rx_frame->rtr) ? 0 : ((rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_FRAME_MAX_DLC : rx_frame->dlc); - data_length = (data_length < buf_sz) ? data_length : buf_sz; + data_length = (data_length < data_len_limit) ? data_length : data_len_limit; for (int i = 0; i < data_length; i++) { data[i] = data_buffer[i]; } diff --git a/components/hal/esp32c3/include/hal/twai_ll.h b/components/hal/esp32c3/include/hal/twai_ll.h index da6e7c0c20..a1a7c3d059 100644 --- a/components/hal/esp32c3/include/hal/twai_ll.h +++ b/components/hal/esp32c3/include/hal/twai_ll.h @@ -647,7 +647,7 @@ static inline void twai_ll_set_tx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t * @param hw Start address of the TWAI registers * @param rx_frame Pointer to store formatted frame * - * @note Call twai_ll_parse_frame_buffer() to parse the formatted frame + * @note Call twai_hal_parse_frame() to parse the formatted frame */ __attribute__((always_inline)) static inline void twai_ll_get_rx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t *rx_frame) @@ -721,47 +721,55 @@ static inline bool twai_ll_frame_is_ext_format(twai_ll_frame_buffer_t *rx_frame) } /** - * @brief Parse formatted TWAI frame (RX Buffer Layout) into its constituent contents + * @brief Parse formatted TWAI frame header (RX Buffer Layout) into twai_frame_header_t * * @param[in] rx_frame Pointer to formatted frame - * @param[out] id 11 or 29bit ID - * @param[out] dlc Data length code - * @param[out] data Data. Left over bytes set to 0. - * @param[out] format Type of TWAI frame + * @param[out] header Pointer to frame header structure */ __attribute__((always_inline)) -static inline void twai_ll_parse_frame_buffer(twai_ll_frame_buffer_t *rx_frame, uint32_t *id, uint8_t *dlc, - uint8_t *data, uint32_t buf_sz, uint32_t *flags) +static inline void twai_ll_parse_frame_header(const twai_ll_frame_buffer_t *rx_frame, twai_frame_header_t *header) { - //Copy frame information - *dlc = rx_frame->dlc; - uint32_t flags_temp = 0; - flags_temp |= (rx_frame->frame_format) ? TWAI_MSG_FLAG_EXTD : 0; - flags_temp |= (rx_frame->rtr) ? TWAI_MSG_FLAG_RTR : 0; - flags_temp |= (rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_MSG_FLAG_DLC_NON_COMP : 0; - *flags = flags_temp; + // Copy frame information + header->dlc = rx_frame->dlc; + header->ide = rx_frame->frame_format; + header->rtr = rx_frame->rtr; + header->fdf = 0; + header->brs = 0; + header->esi = 0; + header->timestamp = 0; - //Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required + // Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required if (rx_frame->frame_format) { uint32_t id_temp = 0; for (int i = 0; i < 4; i++) { id_temp |= rx_frame->extended.id[i] << (8 * i); } id_temp = HAL_SWAP32(id_temp) >> 3; //((byte[i] << 8*(3-i)) >> 3) - *id = id_temp & TWAI_EXTD_ID_MASK; + header->id = id_temp & TWAI_EXTD_ID_MASK; } else { uint32_t id_temp = 0; for (int i = 0; i < 2; i++) { id_temp |= rx_frame->standard.id[i] << (8 * i); } id_temp = HAL_SWAP16(id_temp) >> 5; //((byte[i] << 8*(1-i)) >> 5) - *id = id_temp & TWAI_STD_ID_MASK; + header->id = id_temp & TWAI_STD_ID_MASK; } +} - uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; - //Only copy data if the frame is a data frame (i.e. not a remote frame) +/** + * @brief Parse formatted TWAI frame data (RX Buffer Layout) into data buffer + * + * @param[in] rx_frame Pointer to formatted frame + * @param[out] data Pointer to data buffer + * @param[in] data_len_limit The data length limit, if less than frame data length, over length data will be dropped + */ +__attribute__((always_inline)) +static inline void twai_ll_parse_frame_data(const twai_ll_frame_buffer_t *rx_frame, uint8_t *data, uint8_t data_len_limit) +{ + const uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; + // Only copy data if the frame is a data frame (i.e. not a remote frame) int data_length = (rx_frame->rtr) ? 0 : ((rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_FRAME_MAX_DLC : rx_frame->dlc); - data_length = (data_length < buf_sz) ? data_length : buf_sz; + data_length = (data_length < data_len_limit) ? data_length : data_len_limit; for (int i = 0; i < data_length; i++) { data[i] = data_buffer[i]; } diff --git a/components/hal/esp32c6/include/hal/twai_ll.h b/components/hal/esp32c6/include/hal/twai_ll.h index badf11a27e..86a947a4a2 100644 --- a/components/hal/esp32c6/include/hal/twai_ll.h +++ b/components/hal/esp32c6/include/hal/twai_ll.h @@ -663,7 +663,7 @@ static inline void twai_ll_set_tx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t * @param hw Start address of the TWAI registers * @param rx_frame Pointer to store formatted frame * - * @note Call twai_ll_parse_frame_buffer() to parse the formatted frame + * @note Call twai_hal_parse_frame() to parse the formatted frame */ __attribute__((always_inline)) static inline void twai_ll_get_rx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t *rx_frame) @@ -737,47 +737,55 @@ static inline bool twai_ll_frame_is_ext_format(twai_ll_frame_buffer_t *rx_frame) } /** - * @brief Parse formatted TWAI frame (RX Buffer Layout) into its constituent contents + * @brief Parse formatted TWAI frame header (RX Buffer Layout) into twai_frame_header_t * * @param[in] rx_frame Pointer to formatted frame - * @param[out] id 11 or 29bit ID - * @param[out] dlc Data length code - * @param[out] data Data. Left over bytes set to 0. - * @param[out] format Type of TWAI frame + * @param[out] header Pointer to frame header structure */ __attribute__((always_inline)) -static inline void twai_ll_parse_frame_buffer(twai_ll_frame_buffer_t *rx_frame, uint32_t *id, uint8_t *dlc, - uint8_t *data, uint32_t buf_sz, uint32_t *flags) +static inline void twai_ll_parse_frame_header(const twai_ll_frame_buffer_t *rx_frame, twai_frame_header_t *header) { - //Copy frame information - *dlc = rx_frame->dlc; - uint32_t flags_temp = 0; - flags_temp |= (rx_frame->frame_format) ? TWAI_MSG_FLAG_EXTD : 0; - flags_temp |= (rx_frame->rtr) ? TWAI_MSG_FLAG_RTR : 0; - flags_temp |= (rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_MSG_FLAG_DLC_NON_COMP : 0; - *flags = flags_temp; + // Copy frame information + header->dlc = rx_frame->dlc; + header->ide = rx_frame->frame_format; + header->rtr = rx_frame->rtr; + header->fdf = 0; + header->brs = 0; + header->esi = 0; + header->timestamp = 0; - //Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required + // Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required if (rx_frame->frame_format) { uint32_t id_temp = 0; for (int i = 0; i < 4; i++) { id_temp |= rx_frame->extended.id[i] << (8 * i); } id_temp = HAL_SWAP32(id_temp) >> 3; //((byte[i] << 8*(3-i)) >> 3) - *id = id_temp & TWAI_EXTD_ID_MASK; + header->id = id_temp & TWAI_EXTD_ID_MASK; } else { uint32_t id_temp = 0; for (int i = 0; i < 2; i++) { id_temp |= rx_frame->standard.id[i] << (8 * i); } id_temp = HAL_SWAP16(id_temp) >> 5; //((byte[i] << 8*(1-i)) >> 5) - *id = id_temp & TWAI_STD_ID_MASK; + header->id = id_temp & TWAI_STD_ID_MASK; } +} - uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; - //Only copy data if the frame is a data frame (i.e. not a remote frame) +/** + * @brief Parse formatted TWAI frame data (RX Buffer Layout) into data buffer + * + * @param[in] rx_frame Pointer to formatted frame + * @param[out] data Pointer to data buffer + * @param[in] data_len_limit The data length limit, if less than frame data length, over length data will be dropped + */ +__attribute__((always_inline)) +static inline void twai_ll_parse_frame_data(const twai_ll_frame_buffer_t *rx_frame, uint8_t *data, uint8_t data_len_limit) +{ + const uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; + // Only copy data if the frame is a data frame (i.e. not a remote frame) int data_length = (rx_frame->rtr) ? 0 : ((rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_FRAME_MAX_DLC : rx_frame->dlc); - data_length = (data_length < buf_sz) ? data_length : buf_sz; + data_length = (data_length < data_len_limit) ? data_length : data_len_limit; for (int i = 0; i < data_length; i++) { data[i] = data_buffer[i]; } diff --git a/components/hal/esp32h2/include/hal/twai_ll.h b/components/hal/esp32h2/include/hal/twai_ll.h index 7e40b972d2..d1edfe429f 100644 --- a/components/hal/esp32h2/include/hal/twai_ll.h +++ b/components/hal/esp32h2/include/hal/twai_ll.h @@ -641,7 +641,7 @@ static inline void twai_ll_set_tx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t * @param hw Start address of the TWAI registers * @param rx_frame Pointer to store formatted frame * - * @note Call twai_ll_parse_frame_buffer() to parse the formatted frame + * @note Call twai_hal_parse_frame() to parse the formatted frame */ __attribute__((always_inline)) static inline void twai_ll_get_rx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t *rx_frame) @@ -715,47 +715,55 @@ static inline bool twai_ll_frame_is_ext_format(twai_ll_frame_buffer_t *rx_frame) } /** - * @brief Parse formatted TWAI frame (RX Buffer Layout) into its constituent contents + * @brief Parse formatted TWAI frame header (RX Buffer Layout) into twai_frame_header_t * * @param[in] rx_frame Pointer to formatted frame - * @param[out] id 11 or 29bit ID - * @param[out] dlc Data length code - * @param[out] data Data. Left over bytes set to 0. - * @param[out] format Type of TWAI frame + * @param[out] header Pointer to frame header structure */ __attribute__((always_inline)) -static inline void twai_ll_parse_frame_buffer(twai_ll_frame_buffer_t *rx_frame, uint32_t *id, uint8_t *dlc, - uint8_t *data, uint32_t buf_sz, uint32_t *flags) +static inline void twai_ll_parse_frame_header(const twai_ll_frame_buffer_t *rx_frame, twai_frame_header_t *header) { - //Copy frame information - *dlc = rx_frame->dlc; - uint32_t flags_temp = 0; - flags_temp |= (rx_frame->frame_format) ? TWAI_MSG_FLAG_EXTD : 0; - flags_temp |= (rx_frame->rtr) ? TWAI_MSG_FLAG_RTR : 0; - flags_temp |= (rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_MSG_FLAG_DLC_NON_COMP : 0; - *flags = flags_temp; + // Copy frame information + header->dlc = rx_frame->dlc; + header->ide = rx_frame->frame_format; + header->rtr = rx_frame->rtr; + header->fdf = 0; + header->brs = 0; + header->esi = 0; + header->timestamp = 0; - //Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required + // Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required if (rx_frame->frame_format) { uint32_t id_temp = 0; for (int i = 0; i < 4; i++) { id_temp |= rx_frame->extended.id[i] << (8 * i); } id_temp = HAL_SWAP32(id_temp) >> 3; //((byte[i] << 8*(3-i)) >> 3) - *id = id_temp & TWAI_EXTD_ID_MASK; + header->id = id_temp & TWAI_EXTD_ID_MASK; } else { uint32_t id_temp = 0; for (int i = 0; i < 2; i++) { id_temp |= rx_frame->standard.id[i] << (8 * i); } id_temp = HAL_SWAP16(id_temp) >> 5; //((byte[i] << 8*(1-i)) >> 5) - *id = id_temp & TWAI_STD_ID_MASK; + header->id = id_temp & TWAI_STD_ID_MASK; } +} - uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; - //Only copy data if the frame is a data frame (i.e. not a remote frame) +/** + * @brief Parse formatted TWAI frame data (RX Buffer Layout) into data buffer + * + * @param[in] rx_frame Pointer to formatted frame + * @param[out] data Pointer to data buffer + * @param[in] data_len_limit The data length limit, if less than frame data length, over length data will be dropped + */ +__attribute__((always_inline)) +static inline void twai_ll_parse_frame_data(const twai_ll_frame_buffer_t *rx_frame, uint8_t *data, uint8_t data_len_limit) +{ + const uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; + // Only copy data if the frame is a data frame (i.e. not a remote frame) int data_length = (rx_frame->rtr) ? 0 : ((rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_FRAME_MAX_DLC : rx_frame->dlc); - data_length = (data_length < buf_sz) ? data_length : buf_sz; + data_length = (data_length < data_len_limit) ? data_length : data_len_limit; for (int i = 0; i < data_length; i++) { data[i] = data_buffer[i]; } diff --git a/components/hal/esp32h21/include/hal/twai_ll.h b/components/hal/esp32h21/include/hal/twai_ll.h index 5bf5ed818f..3757cd4d0a 100644 --- a/components/hal/esp32h21/include/hal/twai_ll.h +++ b/components/hal/esp32h21/include/hal/twai_ll.h @@ -641,7 +641,7 @@ static inline void twai_ll_set_tx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t * @param hw Start address of the TWAI registers * @param rx_frame Pointer to store formatted frame * - * @note Call twai_ll_parse_frame_buffer() to parse the formatted frame + * @note Call twai_hal_parse_frame() to parse the formatted frame */ __attribute__((always_inline)) static inline void twai_ll_get_rx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t *rx_frame) @@ -715,47 +715,55 @@ static inline bool twai_ll_frame_is_ext_format(twai_ll_frame_buffer_t *rx_frame) } /** - * @brief Parse formatted TWAI frame (RX Buffer Layout) into its constituent contents + * @brief Parse formatted TWAI frame header (RX Buffer Layout) into twai_frame_header_t * * @param[in] rx_frame Pointer to formatted frame - * @param[out] id 11 or 29bit ID - * @param[out] dlc Data length code - * @param[out] data Data. Left over bytes set to 0. - * @param[out] format Type of TWAI frame + * @param[out] header Pointer to frame header structure */ __attribute__((always_inline)) -static inline void twai_ll_parse_frame_buffer(twai_ll_frame_buffer_t *rx_frame, uint32_t *id, uint8_t *dlc, - uint8_t *data, uint32_t buf_sz, uint32_t *flags) +static inline void twai_ll_parse_frame_header(const twai_ll_frame_buffer_t *rx_frame, twai_frame_header_t *header) { - //Copy frame information - *dlc = rx_frame->dlc; - uint32_t flags_temp = 0; - flags_temp |= (rx_frame->frame_format) ? TWAI_MSG_FLAG_EXTD : 0; - flags_temp |= (rx_frame->rtr) ? TWAI_MSG_FLAG_RTR : 0; - flags_temp |= (rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_MSG_FLAG_DLC_NON_COMP : 0; - *flags = flags_temp; + // Copy frame information + header->dlc = rx_frame->dlc; + header->ide = rx_frame->frame_format; + header->rtr = rx_frame->rtr; + header->fdf = 0; + header->brs = 0; + header->esi = 0; + header->timestamp = 0; - //Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required + // Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required if (rx_frame->frame_format) { uint32_t id_temp = 0; for (int i = 0; i < 4; i++) { id_temp |= rx_frame->extended.id[i] << (8 * i); } id_temp = HAL_SWAP32(id_temp) >> 3; //((byte[i] << 8*(3-i)) >> 3) - *id = id_temp & TWAI_EXTD_ID_MASK; + header->id = id_temp & TWAI_EXTD_ID_MASK; } else { uint32_t id_temp = 0; for (int i = 0; i < 2; i++) { id_temp |= rx_frame->standard.id[i] << (8 * i); } id_temp = HAL_SWAP16(id_temp) >> 5; //((byte[i] << 8*(1-i)) >> 5) - *id = id_temp & TWAI_STD_ID_MASK; + header->id = id_temp & TWAI_STD_ID_MASK; } +} - uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; - //Only copy data if the frame is a data frame (i.e. not a remote frame) +/** + * @brief Parse formatted TWAI frame data (RX Buffer Layout) into data buffer + * + * @param[in] rx_frame Pointer to formatted frame + * @param[out] data Pointer to data buffer + * @param[in] data_len_limit The data length limit, if less than frame data length, over length data will be dropped + */ +__attribute__((always_inline)) +static inline void twai_ll_parse_frame_data(const twai_ll_frame_buffer_t *rx_frame, uint8_t *data, uint8_t data_len_limit) +{ + const uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; + // Only copy data if the frame is a data frame (i.e. not a remote frame) int data_length = (rx_frame->rtr) ? 0 : ((rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_FRAME_MAX_DLC : rx_frame->dlc); - data_length = (data_length < buf_sz) ? data_length : buf_sz; + data_length = (data_length < data_len_limit) ? data_length : data_len_limit; for (int i = 0; i < data_length; i++) { data[i] = data_buffer[i]; } diff --git a/components/hal/esp32p4/include/hal/twai_ll.h b/components/hal/esp32p4/include/hal/twai_ll.h index d23affc076..fb68f9a761 100644 --- a/components/hal/esp32p4/include/hal/twai_ll.h +++ b/components/hal/esp32p4/include/hal/twai_ll.h @@ -696,7 +696,7 @@ static inline void twai_ll_set_tx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t * @param hw Start address of the TWAI registers * @param rx_frame Pointer to store formatted frame * - * @note Call twai_ll_parse_frame_buffer() to parse the formatted frame + * @note Call twai_hal_parse_frame() to parse the formatted frame */ __attribute__((always_inline)) static inline void twai_ll_get_rx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t *rx_frame) @@ -769,47 +769,55 @@ static inline bool twai_ll_frame_is_ext_format(twai_ll_frame_buffer_t *rx_frame) } /** - * @brief Parse formatted TWAI frame (RX Buffer Layout) into its constituent contents + * @brief Parse formatted TWAI frame header (RX Buffer Layout) into twai_frame_header_t * * @param[in] rx_frame Pointer to formatted frame - * @param[out] id 11 or 29bit ID - * @param[out] dlc Data length code - * @param[out] data Data. Left over bytes set to 0. - * @param[out] format Type of TWAI frame + * @param[out] header Pointer to frame header structure */ __attribute__((always_inline)) -static inline void twai_ll_parse_frame_buffer(twai_ll_frame_buffer_t *rx_frame, uint32_t *id, uint8_t *dlc, - uint8_t *data, uint32_t buf_sz, uint32_t *flags) +static inline void twai_ll_parse_frame_header(const twai_ll_frame_buffer_t *rx_frame, twai_frame_header_t *header) { - //Copy frame information - *dlc = rx_frame->dlc; - uint32_t flags_temp = 0; - flags_temp |= (rx_frame->frame_format) ? TWAI_MSG_FLAG_EXTD : 0; - flags_temp |= (rx_frame->rtr) ? TWAI_MSG_FLAG_RTR : 0; - flags_temp |= (rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_MSG_FLAG_DLC_NON_COMP : 0; - *flags = flags_temp; + // Copy frame information + header->dlc = rx_frame->dlc; + header->ide = rx_frame->frame_format; + header->rtr = rx_frame->rtr; + header->fdf = 0; + header->brs = 0; + header->esi = 0; + header->timestamp = 0; - //Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required + // Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required if (rx_frame->frame_format) { uint32_t id_temp = 0; for (int i = 0; i < 4; i++) { id_temp |= rx_frame->extended.id[i] << (8 * i); } id_temp = HAL_SWAP32(id_temp) >> 3; //((byte[i] << 8*(3-i)) >> 3) - *id = id_temp & TWAI_EXTD_ID_MASK; + header->id = id_temp & TWAI_EXTD_ID_MASK; } else { uint32_t id_temp = 0; for (int i = 0; i < 2; i++) { id_temp |= rx_frame->standard.id[i] << (8 * i); } id_temp = HAL_SWAP16(id_temp) >> 5; //((byte[i] << 8*(1-i)) >> 5) - *id = id_temp & TWAI_STD_ID_MASK; + header->id = id_temp & TWAI_STD_ID_MASK; } +} - uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; - //Only copy data if the frame is a data frame (i.e. not a remote frame) +/** + * @brief Parse formatted TWAI frame data (RX Buffer Layout) into data buffer + * + * @param[in] rx_frame Pointer to formatted frame + * @param[out] data Pointer to data buffer + * @param[in] data_len_limit The data length limit, if less than frame data length, over length data will be dropped + */ +__attribute__((always_inline)) +static inline void twai_ll_parse_frame_data(const twai_ll_frame_buffer_t *rx_frame, uint8_t *data, uint8_t data_len_limit) +{ + const uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; + // Only copy data if the frame is a data frame (i.e. not a remote frame) int data_length = (rx_frame->rtr) ? 0 : ((rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_FRAME_MAX_DLC : rx_frame->dlc); - data_length = (data_length < buf_sz) ? data_length : buf_sz; + data_length = (data_length < data_len_limit) ? data_length : data_len_limit; for (int i = 0; i < data_length; i++) { data[i] = data_buffer[i]; } diff --git a/components/hal/esp32s2/include/hal/twai_ll.h b/components/hal/esp32s2/include/hal/twai_ll.h index 6dedd5ad32..a46717c2c5 100644 --- a/components/hal/esp32s2/include/hal/twai_ll.h +++ b/components/hal/esp32s2/include/hal/twai_ll.h @@ -650,7 +650,7 @@ static inline void twai_ll_set_tx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t * @param hw Start address of the TWAI registers * @param rx_frame Pointer to store formatted frame * - * @note Call twai_ll_parse_frame_buffer() to parse the formatted frame + * @note Call twai_hal_parse_frame() to parse the formatted frame */ __attribute__((always_inline)) static inline void twai_ll_get_rx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t *rx_frame) @@ -724,47 +724,55 @@ static inline bool twai_ll_frame_is_ext_format(twai_ll_frame_buffer_t *rx_frame) } /** - * @brief Parse formatted TWAI frame (RX Buffer Layout) into its constituent contents + * @brief Parse formatted TWAI frame header (RX Buffer Layout) into twai_frame_header_t * * @param[in] rx_frame Pointer to formatted frame - * @param[out] id 11 or 29bit ID - * @param[out] dlc Data length code - * @param[out] data Data. Left over bytes set to 0. - * @param[out] format Type of TWAI frame + * @param[out] header Pointer to frame header structure */ __attribute__((always_inline)) -static inline void twai_ll_parse_frame_buffer(twai_ll_frame_buffer_t *rx_frame, uint32_t *id, uint8_t *dlc, - uint8_t *data, uint32_t buf_sz, uint32_t *flags) +static inline void twai_ll_parse_frame_header(const twai_ll_frame_buffer_t *rx_frame, twai_frame_header_t *header) { - //Copy frame information - *dlc = rx_frame->dlc; - uint32_t flags_temp = 0; - flags_temp |= (rx_frame->frame_format) ? TWAI_MSG_FLAG_EXTD : 0; - flags_temp |= (rx_frame->rtr) ? TWAI_MSG_FLAG_RTR : 0; - flags_temp |= (rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_MSG_FLAG_DLC_NON_COMP : 0; - *flags = flags_temp; + // Copy frame information + header->dlc = rx_frame->dlc; + header->ide = rx_frame->frame_format; + header->rtr = rx_frame->rtr; + header->fdf = 0; + header->brs = 0; + header->esi = 0; + header->timestamp = 0; - //Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required + // Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required if (rx_frame->frame_format) { uint32_t id_temp = 0; for (int i = 0; i < 4; i++) { id_temp |= rx_frame->extended.id[i] << (8 * i); } id_temp = HAL_SWAP32(id_temp) >> 3; //((byte[i] << 8*(3-i)) >> 3) - *id = id_temp & TWAI_EXTD_ID_MASK; + header->id = id_temp & TWAI_EXTD_ID_MASK; } else { uint32_t id_temp = 0; for (int i = 0; i < 2; i++) { id_temp |= rx_frame->standard.id[i] << (8 * i); } id_temp = HAL_SWAP16(id_temp) >> 5; //((byte[i] << 8*(1-i)) >> 5) - *id = id_temp & TWAI_STD_ID_MASK; + header->id = id_temp & TWAI_STD_ID_MASK; } +} - uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; - //Only copy data if the frame is a data frame (i.e. not a remote frame) +/** + * @brief Parse formatted TWAI frame data (RX Buffer Layout) into data buffer + * + * @param[in] rx_frame Pointer to formatted frame + * @param[out] data Pointer to data buffer + * @param[in] data_len_limit The data length limit, if less than frame data length, over length data will be dropped + */ +__attribute__((always_inline)) +static inline void twai_ll_parse_frame_data(const twai_ll_frame_buffer_t *rx_frame, uint8_t *data, uint8_t data_len_limit) +{ + const uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; + // Only copy data if the frame is a data frame (i.e. not a remote frame) int data_length = (rx_frame->rtr) ? 0 : ((rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_FRAME_MAX_DLC : rx_frame->dlc); - data_length = (data_length < buf_sz) ? data_length : buf_sz; + data_length = (data_length < data_len_limit) ? data_length : data_len_limit; for (int i = 0; i < data_length; i++) { data[i] = data_buffer[i]; } diff --git a/components/hal/esp32s3/include/hal/twai_ll.h b/components/hal/esp32s3/include/hal/twai_ll.h index a89f1eb570..965f162859 100644 --- a/components/hal/esp32s3/include/hal/twai_ll.h +++ b/components/hal/esp32s3/include/hal/twai_ll.h @@ -647,7 +647,7 @@ static inline void twai_ll_set_tx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t * @param hw Start address of the TWAI registers * @param rx_frame Pointer to store formatted frame * - * @note Call twai_ll_parse_frame_buffer() to parse the formatted frame + * @note Call twai_hal_parse_frame() to parse the formatted frame */ __attribute__((always_inline)) static inline void twai_ll_get_rx_buffer(twai_dev_t *hw, twai_ll_frame_buffer_t *rx_frame) @@ -721,47 +721,55 @@ static inline bool twai_ll_frame_is_ext_format(twai_ll_frame_buffer_t *rx_frame) } /** - * @brief Parse formatted TWAI frame (RX Buffer Layout) into its constituent contents + * @brief Parse formatted TWAI frame header (RX Buffer Layout) into twai_frame_header_t * * @param[in] rx_frame Pointer to formatted frame - * @param[out] id 11 or 29bit ID - * @param[out] dlc Data length code - * @param[out] data Data. Left over bytes set to 0. - * @param[out] format Type of TWAI frame + * @param[out] header Pointer to frame header structure */ __attribute__((always_inline)) -static inline void twai_ll_parse_frame_buffer(twai_ll_frame_buffer_t *rx_frame, uint32_t *id, uint8_t *dlc, - uint8_t *data, uint32_t buf_sz, uint32_t *flags) +static inline void twai_ll_parse_frame_header(const twai_ll_frame_buffer_t *rx_frame, twai_frame_header_t *header) { - //Copy frame information - *dlc = rx_frame->dlc; - uint32_t flags_temp = 0; - flags_temp |= (rx_frame->frame_format) ? TWAI_MSG_FLAG_EXTD : 0; - flags_temp |= (rx_frame->rtr) ? TWAI_MSG_FLAG_RTR : 0; - flags_temp |= (rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_MSG_FLAG_DLC_NON_COMP : 0; - *flags = flags_temp; + // Copy frame information + header->dlc = rx_frame->dlc; + header->ide = rx_frame->frame_format; + header->rtr = rx_frame->rtr; + header->fdf = 0; + header->brs = 0; + header->esi = 0; + header->timestamp = 0; - //Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required + // Copy ID. The ID registers are big endian and left aligned, therefore a bswap will be required if (rx_frame->frame_format) { uint32_t id_temp = 0; for (int i = 0; i < 4; i++) { id_temp |= rx_frame->extended.id[i] << (8 * i); } id_temp = HAL_SWAP32(id_temp) >> 3; //((byte[i] << 8*(3-i)) >> 3) - *id = id_temp & TWAI_EXTD_ID_MASK; + header->id = id_temp & TWAI_EXTD_ID_MASK; } else { uint32_t id_temp = 0; for (int i = 0; i < 2; i++) { id_temp |= rx_frame->standard.id[i] << (8 * i); } id_temp = HAL_SWAP16(id_temp) >> 5; //((byte[i] << 8*(1-i)) >> 5) - *id = id_temp & TWAI_STD_ID_MASK; + header->id = id_temp & TWAI_STD_ID_MASK; } +} - uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; - //Only copy data if the frame is a data frame (i.e. not a remote frame) +/** + * @brief Parse formatted TWAI frame data (RX Buffer Layout) into data buffer + * + * @param[in] rx_frame Pointer to formatted frame + * @param[out] data Pointer to data buffer + * @param[in] data_len_limit The data length limit, if less than frame data length, over length data will be dropped + */ +__attribute__((always_inline)) +static inline void twai_ll_parse_frame_data(const twai_ll_frame_buffer_t *rx_frame, uint8_t *data, uint8_t data_len_limit) +{ + const uint8_t *data_buffer = (rx_frame->frame_format) ? rx_frame->extended.data : rx_frame->standard.data; + // Only copy data if the frame is a data frame (i.e. not a remote frame) int data_length = (rx_frame->rtr) ? 0 : ((rx_frame->dlc > TWAI_FRAME_MAX_DLC) ? TWAI_FRAME_MAX_DLC : rx_frame->dlc); - data_length = (data_length < buf_sz) ? data_length : buf_sz; + data_length = (data_length < data_len_limit) ? data_length : data_len_limit; for (int i = 0; i < data_length; i++) { data[i] = data_buffer[i]; } diff --git a/components/hal/twai_hal_sja1000.c b/components/hal/twai_hal_sja1000.c index 4c5c32ab09..3554123347 100644 --- a/components/hal/twai_hal_sja1000.c +++ b/components/hal/twai_hal_sja1000.c @@ -382,10 +382,10 @@ void twai_hal_format_frame(const twai_hal_trans_desc_t *trans_desc, twai_hal_fra void twai_hal_parse_frame(const twai_hal_frame_t *frame, twai_frame_header_t *header, uint8_t *buffer, uint8_t buffer_len) { - twai_message_t msg_flags = {0}; - twai_ll_parse_frame_buffer((twai_hal_frame_t *)frame, &header->id, (uint8_t *)&header->dlc, buffer, buffer_len, &msg_flags.flags); - header->ide = msg_flags.extd; - header->rtr = msg_flags.rtr; + twai_ll_parse_frame_header((const twai_ll_frame_buffer_t *)frame, header); + if (!header->rtr) { + twai_ll_parse_frame_data((const twai_ll_frame_buffer_t *)frame, buffer, buffer_len); + } } void twai_hal_set_tx_buffer_and_transmit(twai_hal_context_t *hal_ctx, twai_hal_frame_t *tx_frame, uint8_t buffer_idx)