Ein Allwinner A20 SoC besitzt einen eingebauten CAN-Controller, der jedoch im Mainline Kernel deaktiviert ist.
Um den zu aktivieren sind folgende Schritte notwendig (diese Anleitung bezieht sich auf Kernel Version 4.14.39):
Nun, los geht's...
Das DTS-File liegt unter arch/arm/boot/dts/ und heißt (in meinem Fall eines BananaPRO Boards) sun7i-a20-bananapro.dts, hier muss man am Ende folgenden Block einfügen:
&can0 {
pinctrl-names = "default";
pinctrl-0 = <&can0_pins_a>;
status = "okay";
};
anschließend speichern und schließen.
Nach dem man das DTS-File angepasst hat, muss man den Kernel neubauen, dazu im root-Verzeichnis des Kernels erstmal:
make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- -j4 sunxi_defconfig
Damit wird erstmal eine Default-Konfiguration erzeugt.
Anschließend mit einem
make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- -j4 menuconfig
wird die Konfigurationskonsole geöffnet. Danach "Networking support" --> "CAN bus subsystem support" --> "CAN Device Drivers" --> "Allwinner A10 CAN controller", hier sollte ein <*> oder ein <M> stehen, je nach dem, ob man den Treiber im Kernel fest einkompiliert haben möchte oder als Modul. Nun verlässt man die Konsole und übersetzt den Kernel, die Module und DTS:
make ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- -j4 zImage dtbs modules
Abschließend wird der Kernel, die Module und dtb-File auf die SD-Karte kopiert und das SBC neugestartet.
Non sollte nach der Eingabe von
ifconfig -a
folgendes zu sehen sein:
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)
Interrupt:51
ggf. muss man davor noch das Modul sun7i-can laden:
modprobe sun7i_can
Um die Geschwindigkeit zu setzen, geht man wie folgt vor:
ip link set can0 down
ip link set can0 type can bitrate 125000 triple-sampling on loopback off
ip link set can0 up
Hier wird can0 mit 125kBit/s, tripple-sampling und ohne loopback hochgefahren.
Um eine CAN-Botschaft zu senden:
cansend can0 110#1F.FF
Hier wird eine CAN-Botschaft mit der CAN-ID 0x110 gesendet, die aus zwei (0x1F und 0xFF) besteht, gesendet.