CAN bus is locked up until beaglebone finishes booting

I have an emergency, and I would greatly appreciate any help that someone can give. I have the beaglebone on a can bus and while the beaglebone is powered off, everything works great. When I turn the beaglebone on, the bus gets heavy and locks up. Once the beaglebone finishes booting, the CAN bus is active again.

Here is what I think is happening. In the kernel, I do the following:
setup_pin_mux(uart1dcan1_pin_mux);
am33xx_d_can_init(1);

Once I am in userspace, I do the following:
ip link set can0 type can bitrate 250000 triple-sampling on
ifconfig can0 up

I think the bus is heavy in between these two. Is there something I should try? Any thoughts? Thanks,

Are you sure your other node isn’t just continually re-transmitting because its frames are not being acknowledged by anyone on the bus?

I have an emergency, and I would greatly appreciate any help that someone
can give. I have the beaglebone on a can bus and while the beaglebone is
powered off, everything works great. When I turn the beaglebone on, the bus
gets heavy and locks up. Once the beaglebone finishes booting, the CAN bus
is active again.

Here is what I think is happening. In the kernel, I do the following:
setup_pin_mux(uart1dcan1_pin_mux);
am33xx_d_can_init(1);

Once I am in userspace, I do the following:
ip link set can0 type can bitrate 250000 triple-sampling on
ifconfig can0 up

Can you comment out the setup_pin_mux(uart1dcan1_pin_mux) call in the
kernel? Set those lines to inputs if they don't default that way.
Then, right before or after the "ip link/ifconfig" calls in userspace,
manually configure the pinmux via devmem. I know it's a hack, but
maybe it will reduce the duration of the can bus hang until a better
solution can be found.

Well, you are correct in that it is the “setup_in_mux(uart1dcan1_pin_mux);” line. I’m not familiar with devmem… any pointers on how to use this? I’m researching this now, but just in case you beat me to it… :slight_smile:

Well, you are correct in that it is the "setup_in_mux(uart1dcan1_pin_mux);"
line. I'm not familiar with devmem... any pointers on how to use this? I'm
researching this now, but just in case you beat me to it... :slight_smile:

If you're using busybox, it's called devmem. If not, there's devmem2.
The programs just let you read and write random locations in memory.

devmem <addr> <width 8/16/32> <value>

You're interested in the control module registers starting at
0x44e10000. The pinmux settings start at register 0x800. I'd suggest
that you call setup_in_mux() and then look what the raw pinmux values
are set to, and then boot without setup_in_mux() and set the values
for the CAN pins. It's a little tedious, but basically you'll be doing
things like:

devmem 0x44e108xx 32 0x51

but with the addresses of the pins that you use and their correct
mode/input/output settings (see spruh73h.pdf 9.3.51).

Hope this helps,
Frank

That does help, but I’m still not sure on how to use devmem2. If I type in devmem2 0x44e10000 I get:

/dev/mem opened.
Memory mapped at address 0x40244000.
Read at address 0x44E10000 (0x40244000): 0x4E8B0100

How do I know where the two CAN pins were mapped?

That does help, but I'm still not sure on how to use devmem2. If I type in
devmem2 0x44e10000 I get:

/dev/mem opened.
Memory mapped at address 0x40244000.
Read at address 0x44E10000 (0x40244000): 0x4E8B0100

How do I know where the two CAN pins were mapped?

Here's the basic idea:

  1. Figure out which pin that you're interested in. E.g. dcan0_rx
  2. Figure out the Pinmux mode0 name for the pin (dcan0_rx -> uart1_rtsn)
  3. Look up in the control module register in table 9.3 that's named
conf_xxx (e.g. conf_uart1_rtsn). It's at offset 0x97c
  4. Add the offset to 0x44e10000 to read the pin mux setting.

I currently using the I2C bus (pinmux mode 3) on that pin, so here's
what it looks like for me:

# devmem 0x44e1097c 32
0x00000073

You'll probably be writing something like:

# devmem 0x44e1097c 32 0x22

To put it into mode 2 for CAN. (But I guessed on the 0x22 value, so
check before you set it)

Also, the pinmux tables at
GitHub - bradfa/beaglebone_pinmux_tables: BeagleBone pin multiplexing tables have the register
offset listed, but it's from the start of the pinmux registers so you
need to add 0x44e10800 to the offset to get the right address.

Frank

I think I get it now, but just to verify…

I am using dcan1, so the mode0 name is uart1_txd. Looking in the 9.3 table it looks like my offset is 0x984. So I add this to 0x44E1000 and the result is: 0x44E10984.

So when I read this out I get:
root@beaglebone:~# devmem2 0x44E10984
/dev/mem opened.
Memory mapped at address 0x401cf000.
Read at address 0x44E10984 (0x401cf984): 0x00000032

So my command becomes devmem 0x44E10984 32 0x32… right? Then repeat all of that for the dcan1_tx pin?

I think I get it now, but just to verify...

I am using dcan1, so the mode0 name is uart1_txd. Looking in the 9.3 table
it looks like my offset is 0x984. So I add this to 0x44E10000 and the result
is: 0x44E10984.

So when I read this out I get:
root@beaglebone:~# devmem2 0x44E10984
/dev/mem opened.
Memory mapped at address 0x401cf000.
Read at address 0x44E10984 (0x401cf984): 0x00000032

So my command becomes devmem 0x44E10984 32 0x32... right?

Right. Also, the 0x32 you got means input/pullup/mode2, so that sounds
right as well.

Then repeat all
of that for the dcan1_tx pin?

Yes.

Frank