戻る

FreeBSD が起動するブータブル CD-ROM の作成

1 はじめに

FreeBSD が CD-ROM ブートで動けば... と思ったことは誰しもあるのでは ないでしょうか. このページでは,CD-Rを利用して,CD-ROM からブートする FreeBSD を作成する方法を 解説します.なお当然ですが,このページを読んで行ったことについて, ぼくは何の責任も持てませんので,各自の責任のもとで行ってください. とくにセキュリティに関しては,このページではもっとも甘々な設定で説明して あるので,実際に行うときは(とくにインターネットに接続されている環境で利用する 場合には),各自で十分に注意してください.

2 準備

CD-ROM ブートの FreeBSD (以降,CDBSDと呼びます) は,以下のようにして 作成します.
  1. PCに2台のハードディスクを搭載し,2つの FreeBSD をインストールする.
  2. 1番目の FreeBSD (以降,作業用 FreeBSD と呼びます)は,CD-R に焼く イメージを作成したり,実際に CD-R に焼いたりするなどの作業用に使用する.
  3. 2番目の FreeBSD (以降,イメージ用 FreeBSD と呼びます)は,CD-R に焼く イメージとして使用する.
  4. ブータブル CD-ROM を作成するので,ブートイメージを作成する必要がある. ブートイメージには FreeBSD の配布物に含まれる,2.88MB 用の boot.flp を 流用する.
  5. CD-ROM をルートディレクトリとしてマウントするので,そのままでは書き込みが できない.書き込みが必要なディレクトリ(/var, /tmp, /etc, /root など)は, MFS(Memory File System)でマウントしなおす.
  6. /etc の下のファイル(主に rc.conf)の設定を書き換えて CDBSD をブート したいときのために,CDBSD の起動時にはフロッピーディスクが挿入されているか どうかを調べ,挿入されている場合には,フロッピーディスク上の etc ディレクトリ 下のファイルを /etc に上書きコピーしてからブートするようにする.
  7. X の設定も行う.
  8. 本来はセキュリティには十分に注意する必要があるが,ここではセキュリティには 一切配慮しない.各自で十分に注意すること!
  9. なるべくいろいろな PC 上で利用できるような構成にする.
  10. なるべく簡単で楽な方法で CDBSD を作成する.(^^)
CD-ROM を作成するわけですから,当然 CD-R (なるべくなら CD-RW)ドライブが必要. ここでは ATAPI の CD-R/RW ドライブを使用し,mkisofs と /usr/sbin/burncd で CD-ROM を作成することにします. 表1のパーティション構成で CDBSD を作成することにします.

表1 CDBSD作成時のパーティション構成
HDDパーティションデバイス名内容
1台目1番目/dev/ad0s1Windows
1台目2番目/dev/ad0s2a作業用 FreeBSD の /
1台目2番目/dev/ad0s2e作業用 FreeBSD の /var
1台目2番目/dev/ad0s2f作業用 FreeBSD の /usr
1台目3番目/dev/ad0s3e作業用 FreeBSD の /home
2台目1番目/dev/ad1s1aイメージ用 FreeBSD の /
2台目1番目/dev/ad1s1eイメージ用 FreeBSD の /usr

3 作業用 FreeBSD のインストール

まずは,作業用 FreeBSD をインストールする必要があります.これは作業用に 使用するものですから,自分が使いやすいように,好きなようにインストール すればいいです. ただし,CD-R の焼き込みに /usr/sbin/burncd を使用するため,作業用 FreeBSD には FreeBSD-4.0 以上のバージョンが必要.あと mkisofs が必要.あとファイルイメージの 操作に vnode を利用するので,vn デバイスが使えるカーネルが必要.

4 イメージ用 FreeBSD のインストール

4.1 インストール

2台目のHDDの1番目のパーティションに,イメージ用 FreeBSD をインストール します.これも通常どおりインストールしてしまって構いません. 今回は FreeBSD-4.3 を使用します.

インストールが済んだら,イメージ用 FreeBSD を起動してください. 以降ではイメージ用 FreeBSD 側での設定を行います.

4.2 Xの設定

今回はなるべく多くのPC上で動作させたいので,SVGA用のXサーバを利用することに より,機種依存性を極力少なくしています.

XF86Setup を起動して,以下の設定を行います.

  • moused を使用するので,マウスのプロトコルは SysMouse を指定し, デバイスは /dev/sysmouse を指定する.また,2ボタンマウス用に, Emulate3Buttons を指定しておく.
  • キーボードは日本語106を指定する.
  • ビデオカードの選択では,なにも選択せずに Detailed Setup に入り,Server に SVGA,Video RAM は Probed を選択する.
  • Monitor に適切なものを指定する. ぼく は High Frequency SVGA 1024x768 もしくは SVGA 800x600 あたりを指定しています.
  • Modeselection に適切なものを指定する. ぼく は,640x480, 800x600, 1024x768 で 16bpp を指定しています.
設定後に startx をして,ちゃんとXサーバが起動できるかどうかを確認します.

ここで,CDBSD の起動後に,X サーバを自由に選択できるようにしたいので, 以下のようにリンクを張りなおしておきます.

root# rm /usr/X11R6/bin/X
root# ln -s ../../../etc/X /usr/X11R6/bin/X
root# ln -s ../usr/X11R6/bin/XF86_SVGA /etc/X
リンクは,CDBSD の CD-ROM を /cdrom にマウントして中身を見るときのために, すべて相対リンクにします.

4.3 /etc の修正

さらに,/etc 以下の設定ファイルを適切に修正します.

まずは vipw でパスワードを修正します.

root# vipw
で vipw を起動し,root の行を,
root::0:0::0:0:Charlie &:/root:/bin/csh
のように,2カラム目を空欄に修正することにより,パスワード無しに設定します. guestの行も同様にパスワード無しに修正します.
guest::1001:1001::0:0:Guest User:/home/guest:/bin/tcsh
繰り返しますが,セキュリティには各自で十分に注意してください.CDBSD は HDD 上の Windows のパーティションをマウントして操作することができるため,root の パスワードが無い場合には,誰でも Windows 領域にアクセスできることになって しまいます.もしもパスワードを設定したいならば,passwd コマンドで設定して おいてください.

さらに,/etc 以下のファイル(主に /etc/rc.conf など)を適切に修正します. これが CDBSD 起動時のデフォルトの設定になります.ただし /etc/fstab は 後で修正するので,ここで CDBSD 用の修正をする必要はありません. (/etc/fstab をへんに修正すると,イメージ用 FreeBSD が起動できなくなって しまいますので...)

4.4 dot ファイルの作成

/root と /home/guest に置く dot ファイルを,必要なものは作成し, 修正したいものは修正します. さらに,CDBSD の説明として /README を書き,
root# ln -s ../README /root/README
root# su guest
guest> cd /home/guest
guest> ln -s ../../README /home/guest/README
のようなリンクを張っておくといいでしょう. /root と /home は CDBSD の起動時に MFS でマウントされるので, あまり巨大なファイルを置いたり,たくさんのファイルを置いたりしないように 注意してください.

4.5 /usr/tmp の修正とリンクの張りかえ

/usr/tmp はアプリケーションから利用されることはあまり無いので書き込み不可でも 支障はありませんが,一応,
root# rmdir /usr/tmp
root# ln -s ../tmp /usr/tmp
のようにして,/tmp へのリンクにしておきます./var/tmp は rc.diskless2 に よって MFS 上に作成されるので,リンクにする必要はありません.また,CDBSD の CD-ROM を /cdrom などにマウントして中身を見るときのために,
root# cd /
root# rm /compat
root# ln -s usr/compat /compat
のようにして,絶対リンクを相対リンクに張りかえておくといいでしょう.

4.6 マウントポイントの作成

CDBSD では / に書き込みができないため,起動後に /mnt2 などのマウントポイントを 作成することができませんので,あらかじめ
root# mkdir /fd /mnt2 /mnt3 /mnt4 /work /work2
root# mkdir /windows95 /windowsnt
root# chmod 777 /windows95 /windowsnt
のようにして,マウントポイントを多めに作成しておきます. /windows95, /windowsnt は HDD 上の Windows パーティションのマウント用の ためのものなので,属性を書き込み可にしておきます.

4.7 カーネルの作成

