Forum Rule: Always post complete source code & details to reproduce any issue!
Page 37 of 41 FirstFirst ... 27 35 36 37 38 39 ... LastLast
Results 901 to 925 of 1015

Thread: FlexCAN_T4 - FlexCAN for Teensy 4

  1. #901
    Senior Member
    Join Date
    Jun 2014
    Posts
    258
    Just wanted to confirm that the MAX3051 transceivers work okay with Flexcan.
    Can't say yet what could be wrong with nut's setup.

    Click image for larger version. 

Name:	IMG_5427 Large.jpg 
Views:	30 
Size:	210.2 KB 
ID:	27238

    Click image for larger version. 

Name:	IMG_5428 Large.jpg 
Views:	25 
Size:	250.4 KB 
ID:	27239

    Code:
    #include <FlexCAN_T4.h>
    
    FlexCAN_T4<CAN2, RX_SIZE_256, TX_SIZE_16> canbus;
    CAN_message_t msg;
    
    void setup(void) {
      pinMode(2, OUTPUT); 
      digitalWrite(2, LOW); // enable tranceiver
      pinMode(13, OUTPUT);
      digitalWrite(13, HIGH);
      delay(500);
      canbus.begin();
      canbus.setBaudRate(500000);
      canbus.setMaxMB(16); // up to 64 max for T4, not important in FIFO mode, unless you want to use additional mailboxes with FIFO
      canbus.enableFIFO();
      canbus.enableFIFOInterrupt();
      canbus.onReceive(canSniff);
      canbus.mailboxStatus();
      Serial.println("CAN Test");
    }
    
    void canSniff(const CAN_message_t &msg) {
      static uint32_t timeout = millis();
      Serial.print("MB "); Serial.print(msg.mb);
      Serial.print("  OVERRUN: "); Serial.print(msg.flags.overrun);
      Serial.print("  LEN: "); Serial.print(msg.len);
      Serial.print(" EXT: "); Serial.print(msg.flags.extended);
      Serial.print(" TS: "); Serial.print(timeout);
      Serial.print(" ID: "); Serial.print(msg.id, HEX);
      Serial.print(" Buffer: ");
      for ( uint8_t i = 0; i < msg.len; i++ ) {
        Serial.print(msg.buf[i], HEX); Serial.print(" ");
      } Serial.println();
      timeout = millis();
    
      digitalWrite(13, HIGH);
      digitalWrite(13, LOW);
    }
    
    void loop() {
      canbus.events();
    
      static uint32_t timeout = millis();
      if ( millis() - timeout > 49 ) { // send random frame every 20ms
        CAN_message_t msg;
        msg.id = random(0,0);
        for ( uint8_t i = 0; i < 8; i++ ) msg.buf[i] = i + 1;
        canbus.write(msg);
        timeout = millis();
      }
    
    }

  2. #902
    I don't see single shot mode being possible with the library as-is? There are some circumstances where it'd be nice if the CAN hardware didn't try to saturate the bus upon failure to send a frame. In an ECU, for instance, it might be a good idea to use either single shot or 3 shot (if the hardware supports that) so that it tries only for a limited time and then stops.

    I looked at the processor data sheet and... do my eyes deceive me? Is there really no way to set single shot mode with this hardware?! Tell me they aren't that crazy?!

  3. #903
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    honestly, single shot mode in "flexcan" hardware, this is it's behaviour. i spent alot of time on that debugging and really the only way to stop it is by manually aborting, which, you'd have to handle all on your own (or alternatively reconfigure the mailbox woth setMB), however you will still need to tepp your code to stop sending if that is your goal. this loops you round circles. another alternate way is to just deassert the transceiver and force aborts, stop sending, but then you'd not get traffic activity to get out of bus off without reasserting the transceiver. But yes, bus off on flexcan hardware puts all transmissions in retry attempt, not once only.

    EDIT: alternatively we can switch to listen only mode until the bus off state recovers? I did add error reporting recently, perhaps that may be of assistance?
    Last edited by tonton81; 01-18-2022 at 04:00 AM.

  4. #904
    Senior Member brtaylor's Avatar
    Join Date
    Mar 2016
    Location
    Santa Fe, NM
    Posts
    764
    Some more FlexCAN_T4 questions:
    1. I noticed that 128 filters are available for the FIFO, is that for both the Teensy 3.x and 4.x?
    2. What is the FIFO depth (i.e. how many messages can fill the FIFO without me checking before some are dropped)?

    Thanks!

  5. #905
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    not all 128 are implemented, anything above the 32 limit in fifo uses global filter for remaining X and only certain bits are checked, all those filters rely on a single mask, so i didn't bother implementing past that threshold since we have mask and filter independant of each other for first 32 elements. yes it's for all flexcan controllers. FIFO is 6 messages deep, fixed, cannot be changed.

  6. #906
    Quote Originally Posted by tonton81 View Post
    honestly, single shot mode in "flexcan" hardware, this is it's behaviour. i spent alot of time on that debugging and really the only way to stop it is by manually aborting, which, you'd have to handle all on your own (or alternatively reconfigure the mailbox woth setMB), however you will still need to tepp your code to stop sending if that is your goal. this loops you round circles. another alternate way is to just deassert the transceiver and force aborts, stop sending, but then you'd not get traffic activity to get out of bus off without reasserting the transceiver. But yes, bus off on flexcan hardware puts all transmissions in retry attempt, not once only.

    EDIT: alternatively we can switch to listen only mode until the bus off state recovers? I did add error reporting recently, perhaps that may be of assistance?
    Well, here's what is going on (and it seems strange to me). I have two devices set up for CAN-FD testing. One is a Teensy MicroMod running though an MCP2562FD transceiver. This is connected to an ESP32 driving an MCP2517FD that runs through an MCP2562FD. So, both the transceivers are the same. I try sending normal CAN then CAN-FD from each side to the other. Both sides can send CAN traffic to each other and it works fine. The ESP32 can send traffic to the TeensyMM perfectly fine. However, when the TeensyMM tries to send CAN-FD traffic the ESP32 side will fault like crazy giving me all sorts of bit errors, constantly resetting to try to fix the errors then the constant barrage of traffic faults it again, over and over. For some reason the MCP2517FD chip just hates the traffic coming from the TeensyMM when it is a CAN-FD frame. I find this peculiar because the traffic works bidirectionally for CAN traffic and one direction for CAN-FD but not the other. I've looked at it with a logic analyzer and it looks like CAN-FD traffic either direction. I believe the CAN fault happens right after the CRC and it almost makes me think that the two sides might be disagreeing on whether a given frame needs CRC15, 17, or 21. That is supposed to be set in stone but the fault happens around the end of CRC so... maybe? I thought it might be nice if the Teensy didn't spam the bus so that I could test with single instances of the message. But, in practice it would not ordinarily be necessary to limit retries as a message should only very seldom fault and need a re-send.

    The problem is, while I have a logic analyzer it doesn't interpret CAN-FD frames and I have no other FD capable tools so now I don't know which one is being silly. It sure sounds like you've tested the Teensy code against other CAN-FD devices, right? In that case it would seem to be a fault on my ESP32 side that makes it reject the frames from the Teensy improperly. But, the question is why? I've been working on creating a C++ plugin for Saleae Logic to make it interpret CAN-FD traffic. Of course, then I'd have three devices where I wrote the code and then I'm not really a lot further along as this whole thing could be (and likely is) all my fault and adding another thing I wrote may not help me point fingers any better. All I know is that the ESP32 rejects CAN-FD traffic from the Teensy. But, I have no proof that either of them would have trouble talking to different hardware. I have a very new car but it still doesn't use CAN-FD.

    So, I wonder who has used FlexCAN_T4 in FD mode with external hardware and what their experience has been.

  7. #907
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    for different bitrates in FD mode, there is an advanced setbaudrate function which allows different timings for the same bitrates, try using that to try a different timing than the default. you can select the one you want, and it has a layout displayed in serial monitor

    also don't forget about setting the clock rate of flexcan if needed

  8. #908
    Senior Member
    Join Date
    Jan 2015
    Location
    UK
    Posts
    195
    Quote Originally Posted by CollinK View Post
    Well, here's what is going on (and it seems strange to me). I have two devices set up for CAN-FD testing. One is a Teensy MicroMod running though an MCP2562FD transceiver. This is connected to an ESP32 driving an MCP2517FD that runs through an MCP2562FD. So, both the transceivers are the same. I try sending normal CAN then CAN-FD from each side to the other. Both sides can send CAN traffic to each other and it works fine. The ESP32 can send traffic to the TeensyMM perfectly fine. However, when the TeensyMM tries to send CAN-FD traffic the ESP32 side will fault like crazy giving me all sorts of bit errors, constantly resetting to try to fix the errors then the constant barrage of traffic faults it again, over and over. For some reason the MCP2517FD chip just hates the traffic coming from the TeensyMM when it is a CAN-FD frame. I find this peculiar because the traffic works bidirectionally for CAN traffic and one direction for CAN-FD but not the other. I've looked at it with a logic analyzer and it looks like CAN-FD traffic either direction. I believe the CAN fault happens right after the CRC and it almost makes me think that the two sides might be disagreeing on whether a given frame needs CRC15, 17, or 21. That is supposed to be set in stone but the fault happens around the end of CRC so... maybe? I thought it might be nice if the Teensy didn't spam the bus so that I could test with single instances of the message. But, in practice it would not ordinarily be necessary to limit retries as a message should only very seldom fault and need a re-send.

    The problem is, while I have a logic analyzer it doesn't interpret CAN-FD frames and I have no other FD capable tools so now I don't know which one is being silly. It sure sounds like you've tested the Teensy code against other CAN-FD devices, right? In that case it would seem to be a fault on my ESP32 side that makes it reject the frames from the Teensy improperly. But, the question is why? I've been working on creating a C++ plugin for Saleae Logic to make it interpret CAN-FD traffic. Of course, then I'd have three devices where I wrote the code and then I'm not really a lot further along as this whole thing could be (and likely is) all my fault and adding another thing I wrote may not help me point fingers any better. All I know is that the ESP32 rejects CAN-FD traffic from the Teensy. But, I have no proof that either of them would have trouble talking to different hardware. I have a very new car but it still doesn't use CAN-FD.

    So, I wonder who has used FlexCAN_T4 in FD mode with external hardware and what their experience has been.
    There are actually two versions of CAN FD. ISO and non-ISO version. Check you are using the ISO version. The ISO version uses a different CRC checking.

    Check you have set the BRS flag on in the MCP2517FD config.

    If you are using the API library from Microchip chip then check you have these lines or something similar:

    config.IsoCrcEnable = ISO_CRC;

    txObj.bF.ctrl.BRS = 1; // Switch Bitrate true (switch to new data rate)
    txObj.bF.ctrl.FDF = 1; // CAN FD true

    I have a Teensy 3.2 demo using the MCP2517FD chip at:
    https://github.com/skpang/Teensy32_w...FD_CAN_FD_demo

  9. #909
    Senior Member brtaylor's Avatar
    Join Date
    Mar 2016
    Location
    Santa Fe, NM
    Posts
    764
    If I run this on a Teensy 3.2

    Code:
    #include "FlexCAN_T4.h"
    FlexCAN_T4<CAN0, RX_SIZE_256, TX_SIZE_16> can1;
    
    void setup() {
      Serial.begin(115200);
      while (!Serial) {}
      can1.begin();
      can1.setBaudRate(250000);
      can1.enableFIFO();
      can1.mailboxStatus();
    }
    I get the following output:

    Code:
    FIFO Enabled --> Interrupt Disabled
    	FIFO Filters in use: 8
    	Remaining Mailboxes: 8
    		MB8 code: TX_INACTIVE
    		MB9 code: TX_INACTIVE
    		MB10 code: TX_INACTIVE
    		MB11 code: TX_INACTIVE
    		MB12 code: TX_INACTIVE
    		MB13 code: TX_INACTIVE
    		MB14 code: TX_INACTIVE
    		MB15 code: TX_INACTIVE
    Why are 8 filters already in use and what are they?

  10. #910
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    the 8 filters are there, doesn't mean theyre used or not. by default they accept all traffic, it's just to show that FIFO can set up to 8

  11. #911
    Senior Member brtaylor's Avatar
    Join Date
    Mar 2016
    Location
    Santa Fe, NM
    Posts
    764
    Quote Originally Posted by tonton81 View Post
    the 8 filters are there, doesn't mean theyre used or not. by default they accept all traffic, it's just to show that FIFO can set up to 8
    Based on message #905, I thought there were 32 filters available to setup. Did I misunderstand that? Thanks again.

  12. #912
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    change the RFFN value, there is a function for that, then enableFIFO, keep in mind 8 additional filters consume 2 mailboxes, so if you set max mailboxes to 16 and enable FIFO with 16 filters, you'll have 6 remaing TX mailboxes

  13. #913
    Senior Member brtaylor's Avatar
    Join Date
    Mar 2016
    Location
    Santa Fe, NM
    Posts
    764
    Quote Originally Posted by tonton81 View Post
    change the RFFN value, there is a function for that, then enableFIFO, keep in mind 8 additional filters consume 2 mailboxes, so if you set max mailboxes to 16 and enable FIFO with 16 filters, you'll have 6 remaing TX mailboxes
    If I do that with the following code:
    Code:
    #include <FlexCAN_T4.h>
    
    FlexCAN_T4<CAN1, RX_SIZE_256, TX_SIZE_16> can1;
    CAN_message_t msg;
    
    void setup() {
      Serial.begin(115200);
      while (!Serial) {}
      can1.begin();
      can1.setBaudRate(1000000);
      can1.setRFFN(RFFN_32);
      can1.enableFIFO();  // enable FIFO
      can1.setMRP(0);  // prioritize FIFO
      can1.mailboxStatus();
    }
    
    void loop() {}
    I'm only seeing 14 FIFO filters on a Teensy 4.0 (leaving two mailboxes so that I can still transmit messages):
    Code:
    FIFO Enabled --> Interrupt Disabled
    	FIFO Filters in use: 14
    	Remaining Mailboxes: 2
    		MB14 code: TX_INACTIVE
    		MB15 code: TX_INACTIVE
    I get the same result on a Teensy 3.2. Is it expected that I can only get 14 FIFO filters on Teensy 3.x (leaving at least 1 mailbox for transmit)? Why am I not seeing all 64 mailboxes on Teensy 4.x?

    EDIT: when I check the return value from setFIFOFilter it seems like using setRFFN is giving me the correct number of filters and mailboxStatus is just not reporting it correctly.
    Last edited by brtaylor; 01-23-2022 at 04:48 PM.

  14. #914
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    you need to setMaxMB for up to 64 mailboxes, it's possible the mailboxstatus may have a bug in reporting it if it doesnt return same value as setRFFN, but setRFFN cannot exceed the amount of available mailboxes, so try pushing up the mailbox limit first to 64 and see

    setrffn will return correct value despite being limited by maxMB
    Last edited by tonton81; 01-23-2022 at 06:33 PM.

  15. #915
    Senior Member brtaylor's Avatar
    Join Date
    Mar 2016
    Location
    Santa Fe, NM
    Posts
    764
    A question on using masks, from this thread (https://www.microchip.com/forums/m456043.aspx), my expectation was setting a mask of 11111111100 (i.e. 0x7FC) and a filter of 0 would let through ID's 1, 2, 3. However, when I try this in the library with the FIFO, it only lets through ID 0. Any hints on what I'm doing wrong?

    Code:
    #include "FlexCAN_T4.h"
    
    /* Loopback test on Teensy 3.6 can0 transmitting to can1 */
    
    FlexCAN_T4<CAN0, RX_SIZE_8, TX_SIZE_256> can0;
    FlexCAN_T4<CAN1, RX_SIZE_8, TX_SIZE_256> can1;
    
    CAN_message_t tx_msg, rx_msg;
    
    void irq(const CAN_message_t &ref) {
      Serial.print("Received ID: ");
      Serial.println(ref.id);
    }
    
    void setup() {
      Serial.begin(115200);
      while (!Serial) {}
      Serial.println("STARTING TEST");
      /* Enable the CAN transceivers */
      pinMode(26, OUTPUT);
      pinMode(27, OUTPUT);
      digitalWriteFast(26, LOW);
      digitalWriteFast(27, LOW);
      /* Start the CAN bus and set the baud */
      can0.begin();
      can0.setBaudRate(1000000);
      can1.begin();
      can1.setBaudRate(1000000);
      can1.setRFFN(RFFN_32); // 32 filters
      can1.enableFIFO();  // enable FIFO
      can1.setMRP(0);  // prioritize FIFO
      can1.enableFIFOInterrupt();
      can1.onReceive(FIFO, irq);
      can1.setFIFOFilter(REJECT_ALL);
      can1.setFIFOUserFilter(0, 0, 0x7FC, STD);
    
    
      for (int i = 0; i < 10; i++) {
        tx_msg.id = i;
        can0.write(tx_msg);
      }
    }
    
    void loop() {}
    Output:

    Code:
    STARTING TEST
    Received ID: 0

  16. #916
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    Those functions were added for J1939 protocol where first value is a group of ids and the 2nd value is the last bits to mask off, a user requested that, it's different than the filtering you want.

    To dive deeper into what you want, if we use the automatic setMBFilter as an example:
    Code:
    Can0.setMBFilter(MB15, 1, 2, 3);
    If we enable some debug prints, it will show that when a filter and mask is set, relevant bits in the ID/mask also include whether it is standard or extended, and it all affects the mask functionality. When you get to FIFO end, it is even more complex as the bits are all shifted, as well as partial masking for dual masks, it gets even more tricky.

    The result output of the above at the hardware register is:
    the ID of the mailbox is set to 0x40000
    the MASK of the mailbox is set to 0x5FF00000
    now if we reverse the IDs above from 1,2,3 to 3,2,1 we get:
    the ID of the mailbox is set to 0xC0000
    the MASK of the mailbox is set to 0x5FF00000

    the whole ID is actually shifted for 11bits, and the mask bit 30 is set to let the mailbox accept specifically what it is set to STD/EXT

    in either case, the set*UserFilters is used for J1939, and there is no other custom mask ability added yet, but there are automatic functions that calculate the mask for you for that purpose when you just specify the IDs you want, including ranges

  17. #917
    Senior Member brtaylor's Avatar
    Join Date
    Mar 2016
    Location
    Santa Fe, NM
    Posts
    764
    Thanks! I really like the filtering by ID that you implemented, but I'm working on interfacing with a library, where the library is going to provide filter and mask pairs. I'll dig into the library a little to try to see what it would take to add, otherwise, emulating in software might be the easier approach.

  18. #918
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    take a look at the *MBFilterProcessing internal function, if you want to test your own masks being passed directly rather than the autocalculated call you can try that (for testing you can move that function in public of the class). Unfortunately for FIFO end, if you check out the what needs to be done to set masks and actually have them work, it's a little more effort involved.

    if you really need a function for that i can work on one for you, but what name should I give a function for that? the UserFilter is for J1939 and don't want to change that as it'll break existing code for users who are currently using it

  19. #919
    Senior Member brtaylor's Avatar
    Join Date
    Mar 2016
    Location
    Santa Fe, NM
    Posts
    764
    Quote Originally Posted by tonton81 View Post
    take a look at the *MBFilterProcessing internal function, if you want to test your own masks being passed directly rather than the autocalculated call you can try that (for testing you can move that function in public of the class). Unfortunately for FIFO end, if you check out the what needs to be done to set masks and actually have them work, it's a little more effort involved.

    if you really need a function for that i can work on one for you, but what name should I give a function for that? the UserFilter is for J1939 and don't want to change that as it'll break existing code for users who are currently using it
    Thanks, I'll take a look. It's for integration with Drone CAN, so it might be easier to change the Drone CAN side of things too. I'll dig around a bit.

  20. #920
    Junior Member
    Join Date
    Jan 2014
    Location
    Slovenia
    Posts
    4
    I believe I hit a noob problem - been a while since last working on a c++ project

    I want CAN buses to be accessible across the Arduino code (several files) so I can not simply declare and define them in the main (.ino) file.

    What I tried:

    can_bus.h
    Code:
    #ifndef CAN_BUS_H
    #define CAN_BUS_H
    
    #include <Arduino.h>
    #include <FlexCAN_T4.h>
    
    extern FlexCAN_T4<CAN1, RX_SIZE_8, TX_SIZE_8> Can0;
    extern FlexCAN_T4<CAN2, RX_SIZE_8, TX_SIZE_8> Can1;
    
    #endif
    can_bus.cpp
    Code:
    FlexCAN_T4<CAN1, RX_SIZE_8, TX_SIZE_8> Can0;
    FlexCAN_T4<CAN2, RX_SIZE_8, TX_SIZE_8> Can1;
    Of course this doesn't really work. It actually does for initialization and reading,
    but the code freezes as soon as i try to do a Can0.write().

    I know that declaration in can_bus.h needs to be different but I'm not sure how.
    Something to do with templated classes I guess...

    For the moment my 'workaround' is to keep all CAN related code in the .ino file but that makes it bloated.

    Any ideas? Thank you.

  21. #921
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    check out how isotp.h is done, it is a separate/independant plugin for FlexCAN_T4 to demonstrate how 3rd party libraries can use FlexCAN_T4.

    Isotp code is also templated, however you can still apply it's use to non templated code as it uses a base class pointer to FlexCAN_T4, extern isn't required

  22. #922
    Junior Member
    Join Date
    Jan 2014
    Location
    Slovenia
    Posts
    4
    Quote Originally Posted by tonton81 View Post
    check out how isotp.h is done, it is a separate/independant plugin for FlexCAN_T4 to demonstrate how 3rd party libraries can use FlexCAN_T4.

    Isotp code is also templated, however you can still apply it's use to non templated code as it uses a base class pointer to FlexCAN_T4, extern isn't required
    Thank you! Didn't think of that.

  23. #923
    Junior Member
    Join Date
    Jan 2022
    Posts
    2

    Advice on bad CANFD signal?

    Running into a weird issue with the CAN3 CANFD transmission. I've got my script setup as below, most of it matches the documentation's examples, and I've got it set up to broadcast a message every 500 ms. The system works fine for CAN2.0, but when I try and do it using CANFD, the data seems to be getting garbled in output.

    Code:
    #include <FlexCAN_T4.h>
    ​
    // Specify '1' for CANFD and '2' for CAN2.0
    #define CAN_MODE            1
    #define LOOP_INTERVAL       500
    ​
    #define EN_SER              false
    #define SER_BAUD_RATE       115200
    ​
    #define EN_BROADCAST        true
    #define CNT_REC             false
    #define CNT_SEND            false
    #define CANSNIFF            false
    #define CAN_MAILBOX_STATUS  true
    ​
    #define CAN_BAUD_RATE       1000000
    ​
    #define FLASH_LED           true
    #define LED_PIN             13
    ​
    unsigned long last_time;
    ​
    #if FLASH_LED == true
      bool led_state = false;
    #endif
    ​
    #if CNT_REC == true
      unsigned int rec_count = 0;
    #endif
    #if CNT_SEND == true
      unsigned int send_count = 0;
    #endif 
    ​
    #if CAN_MODE == 1
      typedef CANFD_message_t CAN_message;
      typedef FlexCAN_T4FD<CAN3, RX_SIZE_256, TX_SIZE_16> CAN_device;
    #elif CAN_MODE == 2
      typedef CAN_message_t CAN_message;
      typedef FlexCAN_T4<CAN3, RX_SIZE_256, TX_SIZE_16> CAN_device;
    #endif
    ​
    CAN_device CanDevice;
    CAN_message msg_frame;
    ​
    void setup() {
      // put your setup code here, to run once:
      #if EN_SER == true
        Serial.begin(SER_BAUD_RATE);
        Serial.println("Initializing Device...");
        Serial.println("Serial device initialized.");
      #endif
    ​
      #if FLASH_LED == true
        pinMode(LED_PIN, OUTPUT);
      #endif
    ​
      CanDevice.begin();
      
      #if CAN_MODE == 1
        CANFD_timings_t config;
        config.clock = CLK_24MHz;
        config.baudrate = 100000;
        config.baudrateFD = 200000;
        config.propdelay = 190;
        config.bus_length = 1;
        config.sample = 70;
        CanDevice.setBaudRate(config);
    ​
        msg_frame.len = 8;
        msg_frame.id = 0x321;
        //msg_frame.flags.extended = 1;
        //msg_frame.seq = 1;
        msg_frame.buf[0] = 1;
        //msg_frame.buf[7] = 1;
      #elif CAN_MODE == 2
        CanDevice.setBaudRate(CAN_BAUD_RATE);
        CanDevice.enableFIFO();
        CanDevice.enableFIFOInterrupt();
        
        msg_frame.len = 8;
        msg_frame.id = 0x321;
        msg_frame.seq = 1;
        msg_frame.buf[0] = 1;
        msg_frame.buf[7] = 1;
      #endif
      #if CNT_REC == true
        CanDevice.onReceive(countReceives);
      #endif
      #if CANSNIFF == true
        CanDevice.onReceive(canSniff);
      #endif
      #if CAN_MAILBOX_STATUS == true
        CanDevice.mailboxStatus(); 
      #endif
    ​
      last_time = millis();
    }
    ​
    void loop() {
      if (millis() > last_time + LOOP_INTERVAL) {
        
        #if EN_BROADCAST == true
          CanDevice.write(msg_frame);
          #if CNT_SEND == true
            send_count++;
          #endif
        #endif
        #if FLASH_LED == true
          if (led_state) {
            digitalWrite(LED_PIN, LOW);
            led_state = false;
          }
          else {
            digitalWrite(LED_PIN, HIGH);
            led_state = true;
          }
        #endif
        #if EN_SER == true
          #if CNT_REC == true
            Serial.print("Received ");
            Serial.print(rec_count);
            Serial.print(" messages in the last ");
            Serial.print(LOOP_INTERVAL);
            Serial.println(" milliseconds.");
            rec_count = 0;
          #endif
          #if CNT_SEND == true
            Serial.print("Sent ");
            Serial.print(send_count);
            Serial.print(" messages in the last ");
            Serial.print(LOOP_INTERVAL);
            Serial.println(" milliseconds.");
            send_count = 0;
          #endif
        #endif
        last_time = millis();
      }
    }
    ​
    #if CANSNIFF == true
      #if EN_SER == true
        void canSniff(const CAN_message &msg) {
          Serial.print("MB "); 
          Serial.print(msg.mb);
        
          Serial.print("  OVERRUN: ");
          Serial.print(msg.flags.overrun);
          
          Serial.print("  LEN: ");
          Serial.print(msg.len);
        
          Serial.print(" EXT: ");
          Serial.print(msg.flags.extended);
        
          Serial.print(" TS: ");
          Serial.print(msg.timestamp);
        
          Serial.print("ID: ");
          Serial.print(msg.id, HEX);
        
          Serial.print(" Buffer: ");
          for ( uint8_t i = 0; i < msg.len; i++) {
            Serial.print(msg.buf[i], HEX); Serial.print(" ");
          }
        
          Serial.println();
        }
      #endif
    #endif
    ​
    #if CNT_REC == true
      void countReceives(const CAN_message &msg) {
        rec_count++;
      }
    #endif
    I'm snooping on the line using an Analog Discovery 2 and it looks like the signal is getting messed up, with only a couple of bytes of data being sent before it shows an error. I've attached a screenshot of the data stream below.

    Any advice on what is going wrong would be appreciated, I'm at a loss right now.

    I'm using a TJA1050 based CAN transceiver, have two Teensy 4.0s communicating back and forth, with a logic level shifter sitting in between to handle the 5 V -> 3.3 V drop between the transceivers and the Teensys.
    Attached Thumbnails Attached Thumbnails Click image for larger version. 

Name:	CAN-sniff.jpg 
Views:	17 
Size:	39.9 KB 
ID:	27355  

  24. #924
    Senior Member
    Join Date
    Dec 2016
    Location
    Montreal, Canada
    Posts
    4,033
    i believe the tja1050 is CAN2.0 transceiver, FD rates not supported

  25. #925
    Senior Member
    Join Date
    Jan 2015
    Location
    UK
    Posts
    195
    Quote Originally Posted by oVexlz View Post
    Running into a weird issue with the CAN3 CANFD transmission. I've got my script setup as below, most of it matches the documentation's examples, and I've got it set up to broadcast a message every 500 ms. The system works fine for CAN2.0, but when I try and do it using CANFD, the data seems to be getting garbled in output.

    Code:
    #include <FlexCAN_T4.h>
    ​
    // Specify '1' for CANFD and '2' for CAN2.0
    #define CAN_MODE            1
    #define LOOP_INTERVAL       500
    ​
    #define EN_SER              false
    #define SER_BAUD_RATE       115200
    ​
    #define EN_BROADCAST        true
    #define CNT_REC             false
    #define CNT_SEND            false
    #define CANSNIFF            false
    #define CAN_MAILBOX_STATUS  true
    ​
    #define CAN_BAUD_RATE       1000000
    ​
    #define FLASH_LED           true
    #define LED_PIN             13
    ​
    unsigned long last_time;
    ​
    #if FLASH_LED == true
      bool led_state = false;
    #endif
    ​
    #if CNT_REC == true
      unsigned int rec_count = 0;
    #endif
    #if CNT_SEND == true
      unsigned int send_count = 0;
    #endif 
    ​
    #if CAN_MODE == 1
      typedef CANFD_message_t CAN_message;
      typedef FlexCAN_T4FD<CAN3, RX_SIZE_256, TX_SIZE_16> CAN_device;
    #elif CAN_MODE == 2
      typedef CAN_message_t CAN_message;
      typedef FlexCAN_T4<CAN3, RX_SIZE_256, TX_SIZE_16> CAN_device;
    #endif
    ​
    CAN_device CanDevice;
    CAN_message msg_frame;
    ​
    void setup() {
      // put your setup code here, to run once:
      #if EN_SER == true
        Serial.begin(SER_BAUD_RATE);
        Serial.println("Initializing Device...");
        Serial.println("Serial device initialized.");
      #endif
    ​
      #if FLASH_LED == true
        pinMode(LED_PIN, OUTPUT);
      #endif
    ​
      CanDevice.begin();
      
      #if CAN_MODE == 1
        CANFD_timings_t config;
        config.clock = CLK_24MHz;
        config.baudrate = 100000;
        config.baudrateFD = 200000;
        config.propdelay = 190;
        config.bus_length = 1;
        config.sample = 70;
        CanDevice.setBaudRate(config);
    ​
        msg_frame.len = 8;
        msg_frame.id = 0x321;
        //msg_frame.flags.extended = 1;
        //msg_frame.seq = 1;
        msg_frame.buf[0] = 1;
        //msg_frame.buf[7] = 1;
      #elif CAN_MODE == 2
        CanDevice.setBaudRate(CAN_BAUD_RATE);
        CanDevice.enableFIFO();
        CanDevice.enableFIFOInterrupt();
        
        msg_frame.len = 8;
        msg_frame.id = 0x321;
        msg_frame.seq = 1;
        msg_frame.buf[0] = 1;
        msg_frame.buf[7] = 1;
      #endif
      #if CNT_REC == true
        CanDevice.onReceive(countReceives);
      #endif
      #if CANSNIFF == true
        CanDevice.onReceive(canSniff);
      #endif
      #if CAN_MAILBOX_STATUS == true
        CanDevice.mailboxStatus(); 
      #endif
    ​
      last_time = millis();
    }
    ​
    void loop() {
      if (millis() > last_time + LOOP_INTERVAL) {
        
        #if EN_BROADCAST == true
          CanDevice.write(msg_frame);
          #if CNT_SEND == true
            send_count++;
          #endif
        #endif
        #if FLASH_LED == true
          if (led_state) {
            digitalWrite(LED_PIN, LOW);
            led_state = false;
          }
          else {
            digitalWrite(LED_PIN, HIGH);
            led_state = true;
          }
        #endif
        #if EN_SER == true
          #if CNT_REC == true
            Serial.print("Received ");
            Serial.print(rec_count);
            Serial.print(" messages in the last ");
            Serial.print(LOOP_INTERVAL);
            Serial.println(" milliseconds.");
            rec_count = 0;
          #endif
          #if CNT_SEND == true
            Serial.print("Sent ");
            Serial.print(send_count);
            Serial.print(" messages in the last ");
            Serial.print(LOOP_INTERVAL);
            Serial.println(" milliseconds.");
            send_count = 0;
          #endif
        #endif
        last_time = millis();
      }
    }
    ​
    #if CANSNIFF == true
      #if EN_SER == true
        void canSniff(const CAN_message &msg) {
          Serial.print("MB "); 
          Serial.print(msg.mb);
        
          Serial.print("  OVERRUN: ");
          Serial.print(msg.flags.overrun);
          
          Serial.print("  LEN: ");
          Serial.print(msg.len);
        
          Serial.print(" EXT: ");
          Serial.print(msg.flags.extended);
        
          Serial.print(" TS: ");
          Serial.print(msg.timestamp);
        
          Serial.print("ID: ");
          Serial.print(msg.id, HEX);
        
          Serial.print(" Buffer: ");
          for ( uint8_t i = 0; i < msg.len; i++) {
            Serial.print(msg.buf[i], HEX); Serial.print(" ");
          }
        
          Serial.println();
        }
      #endif
    #endif
    ​
    #if CNT_REC == true
      void countReceives(const CAN_message &msg) {
        rec_count++;
      }
    #endif
    I'm snooping on the line using an Analog Discovery 2 and it looks like the signal is getting messed up, with only a couple of bytes of data being sent before it shows an error. I've attached a screenshot of the data stream below.

    Any advice on what is going wrong would be appreciated, I'm at a loss right now.

    I'm using a TJA1050 based CAN transceiver, have two Teensy 4.0s communicating back and forth, with a logic level shifter sitting in between to handle the 5 V -> 3.3 V drop between the transceivers and the Teensys.

    You need to use CAN FD transceivers such as MCP2562FD or TJA1462.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •