Jetson nano and mcp2515 can module

Hi @shgarg,
I’ve reached to the moment when I can init mcp2515 on my Jetson Nano but i cannot send or receive any frames with candump or cansend. Only when I init can0, try to send frame and set can0 down I was able to receive different frame on other device (but only when i set can_clock to 12M, the same value like my oscillator and the same baudrate like other device). I’ve received frame like that:

RCV XTD CAN0 Id 1AC9D337 Len 5 DATA BA EA F7 DD D8 T:799333767

The count of errors in was increasing each attempt to send:

root@huuver-desktop:/home/huuver# ip -d -s link show can0
4: can0: <NOARP,ECHO> mtu 16 qdisc pfifo_fast state DOWN mode DEFAULT group default qlen 10
link/can promiscuity 0
can state STOPPED restart-ms 0
bitrate 500000 sample-point 0.850
tq 100 prop-seg 8 phase-seg1 8 phase-seg2 3 sjw 1
mcp251x: tseg1 3…16 tseg2 2…8 sjw 1…4 brp 1…64 brp-inc 1
clock 12000000
re-started bus-errors arbit-lost error-warn error-pass bus-off
0 0 0 0 0 0 numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
RX: bytes packets errors dropped overrun mcast
0 0 0 0 0 0
TX: bytes packets errors dropped carrier collsns
0 0 10 10 0 0

Also there was no interrupts:

root@huuver-desktop:/home# cat /proc/interrupts | grep mcp
299: 0 0 GPIO 200 Edge mcp251x

I’ve tried to trigger interrupt manually on pin 12 (BCM:gpio79) with Jetson.GPIO library. I followed this guide: https://maker.pro/nvidia-jetson/tutorial/how-to-use-gpio-pins-on-jetson-nano-developer-kit. I connected this pin to pin 40 (BCM:gpio78) and I was cheching input on pin 12. When I was changing pin 40 value I saw changes on pin 12 but when I was listening events or tried to trigger interrupt on that pin, it didn’t work:

root@huuver-desktop:/home/huuver# cat /proc/interrupts | grep gpiolib
114: 0 0 GPIO 15 Edge gpiolib

I’m looking forward for your advice.

Thanks!

Hi all,

I have made progress since before, I have tried lots of things, but this seems to work up to the last point -

  1. I decompiled the .dtb file from @shgarg using dtc and replaced all references to “a02” using “b00” (thanks @742561445)
  2. I changed my can_clock clock-frequency to <0x7a1200> in the .dtb
  3. I changed my can_clock phandle and linux,phandle to <0x12c> (to match the clocks proerty in the mc251 node in spi@0)
  4. I recompiled the .dtb using dtc and replaced “a02” with “b00” in the file name
  5. I replaced “a02” in the filename with “b00” for the .dtbo from @shgarg
  6. Copied the .dtb file to /boot/dtb/
  7. Copied the .dtbo file to /boot/
  8. Copied the.ko file to /lib/modules/4.9.140-tegra/kernel/drivers/net/can/spi/
  9. Rebooted
  10. Ran jetson-io.py and selected Configure for compatible hardware, then selected MCP2515 and this was successful

Attached my dtb and dtbo
dtb and dtbo.zip (88.7 KB)

Now though, when I start the Jetson Nano, it says the following - (logged via dmesg | spi)
[ 8.471554] OF: /spi@7000d400/spi@0: could not get #gpio-cells for /leds
[ 8.485325] mcp251x spi0.0: failed to get GPIO from device tree
[ 8.532635] mcp251x spi0.0 can0: MCP2515 successfully initialized.

When I run ifconfig can0, I get the following -
can0: flags=128 mtu 16
unspec 00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00 txqueuelen 10 (UNSPEC)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0

lsmod gives the following -
Module Size Used by
fuse 103841 4
bnep 16562 2
8723bu 1033005 0
cfg80211 589351 1 8723bu
btusb 40213 0
btrtl 7318 1 btusb
btbcm 8808 1 btusb
btintel 10771 1 btusb
zram 26166 4
overlay 48691 0
mcp251x 14965 0
spidev 13282 0
can_dev 13306 1 mcp251x
nvgpu 1579891 33
bluedroid_pm 13912 0
ip_tables 19441 0
x_tables 28951 1 ip_tables

I cannot see any mention of can or MCP2515 in my /proc/interrupts
Attached - proc-interrupts.txt (8.3 KB)

I think that there is a problem with my interrupt which is causing this. It doesn’t say wrong wiring anymore when the kernel is loaded so I know the wiring and the clock speed is right.

Can anyone help me debug this please?

Hi, anyone help with this? I am really struggling? If you need any more data please let me know

Hi,
Please make below changes in kernel gpio driver source code:
drivers/gpio/gpio-tegra.c
In this function:
static int tegra_gpio_irq_set_type(struct irq_data *d, unsigned int type)
Remove these lines:
tegra_gpio_mask_write(tgi, GPIO_MSK_OE(tgi, gpio), gpio, 0);
tegra_gpio_enable(tgi, gpio);
and ADD these lines:
ret = tegra_gpio_direction_input(&tgi->gc, gpio);
if (ret) {
gpiochip_unlock_as_irq(&tgi->gc, gpio);
return ret;
}
You do not need to modify mcp driver. Please keep the mcp driver as it is.
Compile the kernel, flash the device again with the new Image.
After flash, copy the attached dtbo in /boot/ which works for both A02 and B00.
then choose MCP device in Jetson-IO tool and reboot.
Make connections as mentioned in earlier comments.
Let me know the results.
tegra210-p3448-0000-p3449-0000-a02-mcp251x.zip (1.0 KB)

Attaching dtbo file again

Hi @sharadg,
I modified GPIO driver, recompiled and flashed device and only difference is that there’s always +1 incrementation, no mater how many frames I try to send between bringing interface up and down.

huuver@huuver-desktop:~$ ip -d -s link show can0
4: can0: <NOARP,ECHO> mtu 16 qdisc pfifo_fast state DOWN mode DEFAULT group default qlen 10
link/can promiscuity 0
can state STOPPED restart-ms 0
bitrate 500000 sample-point 0.850
tq 100 prop-seg 8 phase-seg1 8 phase-seg2 3 sjw 1
mcp251x: tseg1 3…16 tseg2 2…8 sjw 1…4 brp 1…64 brp-inc 1
clock 10000000
re-started bus-errors arbit-lost error-warn error-pass bus-off
0 0 0 0 0 0 numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
RX: bytes packets errors dropped overrun mcast
0 0 0 0 0 0
TX: bytes packets errors dropped carrier collsns
0 0 8 8 0 0

I hope that I didn’t make any mistake.

+1 incrementation in? sending msg twice?
so are you receiving interrupts now?
Please send the output of
cat /proc/interrupts | grep mcp

+1 incrementation of TX errors and dropped in output of:

huuver@huuver-desktop:~$ ip -d -s link show can0
4: can0: <NOARP,ECHO> mtu 16 qdisc pfifo_fast state DOWN mode DEFAULT group default qlen 10
link/can promiscuity 0
can state STOPPED restart-ms 0
bitrate 500000 sample-point 0.850
tq 100 prop-seg 8 phase-seg1 8 phase-seg2 3 sjw 1
mcp251x: tseg1 3…16 tseg2 2…8 sjw 1…4 brp 1…64 brp-inc 1
clock 10000000
re-started bus-errors arbit-lost error-warn error-pass bus-off
0 0 0 0 0 0 numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
RX: bytes packets errors dropped overrun mcast
0 0 0 0 0 0
TX: bytes packets errors dropped carrier collsns
0 0 8 8 0 0

There are no interrupts:

huuver@huuver-desktop:~$ cat /proc/interrupts | grep mcp
299: 0 0 0 0 GPIO 200 Edge mcp251x

Hi,
Can you send me output of “dmesg | grep mcp” and “cat /sys/kernel/debug/gpio”.
The problem is with interrupts. Also, you have connected 2 MCPs right? So 2 GPIOs in cat /proc/interrupts | grep mcp. Are the interrupts not coming in both the MCP?

Hi,

I actually don’t have access to Jetson. I can send you outputs in Monday.

Also, you have connected 2 MCPs right?

No, I have connected one MCP to Jetson and I’m trying to communicate with It by other MCP connected to Raspberry or Softing CANro USB.

Hello, could anyone guide me how to modify the .dtb file. For example

@sharadg mentioned that:

So how to do it? And just copy that (modified) .dtb file in /boot or something more we have to do?
I know it may relate to the device tree boot and I discovered some commands such as dft, fdtdump to display the content of .dtb file but I do not know how to change and activate those.

Please help and thanks in advance!

@shgarg,
My outputs:

huuver@huuver-desktop:~$ dmesg | grep mcp
[ 8.120729] mcp251x spi0.0 can0: MCP2515 successfully initialized.
[ 8.134747] mcp251x spi1.0: Cannot initialize MCP2515. Wrong wiring?
[ 8.141229] mcp251x spi1.0: Probe failed, err=19

huuver@huuver-desktop:~$ sudo cat /sys/kernel/debug/gpio
gpiochip0: GPIOs 0-255, parent: platform/6000d000.gpio, tegra-gpio:
gpio-0 ( )
gpio-1 ( )
gpio-2 ( |pcie_wake ) in hi
gpio-3 ( )
gpio-4 ( )
gpio-5 ( )
gpio-6 ( |vdd-usb-hub-en ) out hi
gpio-7 ( )
gpio-8 ( )
gpio-9 ( )
gpio-10 ( )
gpio-11 ( )
gpio-12 (SPI1_MOSI )
gpio-13 (SPI1_MISO )
gpio-14 (SPI1_SCK )
gpio-15 (SPI1_CS0 )
gpio-16 (SPI0_MOSI )
gpio-17 (SPI0_MISO )
gpio-18 (SPI0_SCK )
gpio-19 (SPI0_CS0 )
gpio-20 (SPI0_CS1 )
gpio-21 ( )
gpio-22 ( )
gpio-23 ( )
gpio-24 ( )
gpio-25 ( )
gpio-26 ( )
gpio-27 ( )
gpio-28 ( )
gpio-29 ( )
gpio-30 ( )
gpio-31 ( )
gpio-32 ( )
gpio-33 ( )
gpio-34 ( )
gpio-35 ( )
gpio-36 ( )
gpio-37 ( )
gpio-38 (GPIO13 )
gpio-39 ( )
gpio-40 ( )
gpio-41 ( )
gpio-42 ( )
gpio-43 ( )
gpio-44 ( )
gpio-45 ( )
gpio-46 ( )
gpio-47 ( )
gpio-48 ( )
gpio-49 ( )
gpio-50 (UART1_RTS )
gpio-51 (UART1_CTS )
gpio-52 ( )
gpio-53 ( )
gpio-54 ( )
gpio-55 ( )
gpio-56 ( )
gpio-57 ( )
gpio-58 ( )
gpio-59 ( )
gpio-60 ( )
gpio-61 ( )
gpio-62 ( )
gpio-63 ( )
gpio-64 ( )
gpio-65 ( )
gpio-66 ( )
gpio-67 ( )
gpio-68 ( )
gpio-69 ( )
gpio-70 ( )
gpio-71 ( )
gpio-72 ( )
gpio-73 ( )
gpio-74 ( )
gpio-75 ( )
gpio-76 (I2S0_FS )
gpio-77 (I2S0_DIN )
gpio-78 (I2S0_DOUT )
gpio-79 (I2S0_SCLK )
gpio-80 ( )
gpio-81 ( )
gpio-82 ( )
gpio-83 ( )
gpio-84 ( )
gpio-85 ( )
gpio-86 ( )
gpio-87 ( )
gpio-88 ( )
gpio-89 ( )
gpio-90 ( )
gpio-91 ( )
gpio-92 ( )
gpio-93 ( )
gpio-94 ( )
gpio-95 ( )
gpio-96 ( )
gpio-97 ( )
gpio-98 ( )
gpio-99 ( )
gpio-100 ( )
gpio-101 ( )
gpio-102 ( )
gpio-103 ( )
gpio-104 ( )
gpio-105 ( )
gpio-106 ( )
gpio-107 ( )
gpio-108 ( )
gpio-109 ( )
gpio-110 ( )
gpio-111 ( )
gpio-112 ( )
gpio-113 ( )
gpio-114 ( )
gpio-115 ( )
gpio-116 ( )
gpio-117 ( )
gpio-118 ( )
gpio-119 ( )
gpio-120 ( )
gpio-121 ( )
gpio-122 ( )
gpio-123 ( )
gpio-124 ( )
gpio-125 ( )
gpio-126 ( )
gpio-127 ( )
gpio-128 ( )
gpio-129 ( )
gpio-130 ( )
gpio-131 ( )
gpio-132 ( )
gpio-133 ( )
gpio-134 ( )
gpio-135 ( )
gpio-136 ( )
gpio-137 ( )
gpio-138 ( )
gpio-139 ( )
gpio-140 ( )
gpio-141 ( )
gpio-142 ( )
gpio-143 ( )
gpio-144 ( )
gpio-145 ( )
gpio-146 ( )
gpio-147 ( )
gpio-148 ( )
gpio-149 (GPIO01 )
gpio-150 ( )
gpio-151 ( |cam_reset_gpio ) out lo
gpio-152 ( |camera-control-outpu) out lo
gpio-153 ( )
gpio-154 ( )
gpio-155 ( )
gpio-156 ( )
gpio-157 ( )
gpio-158 ( )
gpio-159 ( )
gpio-160 ( )
gpio-161 ( )
gpio-162 ( )
gpio-163 ( )
gpio-164 ( )
gpio-165 ( )
gpio-166 ( )
gpio-167 ( )
gpio-168 (GPIO07 )
gpio-169 ( )
gpio-170 ( )
gpio-171 ( )
gpio-172 ( )
gpio-173 ( )
gpio-174 ( )
gpio-175 ( )
gpio-176 ( )
gpio-177 ( )
gpio-178 ( )
gpio-179 ( )
gpio-180 ( )
gpio-181 ( )
gpio-182 ( )
gpio-183 ( )
gpio-184 ( )
gpio-185 ( )
gpio-186 ( )
gpio-187 ( |? ) out hi
gpio-188 ( )
gpio-189 ( |Power ) in hi IRQ
gpio-190 ( |Forcerecovery ) in hi IRQ
gpio-191 ( )
gpio-192 ( )
gpio-193 ( )
gpio-194 (GPIO12 )
gpio-195 ( )
gpio-196 ( )
gpio-197 ( )
gpio-198 ( )
gpio-199 ( )
gpio-200 (GPIO11 )
gpio-201 ( |cd ) in lo IRQ
gpio-202 ( |pwm-fan-tach ) in hi IRQ
gpio-203 ( |vdd-3v3-sd ) out hi
gpio-204 ( )
gpio-205 ( )
gpio-206 ( )
gpio-207 ( )
gpio-208 ( )
gpio-209 ( )
gpio-210 ( )
gpio-211 ( )
gpio-212 ( )
gpio-213 ( )
gpio-214 ( )
gpio-215 ( )
gpio-216 (GPIO09 )
gpio-217 ( )
gpio-218 ( )
gpio-219 ( )
gpio-220 ( )
gpio-221 ( )
gpio-222 ( )
gpio-223 ( )
gpio-224 ( )
gpio-225 ( |hdmi2.0_hpd ) in hi IRQ
gpio-226 ( )
gpio-227 ( )
gpio-228 ( |extcon:extcon@1 ) in hi IRQ
gpio-229 ( )
gpio-230 ( )
gpio-231 ( )
gpio-232 (SPI1_CS1 )
gpio-233 ( )
gpio-234 ( )
gpio-235 ( )
gpio-236 ( )
gpio-237 ( )
gpio-238 ( )
gpio-239 ( )

gpiochip1: GPIOs 504-511, parent: platform/max77620-gpio, max77620-gpio, can sleep:
gpio-505 ( |spmic-default-output) out hi
gpio-507 ( |vdd-3v3-sys ) out hi
gpio-510 ( |enable ) out hi
gpio-511 ( |avdd-io-edp-1v05 ) out lo

Hi, @bigboy.061293,
After you configure your Jetson by /opt/nvidia/jetson-io/jetson-io.py and create tegra210-p3448-0000-p3449-0000-a02-mcp251x-can-controller.dtb you must copy this file from /boot and decompile it using command below in folder with this file (if you have different title in jetson-io.py output, you must use it. For example tegra210-p3448-0000-p3449-0000-b00-mcp251x-can-controller.dtb):

dtc -I dtb -O dts tegra210-p3448-0000-p3449-0000-a02-mcp251x-can-controller.dtb -o can.dts

Then you can modify yours .dts file. After modification you must compile your .dts file:

dtc -@ -O dtb -o tegra210-p3448-0000-p3449-0000-a02-mcp251x-can-controller.dtb can.dts

Replace this file in /boot directory and reboot Jetson.

Thank you, I will try and get back later.
Cheer!

Hi guys, I am facing a problem, there are many packets errors. I am holding the sensor which continuously sending (streaming) data via CAN. The module worked fine in RPi. I followed previous instruction and everything seems fine until yesterday, I figure out there are a lot of missed messages. When I check the

ifconfig

It is:

can0: flags=193<UP,RUNNING,NOARP> mtu 16
unspec 00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00 txqueuelen 10 (UNSPEC)
RX packets 30621 bytes 244968 (244.9 KB)
RX errors 25536 dropped 0 overruns 0 frame 25536
TX packets 1 bytes 18446744073709551615 (1844.6 PB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0

Before that, I checked:

ip -details -statistics link show can0

And the can state was BUS-OFF (if CAN driver detects there are many errors packets, it will change to the state BUS-OFF), so I had to do:

sudo ip link set can0 up type can bitrate 500000 restart-ms 100

to restart it automatically. However there are so many packet missed.

I think the problem of being error is about invalid CRC. Everything was fine in my Raspberry Pi (hardware, resistor 120 Ohm… are the same).

Do you guys face the same situation?

Thanks.

I have a similar situation as @bigboy.061293 , I can see a lot of missing messages. I have 5 Arduino devices sending CAN messages, one Arduino listening for messages, and a Jetson Nano also listening. The Arduino receiver receives all messages without any problems, while the jetson nano misses messages (from time to time):

➜ ~ ifconfig can1
can1: flags=193<UP,RUNNING,NOARP> mtu 16
unspec 00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00 txqueuelen 20000 (UNSPEC)
RX packets 5916416 bytes 23665624 (23.6 MB)
RX errors 89482 dropped 0 overruns 0 frame 89482
TX packets 9 bytes 18446744073709551607 (1844.6 PB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0

➜ ~ sudo ip -d -s link show can1
5: can1: <NOARP,UP,LOWER_UP,ECHO> mtu 16 qdisc pfifo_fast state UNKNOWN mode DEFAULT group default qlen 20000
link/can promiscuity 0
can state ERROR-ACTIVE restart-ms 10
bitrate 250000 sample-point 0.750
tq 200 prop-seg 7 phase-seg1 7 phase-seg2 5 sjw 1
mcp251x: tseg1 3…16 tseg2 2…8 sjw 1…4 brp 1…64 brp-inc 1
clock 10000000
re-started bus-errors arbit-lost error-warn error-pass bus-off
0 0 0 5 5 0 numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
RX: bytes packets errors dropped overrun mcast
23665948 5916497 89482 0 89482 0
TX: bytes packets errors dropped carrier collsns
18446744073709551607 9 0 0 0 0

I would really appreciate any help to resolve the problem of the missing messages because I already have software and hardware designs ready, but I’m unable to receive messages reliably. It would be disappointing to use can-usb converter at this point.

After a quick google search and a short test, this seems to have helped, no lost messages in 5 minutes: Too much delay between spi read operations

Try running:
sudo nvpmodel -m 0
sudo jetson_clocks

Hi, that helps a lot, thanks. However, I am facing interesting issue:

My sensor always send a notification message containing how many following messages (indicating how many objects of the sensor detected) should be received. By checking with candump, I discovered:

Before

sudo jetson_clocks

The notification messages announce N but I always receive less than N (notify 10, I receive just 4)

After

sudo jetson_clocks

The notification messages announce N, I receive enough N

It seems to be okay but RX errors still announces the same behavior, which is very close to the RX packets. In this case, I am not sure the mechanism of candump, if it also check the CRC, how ifconfig check the RX errors?

CRC check should be checked by the MCP2515 controller, not by the driver (as far as I know).

This might also happen if sample point configurations differ from your controller, try using different sample points:

ip link set can0 type can bitrate 250000 sample-point 0.75

If you don’t know what sample point is used by other controllers, try anything between 0.6 and 0.875, one of them should be good enough. I’m using 0.75, as per CAN bus protocol recommendations.

Also, make sure your clocks in DTB are properly set (can_clocks must be the same value as your MCP2515 oscillator frequency).

After nvp model change, I get an error rate of less than 0.05%, which is good enough for my application (before it was >1.5%).

Thanks for your advice. I have tried some sample-point from 0.1 to 1 and down and up the interface but nothing changes. I am sure that in DTB, the can_clocks is 8Mhz which is also the crystal for MCP2515.
The strange thing is, the sample configuration worked with Rapsberry Pi. I also did a examination on the bus with oscilloscope, the result is fine too.

I had a situation when I was not able to receive any data, the controller received a lot of errors and went to BUS-OFF state in couple of seconds (I was able to receive some nonsense messages on candump though). Then I tried setting double bitrate (500k instead of 250k) and then the controller started to receive messages, this was due to incorrect clock rates in DTB… If that seems similar, you can try setting double bitrate, just to rule out this possibility.