Android中Linux睡眠唤醒流程

原创 2012年03月27日 16:39:55

-----------------------------------------------------------------------
本文系本站原创,欢迎转载!
转载请注明出处:http://blog.csdn.net/android_huber
交流邮箱:dp.shao@gmail.com
-----------------------------------------------------------------------



        上层 echo on > /sys/power/state 或者 echo mem > /sys/power/state对系统的电源管理进行控制,首先看echo mem > /sys/power/state会进入reauest_suspend_state(state)然后如果是on的话进入late_resume_work(在执行late_resume_work之前会向系统申请main_wake_lock,如果是mem进入early_suspend_work。下面分析early_suspend_work,这个工作队列的执行函数是early_suspend(),在这个函数里会遍历early_suspend_handlers,依次执行里面的early_suspend函数,执行完所有的early_suspend后,释放main_wake_lock,进入wake_unlock函数。对于一个lock进入wake_unlock,首先会将lock从原链表中删除(active_wake_locks),然后加入inactive_locks链表中。对于释放锁,上面两个过程就结束了,但是如果这个锁的类型是WAKE_LOCK_SUSPEND,那么还需要执行一些操作,判断是否可以进入睡眠。首先调has_wake_lock_locked(type)去查找是否还有这种类型的锁,会遍历active_wake_locks[type]链表,如果在这个链表中一检测中有锁,而且该锁不是超时锁,那么就返回-1。如果是超时锁,且已经超时了,那就去释放这个锁,如果没超时就得到一个max_timeout,然后返回max_timeout。接着就会回到wake_unlock函数中,调用mod_timer(&expire_timer,jiffies +has_lock);hsa_lock就是前面返回的max_timeout,这句话的意思就是向系统中再添加定时器,定时时间就是最大的超时时间.expire_timer的操作函数是expire_wake_locks,这里会去检测还有没有锁,没有的话就进入suspend_work,执行suspend,进入睡眠流程。上面wake_unlock中如果没有检测到锁,也会执行suspend。在suspend函数中又会通过has_wake_lock去检测有没有锁,有锁就直接返回。

        suspend函数中,通过pm_suspend(requested_suspend_state)进入suspend操作。这个里面也有唤醒操作,只有等唤醒后才会跳出pm_suspend,跳出后会打印logsuspend:exit suspend, ret =pm_suspend就是判断传入的state是否符合suspend,符合就调用enter_state(state),到现在开始才进入了linux标准的suspend流程。

        enter_state这个函数主要有三个函数调用,分别是suspend_prepare,suspend_devices_and_enter,

suspend_finish。suspend_prepare做一些睡眠的准备工作suspend_devices_and_enter就是真正的设备进入睡眠

suspend_finish唤醒后进行的操作。

        下面来一个一个分析:

        suspend_prepare中首先通过pm_prepare_console,给suspend分配一个虚拟终端来输出信息;接着通过pm_notifier_call_chain来广播一个系统进入suspend的通报;关闭用户态的helper进程;最后通过suspend_freeze_processes来冻结用户态进程,最后会尝试释放一些内存。在suspend_freeze_processes()函数中调用了freeze_processes()函数,而freeze_processes()函数中又调用了try_to_freeze_tasks()来完成冻结任务。在冻结过程中,会判断当前进程是否有wake_lock,若有,则冻结失败,函数会放弃冻结。执行完上面的操作后再次回到enter_state函数中,下面开始调用suspend_devices_and_enter()函数让外设进入休眠。在suspend_devices_and_enter()中首先调用关于平台的suspend_ops->begin,接着通过suspend_console来关闭console,也可以通过改变一个flag来使这个函数无效。接着调用dpm_suspend_startdpm_suspend_start中会执行device_preparedevice_suspend,这两个函数都是调用pm接口里的preparesuspend函数(其实这里就开始通过总线的接口来执行驱动的suspend函数了,通过bus->pm->suspend)。接着回到suspend_devices_and_enter中调用suspend_enter(state);suspend_enter中,首先调用平台相关的suspend_ops->prepare,接着执行dpm_suspend_noirq()调用pm接口里的

pm->suspend_noirq,回到suspend_enter,接着调用suspend_ops->prepare_late,接下来多cpu中非启动的cpu通过函数disable_nonboot_cpus()被关闭,然后通过调用arch_suspend_disable_irqs()关闭本地中断。再后来才到睡眠设备的操作,sysdev_suspend(PMSG_SUSPEND),这样就会进入sysdev_driver.suspend阶段。最后调用suspend_ops->enter()这里就开始执行到睡眠的最后一步了,执行平台相关的睡眠。在平台睡眠的代码中主要是通过suspend_in_iram(suspend_param1)来执行一段汇编代码,最终在汇编中睡死。唤醒的步骤与睡眠的步骤相反,cpu有电后会首先从汇编中起来,接着回到suspend_enter函数中,执行suspend_ops->enter()返回后的一些唤醒代码,这边就不再去说了,基本是按照上面的逆序来操作的。



唤醒

        唤醒的时候,程序从suspend_devices_and_enter函数中出来后,开始执行suspend_finish,接着就会从enter_state中退出来,返回pm_suspend,然后又从pm_suspend返回到wakelock.c中的suspend(),在这里接下来就会打印出”suspend:exit suspend, ret“这些log。

下面是我画的一张睡眠唤醒的流程图,唤醒部分走的是虚线部分。 要是图看不全的话可以保存在本地方便放大了看喔。



需要清晰大图的请至下面网址下载

http://download.csdn.net/detail/android_huber/8537239

android 休眠唤醒机制分析(三) — suspend

前面我们分析了休眠的第一个阶段即浅度休眠,现在我们继续看休眠的第二个阶段 — 深度休眠。在深度休眠的过程中系统会首先冻结所有可以冻结的进程,然后依次挂起所有设备的电源,挂起顺序与设备注册的顺序相反,这...

Android (Linux) Suspend流程

分类: Linux驱动 Android待机唤醒2013-04-23 08:48 1523人阅读 评论(0) 收藏 举报 目录(?)[+] 1. Linux Suspend简...

Linux电源管理-Suspend/Resume流程

前言 根据上一节linux电源管理-概述可知,linux电源管理存在的几种方式,如何查看这几种方式,以及最后的如何睡眠唤醒等。 通过echo mem > /sys/power/state就可以达到睡眠...

linux下休眠/待机命令

if you # cat /sys/power/state mem disk you can echo “mem” > /sys/power/state 这相当于待机 echo “disk”...
  • hshl1214
  • hshl1214
  • 2011年03月07日 10:21
  • 48502

Android睡眠唤醒机制--Kernel态

一、简介       Android系统中定义了几种低功耗状态:earlysuspend、suspend、hibernation.       1) earlysuspend: 是一种低功耗的状态...
  • MyArrow
  • MyArrow
  • 2012年11月01日 14:47
  • 26427

Android 功耗问题debug处理(主要是睡眠时“大”电流问题的debug方法示例)

1. 在手机进入sleep后,被上层apk唤醒的debug方法 请抓取相应的待机的mobilelog, 从kernel_log中分析, 如果log中可以查找到 wake up by RTC 请在相应的...

基于android5.1休眠唤醒流程

1.用户态睡眠流程 framework/base/services/core/java/com/android/server/power/PowerManagerService.java upda...

Android中Linux睡眠唤醒流程

上层 echo on > /sys/power/state 或者 echo mem > /sys/power/state对系统的电源管理进行控制,首先看echo mem > /sys/power/...

Android/linux(earlysuspend、lateresume)睡眠唤醒机制简介

本文属于原创!!如要转载,请注明来源处 http://blog.sina.com.cn/s/blog_759dc36b0100stax.html   背景介绍: 睡眠/唤醒是嵌入式Linu...

Linux睡眠唤醒机制--Kernel态

一、对于休眠(suspend)的简单介绍    在Linux中,休眠主要分三个主要的步骤:    1) 冻结用户态进程和内核态任务    2) 调用注册的设备的suspend的回调函数, 顺序是...
  • MyArrow
  • MyArrow
  • 2012年11月01日 11:54
  • 12584
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:Android中Linux睡眠唤醒流程
举报原因:
原因补充:

(最多只允许输入30个字)