CAN 2.0B Transceiver Suggestions

Status
Not open for further replies.

brad95411

Member
I'm currently in the process of trying to get my Teensy 3.6 to communicate with a preexisting CAN 2.0B device. This device makes use of extended IDs and thus far I've not been able to find any information on datasheets that say one way or the other if the transceivers listed on Collin80's FlexCAN github page support the extended ID format.

I have a few MCP2562s that I purchased from DigiKey a few days ago and they work great with regular 11 bit IDs, I can get back and forth using one of Collin80s examples as well as a simple piece of test code I wrote but as soon as I enable extended IDs on either no communication happens.

Is there something specific I'm missing in datasheets that says "yes this supports extended IDs" or have I just picked the wrong part? Are there parts that other people have tried that work with extended ID's?

Any help is appreciated, thanks!

Collin80's Example Used: https://github.com/collin80/FlexCAN_Library/blob/master/examples/CANTest/CANTest.ino

My Test Code (Please bear with my code, I'm a college student who quickly scratches code together just to see if something will work so this is by no means comprehensive):
Code:
#include <FlexCAN.h>

static CAN_message_t message, received;

#define DEFAULTID 0

void setup() {
  delay(1000);

  Serial.begin(9600);

  while(!Serial)
  {
    delay(1);
  }
  
  Serial.println(F("Setup has begun"));

  Can0.begin(1000000);
  Can1.begin(1000000);

  message.id = 0;
  message.ext = 0; //Changing this to 1 breaks everything
  message.len = 1;
  message.buf[0] = 0;

  Serial.println(F("1: Fire Static Message from CAN 0 to CAN 1"));
  Serial.println(F("2: Check for Message from CAN 1 to CAN 0"));
  Serial.println(F("3: Print data from most recent message from CAN 1 to CAN 0"));
  Serial.println(F("4: Fire Static Message from CAN 1 to CAN 0"));
  Serial.println(F("5: Check for Message from CAN 0 to CAN 1"));
  Serial.println(F("6: Print data from most recent message from CAN 0 to CAN 1"));
  Serial.println(F("Setup Complete"));

}

void loop() {
  if(Serial.available())
  {
    char data = (char) Serial.read();

    if(data == '1')
    {
      message.id = DEFAULTID;
      
      Can0.write(message);

      Serial.println(F("Message sent from CAN 0 to CAN 1"));
    }
    else if(data == '2')
    {
      Serial.print(F("Data available on CAN 0: "));
      Serial.println(Can0.available() ? "True" : "False");
    }
    else if(data == '3')
    {
      if(Can0.available())
      {
        Serial.println(F("Reading from CAN 0 message buffer"));
        
        Can0.read(received);

        printFrame(received);
      }
    }
    else if(data == '4')
    {
      message.id = DEFAULTID | 1;
      
      Can1.write(message);

      Serial.println(F("Message sent from CAN 1 to CAN 0"));
    }
    else if(data == '5')
    {
      Serial.print(F("Data available on CAN 1: "));
      Serial.println(Can1.available() ? "True" : "False");
    }
    else if(data == '6')
    {
      if(Can1.available())
      {
        Serial.println(F("Reading from CAN 1 message buffer"));
        
        Can1.read(received);

        printFrame(received);
      }
    }
    else
    {
      Serial.println("NOT A COMMAND");
    }
  }
  
  delay(1);
}

void printFrame(CAN_message_t &frame)
{
  Serial.print("ID: ");
  Serial.println(frame.id, HEX);

  Serial.println("Available Data");

  for(uint8_t i = 0; i < frame.len; i++)
  {
    Serial.print("Data Element: ");
    Serial.print(i);
    Serial.print(" = ");
    Serial.println(frame.buf[i]);
  }
}
 
I'm no expert, but I have used the extended ID Flex can for J1939 data. I do not think the Transceiver cares weather it is extended or not. The transceiver is just a signal amplifier. I have used several transceivers for extended ID and i have not seen any that say that they work with the extended bit
 
Here is a snippet of code i use:

keyPad = 0;
txmsg.len = 3;
txmsg.ext = 1;
txmsg.id = 0x16EA0000;
//_____________________________________write request for pgn 65253
txmsg.buf[0] = 0xe5;
txmsg.buf[1] = 0xfe;
txmsg.buf[2] = 0x00;
CANbus.write(txmsg);
//_____________________________________write request for pgn 65259
txmsg.buf[0] = 0xeb;
txmsg.buf[1] = 0xfe;
txmsg.buf[2] = 0x00;
CANbus.write(txmsg);
//_____________________________________write request for pgn 65214
txmsg.buf[0] = 0xbe;
txmsg.buf[1] = 0xfe;
txmsg.buf[2] = 0x00;
CANbus.write(txmsg);
 
It seems to work here without issue. This is a screen cap of the extended broadcast using your provided code.

The only change I made was to the DEFAULTID. I set it to 0x131 rather than 0, but it works the same with a 0 value for the DEFAULTID

canExtendedFunctional.JPG
 
Why does he need filters? I have no filters and my extended IDs work without issue.

Doesn't work for me. Messages with extended IDs are not received without setting up the filters (Teensy 3.6).

Can you post a working example that uses 2 Teensies (or the 2 CAN interfaces on 3.6)?
 
So, as an update, I suspect tni is right. I was unable to get the object-less version to work with extended IDs. No real obvious reason according to the library readme and I don't have time with having just started school to figure out why.

But at full speed with Can0 and Can1 and a slightly modified version of one of the examples I was able to get an ID of 10000 to work. Code follows:

Code:
#include <FlexCAN.h>

#ifndef __MK66FX1M0__
  #error "Teensy 3.6 with dual CAN bus is required to run this example"
#endif

static CAN_message_t msg0,msg1;

elapsedMillis RXtimer;
elapsedMillis LEDtimer;
uint32_t RXCount = 0;
boolean displayCAN = true;
const uint8_t redLEDpin = 2;
boolean redLEDstate;

class CANClass : public CANListener 
{
public:
   void printFrame(CAN_message_t &frame, int mailbox);
   void gotFrame(CAN_message_t &frame, int mailbox); //overrides the parent version so we can actually do something
};

void CANClass::printFrame(CAN_message_t &frame, int mailbox)
{
  if(displayCAN){
   Serial.print(mailbox);
   Serial.print(" ID: ");
   Serial.print(frame.id, HEX);
   Serial.print(" Data: ");
   for (int c = 0; c < frame.len; c++) 
   {
      Serial.print(frame.buf[c], HEX);
      Serial.write(' ');
   }
   Serial.println();
  }
   RXCount++;
 
}

void CANClass::gotFrame(CAN_message_t &frame, int mailbox)
{
    printFrame(frame, mailbox);
}

CANClass CANClass0;
CANClass CANClass1;

// -------------------------------------------------------------
void setup(void)
{
  delay(1000);
  Serial.println(F("Hello Teensy 3.6 dual CAN Test With Objects."));
  pinMode(redLEDpin,OUTPUT);
  
  Can0.begin(1000000);  
  Can1.begin(1000000);
  Can0.attachObj(&CANClass0);
  Can1.attachObj(&CANClass1);

  //Setup message 0 (Change example start)
  msg0.id = 0x10000;
  msg0.ext = 1;
  msg0.rtr = 0;
  msg0.len = 2;
  msg0.buf[0] = 26;
  msg0.buf[1] = 48;
  //End message 0 setup (Change example end)
  
  
  CAN_filter_t allPassFilter;
  allPassFilter.id=0;
  allPassFilter.ext=1;
  allPassFilter.rtr=0;

  //leave the first 4 mailboxes to use the default filter. Just change the higher ones
  for (uint8_t filterNum = 4; filterNum < 16;filterNum++){
    Can0.setFilter(allPassFilter,filterNum); 
    Can1.setFilter(allPassFilter,filterNum); 
  }
  for (uint8_t filterNum = 0; filterNum < 16;filterNum++){
     CANClass0.attachMBHandler(filterNum);
     CANClass1.attachMBHandler(filterNum);
  }
  //CANClass0.attachGeneralHandler();
  //CANClass1.attachGeneralHandler();
  
}

// -------------------------------------------------------------
void loop(void)
{
  if (RXtimer > 10000){
    Serial.println("Total Received Messages in 10 Sec:");
    Serial.println(RXCount);
    RXtimer = 0;
    RXCount=0;
    displayCAN = !displayCAN;
  }
  if (LEDtimer >250){
    LEDtimer = 0;
    redLEDstate = !redLEDstate;
    digitalWrite(redLEDpin, redLEDstate);
  }

  Can0.write(msg0); //Write message (Change example)
}
 
Status
Not open for further replies.
Back
Top