MIPS SOCのメーカーからGPLのコードと一緒に提供されるtoolchainのバイナリはすべてLinux用なのでFreeBSDではそのままでは使えません。最近だと仮想マシンでLinux環境を用意する人が多いかもしれませんが、私は貧乏なので仮想マシンを借りる事ができません。
昔はgccやbinutilsをビルドする事を試していましたが、これ自体が大仕事になり、最近はFreeBSDのLinuxエミュレーションでLinux用のtoolchainを使っています。
以下のような物をFreeBSD/amd64上でビルドしています
- RedBoot
- u-boot
- 蟹さんのブート
- rtlbm-mruby
- bcmbm-mruby
ほとんどのtoolchainはi386(32bit)のgcc 4です。gcc 4は偉大で既存のコードをビルドしてもほとんどコンパイルエラーが出ません。
蟹さんはlexraでインストラクションがmipsと違うところがあるようなので、普通にgccをビルドしてもダメだと思います。また蟹さんのtoolchainはなんだかよく分からないコンフィグレーションになっています。
FreeBSDのpkgでmips用gcc 6をインストールしてみて、newlibをコンパイルしようとしたら、気が遠くなるほどエラーが出てあきらめました。
それぞれの開発環境はjailの下においているのですが、Linuxエミュレーションを使う場合は親のホストで以下を実行します。
% sudo kldload linux
いつも使うのであれば/etc/rc.confに以下を書いておくと良いです。
linux_enable="YES"
jailの中では以下を実行しておきます。
% sudo pkg install linux_base-c6
linux_base-c6はCentOS6相当でlinux_base-c7がCentOS7相当のようです。
これでgccなどが使える状態になります。
% file mipsel-linux-uclibc-gcc
mipsel-linux-uclibc-gcc: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV
), dynamically linked, interpreter /lib/ld-linux.so.2, for GNU/Linux 2.2.5, stri
pped
% ./mipsel-linux-uclibc-gcc -v
Using built-in specs.
Target: mipsel-linux-uclibc
Configured with: /home/gracecsm/toolchains/src/toolchains/linux-2.6/buildroot/to
olchain_build_mipsel/gcc-4.2.3/configure --prefix=/projects/hnd/tools/linux/hndt
ools-mipsel-linux-uclibc-4.2.3 --build=i386-pc-linux-gnu --host=i386-pc-linux-gn
u --target=mipsel-linux-uclibc --enable-languages=c,c++ --disable-__cxa_atexit -
-enable-target-optspace --with-gnu-ld --with-gmp=/home/gracecsm/toolchains/src/t
oolchains/linux-2.6/buildroot/toolchain_build_mipsel/gmp --with-mpfr=/home/grace
csm/toolchains/src/toolchains/linux-2.6/buildroot/toolchain_build_mipsel/mpfr --
enable-shared --disable-nls --enable-threads --disable-multilib --with-abi=32 --
with-tune=mips32
Thread model: posix
gcc version 4.2.3
toolchainのpathはそれぞれ違うので、.cshrcとかには書かずに個別にファイルに書いておいてsourceして設定しています。
スピードもネイティブとほとんど変わらない気がします。newlibはもともとすごく時間かかるんですが、コンパイラーのコンフィグレーションにもよっていて、蟹さんのツールチェインだとすごく時間かかるんですが、これはエミュレーションの問題ではないと思います。
toolchainを使ったビルドにはmakeコマンドを使うのですがifの書き方がGNU makeとBSD makeで違います。Linuxエミュレーションを使っていながらBSD makeに依存するのはちょっと変な気がしたので、両方で使えるように以下のようにしました。
# Default configuration is 'RTL8196C'
TARGET = RTL8196C
include $(TARGET).mk
RTL8196C.mkとRTL8196E.mkにそれぞれの設定を書いておいて、そのままビルドするとRTL8196CでビルドされますしRTL8196Eでビルドしたい場合は、以下のようにします。
% make TARGET=RTL8196E
まったく問題なく大変便利です。この話をある人にしたら「Linuxでいいじゃん」と言われてしまいましが、やっぱりBSDが好きなんですよね。
追記:
gdbを実行したところlibexpat.so.0が無いとエラーになります。いろいろ調べたところ、linuxのexpatのpkgがありました。
$ pkg install linux-c6-expat
ところがこれでインストールされるのはlibexpat.so.1でした。しかたなく/compat/linux/libでlibexpat.so.0のシンボリックリンクを作りました。