Sending J1939 CAN-BUS messages with Sparkfun CAN-BUS Shield

Keeping in the spirit of open-source, I have modified the libraries of the Sparkfun CAN-BUS shield. With these updated libraries we are now able to send messages using the standard identifier (11 bits) and also send messages with the extended identifier (29 bits).

I am running the following code in Arduino UNO. This particular CAN-BUS shield does not work with the latest Arduino board (Leonardo). Anyway, here is a simple Arduino program that continuously sends J1939 messages through the CAN network.

The updated MCP2515 libraries can be found at http://www.nunoalves.com/source/canbus_nca26_09_2012.zip. To install this library and use it with your Arduino projects just drop it in the appropriate sub-directory (e.g. ~/Documents/Arduino/libraries in macosx). For reference here is the data sheet for the MCP2515 SPI CAN transceiver. I found all the information in there.

Finally… a big thank you to Fabian Greif and his initial efforts on the MCP2515 library.





18 comments on “Sending J1939 CAN-BUS messages with Sparkfun CAN-BUS Shield

  1. Wayne Little on said:

    I’m trying to test Can Bus using the Sparkfun device on a mega 2560 board. Do I need to connect to a can bus of anytype to test this, is there a way to find the command references.. Wayne

    • Nuno Alves on said:

      It depends what CAN network you are trying to interface with. Is the CANH and CANL connected by a 120 ohm resistor? Do you know the CAN interface parameters that you are supposed to us?
      I havent tried with the mega 2560 board, but make sure that the MOSI, MISO from that arduino board are connected to the pins D11 and D12 of the shield. On some arduino boards, the SPI interface is on different pins.

  2. That’s looks amazing. I’m trying to establish a connection with CAN myself and I bought an arduino uno + sparkfun can shield. I’ve tried several libraries but initializing the connection always fails (even with different speeds). Already tested on 4 different vehicles.

    Any idea how I can get my CAN shield working? Do I have to modify anything in the library? Would be great if I could figure this out.

    • Nuno Alves on said:

      The latest arduino (Leonardo) has a different pinout, so it wont work with this shield without you making some modifications. To save you some hacking time, I would just buy a Arduino UNO or an earlier version (like the one I used). Then I’d start reading the messages you are getting from the CAN bus. Make sure the shield CANH is connected to your car CANH, the same thing for CANL and GND. See the spec sheet for information regarding the location of the pins. Once all that is taken care of, just start reading messages. If you start collecting data, then you can figure out whats going on.
      As for the CAN bus speed… I do not know, you have to see what is the baud rate of your CAN network.
      Good luck!

  3. To continue your spirit of opensource (tyvvvvvm for posting this by the way, saved me so much) here is the modified defaults.h file required to get the Mega 2560 to run with with code (modify in the library)

    #ifndef DEFAULTS_H
    #define DEFAULTS_H

    #define P_MOSI B,2
    #define P_MISO B,3
    #define P_SCK B,1

    //#define MCP2515_CS D,3 // Rev A
    #define MCP2515_CS B,0 // Rev B
    #define MCP2515_INT D,2
    #define LED2_HIGH B,0
    #define LED2_LOW B,0

    #endif // DEFAULTS_H

  4. Do you happen to have a quick copy paste example of sending standard frame messages with your same code?

  5. Hi, when you declare the baud rate, is that number at a ratio? i am using high speed CAN, at 1.0 Mbps, i dont understand what value i would put there,
    Thanks,
    Chris

  6. hi guy im tring to receive sending data with arduino mega2560 due to bus can , a made de connection with using sparkfun arduino can bus schield, but and also made a gut connection betwenn the shield and the arduino
    53 10
    51 11
    50 12
    52 13
    but it not work i no able to read the data com fron the bus , on serial port0.
    i have to send this data to another arduino with the xbee schiled !!
    can someone help me !!
    thx!!!

  7. Anton on said:

    Hi, this is great stuff! You don’t by any chance have a corresponding function, get_meassage for extended identifiers?
    Regards Anton

  8. Christoph on said:

    Hey guys,

    i am struggeling using this code. i have a sparfun can shield an arduino uno. when i set up everything i cannot read messages with a usb-can reader which is approved. do i have to change the ports? i guess it should be set up right in the libraries??
    Thanks.

    • Nuno Alves on said:

      Did you add the 120 ohm resistor in the bus?
      Are you using the extended CAN format?
      Did you specify the CAN BUS frequency correctly? These libraries as they are send messages at 250KBps.
      The libraries have nothing to do with the fact that you can’t read the CAN message in the computer. These libraries just send the messages in the CAN bus.

  9. Pedro on said:

    Nuno,

    Not sure if you still check this but I just wanted to say thank you for this. It really helped me out! I did notice that your message.id is 0x00FF50FF but when you use CANviaUSB it shows as 0x00FF500F. I am having issues with this part as the last 2 of the message id are the source address. I am sending a message with source address 22 (0xff00422) but every time I check the broadcast it actually shows coming from 42 (0xff00442). it kinda looks like the digit before is repeated and the last digit dropped. I am going through the library and see if this is something easy to change. Let me know your thoughts. Thanks!

    • Nuno Alves on said:

      Hi,
      Glad to hear that my library was useful.
      I havent used this library in a while… But I may be able to help you out. I presume you are sending things in the J1939 format, which is defined in the function uint8_t mcp2515_send_message_J1939(tCAN *message). Open up the file mcp2515.cpp. When I wrote this library I based it directly from the datasheet naming conventions. So my suggestion is to read the datasheet and try to match what is in there with my code. The source address (and the rest of the message header) is written in the following lines:

      TXBnSIDH = (message->id) >> 21;

      TXBnSIDL = (message->id) >> 18;
      TXBnSIDL = (TXBnSIDL < < 5) | 0x08 ;

      if (GETBIT((message->id),17)==1) SETBIT(TXBnSIDL,1);
      if (GETBIT((message->id),16)==1) SETBIT(TXBnSIDL,0);

      TXBnEID8 = (message->id)>>8;
      TXBnEID0 = (message->id)>>4;

Leave a Reply

Your email address will not be published. Required fields are marked *

*

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code class="" title="" data-url=""> <del datetime=""> <em> <i> <q cite=""> <strike> <strong> <pre class="" title="" data-url=""> <span class="" title="" data-url="">