CDBSD のカーネルを作成します.とはいってもなるべく多くの種類の PC で 起動させるには GENERIC カーネルを用いるのが一番なので, /usr/src/sys/i386/conf/GENERIC に以下の設定を必要に応じて追加して, カーネルを作成し,make install します.
  • ident を GENERIC → CDBSD に変更.
  • maxusers を 32 → 128 に増加
  • pseudo-device tun を pseudo-device tun 4 に増加
  • pseudo-device bpf を pseudo-device bpf 4 に増加
  • options USER_LDT を追加.
  • options NTFS を追加.
  • options EXT2FS を追加.(Linux インストールマシンで動作させるときに, Linux パーティションを読み書きしたいので)
  • 音が出ないと寂しいので,
    device		pcm0 at isa? irq 5 drq 1 flags 0x0
    device		pca0 at isa? port IO_TIMER1
    
    を追加.

4.8 スペシャルファイルの作成

新しいカーネルで起動し,/dev で
root# ./MAKEDEV snd0
root# ./MAKEDEV ad0s1 ad0s2 ad0s3 ad0s4 ad1s1 ad1s2 ad1s3 ad1s4
root# ./MAKEDEV ad0s1a ad0s2a ad0s3a ad0s4a ad1s1a ad1s2a ad1s3a ad1s4a
などをして,必要なデバイスを作成しておきます.

4.9 mkfsrw.sh の作成

基本的には CDBSD では CD-ROM 上にあるファイルを自由に編集することはできません. これでは /usr/local/etc の下などをちょっと修正してデーモンを起動しなおしたい ときなどに不便です.そこで,指定したディレクトリを MFS でマウントしなおす ようなシェルスクリプト mkrwfs.sh (リスト1)を作成し, /usr/local/sbin に置きます.
リスト1 mkrwfs.sh

#!/bin/sh

# mkrwfs.sh is a script to change read-only file system directory to
# writable directory by MFS (Memory File System). Files and directories
# in the old directory are saved.
#
# usage:
# mkrwfs.sh [directory]
#
# You can specify the directory absolutely or relatively.

dir=$1

