自作コンパイラ開発メモ(2020/12/13)

低レイヤを知りたい人のための C コンパイラ作成入門を読んでコンパイラ自作してる時の作業記録です。

対象箇所

for 文に対応するアセンブリを出力できるようにしました。

実装

  • 関数 foo が定義された c のプログラムを作成
  • 関数名を識別子としてトークナイズ
  • 関数としての node を生成できるようにした
  • 関数の node を消費してアセンブリで指定の関数(foo)を呼び出せるようにした
  • foo が定義されたプログラムを自分のコンパイラの出力とリンクできるようにした
  • 生成された実行ファイルで foo が実行されることを確認した

メモ

primary = num
        | ident ("(" ")")?
        | "(" expr ")"

ident が変数名なのか関数名なのかは直後の()の有無で判断する。

関数の node を消費してアセンブリで指定の関数(foo)を呼び出せるようにした

call foo

今回は擬似的に関数の呼び出しを確認するだけなので node を消費したときは引数なしのfoocallするようにした。

foo が定義されたプログラムを自分のコンパイラの出力とリンクできるようにした

./9cc "$input" > tmp.s
cc tmp.s foo.c -o tmp
./tmp

tmp という実行ファイルを作成している。

tmp.sは自分のコンパイラで出力したアセンブリfoo.cfoo()が定義されている c ファイルです。

ccの引数にこれらの二つのファイルを渡すことで互いにリンクさせることができる。