Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add MSS CAN driver #337

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open

Conversation

haitomatic
Copy link

@haitomatic haitomatic commented Jan 9, 2025

  • Add MSS CAN driver to support MSS CAN pheripheral
  • Remove the unused canfd icicle config

@haitomatic haitomatic marked this pull request as draft January 9, 2025 13:34
@haitomatic haitomatic force-pushed the SSRCDP-10527_CAN_MSS_support branch from 601f100 to 17d7f06 Compare March 11, 2025 13:09
@haitomatic haitomatic marked this pull request as ready for review March 11, 2025 13:17
@haitomatic haitomatic requested a review from jpaali March 11, 2025 13:18
@jpaali jpaali requested a review from jlaitine March 11, 2025 13:36
@haitomatic haitomatic force-pushed the SSRCDP-10527_CAN_MSS_support branch from 17d7f06 to 2bb870d Compare March 11, 2025 14:00
Copy link

@jpaali jpaali left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

just took a quick look at this point.. looks good but need to take a closer look later

#define MPFS_CAN_ACR_AMR_IDE (1 << 2) /* IDE bit; 0: Check against ACR, 1: Don't care */
#define MPFS_CAN_ACR_AMR_RTR (1 << 1) /* RTR bit; 0: Check against ACR, 1: Don't care */

#endif /* __ARCH_RISCV_SRC_MPFS_HARDWARE_MPFS_CAN_H */

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Add a newline in the end of the line

****************************************************************************/

#define print_uint32_t(prefix, val) do { \
char binary_str[90]; /* 32 bits + "0b" + prefix + null terminator */ \

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Instead of 90, you could do

const char p_str[] = prefix; \
char binary_str[sizeof(p_str) + <needed size fo val>]; \

To make it safe... just a suggestion, I do see that 90 is enough in all uses below.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks for the optimized suggestion!

#ifdef CONFIG_NETDEV_CAN_FILTER_IOCTL
uint32_t can_id_masked = cf->can_id & CAN_ERR_MASK;

if (expect_true(!priv->filter.use_mask_filter

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

tinkering with expect is useless in general


/* Data (big endian) */

for (i = 0; i < dlc; i++)

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is just unnecessarily complicated. The cf->data is always 32-bit aligned in nuttx can frames (intentionally). Also your pmsg->data_high and low are 32-bit aligned.

So you can just:
*(uint32_t *)&cf->data[0] = __builtin_bswap32(pmsg->data_high);
*(uint32_t *)&cf->data[4] = __builtin_bswap32(pmsg->data_low);

If in doubt, add a debugassertion for the alignment.....

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes, this's much more elegant operation. i forgot about that. thanks!


if (!(pmsg->msg_ctrl & MPFS_CAN_TX_MSG_CTRL_CMD_RTR))
{
for (i = 0; i < cf->can_dlc; i++)

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is again unnecessary complicated, imho. you can just copy&bswap both 32-bit words as in receive

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes, that's much more elegant operation. i forgot about that. thanks!

canwarn("Failed to send CAN frame due to %s\n",
ret == CAN_INVALID_BUFFER ? "invalid buffer" :
ret == CAN_NO_MSG ? "no TX buffer available" : "unknown err");
return CAN_OK;

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why return CAN_OK in case of failure?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes, err return handling of mpfs_transmit will be fixed. thanks!

{
/* Send the packet */

mpfs_transmit(priv);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should check the return value and return error (probably -EINVAL) in case of != CAN_OK

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes, err return handling of mpfs_transmit will be fixed. thanks!

#endif

/****************************************************************************
* Name: mpfs_fpga_canfd_init
Copy link

@jlaitine jlaitine Mar 12, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Check the Name

* bitrate - CAN controller bitrate
*
* Returned Value:
* On success, a pointer to the MPFS CANFD driver is

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is not a canfd driver

#ifdef CONFIG_MPFS_MSS_CAN0
static mpfs_can_instance_t g_can0;

static uint8_t g_tx_pool0[(sizeof(struct can_frame) + TIMESTAMP_SIZE) *
Copy link

@jlaitine jlaitine Mar 12, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be smart to allocate these as uint32_t buffers. Then you'll get can_frames aligned to 32-bit boundaries and can greatly simplify the copying of the frame data and other fields, as you know that they are all 32-bit aligned. added comments on this below

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

hmm, since i think the CAN payload len dev->d_len is in bytes so it's just more natural to use uint8_t buffer. I took the reference from other CAN drivers also.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

for example ,

static uint8_t g_rx_pool[(sizeof(struct canfd_frame)+MSG_DATA)*POOL_SIZE];

Copy link

@jlaitine jlaitine Mar 17, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure, it was just a suggestion! You should anyhow align to 32-bits, in case you want to optimsize accessing of data. You can also use e.g. "aligned_data(sizeof(uint32_t))"

@jlaitine
Copy link

Looking good in general, I added a few questions and comments!

@haitomatic haitomatic force-pushed the SSRCDP-10527_CAN_MSS_support branch 2 times, most recently from 2aa2408 to 24407d4 Compare March 16, 2025 20:49
@haitomatic haitomatic force-pushed the SSRCDP-10527_CAN_MSS_support branch 2 times, most recently from cc0ac79 to 2ed5e70 Compare March 17, 2025 14:46
@haitomatic haitomatic requested review from jlaitine and jpaali March 17, 2025 14:48
Remove unused icicle canfd config
@haitomatic haitomatic force-pushed the SSRCDP-10527_CAN_MSS_support branch from 25e9f1c to 900f37f Compare March 17, 2025 14:59
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants