MIPS のコードを生成できるものとして、gcc 以外に pcc がある。pcc は、もともと UNIX で使われていたもので、gcc より起源が古い。だが、オープンソースでなかったので、 (gccを採用した) i386 unix や linux の台頭 とともに一度は消えた。
これが、オープンソースになり、ほとんど re-write されて復活したのは、わりと最近。 NetBSD とかもこれでビルドできるらしい。あと、rpm もあって、使ってみることは簡単にできる。
ほかに、オープンソースの まともなコンパイラとして、clang(+llvm) というのがある。詳しくは知らないが、BSD 系で採用されるかも知れないらしい。
なんで、こんなことを書いたかというと ... RHEL 6 のビルドの最初の障壁が gcc だから。どうにもうまくいかなくてうんざりしてきている。
もちろん、クロスはなんとかなるのだが ... qemu を使ってのセルフがどうにも ... 一回作った gcc で、もう一度 gcc をビルドするのだが ... qemu での実行になるので終わらない。rpm の作成ではエラーが出ると そこで終わりになるのだが、延々ビルドした後、internal error が出てしまう。原因はメモリの使いすぎのような気がする。
とにかく、gcc は遅かったり、メモリを使いすぎたりするので 困るのだ。そして 一番の障害が gcc 自身のビルド。その傾向がバージョンが上がるにつれて著しくなっている。
tcc (Tiny C Compiler)
最適化は、ない(か ほとんどない?) がコンパクトかつ超高速な コンパイラとして tccがある。
最初に紹介されたときは、Linux kernel がビルドできるという触れ込みだった。それだけではない。TCCBOOT というのがあって、なんと ブート時に カーネルをビルドして立ち上げる なんてことが出来た。(ただし、いまも出来るかどうかは知らない)。
これは、直接バイナリを出すので、アセンブラもリンカも必要ない。そして C のソースコードを スクリプトとして使える機能がある。最新版は、0.9.25 で、x86_64 にも対応している。あと arm にも対応しているのだが 残念ながら MIPS には対応していない。
コードを見ると arm-gen.c は 2000 行もない。MIPS に移植するのもそれほど困難ではないような気がする。
vcode: a portable, very fast dynamic code generation system
誰か tcc MIPS 版を作っていないか探したところ、見つからなかったかわりに、こんなのが見つかった。
ちょっとだけ見たのだが、MIPS のコード生成部は 1000 行に満たない。それだけ短いのだが、コメントも入っていて MIPS のコード生成部を作る参考になりそうな感じ。
ちょっと、tcc MIPS 版を作りたくなってきた。テストは、実機を使うまでもない。qemu の user モードで十分。
ちなみに、tcc も (ターゲットの) libc や libgcc を使う。これらは別途用意しておく必要がある。
lcc, A Retargetable Compiler for ANSI C
そう言えば lcc なんてのもあったのだった。これは、x86 と ALPHA , SPARC , MIPS に対応している。コード生成部を作る参考になるかもしれない。
tcc の調査
まず、tcc を作ったとして、android で動かせるものなのかどうか。
1) ライブラリ
tcc がリンクしているライブラリは、
libc.so , libm.so , libdl.so
これらのランタイムは、system/lib/ にある。
ビルド時に使用するのは、NDK の platforms/android-8/arch-mips/usr/lib (など)
これだけなら、大丈夫そうだ。
ただ、これしかリンクしていないということは... リンカの機能も独自に作っているということで、なかなか 面倒な話がある。
arm-gen.c 以外のもの を ARM_ で grep すると ...
libtcc.c , tccelf.c , elf.h , tcctok.h で見つかる。特に行数が多いのは、elf.h と tccelf.c
これらは、リロケーション情報を扱っていたりして、勝手に作れば良いというものではない。binutils と互換性があるように作らねばならないので、結構面倒そう。
追記: Android セルフ コンパイラ
C4droid (C/C++ compiler)
ふと、Android で動くコンパイラがあるかもと思って探してみたら あった。
もちろん ARM 用だろう。組み込みのコンパイラは tcc だが、gcc plugin なんてものもあるらしい。