一.前言
Linux的RPM(Runtime power management)框架,是一套运行时电源管理框架,为系统中所有的device提供了一种运行时电源管理的机制。其目的很明确——减少系统运行时的功耗;方式也很简单:由各个驱动自己决定,具体何时将对应的device关闭或打开。和传统的系统休眠唤醒式的电源管理相比,RPM采取的是分而治之的管理思想,将具体的控制策略和控制权力下放到各个驱动;而传统的电源管理,则采取的是中央集权式的管理方法,由Linux suspend / resume机制在合适的时机统一执行设备的休眠和唤醒动作。
当然,RPM框架和PM domain框架存在很强的耦合关系,在具体介绍RPM的实现时,本文同时也会粗略介绍 Linux的PM domain框架。
二.RPM软件框图和使用方法
RPM软件框图如下所示:
由上图可以看出,对于驱动开发者而言,使用RPM很简单:
2.1 RPM在driver中的使能
在驱动对设备进行初始化时,调用pm_rumtime_enable(),使能设备的runtime pm功能。对应的API如下所示:
void pm_runtime_enable(struct device *dev);
2.2 RPM get 操作
当driver认为其设备需要进行工作(打开)时,调用pm_rumtime_get()/ pm_rumtime_get_sync (),向RPM core上报设备状态为开,若条件满足,RPM core会执行到driver的runtime_resume回调函数,配置设备为工作的状态。对应的API如下所示:
static inline int pm_runtime_get(struct device *dev);
static inline int pm_runtime_get_sync(struct device *dev);
可以从名字看出,以上两个API的区别,在于pm_rumtime_get()用于异步操作,而pm_rumtime_get_sync ()用于同步操作。如果你期望在执行get操作后立马访问设备,那么这里推荐你使用pm_rumtime_get_sync ()接口,因为pm_rumtime_get()接口会把一些核心的操作放到一个工作队列(workqueue)中延后执行。//TODO,学习工作队列的原理
2.3 RPM put 操作
当driver认为其设备不需要进行工作(关闭)时,则调用pm_rumtime_put()/ pm_rumtime_put_sync (),向RPM core上报设备状态为关,若条件满足,RPM core会执行到driver的runtime_suspend回调函数,配置设备为关闭的状态。对应的API如下所示:
static inline int pm_runtime_put(struct device *dev);
static inline int pm_runtime_put_sync(struct device *dev);