CANbus Shield Cannot Communicate

Using Arduino Uno R3 with Inland CANbus Shield (Micro Center)
microcenter. com/product/623880/inland-ks0411-can-bus-shield

I have purchased, separately, an OBD2-to-DB9 cable and confirmed the pinout at both ends.
I used SparkFun's CANbus tutorial to find this Github Repository.

Generic 'CAN Read Demo' Sketch
/****************************************************************************
CAN Read Demo for the SparkFun CAN Bus Shield. 

Written by Stephen McCoy. 
Original tutorial available here: http://www.instructables.com/id/CAN-Bus-Sniffing-and-Broadcasting-with-Arduino
Used with permission 2016. License CC By SA. 

Distributed as-is; no warranty is given.
*************************************************************************/

#include <Canbus.h>
#include <defaults.h>
#include <global.h>
#include <mcp2515.h>
#include <mcp2515_defs.h>

//********************************Setup Loop*********************************//

void setup() {
  Serial.begin(9600); // For debug use
  Serial.println("CAN Read - Testing receival of CAN Bus message");  
  delay(1000);
  
  if(Canbus.init(CANSPEED_500))  //Initialise MCP2515 CAN controller at the specified speed
    Serial.println("CAN Init ok");
  else
    Serial.println("Can't init CAN");
    
  delay(1000);
}

//********************************Main Loop*********************************//

void loop(){

  tCAN message;
if (mcp2515_check_message()) 
	{
    if (mcp2515_get_message(&message)) 
	{
        //if(message.id == 0x620 and message.data[2] == 0xFF)  //uncomment when you want to filter
             //{
               
               Serial.print("ID: ");
               Serial.print(message.id,HEX);
               Serial.print(", ");
               Serial.print("Data: ");
               Serial.print(message.header.length,DEC);
               for(int i=0;i<message.header.length;i++) 
                {	
                  Serial.print(message.data[i],HEX);
                  Serial.print(" ");
                }
               Serial.println("");
             //}
           }}

}
'SparkFun CAN Demo' Sketch
CAN-Bus Demo

Toni Klopfenstein @ SparkFun Electronics
September 2015
https://github.com/sparkfun/CAN-Bus_Shield

This example sketch works with the CAN-Bus shield from SparkFun Electronics.

It enables the MCP2515 CAN controller and MCP2551 CAN-Bus driver, and demos
using the chips to communicate with a CAN-Bus.

Resources:

Development environment specifics:
Developed for Arduino 1.6.5

Based off of original example ecu_reader_logger by:
Sukkin Pang
SK Pang Electronics www.skpang.co.uk

This code is beerware; if you see me (or any other SparkFun employee) 
at the local, and you've found our code helpful, please buy us a round!

For the official license, please check out the license file included with the library.

Distributed as-is; no warranty is given.
*************************************************************************/

#include <Canbus.h>
char UserInput;
int data;
char buffer[456];  //Data will be temporarily stored to this buffer before being written to the file

//********************************Setup Loop*********************************//

void setup(){
Serial.begin(9600);
Serial.println("CAN-Bus Demo");

if(Canbus.init(CANSPEED_500))  /* Initialise MCP2515 CAN controller at the specified speed */
  {
    Serial.println("CAN Init ok");
  } else
  {
    Serial.println("Can't init CAN");
  } 
   
  delay(1000); 

Serial.println("Please choose a menu option.");
Serial.println("1.Speed");
Serial.println("2.RPM");
Serial.println("3.Throttle");
Serial.println("4.Coolant Temperature");
Serial.println("5.O2 Voltage");
Serial.println("6.MAF Sensor");

}



//********************************Main Loop*********************************//

void loop(){

while(Serial.available()){
   UserInput = Serial.read();

if (UserInput=='1'){
 Canbus.ecu_req(VEHICLE_SPEED, buffer);
 Serial.print("Vehicle Speed: ");
 Serial.println(buffer);
 delay(500);
}
else if (UserInput=='2'){
 Canbus.ecu_req(ENGINE_RPM, buffer);
 Serial.print("Engine RPM: ");
 Serial.println(buffer);
 delay(500);

}
else if (UserInput=='3'){
 Canbus.ecu_req(THROTTLE, buffer);
 Serial.print("Throttle: ");
 Serial.println(buffer);
 delay(500);

}
else if (UserInput=='4'){
 Canbus.ecu_req(ENGINE_COOLANT_TEMP, buffer);
 Serial.print("Engine Coolant Temp: ");
 Serial.println(buffer);
 delay(500);

}
else if (UserInput=='5'){
 Canbus.ecu_req(O2_VOLTAGE, buffer);
 Serial.print("O2 Voltage: ");
 Serial.println(buffer);
 delay(500);

}
else if (UserInput=='6'){
 Canbus.ecu_req(MAF_SENSOR, buffer);
 Serial.print("MAF Sensor: ");
 Serial.println(buffer);
 delay(500);

}
else
{
  Serial.println(UserInput);
  Serial.println("Not a valid input.");
  Serial.println("Please enter a valid option.");
}

}
}

