コントロール・グループを使用したリソースの管理
制御グループがプロセスを編成する方法、systemdによるリソース・ポリシーの適用方法、およびcgroupを手動で管理するタイミングについて説明します。
cgroupsと呼ばれる制御グループは、systemdサービスを編成し、必要に応じて個々のプロセス(PIDs)を、CPU、メモリー、I/Oなどのシステム・リソースを割り当てるための階層グループに編成するOracle Linuxカーネル機能です。
たとえば、CPU時間の割当てが必要な3つのプロセスを150:100:50の比率で特定した場合は、3つcgroupsを作成し、それぞれに比率の3つ値のいずれかに対応するCPUの重みを割り当て、各cgroupに適切なプロセスを割り当てます。
systemdを使用して、cgroupを構成します。
/sys/fs/cgroup仮想ファイル・システム(このトピックで説明)でcgroupディレクトリを手動で作成すると、基礎となる概念を説明するのに役立ちます。ただし、一時的なデバッグやテストなどの特定のシナリオでは、このアプローチを使用します。ほとんどのユース・ケースでは、systemdを使用してcgroupsを構成し、正確で永続的なリソース管理を確保します。
デフォルトでは、systemdは次のものに対してcgroupを作成します:
-
ホストに設定された各
systemdサービス。たとえば、サーバーには、
NetworkManagerサービスによって所有されるプロセスをグループ化する制御グループNetworkManager.serviceと、firewalldサービスによって所有されるプロセスをグループ化する制御グループfirewalld.serviceなどがあります。 -
ホストの各ユーザー(
UID)。
cgroup機能は/sys/fs/cgroupに仮想ファイル・システムとしてマウントされています。各cgroupには、/sys/fs/cgroupファイル・システム内の対応するディレクトリがあります。たとえば、管理するサービスに対してsystemdによって作成されたcgroupsは、次のサンプル・コード・ブロックに示すように、コマンドls -l /sys/fs/cgroup/system.slice | grep ".service"を実行することで確認できます。
ls -l /sys/fs/cgroup/system.slice | grep ".service"
...root root 0 Mar 22 10:47 atd.service
...root root 0 Mar 22 10:47 auditd.service
...root root 0 Mar 22 10:47 chronyd.service
...root root 0 Mar 22 10:47 crond.service
...root root 0 Mar 22 10:47 dbus-broker.service
...root root 0 Mar 22 10:47 dtprobed.service
...root root 0 Mar 22 10:47 firewalld.service
...root root 0 Mar 22 10:47 httpd.service
...
また、/sys/fs/cgroup仮想ファイル・システムの下にディレクトリを作成し、システム要件に従ってプロセスID (PIDs)を異なるcgroupsに割り当てることで、カスタムcgroupsを作成することもできます。ただし、/sys/fs/cgroup.の下に手動でcgroupsを作成するのではなく、systemdを使用してcgroupsを構成することをお薦めします。
cgroupsをsystemdで管理する推奨方法は、Systemdを使用した制御グループの管理を参照してください。
Linuxカーネルでは、2つのバージョンの制御グループを使用できます。
- 制御グループ・バージョン1 (
cgroups v1) -
リソース単位のコントローラ階層を提供します。各リソース(CPU、メモリー、I/Oなど)には、独自の制御グループ・ツリーがあります。これにより、リソース間の調整が困難になる可能性があります。レガシーAPIを使用します。現在は非推奨と見なされましたが、サポートされているシステムでは互換性があります。
- 制御グループ・バージョン2 (
cgroups v2) -
すべてのコントローラに統一された単一の階層を使用することで、リソース間の調整を改善し、管理を簡素化できます。最新の簡略化されたAPIを使用します。これは、推奨され、積極的に開発された実装です。
次の表に、Oracle Linuxリリースごとの可用性をまとめます。
| Oracle Linuxリリース | cgroups v1 | cgroups v2 |
|---|---|---|
| Oracle Linux 8 | 使用可能(デフォルト) | 使用可能(手動で有効化) |
| Oracle Linux 9 | 使用可能(互換性) | 使用可能(デフォルト) |
| Oracle Linux 10 | 使用不可(非推奨) | 使用可能(デフォルト) |
コントロール・グループの詳細は、cgroups(7)およびsysfs(5)のマニュアル・ページを参照してください。
Oracle Linux 8でのcgroups v2の有効化
Oracle Linux 9およびOracle Linux 10でのcgroups v2の確認
sudo mount -l | grep cgroup
cgroup2 on /sys/fs/cgroup type cgroup2 (rw,nosuid,nodev,noexec,relatime,seclabel,nsdelegate,memory_recursiveprot)
カーネル・リソース・コントローラについて
制御グループは、カーネル・リソース・コントローラを介してリソースの使用を管理します。カーネル・リソース・コントローラは、CPU時間、メモリー、ネットワーク帯域幅、ディスクI/Oなどの単一のリソースを表します。
システムにマウントされたリソース・コントローラを識別するには、/procs/cgroupsファイルの内容を確認します。次に例を示します:
less /proc/cgroups
#subsys_name hierarchy num_cgroups enabled
cpuset 0 103 1
cpu 0 103 1
cpuacct 0 103 1
blkio 0 103 1
memory 0 103 1
devices 0 103 1
freezer 0 103 1
net_cls 0 103 1
perf_event 0 103 1
net_prio 0 103 1
hugetlb 0 103 1
pids 0 103 1
rdma 0 103 1
misc 0 103 1
cgroupsのカーネル・リソース・コントローラの詳細な説明は、cgroups(7)マニュアル・ページをご覧ください。
制御グループ・ファイル・システムについて
cgroup機能は、/sys/fs/cgroupに階層ファイル・システムとしてマウントされています。
ディレクトリ/sys/fs/cgroupは、ルート制御グループとも呼ばれます。
ルート制御グループのディレクトリの内容は、マウントされたバージョンによって若干異なりますが、cgroups v2を使用するシステムでは、通常、次のようなエントリが表示されます。
ls /sys/fs/cgroup
cgroup.controllers cpuset.mems.effective memory.stat
cgroup.max.depth cpu.stat misc.capacity
cgroup.max.descendants dev-hugepages.mount sys-fs-fuse-connections.mount
cgroup.procs dev-mqueue.mount sys-kernel-config.mount
cgroup.stat init.scope sys-kernel-debug.mount
cgroup.subtree_control io.pressure sys-kernel-tracing.mount
cgroup.threads io.stat system.slice
cpu.pressure memory.numa_stat user.slice
cpuset.cpus.effective memory.pressure
mkdirコマンドを使用して、ルート制御グループ内にcgroupサブディレクトリを作成できます。たとえば、次のcgroupサブディレクトリを作成します。/sys/fs/cgroup/MyGroups//sys/fs/cgroup/MyGroups/cgroup1/sys/fs/cgroup/MyGroups/cgroup2
Best design practice is for child
cgroups to be at least 2 levels deep inside the /sys/fs/cgroup. 前述のリストの例では、最初の子グループMyGroupsを、システムに必要な様々なcgroupsを含む親として使用することで、このプラクティスに従っています。 階層内の各cgroupには、次のファイルが含まれます。
-
cgroup.controllers -
この読取り専用ファイルには、現在の
cgroupで使用可能なコントローラがリストされます。このファイルの内容は、親のcgroup内のcgroup.subtree_controlファイルの内容と一致します。 -
cgroup.subtree_control -
このファイルには、現在の
cgroupの直下の子cgroupsに対して有効になっているcgroup.controllersファイル内のコントローラが含まれています。コントローラ(
pidsなど)がcgroup.subtree_controlファイルに存在する場合、対応するコントローラ・インタフェース・ファイル(pids.maxなど)は、現在のcgroupの直下の子に自動的に作成されます。
アプリケーションのリソース管理を実装できる子グループを作成する手順の例は、CPUの重みの設定によるCPU時間配分の制御を参照してください。
cgroupを削除するには、cgroupに他の子グループが含まれていないことを確認してから、ディレクトリを削除します。たとえば、子グループ/sys/fs/cgroup/MyGroups/cgroup1を削除するには、次のコマンドを実行します。
sudo rmdir /sys/fs/cgroup/MyGroups/cgroup1
リソース配分モデルについて
次の配分モデルでは、cgroups v2で使用するリソースを配分するときに制御または規制を実装する方法について説明します:
- 加重
-
このモデルでは、すべての制御グループの重みが合計されます。各グループは、合計の重みに対するグループの重みの比率に基づいて、リソースの一部を受け取ります。
10個の制御グループについて考えてみます。それぞれの重みは100で、合計は1000です。この場合、各グループは、指定されたリソースの10分の1を使用できます。
通常、重みはステートレス・リソースの配分に使用されます。このリソースを適用するには、
CPUWeightオプションが使用されます。 - 制限
-
このモデルでは、グループは最大でリソースの構成量を使用できます。プロセスのメモリー使用量などのリソースが制限を超えた場合、カーネルはメモリー不足(oom)メッセージでプロセスを停止することがあります。
また、サブグループの制限の合計が親グループの制限を超えることができるように、リソースをオーバーコミットすることもできます。過剰コミットメントは、すべてのサブグループのリソースが同時にすべてのリソースが制限に達する可能性が低いことを前提としています。
この配分モデルを実装するには、
MemoryMaxオプションが使用されます。 - 保護
-
このモデルでは、グループに保護された境界が割り当てられます。グループのリソース使用量が保護された量に収まっている場合、カーネルは、同じリソースについて競合する他のグループのためにリソースの使用を奪うことはできません。このモデルでは、リソースのオーバーコミットが許可されます。
このモデルを実装するには、
MemoryLowオプションが使用されます。 - 割当て
-
このモデルでは、リアルタイム予算など、有限タイプのリソースの使用に対して特定の絶対金額が割り当てられます。
sysfsを使用したcgroups v2の管理
トラブルシューティングまたは一時テストのために、/sys/fs/cgroupでcgroups v2階層を直接作成およびチューニングする方法を示します。
systemdを使用して、可能なかぎりすべてのリソース管理を処理します。詳細は、「Systemdを使用した制御グループの管理」を参照してください。
ここに示す例では、systemdがシステムで実行し、systemd以外の機能を表示するアクションのコンテキストを示します。提供される情報は、cgroupsの問題をデバッグする際に役に立ちます。
この手順の例では、それぞれに異なるアプリケーションPIDを割り当てられたcgroups間でCPU時間を割り当てています。CPU時間およびアプリケーションPID値は、各グループのCPU.weightおよびcgroup.procsファイルに設定されています。
また、この例には、cpuコントローラおよびそれに関連付けられたファイル(cpu.weightファイルを含む)を、 /sys/fs/cgroupの下に作成する必要のあるcgroupsで使用できるようにするために必要な手順も含まれています。
CPU時間の配分のための制御グループの準備
この手順では、CPU時間の分布を管理するために制御グループを手動で準備する方法について説明します。制御グループを構成するための推奨方法は、systemdを使用することです。
CPU時間の配分を調整するためのCPU重量の設定
この手順では、制御グループを使用してCPU時間の分布を管理することによって、3つの異なるプロセスのCPUウェイトを設定する方法について説明します。制御グループを構成するための推奨方法は、systemdを使用することです。
この手順は、次の仮定に基づいています。
-
次の
topコマンドの出力例に示すように、CPUリソースを過度に消費しているアプリケーションはsha1sumです:sudo top... PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND 33301 root 20 0 18720 1756 1468 R 99.0 0.0 0:31.09 sha1sum 33302 root 20 0 18720 1772 1480 R 99.0 0.0 0:30.54 sha1sum 33303 root 20 0 18720 1772 1480 R 99.0 0.0 0:30.54 sha1sum 1 root 20 0 109724 17196 11032 S 0.0 0.1 0:03.28 systemd 2 root 20 0 0 0 0 S 0.0 0.0 0:00.00 kthreadd 3 root 0 -20 0 0 0 I 0.0 0.0 0:00.00 rcu_gp 4 root 0 -20 0 0 0 I 0.0 0.0 0:00.00 rcu_par_gp ... -
前述のサンプル出力に示されているように、
sha1sumプロセスには、PID 33301、33302および33303があります。
以降の手順の前提条件として、CPU時間の配分のための制御グループの準備の説明に従って、cgroup-v2の準備を完了する必要があります。これらの準備をスキップした場合、この手順は完了できません。