sub_sp 命令を廃止
VM命令 sub_sp
を廃止しました。
オペランドを負の値にすれば add_sp
で代用できるので。
これで VM のコードが5行減って、実装の量の面でも、仕様の面でも、またちょっとコンパクトになりました。
VM命令がいっぱいあると、入門者視点では「えー、こんなにいっぱい覚えないといけないの……」となりそうなので、少ない数で済ませられるならその方がいいかなと。
ちなみに sub_sp
を使っているのは変数宣言のときだけ。
--- a/vgcodegen.rb +++ b/vgcodegen.rb @@ -290,7 +290,7 @@ def gen_stmts(fn_arg_names, lvar_names, stmts) end def gen_var(fn_arg_names, lvar_names, stmt) - puts " sub_sp 1" + puts " add_sp -1" if stmt.size == 3 _, dest, expr = stmt
panic
たとえばコンパイラが完成するまでのこういう状態だったら、
# 例: vgcodegen.rb: _gen_expr_binary case operator when "+" then _gen_expr_add() else raise not_yet_impl("operator", operator) end
"not yet implemented" というメッセージも間違いではありませんでした。
まだ +
演算子しか実装していないが、これから *
や ==
などの場合の処理も実装していく予定である、という表明になっています(そのつもり)。
しかし、今は完成してだいぶ落ち着いている状況であり、 新たな演算子を追加する予定は今のところありません。
case operator when "+" then _gen_expr_add() when "*" then _gen_expr_mult() when "==" then _gen_expr_eq() when "!=" then _gen_expr_neq() else raise not_yet_impl("operator", operator) end
こうなってくると、 "not yet implemented" というメッセージと実装者(私)の意図とのずれが気になってきます。
というわけで、 not_yet_impl
を使っていた箇所は一律で panic
に置き換えました。
あわせて、パーサで使っていた ParseError
クラスをなくしました。
その他
rbenv local 2.7.6
sub_sp
をなくしたのでサイズはちょっと減りました。
$ wc -l vg*.rb common.rb 66 vgasm.rb 375 vgcodegen.rb 57 vglexer.rb 368 vgparser.rb 442 vgvm.rb 52 common.rb 1360 合計 # コメントを除いたサイズ: $ cat vg*.rb common.rb | grep -v '^ *#' | wc -l 1324