せっかく覚えたezjailが息してない

jailの設定ファイルが、rc.conf,/etc/rc.d/jailからjail.confに変わる。

https://twitter.com/m_bird/status/386369822751076352

そのせいか10.0-BETA1にしたら、ezjail使うたび怒られるようになった。
具体的にはezjail-adminでjailをうまく起動できない。
ezjail覚えたばっかなのに…。

「手動でなんとかしろよ」とエラーメッセージが出るのだが、jailの仕組みはとても複雑で、jail.confの書式も良くわからないしsampleもない。
「rc.d, rc.confをそのままコピー&ペーストしたらいいんだよ」とは言うのだけど、そもそもrc.d, rc.confを自分で書くのが嫌でezjail使ってたのに。

しょうがないんで、あんまり深く追いかけずに別のラッパーであるqjailを試した。

なかなか独特のテイストが感じられるのだが、思ったより手軽で、ドキュメントも(時にはウンザリするくらい)充実している。
もちろんjail.confにも安心対応。

数十個ものjailを作ることも出来たり、一度作成したjailをテンプレートにする機能もあったりして驚く。

ググった感触でいうとあんまり人気ないみたいだけど、結構いい。
細けえ事はどうでもいいからjailを使わせろという諸兄にはおすすめである。

qjailのインストール

2013/10/18時点で2.2と3.2がある。
jail.confに対応しているのは3.2。

話は前後するが、qjail3.2のman qjail(8)から抜粋すると;

This version of qjail has been converted from using the legacy rc.d
rc.conf method of jail definition as used in all pervious versions of
qjail, to using the jail(8) jail.conf method which became available in
9.1-RELEASE.

よって3.2をインストール。
なお、以下でqjailをインストールするFreeBSDは10.0-BETA1でございますので、pkgngを使います。

$ pkg search qjail
qjail-2.2
qjail-3.2
$ sudo pkg install qjail-3.2
Password:
Updating repository catalogue
The following 1 packages will be installed:

        Installing qjail: 3.2

The installation will require 416 KB more space

116 KB to be downloaded

Proceed with installing packages [y/N]: y
qjail-3.2.txz                       100%  116KB 115.9KB/s 115.9KB/s   00:01
Checking integrity... done
[1/1] Installing qjail-3.2... done
########################################################################
Use the qjail utility to deploy small or large numbers of jails quickly.

First issue "rehash" command to enable the qjail command (if using csh).
Then issue "man qjail-intro" to read the qjail introduction.
After reading that do "man qjail" for the usage details.
For the BIG PICTURE issue "man qjail-howto".

########################################################################
For instructions on upgrading jail filesystems
Read /usr/local/share/examples/qjail/upgrade-info.txt
$

qjailでの初期設定

まずはjailのひな形、ベース環境を作る。
qjail installでよい。
ひな形取得先のftpサーバを変更するならオプションで指定する。
書式は以下。

qjail install -h ftp2.jp.freebsd.org

RELEASE以外でのqjail install

しかし、ftpサーバからダウンロードできるのはRELEASEのみ。
BETA, RC, ALPHA, STABLE等々だとダメ。
回避方法は二つ。

①なんでもいいのでRELEASEで作っておいてアップグレードする
②ダウンロードしたディスクイメージを使う。

今回は②にした。
①はman qjail参照。
②をもう少し細かく書くと、ディスクイメージをマウントし、base.txzなどのある「ディレクトリ」をqjail install -fに続けて指定する。

「ディレクトリ」とわざわざ書いたのは、cdで行けるところ、というのを強調したかったから。
ディスクイメージの直接指定はできないし、ftpサーバのディレクトリ指定もダメ。
ガッカリ。

(追記)RELEASE以外でのqjail install

「RELEASE以外」というのは、実はRELEASE-p2といったような、パッチレベルが0以外の場合も該当する。
つまりfreebsd-updateでパッチを当てた状態でqjail installすると失敗する。
これは、qjailは自ホストのOSバージョンをもとにディレクトリを移動するから。
OSバージョンが10.1-RELEASE-p16だったら、ftpサーバの10.1-RELEASE-p16などを見に行ってしまう。
しかし、ftpサーバはパッチレベルごとにはディレクトリが作られないので、参照先がなく失敗する。

ところで、ここでのOSバージョンとは、具体的には環境変数UNAME_rである。
ということは、qjail installのときだけUNAME_rを変更すればパッチレベルが変わっていようがよいのである。
以下、10.1-RELEASE-p16で実行した例。

