はじめに
MicroPython Zephyrポートのドキュメント和訳の和訳を進めながら Zephar ポートのビルドを試してみました。
Zephyr とは
Wikipedia参照。
ビルド環境の準備
ビルド方法についてはここに記載がありますが、まずは Zephar の開発環境を用意します。
ここに記載のとおり、ホストOSに合わせて Zephyr の環境をインストールします。
ここで注意するのは、ここにも記載されているとおり、Zephyr の v3.1.0 にすることです。最新をインストールしたら MicroPython ビルドでエラーになりました。
サポートされているボード
この記事の執筆時点でサポートされているボードは以下のものです。
- 96Boards Carbon
- BBC micro:bit V2
- ST Disco L475 IOT01
- NXP FRDM-K64F
- NXP FRDM-KW41Z
- NXP MIMXRT1050-EVK
- NXP MIMXRT685-EVK
- ST Nucleo H743ZI
- ST Nucleo WB55RG
- ARM Cortex-M3 Emulation (QEMU)
- X86 Emulation (QEMU)
- reel board
- OpenISA VEGAboard
この中で手持ちのものではBBC micro:bit V2があったので、これ用にビルドして試してみることにしました。
ビルドを試す
MIcroPython のソースコードを GitHub からクローンします。
$ git clone https://github.com/micropython/micropython.git
準備で用意しておいた zephyrproject のディレクトリに移動します。
$ cd <zepherprojectのディレクトリ>
次を実行することでビルドが始まります。
$ west build -b bbc_microbit_v2 <micropythonソースコードのディレクトリ>/ports/zephyr
ビルドが完了したら、micro:bit V2 をボスとPCのUSBに接続して次を実行することで、MicroPython ファームウェアが micro:bit V2 に転送されます。
$ west flash
実行してハマったこと
mpremote コマンドで REPL に入ります。
$ mpremote
無事に REPL に入れました。
試しにLチカを試してみます。
Zephyr ポートの GPIO ピンの指定方法は特殊で、ポートとピン番号のペアで指定します。
この値がZephyrのドキュメントを調べてもよくわからなかったのですが、これの edge_connector: connector
定義から察するに次のように指定すればよさそうです。
- P0: ("GPIO_0", 2)
- P1: ("GPIO_0", 3)
- P2: ("GPIO_0", 4)
これに基づいて、P0 に繋いだ LED を点滅させるスクリプトを作成しました。
from time import sleep_ms
from machine import Pin
LED = Pin(("GPIO_0", 2), Pin.OUT)
while True:
LED.value(1)
sleep_ms(500)
LED.value(0)
sleep_ms(500)
いざ、スクリプトを mpremote で書き込もうとすると OSError: 19 が発生します。REPLで挙動を調べてみると、どうやら、そもそも書き込み可能なファイルシステムが無いようです。
ここの記載から察するに、自分でフラッシュ領域のファイルシステムを作らねばならないのかと想像しました。
ところが、FlashArea クラスが存在しない! フラッシュ領域が使えるようなビルド設定になっていなかったようなのです。他のボードのビルド設定を参考にダメもとで、bbc_microbit_v2.confに以下を追加しました。
# Flash drivers
CONFIG_FLASH=y
CONFIG_FLASH_MAP=y
CONFIG_MPU_ALLOW_FLASH_WRITE=y
これで再ビルドしたところ FlashArea クラスが使えるようになりました。
以下を REPL 上で実行して、ファイルシステムを作成します。サイズは何が適切な値かわからなかったので、とりあえずドキュメントの例示のとおりにしています。
import os
from zephyr import FlashArea
block_dev = FlashArea(FlashArea,STORAGE, 4096)
os.VfsLfs2.mkfs(block_dev)
os.mount(block_dev, '/flash')
ファイルシステムができたので、先ほどのLチカスクリプトを書き込んで実行してみました。やっと実行できました。
おわりに
ビルドまではすんなりいけたものの、Lチカまで想像以上に手がかかってしまいました。まあ、ボードが直接MicroPythonでサポートされているのであれば、わざわざ Zephyr ポートに手を出すこともないのですが、ドキュメント和訳できた記念にやってみました。