kernel の再構築


FreeBSD をインストールした時点では GENERIC kernel と呼ばれる kernel がインストールされています。 これは、様々な環境へのインストールを問題なく進めるために、 あらかじめ多くのデバイスに対応できるように、多くのドライバの組み込まれた、 比較的大きな kernel です。

この GENERIC kernel をそのまま使っても構わないのですが、 通常は自分の環境に応じて不要なドライバを切り離したコンパクトな kernel を再構築して運用します。また、GENERIC kernel に含まれないような kernel の機能を使いたい場合にも kernel の再構築は必要です。

ここでは kernel の再構築の手順を紹介します。 基本的に FreeBSD 4.x ベースの内容ですが、他のバージョンにおいても参考になるでしょう。

FreeBSD ハンドブックの『9. FreeBSD カーネルのコンフィグレーション』 にも詳しく手順が記述されていますので、そちらも参照しておくと良いでしょう。 日本語版のハンドブックは /usr/share/doc/ja/books/handbook 配下に格納されています。 index.html から辿れるので w3m 等テキストベースのブラウザを使ってハンドブックを参照しながら作業を進めるのが確実です。


  # cd /usr/share/doc/ja/books/handbook
  # w3m ./index.html

なお、最新のハンドブックの日本語役が以下の Web で参照できますので、 こちらも活用してください。

  FreeBSD ハンドブック
  http://www.jp.FreeBSD.org/www.FreeBSD.org/ja/handbook/

以下、僕の作業手順を紹介します。

1. コンフィグレーションファイルを作成する

作成する kernel の設定を記述したコンフィグレーションファイルを作成します。 この記述にしたがって kernel が作成されます。デフォルトの kernel のことを GENERIC kernel と呼びますが、この GENERIC kernel のコンフィグレーションファイルが /usr/src/sys/i386/conf/GENERIC です。

注) i386 の部分は使用しているアーキテクチャによって変わります。 私の FreeBSD は i386 なのでこのように書いてありますが、FreeBSD(98) の場合は /usr/src/sys/pc98/conf/GENERIC98 になります。

GENERIC kernel のコンフィグレーションファイルをベースにして、 自分用のコンフィグレーションファイルを生成していきます。 まずは、GENERIC を自分のカーネルコンフィグレーションファイルとしてコピーします。 この時のファイル名はホスト名を使う習慣がありますが、特に制限があるわけではありません。 なんだって構いません。 以下の例では僕の環境に合わせて SAPPHIRE というファイル名にしてあります。


  # cd /usr/src/sys/i386/conf
  # cp GENERIC SAPPHIRE

