Skip to content

stage1 の出力を Wasm GC に完全移行する - #815

Merged
narumincho merged 1 commit into
mainfrom
wasm-gc
Oct 31, 2026
Merged

narumincho merged 1 commit into
mainfrom
wasm-gc

Conversation

@narumincho

@narumincho narumincho commented Oct 31, 2026 •

Copy link
Copy Markdown
Owner

Requested by ナルミンチョ · project thread

概要

definy のコンパイラ (core.compile-to-wasm) の出力を Wasm GC に完全移行しました。値は線形メモリのタグ付きの箱ではなく GC のヒープの struct / array になり、使わなくなった値はランタイムの GC が回収します。線形メモリは仕様上縮められず伸びっぱなしだったため、#814 で core 全体のコミットが Workers の上限 128MB に迫っていた問題を根本から解きます。

詳細は新しい docs/wasm-gc.md にまとめました。

変更

  • 値の型: core.wasm-type-* (value / bytes / values / number / boolean / string / list / closure / variant / float と、コンパイルした関数の型)。値はどれも (ref null value) で扱い、フィールド 0 のタグで分岐する
  • ランタイム関数: core.wasm-runtime-* を GC 版に書き直し (31 個)。ホストが値を作って読むための関数 (box_number, values_get, string_from_memory など) もエクスポートする。型セクション・関数の型・エクスポートもパーツにした
  • コンパイラ本体: リスト・レコード・バリアント・クロージャは要素を積んで array.new_fixed / struct.new。呼び出しは引数を名前の順に積む (core.compile-call-arguments-ranked)。文字列リテラルはグローバル変数にし、start 関数が passive data から array.new_data で作る
  • ホスト (src/stage1_compiler.ts): ポインタの代わりに不透明な参照 ValueRef を扱う。書いたオブジェクトの値は WeakMap で使い回す
  • 型チェッカーのインスタンスを 32 パーツごとに作り直す処理を削除
  • デプロイ先の worker.js (definy.cloudflare-workers-runtime-script) も GC 版にし、src/wasi_io.test.ts でアップロードする worker.js を Node.js で動かして確かめるようにした
  • wasm/stage1.wasm を再生成 (115KB → 67KB, 不動点を確認)

測定 (Node.js 26)

変更前 変更後
core 全体のコミットの SubmitEvent の RSS 207MB → 912MB 223MB → 247MB
同じく時間 4.5 秒 2.1 秒
seed 全 608 パーツを型チェッカー 1 インスタンスで検査 1 パーツ約 1.5MB ずつ増える (640MB) 0.43 秒, ヒープ +28MB (GC 後 +7MB)

テスト

  • npm test 582 件通過, npm run check:stage1 通過, npm run check / npm run lint 通過
  • E2E (npm run test:e2e) 41 件通過 (1 回目は同時に走らせた npm test が wasm を書き直して 2 件が落ちたので, その 2 件を単独で再実行して通過)

https://claude.ai/code/session_01DHYnFxNrErMzq3M2VvJN6M


Generated by Claude Code

値を線形メモリのタグ付きの箱ではなく Wasm GC の struct / array で表し,
使わなくなった値をランタイムの GC が回収するようにした (docs/wasm-gc.md)。

- ランタイム関数を GC 版に書き直し (31 個), 型・エクスポートもパーツにした
- 文字列リテラルはグローバル変数にし, start 関数が passive data から作る
- ホスト (src/stage1_compiler.ts) はエクスポートしたランタイム関数で値を作って読む
- 型チェッカーのインスタンスを 32 パーツごとに作り直すのをやめた
- デプロイ先の worker.js も GC 版にし, Node.js で動かすテストを足した
- stage1.wasm は 115KB から 67KB, core 全体のコミットの RSS 増加は約 700MB から約 24MB

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01DHYnFxNrErMzq3M2VvJN6M
@narumincho narumincho self-assigned this Oct 31, 2026
@narumincho
narumincho merged commit 65e9368 into main Oct 31, 2026
1 check passed
@narumincho
narumincho deleted the wasm-gc branch October 31, 2026 05:17
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants