第一百五十一章:电源管理
合道期涉及内核源码:
一
林小源走出钟楼,面前出现了一片幽暗的区域。这里的设备大多处于低功耗状态——光幕暗淡,传送带缓慢,处理器核心只有一盏微弱的指示灯在闪烁。
一个穿着黑色斗篷的身影从阴影中走出。他的斗篷上绣着一颗电池的图案,电池的电量只剩最后一格。
"我是电源管理。"他的声音低沉而平静,"我的工作是让系统在空闲时尽可能少地消耗能量。"
他抬起手,指向远处的一排设备。那些设备正在逐一熄灭——指示灯从亮变暗,风扇从快变慢,最终完全静止。
"这就是 suspend-to-RAM——内存休眠。"电源管理说,"设备状态保存到内存里,CPU 停止,只有内存还在通电维持数据。整个系统的功耗降到最低。"
林小源感到周围的温度在下降——设备关闭后,热量的来源减少了。空气中弥漫着一种寂静,像是整个世界都屏住了呼吸。
"如果内存也断电了呢?"林小源问。
"那就是 suspend-to-disk——磁盘休眠。"电源管理走到一面石壁前,石壁上刻着休眠流程图,"状态保存到磁盘,然后彻底断电。唤醒时从磁盘恢复——像是一场漫长的冬眠后醒来。"
林小源看着那些逐一熄灭的设备,心想:让系统该睡就睡,也是一门本事。
/*
* 电源管理:
*
* 1. 系统休眠 (suspend)
* 内存休眠 (suspend-to-RAM)
* 磁盘休眠 (suspend-to-disk)
*
* 2. 设备电源管理
* runtime PM — 设备级电源管理
* 设备空闲时自动关闭
*
* 3. CPU 频率调节
* cpufreq — 动态调整 CPU 频率
* 空闲时降频省电
*
* 休眠流程:
* 冻结进程 → 设备挂起 → CPU 停止 → 保存状态
* 唤醒: 恢复状态 → CPU 启动 → 设备恢复 → 解冻进程
*/
printf("=== 电源管理 — 节能的机制 ===\n\n");
printf("电源管理:\n\n");
printf("1. 系统休眠:\n");
printf(" suspend-to-RAM (内存休眠)\n");
printf(" suspend-to-disk (磁盘休眠)\n\n");
printf("2. 设备电源管理:\n");
printf(" runtime PM\n");
printf(" 设备空闲时自动关闭\n\n");
printf("3. CPU 频率调节:\n");
printf(" cpufreq\n");
printf(" 动态调整 CPU 频率\n\n");
printf("--- 休眠流程 ---\n");
printf("休眠:\n");
printf(" 冻结进程\n");
printf(" → 设备挂起\n");
printf(" → CPU 停止\n");
printf(" → 保存状态\n\n");
printf("唤醒:\n");
printf(" 恢复状态\n");
printf(" → CPU 启动\n");
printf(" → 设备恢复\n");
printf(" → 解冻进程\n\n");
printf("--- runtime PM ---\n");
printf("设备级电源管理:\n");
printf(" 设备空闲时自动关闭\n");
printf(" 使用时自动开启\n\n");
printf("pm_runtime_get_sync(dev):\n");
printf(" 增加引用计数\n");
printf(" 如果设备关闭则开启\n\n");
printf("pm_runtime_put(dev):\n");
printf(" 减少引用计数\n");
printf(" 如果计数为零则关闭\n\n");
printf("--- cpufreq ---\n");
printf("动态调整 CPU 频率:\n");
printf(" 空闲时降频省电\n");
printf(" 负载高时升频\n\n");
printf("查看:\n");
printf(" cat /sys/devices/system/cpu/cpu0/cpufreq/scaling_cur_freq\n");#include <stdio.h>
/*
* 电源管理:
*
* 1. 系统休眠 (suspend)
* 内存休眠 (suspend-to-RAM)
* 磁盘休眠 (suspend-to-disk)
*
* 2. 设备电源管理
* runtime PM — 设备级电源管理
* 设备空闲时自动关闭
*
* 3. CPU 频率调节
* cpufreq — 动态调整 CPU 频率
* 空闲时降频省电
*
* 休眠流程:
* 冻结进程 → 设备挂起 → CPU 停止 → 保存状态
* 唤醒: 恢复状态 → CPU 启动 → 设备恢复 → 解冻进程
*/
int main() {
printf("=== 电源管理 — 节能的机制 ===\n\n");
printf("电源管理:\n\n");
printf("1. 系统休眠:\n");
printf(" suspend-to-RAM (内存休眠)\n");
printf(" suspend-to-disk (磁盘休眠)\n\n");
printf("2. 设备电源管理:\n");
printf(" runtime PM\n");
printf(" 设备空闲时自动关闭\n\n");
printf("3. CPU 频率调节:\n");
printf(" cpufreq\n");
printf(" 动态调整 CPU 频率\n\n");
printf("--- 休眠流程 ---\n");
printf("休眠:\n");
printf(" 冻结进程\n");
printf(" → 设备挂起\n");
printf(" → CPU 停止\n");
printf(" → 保存状态\n\n");
printf("唤醒:\n");
printf(" 恢复状态\n");
printf(" → CPU 启动\n");
printf(" → 设备恢复\n");
printf(" → 解冻进程\n\n");
printf("--- runtime PM ---\n");
printf("设备级电源管理:\n");
printf(" 设备空闲时自动关闭\n");
printf(" 使用时自动开启\n\n");
printf("pm_runtime_get_sync(dev):\n");
printf(" 增加引用计数\n");
printf(" 如果设备关闭则开启\n\n");
printf("pm_runtime_put(dev):\n");
printf(" 减少引用计数\n");
printf(" 如果计数为零则关闭\n\n");
printf("--- cpufreq ---\n");
printf("动态调整 CPU 频率:\n");
printf(" 空闲时降频省电\n");
printf(" 负载高时升频\n\n");
printf("查看:\n");
printf(" cat /sys/devices/system/cpu/cpu0/cpufreq/scaling_cur_freq\n");
return 0;
}二
林小源跟随电源管理走进了设备区域的内部。一个网卡设备正在发送数据——它的指示灯亮着,功耗较高。但当最后一个数据包发出后,指示灯开始闪烁,然后渐渐暗了下去。
"这是 runtime PM,"电源管理说,"设备有自己的电源状态。当它不再被使用时,引用计数降为零,我会自动把它关闭。下次有人要用它时,再自动唤醒。"
林小源看到网卡上有一个小小的计数器。每有一个驱动在使用它,计数器加一;用完了,计数器减一。当计数器归零的那一刻,网卡的电源被切断,整个设备沉入了睡眠。
"如果一个驱动忘了释放引用呢?"林小源问。
电源管理的表情变得严肃:"那设备就永远不会关闭——白白浪费电。这就是为什么驱动必须在用完设备后调用 pm_runtime_put()。引用计数是 runtime PM 的核心——多一个引用就多一份责任。"
林小源看到远处有一个 USB 控制器,它的引用计数在不断跳动——有设备连接时上升,设备断开时下降。控制器的功耗随着计数器的变化而起伏,像是一颗有节律跳动的心脏。
"runtime PM 的好处是不需要用户干预,"电源管理说,"你插入 U 盘,控制器自动唤醒;拔出 U 盘,控制器自动睡眠。一切都是自动的。"
他算是看明白了,runtime PM 的精髓就是自动化——不用人为干预,设备自己知道什么时候该睡、什么时候该醒。
三
在设备区域的尽头,林小源看到了 CPU 频率调节的控制台。控制台上有几个巨大的旋钮,每个旋钮对应一个 CPU 核心。旋钮的刻度从最低频率到最高频率,当前指针的位置随着 CPU 的负载在实时变化。
"这是 cpufreq。"电源管理走到一个旋钮旁,轻轻转动它。对应的 CPU 核心立刻从低频切到高频,风扇转速也跟着上升。
"负载低的时候,CPU 降频省电。负载高的时候,CPU 升频保性能。"电源管理松开旋钮,让它自己回弹,"但频率切换不是免费的——有延迟,有功耗波动。所以 cpufreq 有多种调度策略:ondemand 看负载即时调整,conservative 温和调整,performance 始终最高频,powersave 始终最低频。"
林小源看着旋钮上的指针在低频和高频之间来回摆动。当他模拟高负载时,指针猛地上升,CPU 核心发出低沉的轰鸣;当他停止负载时,指针缓慢回落,轰鸣声渐渐消失。
"平衡——这就是电源管理的本质。"电源管理说,"你不能让系统一直满负荷运转,也不能让它在需要性能时还省电。找到那个平衡点,就是我的工作。"
林小源低头看了看自己手中的灵力——如果把灵力比作电力,那修炼者也需要在消耗和恢复之间找到平衡。这道理,修仙界和内核世界是一样的。
电源管理的本质就是动态平衡——不能一直满负荷跑,也不能在需要性能时还省电。
道藏笔记
内核启示
电源管理干的事说白了就一句话:不用的时候省着点。系统级的休眠分两种,suspend-to-RAM 把状态存内存、CPU 停机,只剩内存通电;suspend-to-disk 更彻底,状态存磁盘后彻底断电。设备级的 runtime PM 更精细——每个设备有自己的引用计数,没人用就自动断电,有人用就自动唤醒,插个 U 盘控制器自动醒来,拔掉又自动睡去。CPU 频率调节是另一招,负载低时降频省电,负载高时升频保性能。ondemand 看负载即时调整,conservative 温和调整,performance 和 powersave 走极端。这些机制加在一起,就是让系统在性能和功耗之间找到那个最合适的平衡点。
电源管理之试
设备空闲时自动关闭、使用时自动唤醒的设备级电源管理机制叫什么?