コピーした SAPPHIRE というファイルを適当なエディタで編集します。 基本的にハンドブックの『9.4. コンフィグレーションファイル』を参考にしてください。 僕の場合のポイントを以下に記しておきます。

  • cpu を固定する

    僕のマシンは Pentium!!! 668MHz なので、

    
      cpu   I686_CPU
    

    だけを有効にして、それ以外はコメントアウトします。 使用している CPU が分からない場合は dmesg の結果を確認します。 僕の場合は

    
      # dmesg |  fgrep CPU
      CPU: Pentium III/Pentium III Xeon/Celeron (665.05-MHz 686-class CPU)
    

    で 686 を選べば良いことが分かります。

  • ident を変更する

    ident の部分にはカーネルの名前を記述します。コンフィグレーションファイルの名前で良いです。 なので、僕の場合は

    
      ident   SAPPHIRE
    

    となります。

  • 不要なデバイスを外す

    不要なドライバを kernel から切り離し kernel のサイズを小さくします。 kernel の起動にかかる時間を短縮できますし、必要なメモリサイズを少なくすることができます。

    僕の場合、NIC には Intel Pro 10/100B/100+ Ethernet を使っていますので、 必要なドライバは fxp です。fxp 以外の Ethernet ドライバは不要ですので、 全部コメントアウトします。ただし、fxp を使うためには miibus が必要ですので、 miibus も一緒にコメントアウトしないよう注意してください。 fxp 付近はこんな感じになります。

    
      # PCI Ethernet NICs that use the common MII bus controller code.
      # NOTE: Be sure to keep the 'device miibus' line in order to use these NICs!
      device      miibus      # MII bus support
      #device     dc      # DEC/Intel 21143 and various workalikes
      device      fxp     # Intel EtherExpress PRO/100B (82557, 82558)
      #device     pcn     # AMD Am79C97x PCI 10/100 NICs
      #device     rl      # RealTek 8129/8139
    

    注) miibus が必要になったのは 4.4-RELEASE からだったと思います。 それよりも前のバージョンでは不要です。

    使わない SCSI デバイスや USB デバイスに関しても同様にガンガンコメントアウトします。

  • APM を有効にする

    デフォルトでは

    
      device     apm0    at nexus? disable flags 0x20 # Advanced Power Managemen
    

    となっていて APM が無効になっています。上記行の disable を削除して以下のようにします。

    
      device      apm0    at nexus? flags 0x20 # Advanced Power Management
    

    APM を有効にしておけば、shutdown -p now で電源まで落としてくれるので便利です。

    APM を有効にするには、これ以外に /etc/rc.conf で apm_enable="YES" としておく必要があります。

  • 必要な機能を追加する

    GENERIC kernel が全ての機能を取り込んでいるわけではありません。 kernel のコンフィグレーションファイルで指定できるオプションの全ては /usr/src/sys/i386/conf/LINT に記述されています。 LINT を見ながら、自分が組み込みたい機能を記述します。 僕の場合は

    
      options  TCP_DROP_SYNFIN
    

    を追加したりしてます。これは SYN と FIN の両方のビットが立った TCP セグメントを受信した場合にこれを破棄するというオプションです。 このオプションを追加した kernel で net.inet.tcp.drop_synfin1 の場合に機能します。

    FreeBSD は T/TCP (RFC 1644) をサポートしており、T/TCP では SYN+FIN というセグメントを使用するのですが、僕のマシンでは T/TCP は使わないため問題ありません。 たまーに、SYN+FIN なんて変なのを意図的に投げてくる輩がいたりするので、 この機能を使っています。

2. config を実行する

コンフィグレーションファイルが用意できたら config(8) を実行します。 引数はコンフィグレーションファイルです。


  # cd /usr/src/sys/i386/conf
  # config SAPPHIRE
  Don't forget to do a ``make depend''
  Kernel build directory is ../../compile/SAPPHIRE

config を実行すると上記のようにメッセージが出力されます。 メッセージの通り ../../compile/SAPPHIRE に make 用のディレクトリが作成されます。

古い make 環境が残っている場合にコンパイルが上手く行かないことがあります。 その場合はあらかじめ、make 用ディレクトリを削除してから config を実行します。

3. make を実行する

config 実行時に出力されたメッセージにしたがってディレクトリを移動し、 make depend と make を実行します。


  # cd ../../compile/SAPPHIRE
  # make depend
  # make

コンフィグレーションファイルの記述が適切でなく、依存関係の整合性が取れていない場合は make depend で失敗しますので、再度コンフィグレーションファイルの作成からやり直します。 例えば fxp を使うのに miibus が入っていない場合などは、ここでエラーします。

僕は make depend が成功したらそのまま make を実行するように、以下のようにしています。


  # make depend && make

make が実行されると kernel がコンパイルされます。

4. kernel をインストールする

make が正常に完了したら、続けて make install を実行して、 新しい kernel をインストールします。


  # make install

作成した新しい kernel が /kernel としてインストールされます。 これまで使っていた古い kernel は /kernel.old として残っているので、 もし、おかしな kernel を作ってしまった場合は /kernel.old を使って起動することで、 元の環境に戻すことが出来ます。

なお、GENERIC kernel は /kernel.GENERIC として残っているので、 自分で消さない限り消えることはありません。 僕の環境では以下の通りで、GENERIC kernel に比べて 1MB 以上も小さくなっています。

  -r-xr-xr-x  1 root  wheel  2309767 Jul  5 20:15 /kernel
  -r-xr-xr-x  1 root  wheel  3773568 Jun 11 15:14 /kernel.GENERIC

5. 新しい kernel で再起動する

作成した kernel のインストールが完了したら、あとはリブートするだけです。


  # cd /
  # shutdown -r now

これで無事新しい kernel で起動したら作業完了です。


TetsuoSTREAMS > FreeBSD > kernel の再構築