root@kraken:/usr/local # setenv UNAME_r "10.1-RELEASE"
root@kraken:/usr/local # qjail install -h ftp2.jp.freebsd.org
Trying 202.232.140.170:21 ...
Connected to ftp.iij.ad.jp.
220 IIJ FTP server ready (IPv4 client).
230 Login successful.
Remote system type is UNIX.
Using binary mode to transfer files.
200 Switching to Binary mode.
250 Directory successfully changed.
local: base.txz remote: base.txz
229 Entering Extended Passive Mode (|||52115|).
150 Opening BINARY mode data connection for base.txz (66173780 bytes).
 85% |*****************************      | 54994 KiB  999.68 KiB/s    00:09 ETA
226 Transfer complete.
66173780 bytes received in 01:03 (0.99 MiB/s)
221 Goodbye.

The RELEASE distribution files are populating template.
Est LT 1 minute elapse time for this to complete.

Successfully installed qjail system.

追記ここまで

ダウンロードしたディスクイメージからqjail install

仕方がないので淡々と進める。
10.0-BETA1のイメージダウンロードして、ローカルでマウント。

$ fetch ftp://ftp.iij.ad.jp/pub/FreeBSD/releases/ISO-IMAGES/10.0/FreeBSD-10.0-BETA1-amd64-disc1.iso
FreeBSD-10.0-BETA1-amd64-disc1.iso            100% of  693 MB 8138 kBps 01m27s
$
$ sudo mdconfig -a -t vnode -f ./FreeBSD-10.0-BETA1-amd64-disc1.iso -u 0
$ sudo mount -t cd9660 /dev/md0 /mnt

/mntにマウントしたとすると、/mnt/usr/freebsd-dist/が目的の場所。

$ ls /mnt
COPYRIGHT       etc             mnt             sbin            var
bin             lib             proc            sys
boot            libexec         rescue          tmp
dev             media           root            usr
$ ls /mnt/usr
bin             include         libdata         obj             src
freebsd-dist    lib             libexec         sbin            tests
games           lib32           local           share
$ ls /mnt/usr/freebsd-dist/
MANIFEST        doc.txz         kernel.txz      src.txz
base.txz        games.txz       lib32.txz
$

qjail install -fで実行。
終わったらマウントも外そう。

$ sudo qjail install -f /mnt/usr/freebsd-dist/                  
The RELEASE distribution files are populating template.
Est LT 1 minute elapse time for this to complete.

sharedfs is being populated.
Est LT 1 minute elapse time for this to complete.

Successfully installed qjail system.
$
$ sudo umount /mnt
$ sudo mdconfig -d -u 0

qjailの構成

/usr/jailsにいくつかのディレクトリが生まれる。
また、設定ファイルが/usr/local/etc/に格納される。

/usr/jails下は以下の通り。

$ ls /usr/jails
archive         flavors         sharedfs        template

sharedfs:
OSの実行ファイル、ライブラリ。全Jailで共有される。

$ ls /usr/jails/sharedfs/
bin     lib     libexec sbin    sys     usr

template:
OS configuration fileがある。設定変えようと思ったらここかな。

$ ls /usr/jails/template/
COPYRIGHT       home            mnt             sharedfs        var
bin             lib             proc            sys
dev             libexec         root            tmp
etc             media           sbin            usr

archive:
初期状態では空。
qjail archiveコマンドで作成されるアーカイブが格納される。

flavors:
flavorですな。defaultとssh-defaultの二つがある。

$ ls /usr/jails/flavors/
default         ssh-default

そのほか、/usr/local/etc/下に以下のようなファイル、ディレクトリがたくさん出来る。
jailを作ると今度はこのディレクトリの下にjail名でファイルができる。
global, local, vnetの意味が、想像はできるもののよく分からない。

$ ls /usr/local/etc/qjail*
/usr/local/etc/qjail.portsnap.conf
/usr/local/etc/qjail.fstab:
/usr/local/etc/qjail.global:
/usr/local/etc/qjail.local:
/usr/local/etc/qjail.vnet:

jailの作成

書式。代表的なもののみ。

qjail create -n <NIC name>  -f <flavor> -a <アーカイブ> \
 -4 <割り当てるIPアドレス>  jailname

-fと-aは一緒に使えない。

実際に作ってみる。
あっさりと出来上がる。
あっさりしすぎて逆に不安なくらい。

$ sudo qjail create -n em0 -4 192.168.100.240 example01
Successfully created  example01

気がつくと、/etc/jail.confが生まれている!

