Controller Area Network (CAN) Bus: Implementation for ODROID-C1+ and ODROID-XU4

This article explains how to enable the CAN bus on ODROID-C1/C1+/C0 via HW SPI interface. Detailed instruction to exchange data with a MCP2515 Bus Monitor board is also documented.

H/W connection

The following products are required to configure the hardware:

CAN Bus - Figure 1

Figure 2 - ODROID Tinkering kit

Figure 3 - Reference circuit

Figure 4 - Breadboard diagram

Figure 5 - Breadboard illustration

Figure 6 - Connect the CAN module and ODROID-C1 using tinkering kit

Before installing the software, you must modify the mcp2515 driver to set the amlogic GPIO IRQ. Apply this patch to your kernel. Unzip the zip file and type “git apply odroid-c1-mcp251x.patch”. Then, edit arch/arm/boot/dts/meson8b_odroidc.dts and uncomment the can0 section.

Enable the CAN controller kernel driver

ODROID-C1 platform with a MCP2515 chip the configuration is: Linux Kernel Configuration > Networking support > CAN bus subsystem support > CAN device drivers > Platform CAN drivers with Netlink support > CAN bit-timing calculation > Microchip MCP251x SPI CAN controller

Then, reflash the kernel and root file system. See these instructions for how to build and install the kernel.

Verifying CAN support configuration

Load all the required drivers, using the sudo password of “odroid”:

$ sudo su
# modprobe can_raw
# modprobe spicc
# modprobe mcp251x mcp251x_enable_dma=1
Next, verify the CAN host driver:
# ls /sys/class/net/
can0  eth0  ip6tnl0  lo  sit0
# ifconfig can0
can0      Link encap:UNSPEC  HWaddr 00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00  
          NOARP  MTU:16  Metric:1
          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:10 
          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)

Power on the CAN hardware

Set the bitrate before all operations, similar to the following example where the bitrate of the can0 interface is set to 125kbps:

# ip link set can0 type can bitrate 125000 triple-sampling on
# ifconfig can0 up
# ifconfig
can0      Link encap:UNSPEC  HWaddr 00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00  
          UP RUNNING NOARP  MTU:16  Metric:1
          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:10 
          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)
 
eth0      Link encap:Ethernet  HWaddr 00:1e:06:10:18:1c  
          UP BROADCAST MULTICAST  MTU:1500  Metric:1
          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1000 
          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)
          Interrupt:40 
 
lo        Link encap:Local Loopback  
          inet addr:127.0.0.1  Mask:255.0.0.0
          inet6 addr: ::1/128 Scope:Host
          UP LOOPBACK RUNNING  MTU:65536  Metric:1
          RX packets:1360 errors:0 dropped:0 overruns:0 frame:0
          TX packets:1360 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0 
          RX bytes:108256 (108.2 KB)  TX bytes:108256 (108.2 KB)

Installing SocketCAN utils

The package “can-utils” is a collection of CAN drivers and networking tools for Linux. It allows interfacing with CAN bus devices in a similar fashion as other network devices.

$ sudo apt install can-utils
Type the following commands to perform a loopback test on a single CAN port:
# ifconfig can0 down
# ip link set can0 type can bitrate 125000 loopback on
# ifconfig can0 up
# ip -details link show can0
5: can0: <NOARP,UP,LOWER_UP,ECHO> mtu 16 qdisc pfifo_fast state UNKNOWN mode DEFAULT group default qlen 10
    link/can  promiscuity 0 
    can <LOOPBACK,TRIPLE-SAMPLING> state ERROR-ACTIVE restart-ms 0 
          bitrate 125000 sample-point 0.875 
          tq 500 prop-seg 6 phase-seg1 7 phase-seg2 2 sjw 1
          mcp251x: tseg1 3..16 tseg2 2..8 sjw 1..4 brp 1..64 brp-inc 1
          clock 10000000
The following command shows the received message from the CAN bus:
$ candump can0
In a second terminal, the following command sends 3 bytes on the bus (0x11, 0x22, 0x33) with the identifier 500:
$ cansend can0 500#11.22.33
To test the CAN-bus link between 2 ODROID-C1 boards, first connect the CANL and CANH pins of two ODROID-C1 boards.

Figure 7 - connecting the CANL and CANH pins of two ODROID-C1 boards

Power-up both boards, then type the following into the shell of both boards for configuration the CAN bus device:

$ modprobe can_raw
$ modprobe spicc
$ modprobe mcp251x mcp251x_enable_dma=1
$ ip link set can0 type can bitrate 125000 triple-sampling on
$ ifconfig can0 up
Type the following to the shell of board 1 (which is used for testing receiving over can0 device):
$ candump can0
Type the following to the shell of board 2 (which is used for testing sending data packets over can0 device):
$ cansend can0 500#11.22.33
At this point, board 1 will receive the data packet sent from board 2:
# candump can0
  can0  500   [3]  11 22 33
  can0  500   [3]  11 22 33
For comments, questions, and suggestions, please visit the original Wiki page at https://wiki.odroid.com/odroid-c1/application_note/gpio/can-bus.

Be the first to comment

Leave a Reply