Slide 1

Slide 1 text

FFI: RustとWebAssemblyと JavaScriptと @d0iasm

Slide 2

Slide 2 text

何をしてきた? ● インターンシップ @ Google ○ Chrome OS / Chrome browser ● Coreboot (オープンソースBIOS) 開発 @ GSoC 今は何してる? ● インターンシップ @ Wasmer (Rust 使用) ● RISC-Vエミュレータ開発 @ 趣味 (Rust 使用) ● 修論 @ 大学 (Rust 不使用) Doi Asami d0iasm

Slide 3

Slide 3 text

rvemu: RISC-V Emulator Web上で動くRustで書かれたRISC-Vエミュレータ ブログ: https://d0iasm.github.io/blog/risc-v/2019/12/19/fibonacci-numbers-on-my-riscv-emulator.html ● 現在RV64Gをサポート ● まだ実用レベルでは無い ● ほとんどの部分がRustで書 かれている

Slide 4

Slide 4 text

rvemu: RISC-V Emulator 仕組み ● バックエンドの仕組みは必要なく、ブラウザだけで動く ● メインのコード(CPUエミュレーション)がRustで書かれている ● ブラウザがサポートしている言語は JavaScriptのみ 疑問 ● Rustでフロントエンド開発するために、どうやって JavaScriptとやり取りする? Rust JavaScript Browser

Slide 5

Slide 5 text

RustをWebAssemblyにコンパイル Rust JavaScript Browser WebAssembly compile ● スタック形式のVMで動くバイ ナリ ● LLVMが生成形式のターゲッ トとしてサポート

Slide 6

Slide 6 text

RustをWebAssemblyにコンパイル Rust JavaScript Browser WebAssembly compile i32 | i64 | f32 | f64 の型しか サポートしていない OK: fn add(a: i32, b: i32) -> i32 NG: fn concat(a: &str, b: &str) -> String

Slide 7

Slide 7 text

wasm-bindgen (https://github.com/rustwasm/wasm-bindgen) ● RustとJS間のグルーコードを生成してくれるツール ● FFI (foreign function interface) の一種 ○ 異なるプログラミング言語間でやりとりをするための仕組み ● JSから呼び出したいRustの関数に #[wasm_bindgen] をつけると、文字列等の データのやりとりが可能になる wasm_bindgenによって生成される ファイル ● sample.js: グルーコード ● sample_bg.wasm: 関数本体 sample.rs $ wasm-pack build --target web

Slide 8

Slide 8 text

wasm-bindgen (https://github.com/rustwasm/wasm-bindgen) sample.rs index.js $ wasm-pack build --target web sample.js sample_bg.wasm

Slide 9

Slide 9 text

使い方はわかった。 で、 どういう仕組み? wasm-bindgenの実装と 生成されたコードを読んでみました

Slide 10

Slide 10 text

wasm-bindgenで文字列を扱う仕組み lib.rs hoge.js (プロジェクト名.js) 生成 生成されたJSコードから予想できること 1. Wasmが持つメモリ領域に対して mallocを し、文字列を保存する 2. 確保したメモリのポインタを ptr0とする 3. Rust関数の本体(wasm.bar)に対し、ポイン タ(ptr0)と変数の長さ(len0)を引数として渡 す。型はどちらもi32

Slide 11

Slide 11 text

wasm-bindgenで文字列を扱う仕組み src/lib.rs in rustwasm/wasm-bindgen JSコードからの予想通り、 Wasmが持つメモリ領域に対し てメモリ確保をしていることを確 認

Slide 12

Slide 12 text

wasm-bindgenで文字列を扱う仕組み Rust JavaScript WebAssembly fn bar(a: &str) fn bar(ptr: i32, len: i32) 変形&生成 f o o bar(“foo”); 1. メモリ確保 2. 文字列保存 3. ポインタと文字列の長さを 使ってWasmの関数を呼ぶ Linear Memory

Slide 13

Slide 13 text

まとめ ● RustとJS間をWebAssemblyを介することによってやりとり可能にする wasm-bindgenのツールについて紹介した ● wasm-bindgenがどのように文字列をやりとりしているのかを説明した ● 今回は触れなかったが、 web-sysという、DOMをRustから操作できるライブラリも 存在する FFIの技術を使用することで Rustでフロントエンド開発ができる!  ―― Rust is everywhere ありがとうございました @d0iasm 今回使用したコード : https://github.com/d0iasm/wasm-bindgen-sample

Slide 14

Slide 14 text

● Rust, WebAssembly, and Javascript Make Three: An FFI Story ○ https://youtu.be/nvLw_XKlZaU ● rustwasm/wasm-bindgen/examples/without-a-bundler ○ https://github.com/rustwasm/wasm-bindgen/tree/master/exampl es/without-a-bundler ● Design of wasm-bindgen ○ https://rustwasm.github.io/docs/wasm-bindgen/contributing/desi gn/index.html References