example01 {
host.hostname       =  "exmaple01";
path                =  "/usr/jails/exmaple01";
mount.fstab         =  "/usr/local/etc/qjail.fstab/exmaple01";
exec.start          =  "/bin/sh /etc/rc";
exec.stop           =  "/bin/sh /etc/rc.shutdown";
exec.consolelog     =  "/var/log/qjail.exmaple01.console.log";
devfs_ruleset       =  "4";
allow.mount.devfs;
mount.devfs         =  "1";
ip4.addr            =  192.168.100.240;
interface           =  "em0";
}

jail起動…の前に、qjail listで確認。

qjail list

作成済みのjailはqjail listで確認できる。

$ sudo qjail list
STA JID  NIC IP              Jailname
--- ---- --- --------------- --------------------------------------------------
DS  N/A  em0 192.168.100.240 example01

最初のカラムのSTAはStatusの略。

一文字め:Jailの種別
    D: ディレクトリベースのjail.
    I: イメージベースのjail.
二文字め:状態
    R: 実行中
    S: 停止中

JIDはjail IDのこと。そのほかは見たまま。

qjail start

qjail startでjailを起動。
qjail listの表示も変わり、ネットワークインタフェースへのaliasも実行してくれている。

$ sudo qjail start example01
Jail successfully started  example01
$
$ sudo qjail list
STA JID  NIC IP              Jailname
--- ---- --- --------------- --------------------------------------------------
DR  N/A  em0 192.168.100.240 example01

$ ifconfig em0
em0: flags=8843<UP,BROADCAST,RUNNING,SIMPLEX,MULTICAST> metric 0 mtu 1500
        options=9b<RXCSUM,TXCSUM,VLAN_MTU,VLAN_HWTAGGING,VLAN_HWCSUM>
        ether 08:00:27:a1:d7:05
        inet 192.168.100.110 netmask 0xffffff00 broadcast 192.168.100.255
        inet 192.168.100.240 netmask 0xffffffff broadcast 192.168.100.240
        nd6 options=29<PERFORMNUD,IFDISABLED,AUTO_LINKLOCAL>
        media: Ethernet autoselect (1000baseT <full-duplex>)
        status: active

qjail consoleでjailの中へ

qjail consoleでコンソールにアクセスできる。

$ sudo qjail console example01
FreeBSD 10.0-BETA1 (GENERIC) #0 r256420: Sun Oct 13 01:43:07 UTC 2013

Welcome to your FreeBSD jail.
example01 /root >

特に何もしていないけど、/etc/localtimeと/etc/resolv.confは作ってくれた。wall_cmos_clockはなかった。

exmaple01 /root >ls /etc | egrep "resolv|clock|localtime"
localtime
resolv.conf

qjail stopで止めて、archiveでアーカイブ、deleteで削除完了

単純にstopしてdeleteするのは面白くないから、deleteの前にarchiveしてみた。
/usr/jails/archiveの下に<jail名>@日付秒.tarというファイルが出来ている。
また、deleteしてもjail.confには記載が残っているようだ。

$ sudo qjail stop example01
Jail successfully stopped  example01
$ sudo qjail archive example01
Successfully archived example01
$ ls /usr/jails/archive/
example01@201310182327.36.tar
$ sudo qjail delete example01
Successfully deleted  example01
$ sudo qjail list
STA JID  NIC IP              Jailname
--- ---- --- --------------- --------------------------------------------------

$
$ cat /etc/jail.conf
example01 {
host.hostname       =  "example01";
(後略)

qjail restoreでarchive済みのjailを復活可能ッ!

ためしにrestoreしてみたら何事もなかったかのように復活して驚いた。
これはスナップショット的に使えますね。

$ sudo qjail restore example01
Successfully restored example01
$ sudo qjail list
STA JID  NIC IP              Jailname
--- ---- --- --------------- --------------------------------------------------
DS  N/A  em0 192.168.100.240 example01
$
$ sudo qjail start example01
Jail successfully started  example01
[vanilla@yaryka ~]$ sudo qjail console example01
Last login: Thu Oct 17 23:50:08 on pts/3
FreeBSD 10.0-BETA1 (GENERIC) #0 r256420: Sun Oct 13 01:43:07 UTC 2013

Welcome to your FreeBSD jail.
example01 /root >

qjail、便利だよね?

ご覧の通り、qjailはjailをマクロなレベルで扱うことに長けているようで、とても便利に感じる。
qjailにはほかにもqjail configというコマンドがあり、既存のjailの設定(たとえばIPアドレスとか)を変えたりできるし、jailのOSアップデートも手軽にできるようだ。
そのあたりはまた試すとして、しばらくjailはqjailでメンテしようと思った。