【原創】Linux Suspend流程分析


背景

  • Read the fucking source code! --By 魯迅
  • A picture is worth a thousand words. --By 高爾基

說明:

  1. Kernel版本:4.14
  2. ARM64處理器
  3. 使用工具:Source Insight 3.5, Visio

1. 介紹

Linux Kernel支持四種Sleep State

  • Suspend-to-Idle
    純軟件,輕量級的Suspend操作,它會freeze user spacesuspend the timekeepingput all I/O devices into low-power states
    處於S2Idle狀態下時,設備中斷就可以將其喚醒。

  • Standby
    除了實現Suspend-to-Idle時的操作外,還會將nonboot CPUs置於offline狀態,以及suspend all low-level system functions。由於系統核心邏輯單元保持上電狀態,操作的狀態不會丟失,也會很容易恢復到之前的狀態。
    處於Standby狀態時,可能需要依賴平台來設置喚醒源。

  • Suspend-to-RAM
    STR/S2RAM時,除了Memory需要進行自刷新來保持數據外,其他的所有設備都需要進入到低功耗狀態。除了實現Standby中的操作外,還有一些平台相關的操作要進行。比如,在STR的最后一步,將控制權交給Firmware,然后下電,等着喚醒時再重新Resume回來。由於存在掉電行為,因此Resume的時候需要重新進行配置。
    處於STR狀態時,需要依賴平台設置喚醒源。
    本文主要分析的流程就是STR

  • Hibernation
    Suspend-to-Disk, STD,簡而言之,這個操作會將運行時的context保存在Disk這種非易失的存儲器中,然后進行掉電操作。當按下電源鍵進行喚醒時,Firmware/Uboot會將保存的context進行恢復。

上述四個狀態,功耗節省效果依次增強,同時喚醒回來的時間開銷也相應加大。

2. 流程

通過/sys接口可以觸發Suspend流程:

  • cat /sys/power/state:查看支持的操作,比如:freeze, mem
  • echo mem > /sys/power/state:進行STR操作;
  • echo freeze > /sys/power/state:進行S2Idle操作;

代碼路徑:
kernel/power/main.c
kernel/power/suspend.c

STR流程如下圖,入口函數為pm_suspend

簡而言之,這是一張信息量很大的圖片,涵蓋了Suspend To Ram的整個流程。
圖片中,從上到下涉及到進程的freeze,各種設備驅動的Suspend,平台的Suspend,CPU的Offline操作,syscore的Suspend操作。其中涉及到CPU的操作時,在ARMv8中,會通過PSCI接口調用到ARM Trusted Firmware, ATF,這個在【原創】Linux PSCI框架探討過。
多說無益,看圖吧。

3. process freeze

Suspend過程中,有一個函數suspend_freeze_processes引起了我的好奇心,我刻意分析了下。在Suspend的時候是需要將用戶進程和內核線程freeze掉,避免它們來搗亂,比如你在Suspend某個驅動的時候,此時用戶還在使用該驅動的資源,這時候可能就會引起問題了。不過,內核線程並不是所有的都能freeze掉。
記住兩個知識點:

  • 用戶線程的freeze是通過發送信號來觸發執行的;
  • 內核線程的freeze是通過主動調用函數觸發的;

具體還是看圖吧:

進程的操作比較復雜,以后在研究進程管理的時候再分析。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM