対象読者:複数人でOS開発をやっているプロジェクト、環境が変わった時に毎回OS開発環境を構築し直すのが面倒な人

livaです。 OSの開発環境を作るのって、面倒ですよね。一度環境構築した方法が新しいパソコンで使えなかったり、特に共同開発になるとWindows,Mac,Linuxといろいろな環境に対応させなければならないので。

私が主導しているプロジェクトでは、Vagrantを使って、どんなPCでも「コマンド一つで」手軽にOS開発環境を構築できるようになっているので、今回はVagrantの導入方法について解説していきたいと思います。

Vagrant

そもそもVagrantって何だ、という人も多いかもしれません。 では、VirtualBoxならどうでしょう?これならご存知ですかね。

一応説明しておくと、VirtualBoxは、今お使いのOSの上で別のOSを立ち上げる事ができるソフトウェア(仮想マシン)です。OS開発を始めると、デバッグにqemuやBochsといったエミュレータを使う事になると思うのですが、VirtualBoxもこれらのエミュレータの仲間です。

仮にVirtualBoxの上でOS開発を行うようにすれば、あなたが使っているパソコンのOSがWindowsであろうと、Macであろうと、Linuxであろうと、そのVirtualBox上で動かしているOSさえ同じなら、同じ開発環境構築手法を使ってどんなパソコン上でもOS開発ができる、という事になります。しかも、これならうっかり手元のOSを壊してしまう心配もありません。便利そうですね。

とはいえ、VirtualBox上で開発するのは意外と不便です。自分の使ってるOSの上に新しくVirtualBoxのGUIが立ち上がって、その上でエディタを開いてOSを開発する、みたいな形になるのですが、実際に使ってみるとGUIが重かったりするなど、とにかく使いづらいのです。仮想マシンにsshサーバーを立てて、手元から繋いでCUI環境にするという方法もありますが、ssh環境の整備やポートを適切に設定しなければいけなかったりと中々面倒です。

そこで登場するのがVagrantです。VagrantはVirtualBoxのラッパーみたいな物で、ターミナルからvagrantコマンドを叩くと裏でVirtualBox仮想マシンを立ち上げ、そこにssh接続をしてくれます。 ssh絡みの面倒な部分も全てVagrantが面倒を見てくれるので、環境整備をする必要もありません。世の中便利になったものです。

Vagrantを使ってみる

まず、VirtualBoxとVagrantをインストールしましょう。どちらも公式サイトからインストールできます。

次に、Vagrantfileと呼ばれるファイルを作ります。ターミナルで以下のコマンドを実行してみてください。 (基本的に説明にはUNIX環境を用いますが、Windowsでも同様の方法でできるはずです)

$ vagrant init ubuntu14.04

これでVagrantfileが出来ます。(中身はただのテキストファイルです) コマンドから分かる通り、このVagrantfileはubuntu14.04ベースの仮想マシンを作ってくれます。指定の仕方を変えれば、CentOS等、好きなOSをインストールできます。もちろん、ubuntu14.04ベースの仮想マシンなので、OS開発の際はubuntuに用意されているツールは全て使う事ができます。

OS開発環境を自力でいろいろ整えたいと思うと、Linuxを使うのが一番簡単なので、特にこだわりが無ければ何も考えずにこのまま進むと良いでしょう。これ以降の解説もubuntu14.04で仮想マシンを作成したとして行います。

Vagrantfileが作成されたのを確認したら、以下のコマンドを実行してみてください。

$ vagrant up

このコマンドは、シャットダウンされている仮想マシンを立ち上げるための物です。仮に仮想マシンが存在しなければ、Vagrantfileを元に自動で仮想マシンを作成してくれます。(逆に言うと、vagrant upはVagrantfileのあるディレクトリでやってくださいね)

最初は仮想マシンイメージのダウンロード等があるので、少し時間が掛かるかと思います。

仮想マシンが立ち上がったら、ssh接続してみましょう。

$ vagrant ssh

ubuntuからのメッセージが表示されたら、成功です。

パソコンを再起動した時は、もう一度vagrant upを実行して、vagrant sshすればssh接続できます。既に仮想マシンが作成されているので、vagrant upで仮想マシンイメージをダウンロードしたりする事はないので安心してください。

余談ですが、Vagrantを使う上で以下のコマンドを覚えておくと良いでしょう。

$ vagrant halt // 仮想マシンのシャットダウン
$ vagrant reload // 仮想マシンの再起動

プロビジョニングレシピの作成

ubuntuが起動したらその上で開発環境を構築していく(必要なツールをインストールしたり)事になると思うのですが、その際に実行したコマンドをメモっておきましょう。

