LinuxでCAN通信 (CAN FD対応)

要点

  • LinuxカーネルはCAN通信をサポートしている。
  • Ubuntuではカーネルコンフィグをいじらなくてもデフォで使える。
  • ネットワークインターフェースとして扱われ、ソケットAPIで叩ける。

CAN / CAN FDについて

USB-CANアダプタ

  1. Pibiger USB TO CAN FD Converter Adapter Cable SavvyCANFD-C:CAN FD対応
  2. DSD TECH USB-CAN バス アダプター:CAN FD非対応
  3. DSD TECH SH-C31A USB-CANアダプター:ファーム書き換えでCAN FD対応 (未確認)

※ (1) について

ツールのインストール

Ubuntuなどの場合、下記のコマンドでツールをインストールする。

sudo apt install iproute2
sudo apt install can-utils

CANインターフェースの設定

USBデバイスとして認識されていることを確認する。

$ lsusb
Bus 001 Device 006: ID 0c72:0012 PEAK System PCAN-USB FD
Bus 001 Device 005: ID 0c72:0012 PEAK System PCAN-USB FD
...

ネットワークインターフェース(can0, can1,...)として認識されていることを確認する。

$ ls /sys/class/net/
can0  can1 enp0s3  enp0s8  lo
$ ip link show type can
5: can0: <NOARP,ECHO> mtu 16 qdisc noop state DOWN mode DEFAULT group default qlen 10
    link/can 
6: can1: <NOARP,ECHO> mtu 16 qdisc noop state DOWN mode DEFAULT group default qlen 10
    link/can 

ビットレート500kbpsに設定してlink upする。

$ sudo ip link set can0 type can bitrate 500000
$ sudo ip link set can0 up

link downする。(設定変更するときはいったんlink downする。)

$ sudo ip link set can0 down

CAN FDに設定する。

$ sudo ip link set can0 type can bitrate 1000000 fd on

調停部のビットレートを1Mbps、データ部のビットレートを5Mbpsに設定する。

$ sudo ip link set can0 type can bitrate 1000000 dbitrate 5000000 fd on

調停部のサンプルポイントを0.8、データ部のサンプルポイントを0.75に設定する。

$ sudo ip link set can0 up type can bitrate 1000000 dbitrate 5000000 sample-point 0.8 dsample-point 0.75 fd on

設定の詳細を確認する。

$ ip -details link show can0

通信の確認

can-utilsのcandumpとcansendを使って通信を確認する。

can0で受信を待ち受ける。

$ candump can0

can1で送信する。
(ID = 0x123, Data = 0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF)

$ cansend can1 123#0123456789ABCDEF
あるいは
$ cansend can1 123#01.23.45.67.89.AB.CD.EF

can0で受信を確認する。

  can0  123   [8]  01 23 45 67 89 AB CD EF

can1で送信する。(CANFD)
(ID = 0x123, Data 16バイト)
※ ##の後の1.は、データ部のビットレート切り替えを意味する。0だと切り替えなし。

cansend can1 123##1.0123456789ABCDEF0123456789ABCDEF

can0で受信を確認する。

  can0  123  [16]  01 23 45 67 89 AB CD EF 01 23 45 67 89 AB CD EF

C言語でのCAN通信のプログラム

can-utilsのソースを参考にする。
送信は cansend.c 、受信は candump.c が参考になる。
基本的にはIP通信のソケットAPIを使ったプログラムと同様であるが、
構造体がCAN通信特有であることに注意。

CAN FDでデータ部のビット切り替えをする場合、canfd_frame構造体の flags に CANFD_BRS をセットすることに注意。CANFD_BRS は、/linux/can.h で定義されている。

    struct canfd_frame tx_frame;
...
    tx_frame.flags = CANFD_BRS;