Upgrade to Pro — share decks privately, control downloads, hide ads and more …

ESP32 de CANをZephyrでやってみた

ESP32 de CANをZephyrでやってみた

2025/10/20(Mon.)に大阪で開催されたZephyr Project Meetup: Osaka, JapanのLTで話した内容です。
ESP32(初代)にCAN TransceiverのMCP2562FDを接続し、ZephyrでCAN通信した事例を紹介しています。

Avatar for thatsdone

thatsdone

October 19, 2025
Tweet

More Decks by thatsdone

Other Decks in Technology

Transcript

  1. 2 About Me Masanori Itoh – 伊藤 雅典 (いとうまさのり) 

    所属 ✓ AGL (一般人枠)  仕事 ✓ 自動車関係 ✓ ソフト一般、Observability、車両の診断機能(ダイアグ)、 標準化…とかいろいろ ✓ 自社OSPOの運営  Keywords ✓ Operating System, Cloud Infrastructure, etc. ✓ https://github.com/thatsdone ✓ https://www.linkedin.com/in/masanori-itoh-6401603/
  2. 4 話の発端:AGL SoDeV  やりたいこと ➢ SDVのReference PFをフルOSSで作ろうぜ!  方針

    ➢ Xenをハイパーバイザに使い、要件(RTとかASILとか)の厳しいところは Zephyrで手堅くいく。そのほかAGLとかAOSPとか…  ターゲット ➢ Sparrow Hawk Renesas R-Car V4H High Performance AI SBC ✓ https://www.renesas.com/en/support/partners/r-car-consortium/r-car- consortium-proactive-partner-list/rtx-sparrow-hawk 常田さんのCOSCUP2025講演より
  3. 5 話の発端:AGL SoDeV  経緯というか課題というか… 1. Xenのdom0はdomain(VM)の再起動等に必要 ✓xen-troopsのものカイゼンして使う 2. XenのdomDはYoctoが基本だが、可能な限りZephyrに振り向けたい

    3. domUもASILが求められるものはZephyrにしたい ✓ サンプルが必用→趣旨からしてCANの負荷発生器がgood 4. そうするとXen上でI/Oをやりとりする準備がいろいろ必要 ✓ Zephyrのvirtio-can driverとか…  常田大明神のお言葉 (神託?) ➢ 1.~4.の開発のため、(Zephyrが動く)マイコンでCAN通信できる環境を準備 しておくべし
  4. 6 やってみた  自分のモチベーション ➢ 出来心で買ったまま放置しているマイコンが手元にいくらかある… ➢ あれ?ESP32ってCANのコントローラを内蔵してるじゃん… ➢ CANのトランシーバって200円くらいで買えるじゃん…

    ➢ Zephyrの勉強ついでにやってみるかぁ  素材 ➢ Espressif ESP32-DevKitC ESP32-WROVER-E (初期のわりと古めのESP32) ✓ https://akizukidenshi.com/catalog/g/g115674/ ➢ Microchip MCP2562FD (CAN Transceiver) ✓ https://akizukidenshi.com/catalog/g/g114383/ ➢ そのほかパスコン(0.1uF)+終端抵抗(120Ω)+ブレッドボード+ジャンパワイヤほか
  5. 7 やってみた  回路図とできあがったもの ➢ 「みは」さんの記事「ESP32でCAN通信してみた。 MCP2562FDの記事」の回路に従いました ✓ https://ameblo.jp/fc2miha/entry-12833773100.html STBYをLOWに固定しているの

    で、CANバスは常に動いている (BUS STOPしない) Microchip MCP2562FD Espressif ESP32 DevKitC CANの規格上必要な終 端抵抗(120Ω) 赤がCAN_H 白がCAN_L 終端抵抗 (120Ω) MCP2562FD
  6. 8 やってみた  動いた! RaspberryPi Zero W はじめてのESP32 de CAN疎通時

    ターゲット(Sparrow Hawk)疎通時 DSD SH-C31A ESP32 + MCP2562FD ESP32 + MCP2562FD Renesas Sparrow Hawk (R-Car V4H)
  7. 9 やってみた  疎通成功! $ west espressif monitor (snip) [00:00:00.175,000]

    <dbg> can_sja1000: can_sja1000_init: initial sample point error: 0 *** Booting Zephyr OS build v4.2.0-4096-g1c1598601b5c *** (snip) uart:~$ can show can@3ff6b000 core clock: 40000000 Hz max bitrate: 1000000 bps max std filters: 5 max ext filters: 5 capabilities: normal loopback listen-only one-shot triple-sampling mode: normal state: error-active rx errors: 0 tx errors: 0 timing: sjw 1..4, prop_seg 0..0, phase_seg1 1..16, phase_seg2 1..8, prescaler 1..64 transceiver: passive/none statistics: bit errors: 0 bit0 errors: 0 bit1 errors: 0 stuff errors: 0 crc errors: 0 form errors: 0 ack errors: 0 rx overruns: 0 uart:~$ can send can@3ff6b000 234 56 enqueuing CAN frame #0 with standard (11-bit) CAN ID 0x234, RTR 0, CAN FD 0, BRS 0, DLC 1 CAN frame #0 successfully sent uart:~$ なんかおかしい can shellのソースを眺めると、情報取 得に失敗(結果がNULL)だ と、’passive/nne’と表示される模様 CAN ID: 0x234、ペイロード 0x56 (1byte)で送信要求成功している ESP32 SOC内蔵のCAN controllerはNXPの SJA1000互換のIPを使っているらしい。
  8. 10 やってみた  疎通成功! ➢ 対向側(RPi Zero W) $ sudo

    ip link set can0 down $ sudo ip link set can0 type can bitrate 500000 restart-ms 500 $ sudo ip link set can0 up $ ip addr show dev can0 2: can0: <NOARP,UP,LOWER_UP,ECHO> mtu 16 qdisc pfifo_fast state UP group ・ default qlen 10 link/can $ candump can0 can0 234 [1] 56 受信成功! can0はSocketCANのI/F 自動で認識されるが、手動の場合は以下が必用 $ sudo modprobe can $sudo modeprobe can-raw candumpはcan-utils付属のツール 500msごとにチェックしてCANが Bus STOPしないようにしている
  9. 11 やってみた  dtsへの修正 $ git diff boards/ diff --git

    a/boards/espressif/esp32_devkitc/esp32_devkitc-pinctrl.dtsi b/boards/espressif/esp32_devkitc/esp32_devkitc-pinctrl.dtsi index fef35fba088..01e647d95a0 100644 --- a/boards/espressif/esp32_devkitc/esp32_devkitc-pinctrl.dtsi +++ b/boards/espressif/esp32_devkitc/esp32_devkitc-pinctrl.dtsi @@ -110,4 +110,13 @@ input-enable; }; }; + + twai_default: twai_default { + group1 { + pinmux = <TWAI_TX_GPIO26>, + <TWAI_RX_GPIO27>; + bias-disable; + }; + }; + }; diff --git a/boards/espressif/esp32_devkitc/esp32_devkitc_procpu.dts b/boards/espressif/esp32_devkitc/esp32_devkitc_procpu.dts index 7432a24d48a..d81bb4e5950 100644 --- a/boards/espressif/esp32_devkitc/esp32_devkitc_procpu.dts +++ b/boards/espressif/esp32_devkitc/esp32_devkitc_procpu.dts @@ -145,3 +145,15 @@ &wifi { status = "okay"; }; + +&twai { + status = "okay"; + pinctrl-0 = <&twai_default>; + pinctrl-names = "default"; + bus-speed = <500000>; + + can-transceiver { + max-bitrate = <1000000>; + }; + +} ES32ではpin定義が別ファイル になっている。Transceiver (こ の場合はMCP2562FD)のRX/TX とどのpinでつなぐか? 肝心のデバイス定義がないので追加
  10. 12 やってみた CONFIG_CAN=y CONFIG_CAN_ESP32_TWAI=y CONFIG_SHELL=y CONFIG_CAN_SHELL=y CONFIG_ISOTP=y CONFIG_POSIX_API=y CONFIG_NETWORKING=y CONFIG_NET_LOOPBACK=y

    CONFIG_NET_IPV4=y CONFIG_NET_DHCPV4=y CONFIG_NET_NATIVE=y CONFIG_NET_L2_WIFI_MGMT=y CONFIG_WIFI=y CONFIG_NET_L2_WIFI_SHELL=y CONFIG_NET_DRIVERS=y CONFIG_NET_CANBUS=y CONFIG_NET_SOCKETS=y CONFIG_NET_SOCKETS_CAN=y CONFIG_STATS=y CONFIG_CAN_STATS=y CONFIG_LOG=y CONFIG_CAN_LOG_LEVEL_DBG=y CONFIG_GPIO=y  初期疎通時の prj.conf の設定 ➢ 赤は必須(のはず) ➢ 緑はCAN shell有効化、統計情報・デバッグ情報を 出すのに有用 ➢ ISOTPはダイアグ(UDS)のすぐ下のレイヤ ✓ 今後使う予定 ➢ CONFIG_GPIOは、CAN Busの状態制御をしたい場合 に必要になる(はず) ✓ 現状はGNDにつないでLOW固定(=常にactive) ✓ この場合、dtsにさらに追加が必要(な気がする) ➢ CONFIG_NET系は SocketCANで使うため ✓ 今後使う予定 ➢ CONFIG_WIFIはネットにつなぐため ✓ 今後(ついでに)使う予定
  11. 13 やってみた  main.c ➢ 実質 can_start() しているだけ。全部省略して shell から実行するのも可能(なはず)

    (snip) 24 int docan(void) 25 { 26 const struct device *dev = DEVICE_DT_GET(DT_NODELABEL(twai)); 27 int ret; 28 int fd; 29 ret = device_is_ready(dev); 30 printf("device_is_ready(): %d¥n", ret); 31 if (!ret) { 32 return 0; 33 } 34 ret = can_start(dev); 35 printf("can_start(): %d¥n", ret); 36 return 0; 37 } 38 int main(void) 39 { 40 printf("Hello World! %s¥n", CONFIG_BOARD_TARGET); 41 printf("Calling docan()¥n"); 42 docan(); 43 printf("Returned from docan()¥n"); 44 return 0; 45 }
  12. 14 まとめ  結論 ➢ AGL SoDeVのターゲットと、ESP32 w/ZephyrでCAN通信の動作確認できた!  まなび、気づき

    ➢ 動作確認するだけなら、hello worldだけで shell に落ちればよかった★shell便利 ☺ ➢ dts にCANコントローラ(TWAI)の定義追加が必用 ➢ prj.conf も注意が必要(必須のもの、書いてはいけないもの…とか) ➢ shell のcanコマンドの状態表示は正確ではない(ようだ) ✓ 現状、すくなくともこの組み合わせでは…  謝辞 ➢ 一般人がここまでたどり着くにあたり、日本のAGL/Zephyrコミュニティの皆さんに絶大な ご支援をいただきました。感謝いたします!
  13. 15 まとめ  今後 ➢ AGL付属のCAN負荷ジェネレータの移植 (simple_can_simulator.py) ✓ これは素直に作るだけ ➢

    Zephyr virtio-can driverの開発のお手伝い(?) ✓ 上記はfrontendの話。backendまで含めてどう作るのが筋がよさそうか、議論中 ➢ Zephyr UDS on CAN Libraryの開発(DoIPも?) ✓ クルマ屋の観点からは必要なので、負荷ジェネレータの後、こちらに手をやるかもしれ ない
  14. 16 参考:動作確認マトリックス # マイコン CANデバイス OS Zephyr対向確認 1 ESP32-WROVER-E MCP2562FD

    Zephyr - 2 Raspberry Pi 5 SH-C31A (USB) RaspiOS (64bit) - 3 Raspberry Pi 5 RS485 CAN HAT (SPI) RaspiOS (64bit) Not Yet 4 Raspberry Pi Zero W SH-C31A (USB) RaspiOS Lite (32bit) 〇 5 Raspberry Pi Zero W RS485 CAN HAT (SPI) RaspiOS Lite (32bit) - 6 Renesas R-Car V4H Sparrow Hawk 内蔵 Yocto (Scarthgap) 〇
  15. 17 宣伝  AGL OSPO-EGでは「自動車業界からのOSSコントリビューションを阻害する理 由のサーベイ」を行っています。ご協力よろしくお願いいたします! A Survey on the

    Barriers to OSS Contributions in the Automotive Industry https://docs.google.com/forms/d/e/1FAIpQLSdZ1VInvBj72zV6CCTSSU0misi4Az2T9j2ggtawutMLX3b_YA/viewform 自動車業界におけるOSSコントリビューションの阻害要因に関する調査 https://docs.google.com/forms/d/e/1FAIpQLSeYM4q8DUy0S0D2aV6f5QEittTIZ0b5bekGT_-BNhcPIBmDPA/viewform
  16. 19 SoDev Architecture Type 1 Hypervisor (e.g. Xen) Automotive SoC

    or Virtual Environment Dom 0 Linux/Zephyr Control Domain (Optional) Dom D Linux/AGL VirtIO Backend Driver Domain VirtIO Compliant SoC BSP Dom U AAOS VM Management & Monitoring Dom0 Kernel Guest & Function Domains Dom U AGL Dom U Zephyr VirtIO Frontend VirtIO Frontend VirtIO Frontend Infotainment (IVI, RSE, HUD…) IC Graphical Stack IC/ADAS RT Stack Dom U AGL VirtIO Frontend Infotainment (IVI, RSE, HUD…) Unified HMI
  17. 21 参考  Sparrow HawkとRaspberry Pi5 と Raspberry Pi Zero

    Wの3ノードCAN通信 実験時の風景(まだESP32は参加していない時点) 寂しそうに仲間にしてほしそうにしている ESP32 w/MCP2562FD ツイストペアになっていない、なんちゃって CANバス
  18. 22 気づきのたぐい  ESP32の内蔵CANコントローラ(TWAI)を使う場合 ➢ dtsに記述追加が必要 ✓ CONFIG_CAN=y に加えて CONFIG_CAN_ESP32_TWAI=y

    が必用だがdtsに記述追加 しないとビルドエラーになる  ZephyrのCAN shell便利 ➢ CONFIG_SHELL=y & CONFIG_CAN_SHELL=y しておく ➢ ただしESP32 TWAIでは、送信は動いているが状態表示とか実機の状態を正しく反映してい なさそう  ESP32固有の west 拡張(plugin?)便利 ➢ west espressif monitor ✓ リセットして再起動かけてくれる  WSL2でzephyr開発環境 ➢ usbipd と WIN USB便利。WSL2環境で快適に開発作業できる ☺