明けましておめでとうございます!
タイトルの通り。mruby/edge のVMを、mruby/c 1.2 相当の内容に書き換えた。
mruby/c 1.2 の実装は以前軽く読んだ。
PRはめちゃでかい。 +2,605 −1,376
だそうです。
合わせてcrateをいくつかリリースした。
mruby/edgeとmecのcrateを更新した。以下でmecを更新してください。なぜかもう rc3
ですが、ええじゃないですか。
$ cargo install mec --version=1.0.0-rc3 $ mec --version Version: 1.0.0-rc3
今RCでリリースしているバージョンでは、ちゃんとクラスを定義してオブジェクトを作ることが...できる! 以下のようなRubyスクリプトを用意して、
class MyMRubyClass def initialize(value) @value = value end def update(value) @value = value * 2 end def value @value end def print_self puts "Value: #{value}" end end def main obj = MyMRubyClass.new(123) obj.print_self obj.update(456) obj.print_self return obj.value end
以下のようにwasmバイナリにコンパイルしたら、
$ mec --fnname main examples/object.rb running: `cp /Users/udzura/ghq/github.com/udzura/mrubyedge/mec/examples/object.rb src/` running: `mrbc src/object.rb` running: `cargo build --target wasm32-wasip1 --release` running: `cp ./target/wasm32-wasip1/release/mywasm.wasm /Users/udzura/ghq/github.com/udzura/mrubyedge/mec/object.wasm` running: `cd .. && rm -rf work-mrubyedge-r6uYcPUZkjTYN17nL04bPff0dbfSrLP9` [ok] wasm file is generated: object.wasm
wasmtimeで実行できる。すごい! オブジェクト指向スクリプト言語 for WASMじゃん。
$ wasmtime --invoke main object.wasm Value: 123 Value: 912
実装した命令など
optable.rs
を見るとわかる。なんとなく半分超えぐらいか?
しかし、たとえば GETUPVAR とか、正しい実装なのかよくわからない。命令が出るRubyスクリプトを探しつつ地道にデバッグするしかない。mruby/c 1.2でサポートされているものを優先して実装しているが、mruby/c 1.2の時の命令(mruby 1系)ではなく現行のmruby 3系の命令に合わせているので、サポート済みの命令が完全に一致しているわけではない。
内部実装についてもう少し言及すると、去年の段階では雰囲気でやっていたのを、 mruby/c のC実装を参照しながらなるべく忠実? にRustに置き換えた*1。リポジトリにはmruby/cのライセンスファイルも同梱してある。
mruby/c 1.2 で何ができるかは、以下のQiita記事を読めば雰囲気が掴める。
そう、そもそも mruby/c 1.2 の時点ではブロックも、例外もサポートしていないのだ...。なので堂々と後回しに...。
とはいえ、それでもまだまだ標準ライブラリ、preludeを全然実装していないので、これから地道にやろうかな...。という感じ。だいぶやったな! ってなったらRCを外します。例外は去年kateiさんに何か言われたので早めに向き合っちゃおうかな...。
ちなみにVMを置き換えた結果、わずかに fib()
が速くなった*2 *3。書き換え時に、レジスタにHashMapを使うのをやめたりはしていたが、そういうのが効いたとかじゃないと思うが...まあ、遅くなってなくて良かった。
$ time wasmtime --invoke fib fib.wasm 30 warning: using `--invoke` with a function that takes arguments is experimental and may break in the future warning: using `--invoke` with a function that returns values is experimental and may break in the future 832040 wasmtime --invoke fib fib.wasm 30 2.49s user 0.01s system 99% cpu 2.504 total $ time wasmtime --invoke fib fib-1.0.0-rc2.wasm 30 warning: using `--invoke` with a function that takes arguments is experimental and may break in the future warning: using `--invoke` with a function that returns values is experimental and may break in the future 832040 wasmtime --invoke fib fib-1.0.0-rc2.wasm 30 1.99s user 0.01s system 99% cpu 2.007 total
ちゃんとしたチューニングは機能が揃ってからにしますが...。Rcとか大量利用してるしきっと何かありそう。
RubyKaigi 2024 の時の実装に比べて、Rubyっぽいコードがかなり動くようになっていると思うので、ぜひお試しください。ちなみにimport/exportの仕様は変えていない。