Scheme Compiler の勉強(14) - 自動テストの修正と gauche への移行

  • tests-driver.scm は、実害はないけど細かい問題がある。同じ手続きが2回定義されていたり。これもさっき気付いたが(http://practical-scheme.net/wiliki/schemexref.cgi?error)、 ChezScheme の error はメッセージの format を行う。仕様上はそうではなさそう。そして gauche は仕様どおりの手続き error に加え、format をおこなう errorf が用意されているが、これと ChezScheme の error とは微妙に引数が違う(今まで微妙にエラーメッセージが変だった・・)。素人の自分にはどの error の定義が「正しい」とも言いがたい。よし、もはや scheme の世界で処理系に依存しないプログラムなんてものは無理だ、と判断しよう。
  • 思いつき&慣れるため、tests-driver.scm を gauche っぽくしてみる。まず gauche.test を使う。それから gauche の file.util の file->string を使って、 get-string なる地味なファイルの中身を文字列にする手続きを削除。あと tests-1.3-req.scm の残りは not, char?, fxlognot だけ。
  • もうしばらくしたら gauche のプロファイラも使って、 LLVM IR (いままでアセンブラと書いていたが)の最適化をした場合としない場合で実行速度もデータにしよう。実行時間、コンパイル時間、最適化時間、最適化後の実行時間とか。
gosh> (load "./compiler")
#t
gosh> (test-all)
Testing compiler test ...                                        
<fxadd1>-----------------------------------------------------------------------
test 0, expects "1\n" ==> ok
test 1, expects "0\n" ==> ok
test 2, expects "2\n" ==> ok
test 3, expects "-99\n" ==> ok
test 4, expects "1001\n" ==> ok
test 5, expects "536870911\n" ==> ok
test 6, expects "-536870911\n" ==> ok
test 7, expects "2\n" ==> ok
test 8, expects "18\n" ==> ok
;; 中略
<boolean?>---------------------------------------------------------------------
test 59, expects "#t\n" ==> ok
test 60, expects "#t\n" ==> ok
test 61, expects "#f\n" ==> ok
test 62, expects "#f\n" ==> ok
test 63, expects "#f\n" ==> ok
test 64, expects "#f\n" ==> ok
test 65, expects "#f\n" ==> ok
test 66, expects "#t\n" ==> ok
test 67, expects "#t\n" ==> ok
passed.
#<undef>
gosh> 
  • http://llvm.org/docs/tutorial/ おお、 LLVMコンパイラを開発するためのチュートリアルらしきものがあった。ドキュメントは結構充実している。これで llvm-gcc -S -emit-llvmコンパイラ自身から情報を得ながら進めるやり方への依存が減るかも(割と気に入っているけど)。またもっとまともな LLVM IR が出力できるようになるに違いない。関数定義が出てきたときあたりにはきっと読むことになるだろう。
  • ちなみに schemescheme コンパイラを実装する良さは、あちこちで書かれているけど、最初から構文木が手に入るということ。これは重要だけど多分コンパイラの本質ではない部分(字句解析など)のステップをすっ飛ばして、面白いところだけをやれるということ。(Common Lispscheme を書くのもほとんど同じだと思うけど、 #f, #t とか微妙な違いはどうするんだろう。リーダーマクロをわざわざ定義するか、nil, t を替わりに使うものなのだろうか。)
  • 上記の LLVMコンパイラの例は、AST の定義だとかを地道にやっている?しかも IR をライブラリを使って堅実に構築?これ何をやっているか把握するの面倒じゃないのだろうか。