はじめに
AtomVM ではターゲットマシンに焼くアプリケーションのファイルが .avm という拡張子を伴うファイルです。これがどんなんか軽く調べました。
まずは軽い考察
いつもの Elixir や Nerves では Erlang Runtime System (ERTS) が解釈する .beam という拡張子のついた BEAM 中間ファイルが用いられます。AtomVM の処理系は ERTS そのものではないので全く別のファイルなのか、何らかの関連性を持ったファイルなのか気になってました。
まずここでヒントになるのは使ってオヤと思う点です。コンパイルにはいつもの Elixir 環境を用いて mix compile でコンパイルします。ここは AtomVM 独自ではないです。そして、その結果としてディレクトリの下には .beam ファイルができます。
そしてターゲットマシンにロードするファイルを作成するには mix atomvm.packbeam という追加の mix コマンドを用います。packbeam が示唆していますね。BEAM ファイルを固めてそうです。では本当にそうなのか追いかけます。
AVM形式のファイルを追いかける
以上の話から .avm 形式のファイルはいきなり個別のファイルにバラせるのではないかと思わせます。と思って試しても unzip とかではバラせません。
1行目を見てみると /usr/bin/env コマンドを起動しています。
head -n 1 Blinky.avm
#!/usr/bin/env AtomVM
この後は Elixir.Blinky.beam というのも見えますが基本バイナリファイルでよくわかりませんでした。これ、AtomVM のユーティリティとして中をみるコマンドがありました。
PackBEAM コマンドを作る
通常の開発環境で mix atomvm.packbeam する他に、おんなじ名前のUNIXコマンドがありました。その名も PackBEAM です。以下で作れます。
- 適当な作業ディレクトリを作る
-
git clone https://github.com/atomvm/AtomVM.gitでダウンロード- AtomVM というディレクトが出来てその下に展開される
- AtomVM 下の作業ディレクトリを作成する
mkdir AtomVM/build; cd AtomVM/build(ここでbuildはお好きな名前で) -
cmake ..でまるっとコンパイル-
tools/packbeamディレクトリが出来るのでcd tools/packbeamで移動
-
-
makeを実行するとその場にPackBEAMコマンドが爆誕する
PackBEAM コマンドを使う
PackBEAM か PackBEAM -h でヘルプです。
./PackBEAM
Missing avm file.
Usage: ./PackBEAM [-h] [-l] <avm-file> [<options>]
-h Print this help menu.
-i Include file and line information.
-l <input-avm-file> List the contents of an AVM file.
[-a] <output-avm-file> <input-beam-or-avm-file>+ Create an AVM file (archive if -a specified).
これを見ると、複数の .beam ファイルから .avm ファイルをつくるように見えます。そして -l で listing してくれるみたいなのでやってみます。前に はじめてね AtomVM(1) ESP32でLチカ で作った Blinky.avm を ~/tmp において見てみます。
% ./PackBEAM -l ~/tmp/Blinky.avm | wc -l
137
% ./PackBEAM -l ~/tmp/Blinky.avm | egrep -v beam
%
137行ですべての行に beam が含まれてます。最初と最後を見てみます。
% ./PackBEAM -l ~/tmp/Blinky.avm | head
Elixir.Blinky.beam *
Elixir.Mix.Tasks.Atomvm.Check.beam
Elixir.Mix.Tasks.Atomvm.Stm32.Flash.beam
Elixir.Mix.Tasks.Atomvm.Esp32.Info.beam
Elixir.Mix.Tasks.Atomvm.Packbeam.beam
Elixir.ExAtomVM.PackBEAM.beam
Elixir.Mix.Tasks.Atomvm.Esp32.Install.beam
Elixir.ExAtomVM.beam
Elixir.Mix.Tasks.Atomvm.Pico.Flash.beam
Elixir.Mix.Tasks.Atomvm.Esp32.Flash.beam
% ./PackBEAM -l ~/tmp/Blinky.avm | tail
Elixir.List.Chars.BitString.beam
Elixir.List.Chars.Float.beam
Elixir.List.Chars.Integer.beam
Elixir.List.Chars.List.beam
Elixir.String.Chars.beam
Elixir.String.Chars.Atom.beam
Elixir.String.Chars.BitString.beam
Elixir.String.Chars.Float.beam
Elixir.String.Chars.Integer.beam
Elixir.String.Chars.List.beam
先頭行にアプリケーションである Elixir.Blinky.beam があります。中を詳しく見てないですが * がある .beam ファイルに起動時に最初に実行される start/0 関数があるのではないかと思います。
% ./PackBEAM -l ~/tmp/Blinky.avm | egrep atomvm
atomvm.beam
% ./PackBEAM -l ~/tmp/Blinky.avm | egrep GPIO
Elixir.GPIO.beam
これまでコンパイルで苦しんだライブラリ atomvm も GPIO もちゃんと含まれているようです。
まとめ
PackBEAM コマンドによって、AVM ファイルにはコンパイルされたアプリケーションとライブラリの BEAM ファイルが詰め込まれているのがわかりました。
ただ他にどんな情報が入っているのかは調べてません。さらに BEAM 形式と言っても、AtomVMの実行できる範囲には制限があって完全に同一仕様の BEAM ははずはありません。何らかの制約が入った BEAM ファイルのはずです。そのあたり、今後、理解していきたいと思います。
公式ドキュメントがある!
とここまで書いてて packbeam に関する公式ページがあるのに気が付きました。Packbeam format に詳しく書いてありますね。先にこっちを見つけて入れてれば… というところです。
参考文献
-
AtomVM
- はじめてね AtomVM(0) 資源の乏しい計算環境でElixirを楽しむ
- AtomVM: Elixir で ESP32-S3 の LED を光らせる (2025年8月)
- AtomVM: how to run Elixir code on a 3 $ microcontroller 作者の Davide Bettio さんの2018年の記事
- ElixirでIoT#3.1:ESP32やSTM32でElixirが動く!AtomVMという選択肢 これも古いので初学者は新しいドキュメントを
- Piyopiyo.ex
- @kikuyuta の Elixir 関連ドキュメント集