2.软文推荐
3.软文推荐
1、Linux 电源管理的组成电源管理(Power Management)在 Linux Kernel 中,是一个比较庞大的子系统,涉及到供电(Power Supply)、充电(Charger)、时钟(Clock)、频率(Frequency)、电压(Voltage)、睡眠/唤醒(Suspend/Resume)等方方面面。
注1:该图片只是一个示意图,并没有划分软件层次,因此模块之间的关系不一定是真正的关系。
注2:Framework 是一个中间层的软件,提供软件开发的框架。其目有三:一是屏蔽具体的实现细节,固定对上的接口,这样可以方便上层软件的开发和维护;二是尽可能抽象公共逻辑,并在 Framework 内实现,以提高重用性、减少开发量;三是向下层提供一系列的回调函数(callback function),下层软件可能面对差别较大的现实,但只要填充这些回调函数,即可完成所有逻辑,减小了开发的难度。
注3:Runtime PM 是 Linux Kernel 亲生的运行时电源管理机制,Wakelock 是由 Android 提出的机制。这两种机制的目的是一样的,因此只需要支持一种即可。另外,由于 Wakelock 机制路子太野了,饱受 Linux 社区的鄙视。
在对图片中的这些组件(也可以称作 Framework )进行详细描述之前,先在这里了解一下基本概念。
kernel/power/
drivers/power/
drivers/base/power/
drivers/cpuidle/
drivers/cpufreq/
drivers/devfreq/
include/linux/power_supply.h
include/linux/cpuidle.h
include/linux/cpufreq.h
include/linux/cpu_pm.h
include/linux/device.h
include/linux/pm.h
include/linux/pm_domain.h
include/linux/pm_runtime.h
include/linux/pm_wakeup.h
include/linux/qos.h
include/linux/suspend.h
Documentation/power/xxx.txt
电源管理的东西很多,大家没必要每个都学一遍,用到的时候去研究即可。
3、实例分析最近博主遇到 i2c 传输慢和中断触发慢的问题,一般这种【慢】的情况大都和【性能与功耗冲突】相关,研究了 Qos 系统,打了笔 patch 解决了。
中断触发慢:注册的下降沿中断,从下降沿打到芯片中,到跑到中断处理函数,快则 270us,慢则 2.7ms。由于所做功能对中断处理时间有要求,因此要解决中断处理慢的问题。
抓 trace 分析使用上次博主发的脚本,可以抓到 ftrace,这个脚本中博主使能了 sched_switch、sched_wakeup、irq、irq_handler_entry、irq_handler_exit、cpu_idle、pm_qos_update_request 等 event。这些 event 可以记录下 CPU 调度和中断处理情况。
从抓到的 trace 分析,中断处理慢并不是由于 CPU loading 重导致的处理不及时,而是中断来的时候,CPU0 处于 idle 状态,而 kernel-5.10 以后除了特定的 feature,所有的中断都默认发到 CPU0,这样即便设置了中断可以唤醒系统,把 CPU0 从 idle 转为 active 也要 1ms。
问题确定后,就是如何处理的问题了。找了低功耗的同事,确认 CPU 在没事情做的时候就是会进入 idle,即便在游戏场景,也不会禁止 CPU 进入 idle。
研究了一下 Linux 电源管理子系统,发现 Qos 有接口可以使用:在某一段时间内拉 Qos,可以让 CPU 在这段时间不进入 idle,使用完毕再去掉 Qos,让 CPU 可以进入 idle,这样满足了性能需求,带来的功耗也不是特别高。
PM QoS classes framework 位于 kernel/power/qos.c 中,负责系统级别的 PM QoS 管理。per-device PM QoS framework 位于 drivers/base/power/qos.c 中,负责 per-device 的 PM QoS 管理。Common header 位于 include/linux/pm_qos.h 中,负责通用数据结构的抽象、函数声明等工作。
在 kernel/power/qos.c 中,有 cpu_latency_qos_update_request 接口可以使用,通过该接口将 Qos 拉到 150,使用完毕再将 Qos 拉到 -1(关闭)。
使用方法:
1、文件开头注册自己的结构体:
struct pm_qos_request my_qos_request;
2、自己驱动的 probe 函数加上:
cpu_latency_qos_add_request(my_qos_request, PM_QOS_DEFAULT_VALUE);
3、在做事情前加上:
cpu_latency_qos_update_request(my_qos_request, 150);
4、在做事情后加上:
cpu_latency_qos_update_request(my_qos_request, PM_QOS_DEFAULT_VALUE);
PM_QOS_DEFAULT_VALUE 其实就是 -1
这样在自己做事情期间,CPU 就不会进入 idle,自己模块的性能就会好很多。如果还要更好,可以在此期间调节 CPU 频率,但调频带来的功耗很高,需要自己评估。
该 patch 解决的问题:1、中断处理慢,可以在第一次中断打进来后,拉 Qos,这样自己后面的几次中断处理一定会快,使用完毕后,去掉 Qos。
2、i2c 传输慢,其中一种情况是 i2c 传输完毕返回时,CPU0 进入 idle,导致 i2c 中断打不进来,详情参考我的文章(背景:设置 i2c 中断无法唤醒系统):
本文来源:www.lxlinux.net/12671.html,若引用不当,请联系修改。

立即
返回
1
目录:1、VPS和虚拟主机的区别是什么?2、VPS和普通主机有什么区别啊3、VPS是什么,一台VPS大约多少钱4、VPS、虚拟机、云主机,这三个到底...