It does not seem to be working. I have tried both sketches with no luck.
I tried baud rates of 125k, 250k, 500k. No change.
In tinkering with the code, it seems the buffer is empty.

Interestingly, when I plug it into my car (tried 2 cars now) it turns on weird lights on my dash. On my 2008 Tundra, it turns on the Traction Control light and another one. On my 2010 Hyundai Elantra, it turns on the Electric Power Steering and Battery lights.

On the Hyundai, these lights go away when unplugging OBD2. On the Tundra the lights turn off when power cycling the vehicle.
Not sure if this is an indicator that some wiring/pins are incorrect.

I have read some suggestions that maybe the crystal oscillator in the Inland CANbus shield is not the expected 16mHz frequency as the SparkFun (or others) shields.
When inspecting mine, it does not have the typical silver, oval shaped oscillator (maybe the size of 2-3 grains of rice) that the Arduino and others have. It seems to be much smaller, maybe about 1/2 grain of rice with no useful markings.

Any help would be appreciated.

Please post a schematic of each of your CAN prototypes. You do have two because CAN will not operate unless its transmission is acknowledged by another CAN node, it cannot ack itself. Do you have termination resistors on each end of the bus? If they are absent it probably will not work reliably. Youi do have them programmed at the same baud with appropriate settings depending on crystal. It must be an old car, randomly pumping data into it can do a lot of damage. It also helps a lot if you post links to technical information on each of the hardware devices, sales info does not count.

Welcome to the forum.

I recommend:

  • Get yourself an oscilloscope. Even an old analog one will do. CAN is slow. It will allow you to look at the bit timing and signal levels.
  • Figure out how to set your MCP2515 to listen only mode instead of normal mode. That way you can listen to a CAN bus without creating errors because you did not set the baud rate correctly. The answer is in your CAN library and the MCP2515 datasheet.
  • Get yourself a second CAN board so you can do experiments with two Arduinos before you connect to a live car.
  • If you struggle with the CAN library, try another one. I think there are several that support MCP2510 and MCP2515. Maybe you like the style better.
  • Search the forum for MCP2510 and MCP2515. I have seen quite a few posts that may be helpful.
  • Have a look at the Wikipedia page for CAN. It has some pictures about the stuff gilshultz mentioned.

Another often used crystal speed is 8MHz. That will result in half the CAN bit rate if you use the 16MHz values. A module with 8MHz crystal will not be able to run at 1Mbit/s.

1 Like

You can cheat and adjust your baud so if you have a 8 instead of a 16MHz set your baud at 2X what you want. Also start at a low baud rate. the lower the better then when it is working step it up a notch at a time. The faster the baud the more critical the hardware (wiring) becomes.

There are two types of OBD2 to DB9 cables and they have different pinouts.

This shied uses a CiA 303-1 cable, where:
DB9 pins 3+6 are ground, 2 - CAN Low, 7 CAN High, 9 - Battery (12v)

All you need to do is find the other type of cable, like this:
https://www.mouser.com/datasheet/2/119/DS_OBD-M-DB9-F-ES(1)-2727.pdf

Also, they also decided to use pin 8 for the 2515's interrupt (INT), which means any code that uses the 328P's hardware interrupt on pin 2 won't work well or at all.

CiA 303-1 Info:
https://www.phoenixcontact.com/assets/downloads_ed/global/web_dwl_technical_info/CANopen.pdf

1 Like

Hi there,

Thanks for the help, but I still absolutely cannot get this stuff to work.
I got the SparkFun CANbus shield for a better chance of success.

I verified the pinout on my cable matches SparkFun's cable exactly.

I traced the pins on each shield's DB9 connector, specifically the CAN breakout pins.
The SparkFun shield seems to be proper, but the Inland shield seems to have the pin arrangement mixed up, which might explain why my vehicles acted funny when connecting it.

I tried removing the OBD2->DB9 cable from the shield and used jumper wires to only connect the CAN H/L wires and signal ground.
A 120ohm resistor made no changes, and I can't find a terminating resistor mentioned in SparkFun's documentation. So I'm unsure if this is necessary or not.

I've gone through the source files as much as possible and tried to tweak various parameters such as baud rate (no idea if it should be 125k, 250k, 500k for my car), possible chip select pins, etc.

Nothing gives any sort of results, not even garbage.

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.