Linux
CentOS
systemd

CentOS7導入時に調べたsystemdの話

More than 3 years have passed since last update.

筆者はsystemdどころかinit自体よくわからない状態からスタートしています。

  • 従来のSysVinitやUpstart(RHEL6における実装)に代わるサービス管理のアーキテクチャー。
  • Fedora15で採用後、2014年リリースのRHEL7(CentOS7)でも正式採用、事実上の標準となりつつある。

従来

  • /sbin/init/etc/inittabに記載された各ランレベルごとの設定に従ってすべてのプロセスをrcスクリプトによって起動していく。
  • rcスクリプトの実体は/etc/init.d内のシェルスクリプトのシンボリックリンク。/etc/init.dserviceコマンドでの起動終了等でも操作しているもの(実際は直接スクリプトを叩くのとserviceコマンドとでは差異がある模様で、直接だとカレントの環境を使ってしまうので望まぬっ結果となる可能性があるらしい)。
  • この他にも/sbin/initにはデバイスの読み込みやらファイルシステムのマウントやら、起動時に必要な処理が様々組み込まれている。
  • SysVinitはPIDを直接には知らず、PIDファイルを介してアクセスしている。

systemd

  • /sbin/initが実行していた処理をUnit単位で分割、並行起動できるようにしている。
  • Unit定義ファイルの実体は2箇所に存在。
    • システムデフォルトは/usr/lib/sytemd/system配下
    • 管理者がカスタマイズする内容は/etc/systemd/system配下
    • 従ってデフォルト設定を変更する場合は前者から後者のパスへコピーして編集すればよい
  • Unitの種類は拡張子によって判別でき、サービスを管理する.service、マウントポイントを表す.mount、デバイスに対応した.device等がある。
  • Unit間は依存関係を定義できる。ひとつはUnitファイル内の[Unit]セクションにて、Wants=Require=オプションで定義すること。もうひとつはそのUnitの名を関したwantsディレクトリ内に、依存するUnitのシンボリックリンクを置くこと。
  • 前後関係の定義は同じく[Unit]セクションのAfter=Before=オプションを使用する。
  • Unitにはデバイスやマウントポイントも存在しているので、これらを対象とした依存関係も書くことができる。

起動時のプロセス

  1. systemdがdefault.targetを起動する。これはmulti-user.targetrescue.targetのシンボリックリンクであり、従来のランレベルに相当する。
  2. 例えばmulti-user.targetが呼ばれた場合、/etc/systemd/system/multi-user.target.wantsディレクトリ内の各サービスを起動する。これらは各service unitのシンボリックリンクに相当する。つまりサービスの自動起動化とは、このシンボリックリンクを張ることに相当している(systemctl enableコマンドの出力を見るとわかる)。
  3. その後は各Unitの前後関係、依存関係に基づいて起動処理が実行されていく。

操作

Unitの操作にはsystemctlコマンドを使用する
* start/stop 起動終了
* reload/restart 設定ファイルの再読み込み、サービスの再起動
* enable/disable 自動起動の有効化無効化(chkconfigにあたる)
* mask/unmask サービス自体の有効化無効化(unmask状態だと起動不可となる)
* status 状態確認
* list-unit-files 全ユニット表示
* list-units 起動中のユニット表示

ランレベル変更に相当するdefault.targetのターゲット変更にはset-defaultを用いる。

# systemctl set-default multi-user.target

Unitファイルに変更を加えた際はdaemon-reloadで変更内容を読み込ませる。

# systemctl daemon-reload

Unitファイルの作成

未消化

  • プロセス管理にはcgroupsを用いているらしいがよくわからない。
  • journaldがsyslogに代わって使われているらしいが、そもそもsyslogからよくわかってない。

参考