一通り開発環境構築が終了したとして、ここからは別のパソコンでも同様の環境構築を手作業で行わなくても良いようにする(Vagrantにやらせる)方法を説明します。

まずはホストOS(あなたのパソコンにインストールされているOS、仮想マシン上のOSではないですよ)のVagrantfileがあるディレクトリに、bootstrap.shというファイルを作成しましょう。これは名前の通りシェルスクリプトで、あなたが開発環境を構築した際に実行したコマンドをシェルスクリプト化したものです。つまり、シェルスクリプトにしておく事で、次に環境構築する際は、Vagrantが代わりに実行してくれるという事です。

基本的には実行したコマンドをそのまま羅列してシェルスクリプトにしてしまえば良いのですが、一つだけおまじないを。

このシェルスクリプトは、後でVagrantfileを編集する事で、初回のvagrant up時、及びvagrant provisionをした時に実行されるように設定します。ただ、vagrant provisionが実行される度に環境構築は何回も走って欲しくない(冪等性が担保されている場合は別)ので、初回のみ実行されるようにしてしまいましょう。

#!/bin/sh
test -f /etc/bootstrapped && exit

// ここに環境構築時に実行したコマンドを羅列する
sudo apt-get install -y gcc g++ make

date > /etc/bootstrapped

こうすれば、初回の仮想マシン作成時にのみ実行される環境構築シェルスクリプトになります。

次に、Vagrantfileに以下のような行を追加しましょう。場所としては、config.vm.box = “ubuntu14.04”等と書かれている所の直下が良いでしょう。

config.vm.provision :shell, :path => "bootstrap.sh", :privileged => true

後は、Vagrantfileとbootstrap.shをコピーして、そのマシンでvagrant upとすれば(もちろん、事前にVagrantとVirtualboxはインストールする事)、自動でOS開発環境が構築できます。

qemu

OS開発環境構築は終わったのですが、実は一つだけ問題があります。 仮想マシン上でqemuデバッグをする事があると思うのですが、その際、仮想マシンへのssh接続だと、qemuの画面(VGA出力)を表示できないのです。これではデバッグが捗らないので、我がプロジェクトで使用している方法を書いておきます。参考にしてみてください。

まず、Vagrantfile内にconfig.vm.networkに関する設定を追加しましょう。

config.vm.network "forwarded_port", guest: 5900, host: 15900

これは仮想マシンの5900ポートをホストOSの15900にマッピングするという設定です。 次に、QEMUの画面出力をvnc(デフォルトはポート番号5900)にして立ち上げます。 つまり、ネットワーク経由でqemu上で立ち上がってるOSを遠隔操作できるようにする事で、VirtualBoxの壁を超えるという事になります。

# qemu -hda $(IMAGE) -vnc 0.0.0.0:0,password

次にqemuのコンソールでvncのパスワードを設定します。

(qemu) set_password vnc hogehoge

最後に、ホストOSから15900ポートに対してvnc接続し(ホストOS上では適当なvncクライアントを使ってください)、パスワードに先ほど設定したhogehogeを入れると、qemuのVGA出力画面が表示されるはずです。

ただ、この方法だとqemuにvnc接続する際に毎回パスワードを求められてしまって面倒ですよね。vncを使わずにX11転送で接続することもできるらしいのですが、ごめんなさい、それについては検証していないので、次の章では全く別の方法を紹介させてください。

共有フォルダ

ソースコードの共有等でホストOSとゲストOSの間でファイルを共有したくなる事があります。Macでは(恐らくWindowsやLinuxでも)ホストOSのVagrantfileのあるフォルダがゲストOSの/vagrant以下と同期されているので、これを利用すればできます。(Hyper-Vを使う場合はよく分からないのですが、どうやら共有フォルダはサポートされてないようです。その場合、自前でsambaサーバーを建てたりしないといけないかもしれません。ここではホストOSとゲストOSの間でファイル共有ができたとして話を進めます)

共有フォルダはソースコード共有に使うだけでなく、作成したOSのディスクイメージを共有する事にも使えます。つまり、仮想マシン上でディスクイメージを作ったらそれをホストOSに引っ張ってきてホストOS上のqemuで起動すれば、vncの設定といった面倒な事をしなくてもOSのデバッグが行えます。

お疲れ様でした

Vagrantを使って簡単にOS開発環境を構築する方法を書いてみました。これでパソコンを買い換えても、プロジェクトメンバーが増えても安心ですね!

ちなみに、ここでは基本的な事しか説明していませんが、Vagrantを上手く活用すると、いろいろな事ができるはずです。皆さんいろいろ試してみて、自分好みの環境を作ってみてください。

実際に自分で環境を作ってみた!という方は、osdev-jpオープンコミュニティの方に専用のスペースを設けたので、是非そこに書いてください!