case $dir in
/*)
    # dir is absolute directory.
    absodir=$dir
    ;;
*)
    # dir is relative directory.
    absodir=`/bin/pwd`/$dir
    ;;
esac

if [ -d $dir ]; then
    # Backup files and directories in old directory.
    /usr/bin/tar czPf /tmp/mkrwfs.tmp.tgz $dir

    /sbin/mount_mfs -s 4096 -T qp120at dummy $absodir
    /bin/chmod 755 $dir

    # Restore the files and directories.
    /usr/bin/tar xzPf /tmp/mkrwfs.tmp.tgz
    rm -f /tmp/mkrwfs.tmp.tgz
else
    echo "$absodir: cannot mount to MFS. (not found)"
fi
mkrwfs.sh は,CDBSD の起動後に,
root# mkrwfs.sh /usr/local/etc
のようにして使用します.指定したディレクトリを MFS でマウントしなおし, 既存のファイルやディレクトリをコピーします.ディレクトリは絶対パスでも 相対パスでも指定できます.

4.10 パッケージのインストール

CDBSD で使用したいパッケージをインストールしておく必要があります. カーネルの構築などに HDD の空きを必要とするので,パッケージのインストールは 最後に行うようにします.

5 イメージの作成

作業用 FreeBSD で各種の設定をした後に,実際に CD-R に焼いて CDBSD を 作成します.まず作業用 FreeBSD を起動し,
root# mkdir /cdbsd
root# mount /dev/ad1s1a /cdbsd
root# mount /dev/ad1s1e /cdbsd/usr
のようにして,イメージ用 FreeBSD のパーティションを /cdbsd にマウント してください.

5.1 ブート用のイメージの作成

CD-ROMからブートさせるためには,ブート用のFDイメージを作成する必要があります. ブート用のFDイメージには,2.88MBのものも使えますので,FreeBSD の配布物に 含まれている 2.88MB の boot.flp を流用してブート用のFDイメージを作成します. kern.flp と mfsroot.flp を使用しない理由は,これらのFDはまず kern.flp で起動して,起動後に mfsroot.flp に差し替えてというように 2段階の構成になっているため流用しにくいのと,サイズの上限が1.44MBのために カーネルのサイズが制限されてしまうという理由からです.

FreeBSD では vnconfig の機能を使用して,イメージファイルをマウントすることが できます.(Linux の loopback filesystem に相当するものです)

root# mkdir /fd
root# vnconfig -c vn0 boot.flp
root# mount /dev/vn0c /fd
これで,boot.flp を /fd にマウントし,読み書きできるようになります.
root# cd /fd
root# ls
boot kernel.gz
root# 
まず,ブート時に CD-ROM がマウントされるよう,
root# mkdir /fd/etc
root# cd /fd/etc
root# vi fstab
のようにして,/fd/etc/fstab をリスト2のように作成します. 起動時には,ブートしたディスクの /etc/fstab が読まれる (参考文献[3]p.29参照)ので,boot.flp 中に /etc/fstab を 作成して,/dev/acd0c を / にマウントするようにします.
リスト2 ブート用FDの /etc/fstab の例

/dev/acd0c		/		cd9660	ro		0	0

さらに,イメージ用 FreeBSD のカーネルを boot.flp 上にコピーします.

root# cp /cdbsd/kernel /tmp
root# cd /tmp
root# gzip -9 kernel
root# mv kernel.gz /fd
作業が終了したら,アンマウントします.
root# cd /
root# umount /fd
root# vnconfig -u vn0
これで CD-ROM からブートするための 2.88MB の FD イメージを作成することが できました.ところで実は,ここで行っているのは,CD-ROM 上に置く FD の ブートイメージを修正して,FD 上の fstab を参照して CD-ROM をマウントし, FD 上のカーネルで起動するようにしているだけです.したがって,CD-ROM 上の カーネルを読み込んでブートするわけではないため,本当の意味での CD-ROM ブートと は言えないかもしれません. 本当は CD-ROM 上の /kernel を読み込んでブートするようにしたいと思い, boot.flp 上の /boot.config, /boot/loader.rc, /boot/loader.conf などを いろいろ編集したり,/boot/loader のかわりに /boot/cdboot を利用したり などして指向錯誤したのですが,うまくいきませんでした.現在,これを実現する 方法を見つけようと思い,boot2 や loader などのソース (/usr/src/sys/boot/i386 以下にあります)を読んだりしていますので, うまく実現する方法が見つかりましたら,また報告しようと思っています.

5.2 /etc/rc.cdrom の作成

/tmp を MFS でマウントして書き込み可にするなどの,CDBSD特有の処理を するために,/etc/rc.cdrom を作成します.

FreeBSD では,ネットワークブートによるディスクレスマシンを作成する場合の ために,/etc/rc.diskless1, /etc/rc.diskless2 というスクリプトがあります. 今回は CD-ROM からのブートですから /etc/rc.diskless1 は不要です. /etc/rc.diskless2 の処理はそのまま流用できるので,/etc/rc.diskless2 を 利用して /var や /dev を作成することにします.

CDBSD のブート時には,以下の作業が必要になります.

  • /tmp を MFS で作成する.
  • /etc を MFS で作成し,既存の /etc のファイル・ディレクトリをコピーする.
  • /root を MFS で作成し,既存の /root のファイル・ディレクトリをコピーする.
  • /home を MFS で作成し,既存の /home のファイル・ディレクトリをコピーする.
  • FDが挿入されているかどうかを調べ,挿入されている場合には, FD上の /etc ディレクトリ下のファイルを /etc に上書きコピーする.
これらの作業を /etc/rc.cdrom (リスト3) にまとめ,起動時に 自動で行われるようにします. /etc/rc.cdrom では,FD のチェック時に,msdos ファイルシステム,ufs を順次 チェックしますので,FD はどちらのファイルシステムになっていても構いません.
リスト3 /etc/rc.cdrom

# chkerr:
#
# Routine to check for error
#
#       checks error code and drops into shell on failure.
#       if shell exits, terminates script as well as /etc/rc.
#
chkerr() {
	case $1 in
	0)
		;;
	*)
		echo "$2 failed: dropping into /bin/sh"
		/bin/sh
		# RESUME
		;;
	esac
}

# Create an MFS /tmp to temporarily hold files from /etc until we
# can bootstrap /etc as an MFS.

/sbin/mount_mfs -s 4096 -T qp120at dummy /tmp
chkerr $? "MFS mount on /tmp"
/bin/cp -Rp /etc /tmp
chkerr $? "cp /etc to /tmp/etc MFS"

/sbin/mount_mfs -s 4096 -T qp120at dummy /etc
chkerr $? "MFS mount on /etc"
/bin/chmod 755 /etc

/bin/cp -Rp /tmp/etc /
chkerr $? "cp /tmp/etc to /etc MFS"

rm -rf /tmp/etc

# Create an MFS /root

if [ -d /root ]; then
	/bin/cp -Rp /root /tmp
	chkerr $? "cp /root to /tmp/root MFS"

	/sbin/mount_mfs -s 4096 -T qp120at dummy /root
	chkerr $? "MFS mount on /root"
	/bin/chmod 755 /root

	/bin/cp -Rp /tmp/root /
	chkerr $? "cp /tmp/root to /root MFS"

	rm -rf /tmp/root
fi

# Create an MFS /home

if [ -d /home ]; then
	/bin/cp -Rp /home /tmp
	chkerr $? "cp /home to /tmp/home MFS"

	/sbin/mount_mfs -s 4096 -T qp120at dummy /home
	chkerr $? "MFS mount on /home"
	/bin/chmod 755 /home

	/bin/cp -Rp /tmp/home /
	chkerr $? "cp /tmp/home to /home MFS"

	rm -rf /tmp/home
fi

#/sbin/umount /tmp

# check FD inserted
dd if=/dev/fd0a of=/dev/null count=1 > /dev/null 2>&1
case $? in
0)
	echo "FD inserted. Now trying to mount FD."
	if /sbin/mount -t msdos /dev/fd0a /mnt > /dev/null 2>&1 ; then
		echo "FD mounted as msdosfs"
		if [ -d /mnt/etc ] ; then
			echo "Found /etc on FD. Now copying FD to /etc"
			/bin/cp -Rp /mnt/etc /
			chkerr $? "cp /etc on FD to /etc MFS"
		else
			echo "Not found /etc on FD"
		fi
		/sbin/umount /mnt
		chkerr $? "Unmounted FD"
	elif /sbin/mount -t ufs /dev/fd0a /mnt > /dev/null 2>&1 ; then
		echo "FD mounted as ufs"
		if [ -d /mnt/etc ] ; then
			echo "Found /etc on FD. Now copying FD to /etc"
			/bin/cp -Rp /mnt/etc /
			chkerr $? "cp /etc on FD to /etc MFS"
		else
			echo "Not found /etc on FD"
		fi
		/sbin/umount /mnt
		chkerr $? "Unmounted FD"
	elif /usr/bin/gzip -cd /dev/fd0a > /tmp/fd_etc.tar 2> /dev/null ; then
		if /usr/bin/tar xf /tmp/fd_etc.tar -C /etc > /dev/null 2>&1 ; then
			echo "/etc extracted from FD as tar+gzip archive"
		else
			echo "FD not tar+gzip format"
		fi
		rm -f /tmp/fd_etc.tar
	elif /usr/bin/tar xf /dev/fd0a -C /etc > /dev/null 2>&1 ; then
		echo "/etc extracted from FD as tar archive"
	else
		echo "Unknown format FD"
	fi
	;;
*)
	echo "No FD inserted"
	;;
esac

# /var, /dev mount by MFS.
diskless_mount="/etc/rc.diskless2"

実は リスト3 には,tar と tar+gzip によるアーカイブも 展開できるような処理が入っているのですが,あまりうまく動作しませんでした. 興味のあるかたは試してみてください.

なお, ぼく ははじめのうち,FD を union file system で / にマウントするとか, FDを union file system で /fd あたりにマウントし,/etc -> /fd/etc のようなリンクを張るなど考えましたが,どちらもうまく起動できませんでした (/etc をリンクにすることはできなかった). また,MFS は /md にマウントして,/tmp は /tmp -> /md/tmp のようなリンクにして, ホームディレクトリとかは /md/home に置くようにしたかったが,これも うまく起動できませんでした. (/tmp をリンクにしたら,ifconfig 実行時に OS がフリーズした)

5.3 /etc/rc の修正

/etc/rc.cdrom が /etc/rc から呼ばれるように,/etc/rc に (リスト4)の修正を加えます.rc から呼ばれるスクリプトが /tmp を使うような場合が考えられるので,/tmp の作成は早い段階で行う必要が あります.このため,/etc/rc の先頭付近で /etc/rc.cdrom を呼び出すようにします.
リスト4 /etc/rc の修正(rc.patch)

--- rc~	Wed May 30 06:10:20 2001
+++ rc	Wed May 30 06:10:24 2001
@@ -52,6 +52,12 @@
 PATH=/sbin:/bin:/usr/sbin:/usr/bin:/usr/local/sbin
 export HOME PATH
 
+# for CD-ROM boot.
+#
+if [ -r /etc/rc.cdrom ]; then
+	. /etc/rc.cdrom
+fi
+
 # BOOTP diskless boot.  We have to run the rc file early in order to
 # retarget various config files.
 # See /usr/share/examples/diskless/clone_root for details on how
オリジナルの /etc/rc はイメージ用 FreeBSD の起動に必要なので,消さないように してください.(後述の /etc/fstab も同様)
root# cd /cdbsd/etc
root# mv rc rc.org
root# cp rc.org rc
root# patch < rc.patch
root# mv rc.org rc.orig
root# mv rc rc.cdbsd

また,CDBSD の起動時の /var の作成は /cdbsd/etc/rc.diskless2 で行われるの ですが, 標準では /var/log や /var/at が作成されません.そこで /cdbsd/etc/rc.diskless2 の以下の行を修正し,/var/log と /var/at が 作成されるようにします.

var_dirs="run dev db msgs tmp spool spool/mqueue spool/lpd spool/output \
        spool/output/lpd"
を,
var_dirs="run dev db msgs tmp log at at/jobs at/spool spool spool/mqueue spool/lpd spool/output \
        spool/output/lpd"
に修正.(var_dirs に log, at, at/jobs, at/spool を追加)

5.4 /etc/fstabの修正

/cdbsd/etc/fstab を /cdbsd/etc/fstab.orig にコピーし, /cdbsd/etc/fstab.cdbsd を作成します.(リスト5)
リスト5 fstab.cdbsd

# Device		Mountpoint	FStype	Options		Dump	Pass#
#/dev/ad1s1b		none		swap	sw		0	0
#/dev/ad1s1a		/		ufs	rw		1	1
#/dev/ad1s1e		/usr		ufs	rw		2	2
#/dev/ad0s2a		/fbsd4		ufs	rw		0	0
#/dev/ad0s2e		/fbsd4/var	ufs	rw		0	0
#/dev/ad0s2f		/fbsd4/usr	ufs	rw		0	0
#/dev/ad0s3e		/fbsd4/home	ufs	rw		0	0
#/dev/acd0c		/cdrom		cd9660	ro,noauto	0	0
/dev/acd0c		/		cd9660	ro		0	0
/dev/fd0a		/fd		msdos	rw,noauto	0	0
/dev/ad0s1		/windows95	msdos	rw,noauto	0	0
/dev/ad0s1		/windowsnt	ntfs	rw,noauto	0	0
proc			/proc		procfs	rw		0	0
fstab.cdbsd では SWAP を無効にし,FD や Windows のマウント用のエントリを 追加しています.これらは noauto オプションをつけてあるので,CDBSD の 起動時に勝手にマウントされることはありません.

6 CD-R への焼き込み

これで,イメージ用 FreeBSD のすべての準備ができました.いよいよ CD-R に 焼きつけて,CDBSD を作成します.

6.1 ISO9660イメージの作成

イメージ用 FreeBSD のディレクトリ構成を ISO9660 イメージにして, CD-R に焼き込むためのイメージを作成します.作業用 FreeBSD 上で, リスト6のようなシェルスクリプトを使用して,イメージを 作成してください.
リスト6 CDBSDのイメージ作成用シェルスクリプト(mkimg.sh)

#!/bin/sh

cp /cdbsd/etc/fstab.cdbsd /cdbsd/etc/fstab
cp /cdbsd/etc/rc.cdbsd /cdbsd/etc/rc
rm -fR /cdbsd/tmp/.[A-z]* /cdbsd/tmp/*
rm -fR /cdbsd/var/tmp/.[A-z]* /cdbsd/var/tmp/*
rm -fR /cdbsd/usr/tmp/.[A-z]* /cdbsd/usr/tmp/*
echo -n "" > /cdbsd/root/.history
echo -n "" > /cdbsd/usr/home/guest/.history

mkisofs -A "CDBSD" -R -J -b boot.flp -c boot.catalog -o /usr/tmp/cdbsd.img /cdbsd

cp /cdbsd/etc/fstab.orig /cdbsd/etc/fstab
cp /cdbsd/etc/rc.orig /cdbsd/etc/rc
mkisofs が /cdrom/etc/master.passwd などを参照する必要があるため,mkimg.sh は root 権限で実行する必要があります.

ISO9660 ファイルシステムを作成したら,まずは ls -l cdbsd.img をして, ファイルサイズが 333000 セクタ × 2048バイト = 681984000 バイト (650MB のメディアの場合)を超えていないことを確認してください.

作成したイメージをマウントして,正しいイメージが作成しているかどうかを 確認します.ブート用の FD のイメージを作成したときと同様に,vnconfig を 利用します.

root# vnconfig -c vn0 /usr/tmp/cdbsd.img 
root# mount_cd9660 /dev/vn0c /cdrom
root# ls /cdrom
確認できたら,アンマウントします.
root# cd /
root# umount /cdrom
root# vnconfig -u vn0

6.2 イメージの焼き込み

実際に CDBSD を CD-R に焼き込みます.

今回は ATAPI の CD-R/RW ドライブを使用しているので,焼き付けには /usr/sbin/burncd を使用します.CD-RW の場合には,はじめに

root# burncd blank
で,メディアをクリアします.ドライブを指定したい場合には,-f オプションを 使用します.
root# burncd -f /dev/acd0c blank
では,いよいよ CDBSD のイメージを焼き込みます.
root# burncd -s 4 data /usr/tmp/cdbsd.img fixate
-s オプションで焼き込みの速度を指定できるので,ドライブとメディアにあった 適切な速度を指定してください.また,最後の fixate は必ずつけてください. これがないと正常な CD-ROM を作成できません.

7 起動

さて,いよいよ CDBSD のブートです.適当な PC を CD-ROM からブートするように BIOS 設定を変更して,CDBSD の CD-ROM を入れてブートします. ログインプロンプトまで無事にたどり着けたでしょうか? ブート中は CD-ROM から各種ファイルが読まれるため,CD-ROM ドライブの ヘッドが頻繁に動きます.あまり頻繁に CDBSD を使用していると,CD-ROM ドライブの寿命を縮めることになるかもしれません.

/etc/rc.conf などを修正してブートしたいときには,Windows でフォーマットした FD を用意して,FD 上に etc というディレクトリを作成し,そこに差し替えたい rc.conf を置くようにします.CDBSD の起動時に FD を挿入しておけば, FD 上の rc.conf を /etc に上書きコピーして起動します.

最後に,CDBSD を終了させたいときは,

root# umount -a
で /windows95 や /fd をアンマウントした後に,
root# shutdown -p now
もしくは
root# reboot
で,終了できます.Windows 領域を忘れずにアンマウントするようにしましょう.

8 おわりに

CD-ROM ブートの FreeBSD を作成する方法を説明しましたが,いかがだった でしょうか.いろいろなパッケージ構成の CDBSD を作成して,常にリュックに入れて 持ち歩いていれば,いざというときにはいつでも FreeBSD を使うことができるという 安心感があります.(自己満足ですが...(^^;))

コラム - md の利用

今回のような書き込みのできないメディアからブートさせたい場合には, 記憶メディア上でなく,カーネルの内部にあらかじめ内容を持ったディレクトリを 保持させておくと便利なことがあります.そのような場合には,md (Memory Disk) ドライバが利用できます.

md は FreeBSD-4.0 から追加されました.ソースコード自体は FreeBSD-4.3 まで ほとんど変更されていません.仕組みは NetBSD の md ドライバとほとんど同じで, md の定義を行うとカーネル内に

static u_char mfs_root[MD_ROOT_SIZE*1024] = "MFS Filesystem goes here";
のようにして,静的な配列として記憶領域が確保されます (/usr/src/sys/dev/md/md.c 参照). カーネルの作成時に,必要なディレクトリやファイルを ufs のイメージにして, あらかじめ配列 mfs_root[] に格納しておくことにより,カーネルの起動直後に
# mount /dev/md0c /mnt
のようにして,配列 mfs_root[] 上の ufs のイメージをマウントして読み書き できるようになります.

md の便利な点は,必要なファイルやディレクトリをあらかじめ書き込んでおく ことができるということです.この点は,プロセスとして実装されている MFS と大きく異なっています.(mount_mfs は newfs と同一の実体として 実装されている.詳しくは参考文献[4]参照)

通常のプログラミング方法からいえば,配列 mfs_root[] へのイメージの書き込みは カーネルのコンパイル前に,

static u_char mfs_root[MD_ROOT_SIZE*1024] = {
  0x00, 0x01, 0x02, 0x03, ...
};
のようにして行うべきでしょうが,FreeBSD では write_mfs_in_kernel (/usr/src/release/write_mfs_in_kernel.c) というプログラムを使用することにより,コンパイル後のカーネルに対して イメージを書き込むことができます. 実際に使用するときには,ufs のイメージ root.img を作成して,
> write_mfs_in_kernel kernel root.img
のようにします.write_mfs_in_kernel の詳しい使いかたに関しては, /usr/src/release/Makefile を参照してください.

write_mfs_in_kernel のしくみは簡単です.カーネル内での配列 mfs_root[] の定義を 見ればわかりますが,配列 mfs_root[] の先頭は "MFS Filesystem goes here" という 文字列で初期化されています.write_mfs_in_kernel は kernel をファイルオープン してこの文字列を検索し,見つかったらその部分を先頭として,以降の領域を root.img で書き換えるだけです.

実際に md にファイルシステムを持つカーネルを作成する方法を説明しましょう. まず,カーネルのコンフィグファイルに以下の行を追加して,カーネルを作成します.

pseudo-device	md			# Memory "disks"
options		MD_ROOT_SIZE=1440	# MFS size (kB). See sys/dev/md/md.c
さらに,以下のようにして ufs のファイルイメージを作成します. root.img のサイズが MD_ROOT_SIZE と一致するように注意してください.
root# cd /usr/tmp
root# dd of=root.img if=/dev/zero count=1440 bs=1k
root# awk 'BEGIN {printf "%c%c", 85, 170}' | dd of=root.img obs=1 seek=510 conv=notrunc
root# vnconfig -s labels -c vn0 root.img
root# dd if=/boot/boot1 of=root.img conv=notrunc
root# disklabel -rw vn0 auto
root# newfs vn0c
root# mount /dev/vn0c /mnt
root# cp -R /usr/tmp/sample /mnt
root# umount /mnt
root# vnconfig -u vn0
write_mfs_in_kernel を使用して,カーネルに root.img を書き込みます.
root# cd /usr/src/sys/compile/CDBSD
root# cp /usr/src/release/write_mfs_in_kernel.c .
root# gcc write_mfs_in_kernel.c -o write_mfs_in_kernel
root# ./write_mfs_in_kernel kernel /usr/tmp/root.img
これで,このカーネルを make install し,起動後に,
root# cd /dev
root# ./MAKEDEV md0
root# mount /dev/md0c /mnt
のようにすることにより,カーネルに書き込んだディレクトリ構成が,/mnt に 現れます.

/usr/src/release 以下には,インストーラなどを作成するためのファイルがあります ので,CDBSD を作成する上で多いに参考になっています. また,FreeBSD ハンドブックやFAQ日本語版なども非常に参考になっていますので, 併せて参照するとよいでしょう.

ファイルのダウンロード

mkrwfs.sh
ブート用FDの /etc/fstab の例
/etc/rc.cdrom
/etc/rc の修正(rc.patch)
fstab.cdbsd
CDBSDのイメージ作成用シェルスクリプト(mkimg.sh)

参考文献

  • [1] 「cdrecord/mkisofsを使ったCD-ROM/CD-R完全ガイド」,山森丈範, SoftwareDesign FreeBSD Issue パワーアップ FreeBSD p.40
  • [2] 「PXE で FreeBSD をディスクレスブートしよう」,山森丈範, SoftwareDesign FreeBSD Issue パワーアップ FreeBSD p.166
  • [3] 「FreeBSDカーネル入門」,大木敦雄,ASCII
  • [4] 「Memory File System」,山本和彦,BSD magazine No.4 p.51
  • [5] FreeBSD ハンドブック,FAQ
  • [6] FreeBSD のソースコード(主に /usr/src/release)

戻る