defmt のセットアップ
セットアップを簡単にするために、Cargo プロジェクトテンプレートを作成しました。 セットアップ手順は次のとおりです。
probe-runの v0.1.4(またはそれ以降)をインストールします。これは、組み込みアプリをネイティブアプリであるかのように実行できる、カスタム Cargo runner です。
$ cargo install probe-run
cargo-generateでプロジェクトテンプレートを初期化するか、コピーを取得してCargo.tomlを手動で初期化します。
$ cargo generate \
--git https://github.com/knurling-rs/app-template \
--branch main \
--name my-app
cargo-generate を使用しない場合は、Cargo.toml の author フィールドと name フィールドを手動で入力する必要があります。
# Cargo.toml
[package]
-# authors = ["{{authors}}"]
-# name = "{{project-name}}"
+name = "my-app"
その後、テンプレートには TODO がいくつかあります。
ripgrep を使って TODO という語を検索し(rg TODO .cargo .)、それらを見つけることができますが、このブログ記事ではそのすべてを順を追って説明します。
probe-run --list-chipsからチップを選び、それを.cargo/config.tomlに入力します。
たとえば、私たちのワークショップのいずれかで使用した nRF52840 Development Kit を持っている場合は、{{chip}} を nRF52840_xxAA に置き換えます。
# .cargo/config.toml
[target.'cfg(all(target_arch = "arm", target_os = "none"))']
-runner = "probe-run --chip {{chip}} --defmt"
+runner = "probe-run --chip nRF52840_xxAA --defmt"
.cargo/config.tomlのコンパイルターゲットを調整します。
nRF52840 チップでは、thumbv7em-none-eabihf ターゲットを使用します。
# .cargo/config.toml
[build]
-target = "thumbv6m-none-eabi" # Cortex-M0 and Cortex-M0+
-# target = "thumbv7m-none-eabi" # Cortex-M3
-# target = "thumbv7em-none-eabi" # Cortex-M4 and Cortex-M7 (no FPU)
-# target = "thumbv7em-none-eabihf" # Cortex-M4F and Cortex-M7F (with FPU)
+target = "thumbv7em-none-eabihf" # Cortex-M4F(FPU あり)
まだ行っていない場合は、上記のターゲット用の rust-std コンポーネントをインストールします。
$ rustup target add thumbv7em-none-eabihf
- HAL を依存関係として追加します。
nRF52840 では、nrf52840-hal を使用します。
# Cargo.toml
[dependencies]
-# some-hal = "1.2.3"
+nrf52840-hal = "0.11.0"
- HAL を選択したので、
src/lib.rsの HAL インポートを修正します。
// my-app/src/lib.rs
-// use some_hal as _; // memory layout
+use nrf52840_hal as _; // メモリレイアウト
Hello defmt
これで、初めての defmt 対応アプリケーションを cargo-run する準備がすべて整いました!
src/bin ディレクトリにはいくつかの例があります。
// my-app/src/bin/hello.rs
#![no_main]
#![no_std]
use my_app as _; // グローバルロガー + パニック時の振る舞い + メモリレイアウト
#[cortex_m_rt::entry]
fn main() -> ! {
defmt::info!("Hello, world!");
my_app::exit()
}
このプログラムを cargo run すると、おなじみの “Hello, world!” 出力が生成されます。
$ # `rb` は `run --bin` のエイリアスです
$ cargo rb hello
Finished dev [optimized + debuginfo] target(s) in 0.03s
flashing program ..
DONE
resetting device
0.000000 INFO Hello, world!
(..)
$ echo $?
0
または、代わりに VS code + Rust-Analyzer を使用している場合は、src/bin/hello.rs ファイルを開き、以前のブログ記事で実演したように “Run” ボタンをクリックできます。
詳細については、defmt bookを確認してください。