省電力とCPU周波数・アイドル状態の管理
CPUの電力を削る仕組みを原理から押さえれば、なぜ低負荷でも熱いのか、なぜ応答が遅れるのかを切り分けられます。P-stateとC-state、cpufreqガバナ、tickless動作、電力と応答性のトレードオフを設計判断として整理します。
- 1.P-state(DVFS)は動作中の電圧と周波数を下げて性能あたりの電力を削る軸、C-stateは仕事がない間にコアを段階的に止めて漏れ電力を削る軸で、別物。
- 2.cpufreqガバナが周波数を選ぶ。schedutilはスケジューラの負荷追跡(PELT)を直接使い、旧来のondemandより応答が速く無駄が少ない。
- 3.深いC-stateは電力を大きく下げるが復帰に遅延(exit latency)がかかる。tickless(NO_HZ)と組み合わせて滞在を長くするほど省電力だが、応答性とは綱引きになる。
省電力には独立した二つの軸がある
CPUの消費電力を削る話は、しばしば「周波数を下げる」一語に丸められますが、実際には性質の異なる二つの軸を別々に制御しています。動いている間の電力を削る軸と、止まっている間の電力を削る軸です。この二つを混同すると、「負荷が低いのに周波数が上がったままで熱い」「アイドルなのに電力が下がらない」といった現象を原理から読めません。
P-state(動作中の電圧・周波数=DVFS)とC-state(アイドル中の停止深度)の違いをまず分離します。次に周波数を選ぶ cpufreq ガバナ(特に schedutil)、停止深度を選ぶ cpuidle、そして tickless が省電力を成立させる仕組みを見ます。最後に深いC-stateの復帰遅延がもたらす電力と応答性のトレードオフを設計判断として整理します。
P-state(DVFS)── 動いている間の電力を削る
CPUが命令を実行している間の動的消費電力は、おおまかに「電力 ∝ 容量 × 電圧の2乗 × 周波数」に比例します。周波数を上げるには電圧も上げる必要があるため、電圧と周波数を同時に下げる DVFS(動的電圧・周波数スケーリング) は、電力を効果的に削れます。この「電圧・周波数の組」の選択肢が P-state(Performance state) です。P0 が最も高性能・高電力、番号が大きいほど低周波・低電圧になります。
ここで重要なのは、P-stateはコアが仕事をしている前提の制御だという点です。負荷に対して周波数が高すぎれば電力を無駄にし、低すぎれば処理が長引いてかえって総エネルギーが増える(処理を早く終えて眠る race to idle の逆)。だからP-stateは「いまどれだけ仕事があるか」を見て選ばれます。
動的電力 ≈ C × V^2 × f (V は周波数 f に概ね連動して下げられる)
→ 周波数を半分にし電圧も下げると、動的電力は大きく下がる
→ ただし同じ仕事の所要時間は延びるため、総エネルギーは単純比例しない
P-state は「動作中」の電圧・周波数の組
P0 = 最高性能・最高電力 … Pn = 低周波・低電圧
近年のIntel CPUでは、OSがP-stateを直接指定するのではなく、OSが性能ヒント(最小・最大・希望)を渡し、ファームウェア側(HWP: Hardware-managed P-states)が実際の周波数を決める方式が主流です。intel_pstate ドライバはこのHWPを使い、応答をハードウェアの速い時間粒度に任せます。
C-state ── 止まっている間の電力を削る
実行すべきタスクが無くなりアイドルになると、別の軸が働きます。C-state(CPU idle state) は、コアをどれだけ深く停止させるかの段階です。C0 は通常動作(命令実行中)で、C1 以降が停止状態です。番号が大きいほど深く、より多くのものを止めます。
- 浅いC-state(C1など): 命令の発行を止めるだけ。復帰は数サイクル〜マイクロ秒未満で速い。
- 深いC-state(C6など): コアのクロックを止め、電圧を落とし、L1/L2キャッシュをフラッシュしてコア電源を切るところまで進む。漏れ電力(リーク電流)まで削れるが、復帰にはキャッシュの暖め直しやPLL再ロックが必要で遅い。
深いほど省電力だが復帰が遅い、という非対称が本質です。この「復帰にかかる時間」を exit latency と呼び、後述のトレードオフの中心になります。
| 観点 | P-state(DVFS) | C-state(idle) |
|---|---|---|
| 対象 | 動作中のコア | アイドルのコア |
| 削る電力 | 動的電力(V^2×f) | 停止+漏れ電力 |
| 何を変える | 電圧と周波数の組 | 停止の深さ(何を止めるか) |
| 選ぶ主体 | cpufreq ガバナ/HWP | cpuidle ガバナ |
| 代償 | 性能(処理が延びる) | 復帰遅延(exit latency) |
「周波数を最低に固定すれば省電力」は半分しか正しくありません。それはP-state側の話で、アイドル時の漏れ電力はC-stateが深く入って初めて削れます。逆にC-stateを浅く固定(深いアイドルを禁止)すると、低負荷でも電力が下がりません。サーバーで intel_idle.max_cstate を絞ると応答遅延は減りますが、待機電力は増える、という典型的な綱引きはこの二軸の独立性から来ます。
cpufreq ガバナ ── 周波数を「いつ」「どう」選ぶか
P-stateを実際に動かすのが cpufreq サブシステムで、選択ポリシーを ガバナ が担います。代表的なものを並べると、判断の歴史が見えます。
| ガバナ | 周波数の決め方 | 特徴 |
|---|---|---|
| performance | 常に最高に固定 | 応答最優先・省電力なし |
| powersave | 常に最低に固定 | 電力最優先(intel_pstateでは挙動が別) |
| ondemand | 周期サンプルの使用率で段階 | 反応が一拍遅れ、過渡で振動しやすい |
| schedutil | スケジューラの負荷追跡を直接使用 | 更新が即時で無駄が少ない・現在の既定 |
ondemand は一定周期でCPU使用率をサンプリングし、しきい値を超えたら周波数を上げる方式でした。問題は、サンプリング周期という固定の遅れがあること、そして使用率という間接指標がバースト的な負荷をうまく捉えられないことです。結果として、上げ遅れ(もたつき)と、要らないのに上げてしまう振動が起きがちでした。
これを置き換えたのが schedutil です。schedutilは独自にサンプリングせず、スケジューラがもともと維持している負荷追跡(PELT: タスクごとの指数移動平均的な利用率)を直接読んで周波数を決めます。タスクが起きてランキューに入った瞬間に利用率が反映され、周波数更新が走るため、ondemandのサンプリング遅延が消えます。負荷の源と周波数決定が同じ数字を共有するので、過大評価も減ります。schedutilが参照するこの利用率信号の作り方は /os/cfs-scheduler-internals/ のPELTと地続きです。
ondemand: タイマで使用率をサンプル → しきい値判定 → 周波数変更
(周期ぶんの遅れ+間接指標)
schedutil: スケジューラの利用率(util)が変化 → その場で目標周波数を算出
次の目標 f ≈ 現在の最大周波数 × (util / 容量) × 余裕係数(1.25)
(遅延なし・負荷の一次情報を共有)
schedutilが目標周波数に余裕係数(約1.25倍)を掛けるのは、利用率がちょうど100%だと処理が常にギリギリで、わずかな増加で遅延が膨らむからです。少し高めに振っておくことで、応答性を保ちます。逆にこの係数を理解せず「使用率50%なのに周波数が高い」と驚くことがありますが、これは設計どおりです。電力一辺倒ではなく応答性とのバランスがガバナに組み込まれている、と読むのが正しい見方です。
アイドルの深さを選ぶ ── cpuidle と tickless
C-stateの選択は cpuidle サブシステムが担います。コアがアイドルに入るとき、cpuidleガバナは「次に割り込みが来るまでどれくらい眠れそうか(予測滞在時間)」を見積もり、その時間が深いC-stateのexit latencyに見合うかを判断します。短時間しか眠れないなら浅いC-state、長く眠れるなら深いC-stateを選びます。深いほど復帰コストが高いので、滞在が短いと「眠った瞬間に起こされて損」になるためです。
ここで効いてくるのが tickless です。従来は周期タイマ割り込み(tick)が HZ 回/秒で律儀に入るため、せっかく深く眠ってもtickで何度も起こされ、深いC-stateに長く滞在できませんでした。tickless(NO_HZ_IDLE)はアイドル中の周期tickを止めるので、次に本当に必要なイベント(タイマ満了や割り込み)まで連続して眠れます。これがC-stateの効果を引き出す前提です。tickを止めても時刻は連続カウンタ(clocksource)が握るので失われない、という仕組みは /os/kernel-timekeeping-timers/ で扱ったとおりです。
アイドル進入時の判断(cpuidle):
予測滞在時間を見積もる(次タイマ・過去の割り込み傾向から)
for 深い順に各 C-state:
if 予測滞在時間 > その state の(exit latency に見合うしきい値):
その C-state を選んで眠る; break
tickless が無いと予測滞在時間は最大 1 tick で頭打ちになり
深い C-state を選べない → 省電力が効かない
電力と応答性のトレードオフを設計する
ここまでの二軸は、最終的に電力 対 応答性という一つの綱引きに収束します。深いC-stateは待機電力を大きく削りますが、exit latencyのぶん、割り込みやタスク起床への反応が遅れます。数十マイクロ秒のexit latencyは、Webサーバーの平均応答にはほぼ無視できますが、低遅延が要求される用途(高頻度取引、リアルタイム制御、パケット処理のホットパス)では致命的になり得ます。
| 狙い | P-state方針 | C-state方針 | 代償 |
|---|---|---|---|
| 最大スループット | performance固定 | 深いidle許可 | ピーク電力・発熱が高い |
| バッテリ最優先 | schedutil(低めに追従) | 最深まで許可 | 応答に復帰遅延が乗る |
| 低遅延・確定性 | performance寄り | 浅いC-stateに制限 | 待機電力が増える |
| 汎用バランス | schedutil | cpuidle自動 | 極端な要件には未最適 |
設計判断の要点は三つです。第一に、確定的な低遅延が要るなら深いアイドルを禁止する。cpuidle の最大深度を制限したり、busy-pollで意図的にアイドルへ入れない構成にします。第二に、スループット最優先なら周波数を高く保つ。ただしサーマルスロットリング(温度上限で強制的に周波数が落ちる現象)に達すると逆効果なので、冷却が前提です。第三に、多くの汎用ワークロードでは schedutil + cpuidle 自動が最良点で、無理な固定はかえって損をします。
レイテンシ障害の調査で「省電力を全部オフ」にしがちですが、これは諸刃です。深いC-stateを禁止すると最悪レイテンシは安定しますが、コアが常に温まったまま発熱が増え、サーマルスロットリングでかえって周波数が落ちて遅くなることがあります。さらに、周波数を最高固定にしても、応答性の本丸が「割り込み後にCPUを得るまでの遅れ」なら効きません。その遅れの源はプリエンプション設計(/os/kernel-preemption/)であり、締め切り保証が要るなら /os/realtime-scheduling/ の枠組みで考えるべきです。電力設定はレイテンシ要因の一つにすぎません。
まとめ
- 省電力は**P-state(動作中の電圧・周波数=DVFS)とC-state(アイドル中の停止深度)**という独立した二軸で、混同しないことが原理理解の起点。動的電力は電圧の2乗×周波数に効くので、電圧と周波数を同時に下げるDVFSが有効。
- 周波数選択は cpufreq ガバナが担い、schedutil はスケジューラの負荷追跡(PELT)を直接使うため、サンプリング遅延のあった ondemand より反応が速く無駄が少ない。目標に余裕係数を掛けるのは応答性確保のため。
- 停止深度は cpuidle が予測滞在時間と exit latency を比べて選ぶ。深いC-stateは省電力だが復帰が遅く、tickless(NO_HZ_IDLE)でtickを止めて初めて長く滞在できる。
- すべては電力 対 応答性の綱引きに収束する。確定的低遅延なら深いアイドルを制限、スループット最優先なら周波数を高く保つ(ただしサーマルスロットリング注意)、汎用なら schedutil+自動が最良点。
- 省電力を切れば速くなるとは限らない。発熱増→スロットリングや、応答の本丸がプリエンプション(/os/kernel-preemption/)・締め切り保証(/os/realtime-scheduling/)側にある場合は効かない。
OS Article
省電力とCPU周波数・アイドル状態の管理を実務で読む
TL;DRは入口です。実際に選ぶ・使う段階では、何を解決するか、何と比較するか、導入後にどこで詰まるかまで見る必要があります。
解決すること
省電力
比較で見る軸
難易度: advanced / カテゴリ: OS / タグ数: 6
導入後に効く点
cpufreqガバナが周波数を選ぶ。schedutilはスケジューラの負荷追跡(PELT)を直接使い、旧来のondemandより応答が速く無駄が少ない。
先に潰すリスク
用語だけ覚えても、設計・実装・運用でどこに効くかを確認しないと判断を誤る。
- 難易度
- advanced
- カテゴリ
- OS
- タグ数
- 6
判断チェックリスト
- 自社の用途が「省電力 / DVFS」に近いか確認する。
- 強みである「P-state(DVFS)は動作中の電圧と周波数を下げて性能あたりの電力を削る軸、C-stateは仕事がない間にコアを段階的に止めて漏れ電力を削る軸で、別物。」が本当に評価軸になるか確認する。
- 注意点の「用語だけ覚えても、設計・実装・運用でどこに効くかを確認しないと判断を誤る。」を運用で吸収できるか確認する。
- 公開値や仕様値は、対象プラン・対象機種・対象リージョンまで確認する。
- 既存システム、ID、ネットワーク、監視、バックアップとの接続方法を先に洗い出す。
- 小さく試してから、本番移行、権限設計、障害時手順、コスト監視を決める。