こんにちは。
前回の記事「Docker コンテナ構築入門」でDockerでのコンテナ構築方法を説明しました。
今回はコンテナ型仮想化技術の仕組みにフォーカスを当てた記事を書いていきます。
特徴とコンテナを構成するNamespace, cgroup, Capabilityについて説明します。
コンテナ型仮想環境
コンテナ型仮想環境は、仮想化技術の一種です。
筆者は以前にOracle社のVirtualBoxを利用した経験があったため、VirtualBoxが該当するホスト型仮想環境と比較して説明します。
ホスト型は、仮想環境ごとにゲストOSを立ち上げるのに対し、コンテナ型はホストOSのカーネルを共有して動作しています。
そのため、他の仮想化技術と比べ起動が速く、軽量に動作するといったメリットがあります。
また、ホストOSと独立した環境を作成できるので、管理が楽といったメリットもあります。
コンテナを構成する代表的なLinuxカーネルの機能
結論から言うと、コンテナは複数のLinuxカーネルの機能を組み合わせて構成されており、「コンテナ」と呼ばれる単一の技術でできているわけではありません。
その中でも重要な以下の3つの要素を説明します。
- Namespace "ネームスペース"
- cgroup "コントロールグループ"
- Capability "ケイパビリティ"
Namespace
Namespaceは、プロセスが参照するプロセスIDやマウントポイントなど、カーネルリソースを他のプロセスと分離し、ファイルツリーなどが独立したOS環境のように見せる機能です。
日本語では名前空間とも呼ばれています。
Namespaceはすべてのプロセスに関連付けられており、デフォルトでは親プロセスと同じNamespaceを参照します。そのため、同じNamespaceに存在する関係のないプロセスやリソースまで参照できてしまい、ファイルツリーの干渉やマウントなどのファイルシステムに影響を与えてしまう可能性があります。
そこでコンテナは、新たなNamespaceを関連付けることで、コンテナ内のリソースだけ見えるように隔離しています。
なお、Namespaceには7つ種類が存在し、それぞれ隔離できるリソースは異なります。
名前空間 | 定数 | 分離対象 |
---|---|---|
IPC | CLONE_NEWIPC | System V IPC, POSIX メッセージキュー |
Network | CLONE_NEWNET | ネットワークデバイス、スタック、ポートなど |
Mount | CLONE_NEWNS | マウントポイント |
PID | CLONE_NEWPID | プロセス ID |
User | CLONE_NEWUSER | ユーザー ID とグループ ID |
UTS | CLONE_NEWUTS | ホスト名と NIS ドメイン名 |
ちなみに、Docker
を介さずLinuxコマンドでNamespaceを作成する方法は、こちらにまとめてあります。
unshareコマンドで、Namespaceを作成してみる
cgroup
controll groupの略です。
cgroup
はプロセスをグループ化し、グループ化したプロセスに対してリソースの管理を行う機能です。
例えばホストが持つCPUやメモリなどのリソースを制限することができます。
そうすることで、あるプロセスが多くのCPUやメモリを消費し、動作が遅く不安定になったり、他のプロセスが強制終了したりといったことを抑制することができます。
cgroupは具体的に、
- CPU時間・メモリ使用量の制限
- デバイスのアクセス制御
- ネットワーク優先度の設定
- 各リソースの使用量の確認
などといった事ができます。
Capability
通常プロセスは、特権(root権限)あるいは一般ユーザ権限で動いています。
特権が必要になるのは、
- 特権ポート(<1024)を使用する場合
- ネットワークの疎通確認に良く使う
$ping
コマンドなどのようにRawソケットを使用する場合 -
$ntpd
などでシステムの時刻を設定する場合
などが該当します。
しかし、上記のようなプロセスを実行する際に特権すべてを与えてしまうと、プロセスに脆弱性があった場合に、不正な操作によりプロセスが持っている権限を悪用され、システムに悪影響を与える可能性があり、セキュリティの観点であまり良くありません。
それに対し、特権をさらに細分化し、プロセスに特権すべてを与えるのではなく最小限にすることで、脆弱性が発見されて悪用されたとしてもそのプロセスが必要とする最小限の権限しか奪われないため、被害の範囲を狭めることができます。
この細分化した特権がCapabilityです。