xv6 on VirtualBox
せっかくMacBook AirにVirtualBoxをインストールしたので、xv6をVirtualBoxで動かそうという話(わざわざそんなことをする人はいないだろうので、誰得なわけだが)。この日記を読んでいる人には説明の必要はないだろうけど、xv6はUNIX v6をx86に移植してOS講義の教材に使おうというMITのプロジェクト。講義を重ねることでバージョンは上がっていて、最新バージョンはrev4になっている。
xv6は仮想マシン上で動かすことを想定されていて、bochsやQEMUで動くように環境が整備されている。VirtualBoxで動かすには何も難しいことはなく、ディスクフォーマットをVDI形式に変換するだけでOK。
xv6のビルドにはELFを吐くツールチェイン(gcc、binutils、gdb)が必要である。Linuxなら問題ないだろうけど、Mac OS Xの場合は、xv6のページにあるツールチェインをインストールする必要がある。私はLinux上でビルドしてコピーしちゃったけど。
xv6のmakeに成功するとxv6.imgとfs.imgという二つのディスクイメージが生成される。xv6.imgがブートローダからカーネル、fs.imgがxv6のファイルシステムになる。
$ VBoxManage clonehd --format vdi xv6.img xv6.vdi $ VBoxManage clonehd --format vdi fs.img fs.vdi
そして、VirtualBoxを起動してVMを新規作成し、xv6.vdiをprimary master、fs.vdiをprimary slaveのIDEに設定する。これでOK。
xv6はVGA以外にシリアルにも出力しているので、ヘッドレスモード+シリアルコンソールできればうれしかったのだけど、現状出力が崩れてしまって使い物にならない(出力文字が欠けてしまう)。ちゃんと調べてないけどxv6のドライバを疑っている。まぁ、どこで何の役に立つかはわからないので、設定方法は残しておく。
VirtualBoxのシリアル設定には、host pipeとhost deviceの2種類のポートモードがあるが、後者はroot権限が必要なので前者を使う。このモードでは、ホストOSのUNIXドメインソケットを介してゲストOSのシリアルと通信できる。次のスクリーンショットのように設定した。
VirtualBoxのマニュアルには、UNIXドメインソケットの通信にsocatを使えとあるが、Mac OSには標準でインストールされていない。まぁ、xv6用に使うならncで十分だろう。VirtualBoxをヘッドレスモードで起動するコマンドはVBoxHeadlessである。次のようなスクリプトを書いてみた。Ctrl-dでncの接続を切ると、xv6 VMの電源を落とすようにしている。
#!/bin/sh name=xv6 com1=/tmp/serial port=10000 TERM=vt100 # start VM VBoxHeadless -s $name & # connect serial console while [ ! -e $com1 ]; do sleep 1 done nc -U $com1 #socat UNIX-CONNECT:$com1 TCP-LISTEN:$port & #telnet 127.0.0.1 $port # destroy VM VBoxManage controlvm $name poweroff