ATSAMC21J16A: How to switch between CAN FD and CAN (without FD)

Go To Last Post
2 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hello,

 

I have build a CAN-Tester. The CAN bitrate depends on the tested device. This works fine, but now I have want to introduce CAN FD with bitrate switch. This only works once. If I want to change the bitrate again or if I want to switch to a CAN mode without CANFD my program locks at the marked line:

 

void CAN_config_interfaces (uint16_t BRP, bool CAN_FD, bool listen_only)
{
    for (CAN_interfaces i1 = 0; i1 < CAN_interface_count; i1++)
    {
        can_async_disable (&CAN[i1]);

        hri_can_set_CCCR_INIT_bit (CAN[i1].dev.hw);
        while (hri_can_get_CCCR_INIT_bit (CAN[i1].dev.hw) == 0);            // Here it locks
        hri_can_set_CCCR_CCE_bit (CAN[i1].dev.hw);            

        hri_can_write_NBTP_NBRP_bf (CAN[i1].dev.hw, BRP - 1);

        if (CAN_FD)
        {
            hri_can_set_CCCR_FDOE_bit (CAN[i1].dev.hw);
            hri_can_set_CCCR_BRSE_bit (CAN[i1].dev.hw);
        }
        else
        {
            hri_can_clear_CCCR_FDOE_bit (CAN[i1].dev.hw);
            hri_can_clear_CCCR_BRSE_bit (CAN[i1].dev.hw);
        }

        hri_can_clear_CCCR_CCE_bit (CAN[i1].dev.hw);
        hri_can_clear_CCCR_INIT_bit (CAN[i1].dev.hw);
        while (hri_can_get_CCCR_INIT_bit (CAN[i1].dev.hw));        

        if (listen_only)
            can_async_set_mode (&CAN[i1], CAN_MODE_MONITORING);
        else
            can_async_set_mode (&CAN[i1], CAN_MODE_NORMAL);

        struct can_filter filter;
        filter.id = 0;
        filter.mask = 0;
        can_async_set_filter (&CAN[i1], 0, CAN_FMT_STDID, &filter);

        can_async_enable (&CAN[i1]);
    }
}

 

Has anyone a hint how to do this properly?

 

 

best regards

 

Bumbum

This topic has a solution.
Last Edited: Tue. Aug 2, 2022 - 12:20 PM
This reply has been marked as the solution. 
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hello,

 

I was on this problem for several days now and today after my post here I found the reason: My data buffer for receiving messages with can_async_read was only 8 Bytes in size. I don't know how this was causing the crash, because while switching bitrate I don't call can_async_read at all. But increasing the buffer size to 64 Byte has solved my problem. I guess there must be some buffer overflow before which causes my program to crash on this specific routine.

 

best regards

Bumbum