xv6をWindows環境(cygwin環境)で手軽にビルドする

cygwingcc(binutil)だと出力可能なバイナリーフォーマットが原因で、自作OSのビルドが出来ないケースが多々ある。

そこで、cygwinportsを利用しgccを導入することでこの問題を解決する。

ついでに今回はxv6をビルドしてみた。

cygwin & apt-cyg の導入までは色々解説があるので適当にお願いします。

クロス開発環境を導入する。

$ apt-cyg update -m ftp://ftp.cygwinports.org/pub/cygwinports
$ apt-cyg install linux-i686-gcc-core
(省略)
$ i686-pc-linux-gnu-gcc -v
組み込み spec を使用しています。
COLLECT_GCC=i686-pc-linux-gnu-gcc
COLLECT_LTO_WRAPPER=/usr/lib/gcc/i686-pc-linux-gnu/4.8.2/lto-wrapper.exe
ターゲット: i686-pc-linux-gnu
configure 設定: /usr/src/ports/linux-i686-gcc/linux-i686-gcc-4.8.2-1/src/gcc-4.8.2/configure --srcdir=/usr/src/ports/linux-i686-gcc/linux-i686-gcc-4.8.2-1/src/gcc-4.8.2 --prefix=/usr --exec-prefix=/usr --bindir=/usr/bin --sbindir=/usr/sbin --libexecdir=/usr/libexec --datadir=/usr/share --localstatedir=/var --sysconfdir=/etc --libdir=/usr/lib --datarootdir=/usr/share --docdir=/usr/share/doc/linux-i686-gcc --htmldir=/usr/share/doc/linux-i686-gcc/html -C --build=i686-pc-cygwin --host=i686-pc-cygwin --target=i686-pc-linux-gnu --without-libiconv-prefix --without-libintl-prefix --with-sysroot=/usr/i686-pc-linux-gnu/sys-root --with-build-sysroot=/usr/i686-pc-linux-gnu/sys-root --libexecdir=/usr/lib --enable-shared --enable-shared-libgcc --enable-static --enable-languages=c,c++,fortran,ada,java,go,lto,objc,obj-c++ --enable-version-specific-runtime-libs --disable-alsa --enable-libada --enable-libgomp --enable-libitm --enable-libjava --enable-libquadmath --enable-libquadmath-support --enable-libssp --enable-default-preferences-peer=file --disable-java-awt --disable-jni --with-arch=i686 --with-tune=generic --with-dwarf2 --with-ecj-jar=/usr/share/java/ecj.jar --with-gnu-as --with-gnu-ld --with-cloog-include=/usr/include/cloog-isl --with-system-zlib
スレッドモデル: posix
gcc バージョン 4.8.2 (GCC)

導入成功!

xv6のMakefileを書き換えビルドする。

xv6のソースを展開し、Makefileの"TOOLPREFIX"を"TOOLPREFIX = i686-pc-linux-gnu-"と設定。

後はmakeするだけで完成する

$ make
i686-pc-linux-gnu-gcc -fno-pic -static -fno-builtin -fno-strict-aliasing -Wall -MD -ggdb -m32 -Werror -fno-omit-frame-pointer -fno-stack-protector -fno-pic -O -nostdinc -I. -c bootmain.c
i686-pc-linux-gnu-gcc -fno-pic -static -fno-builtin -fno-strict-aliasing -Wall -MD -ggdb -m32 -Werror -fno-omit-frame-pointer -fno-stack-protector -fno-pic -nostdinc -I. -c bootasm.S
i686-pc-linux-gnu-ld -m    elf_i386 -N -e start -Ttext 0x7C00 -o bootblock.o bootasm.o bootmain.o
i686-pc-linux-gnu-objdump -S bootblock.o > bootblock.asm
i686-pc-linux-gnu-objcopy -S -O binary -j .text bootblock.o bootblock
./sign.pl bootblock
boot block is 447 bytes (max 510)
i686-pc-linux-gnu-gcc -fno-pic -static -fno-builtin -fno-strict-aliasing -Wall -MD -ggdb -m32 -Werror -fno-omit-frame-pointer -fno-stack-protector   -c -o bio.o bio.c
(省略)
i686-pc-linux-gnu-gcc -fno-pic -static -fno-builtin -fno-strict-aliasing -Wall -MD -ggdb -m32 -Werror -fno-omit-frame-pointer -fno-stack-protector   -c -o wc.o wc.c
i686-pc-linux-gnu-ld -m    elf_i386 -N -e main -Ttext 0 -o _wc wc.o ulib.o usys.o printf.o umalloc.o
i686-pc-linux-gnu-objdump -S _wc > wc.asm
i686-pc-linux-gnu-objdump -t _wc | sed '1,/SYMBOL TABLE/d; s/ .* / /; /^$/d' > wc.sym
i686-pc-linux-gnu-gcc -fno-pic -static -fno-builtin -fno-strict-aliasing -Wall -MD -ggdb -m32 -Werror -fno-omit-frame-pointer -fno-stack-protector   -c -o zombie.o zombie.c
i686-pc-linux-gnu-ld -m    elf_i386 -N -e main -Ttext 0 -o _zombie zombie.o ulib.o usys.o printf.o umalloc.o
i686-pc-linux-gnu-objdump -S _zombie > zombie.asm
i686-pc-linux-gnu-objdump -t _zombie | sed '1,/SYMBOL TABLE/d; s/ .* / /; /^$/d' > zombie.sym
./mkfs fs.img README _cat _echo _forktest _grep _init _kill _ln _ls _mkdir _rm _sh _stressfs _usertests _wc _zombie
used 29 (bit 1 ninode 26) free 29 log 10 total 1024
balloc: first 394 blocks have been allocated
balloc: write bitmap block at sector 28
dd if=/dev/zero of=xv6.img count=10000
10000+0 レコード入力
10000+0 レコード出力
5120000 バイト (5.1 MB) コピーされました、 0.271833 秒、 18.8 MB/秒
dd if=bootblock of=xv6.img conv=notrunc
1+0 レコード入力
1+0 レコード出力
512 バイト (512 B) コピーされました、 0.0163324 秒、 31.3 kB/秒
dd if=kernel of=xv6.img seek=1 conv=notrunc
248+1 レコード入力
248+1 レコード出力
126980 バイト (127 kB) コピーされました、 0.0212534 秒、 6.0 MB/秒

xv6.imgが無事に完成!ちゃんと起動する!