ライブラリ名前空間の実装 - Scheme VM を書く

やったことは

  • pass1 においてライブラリの参照を解決すること
  • pass2 はスルー
  • pass3 では import をきっかけに
    • ライブラリ body のコンパイル
    • ライブラリのロードを実行
  • VM で使用している define 用の hash-table を多段にすること。

これで

(library (higepon)
 (export hello)
 (import)
 (define hello "hello higepon\n"))

(import (higepon))
(display hello)

が動くようになった。これはまだ正しくなくて display を使うための import が必要。

テスト

一つ安定して動くようになった例が出来たのでテストを簡単にかける仕組みを用意。
一つのテスト後とにライブラリの名前空間をリセットする。そうでないと「このライブラリはすでに import 済みだ」と怒られてしまう。
あとはエラーを捕捉できるように。いままでサボっていたがこれでエラーケースもテストできる様に。

システムが提供するライブラリ

display は (rnrs io simple (6)) に提供されるので

(library (rnrs io simple (6))
         (export display)
         (import)
         (define (display x . port)
           (if (null? port)
               (sys-display x)
               (sys-display x (car port)))))

のようにラップして作った。

only の実装

only, rename, prefix の実装は似ているところがある。
ライブラリ内では参照できるのだけど、外部では違う名前で参照したり参照できなかったりするところ。
内部から参照できることからも分かる通り、識別子をそのままリネームしてしまうのは良くない。
コンパイル時に識別子のエイリアスが指定できれば良い。

hoge => hoge     ;; normal
hage => lib:hage ;; prefix lib or rename
huga => #f       ;; only or except

ついでに except, prefix, rename も実装できた。
バージョンは華麗にスルーしたい。