← Documents Documentation/admin-guide/pm/suspend-flows.rst GitHub 원문 ↗

Linux 6.18.37 · Administration / Power Management

System Suspend Code Flows

Suspend-to-Idle과 platform-dependent suspend/resume의 task, device, IRQ, CPU, firmware 단계 순서를 설명합니다.

Source pathDocumentation/admin-guide/pm/suspend-flows.rst
Source versionLinux v6.18.37
TranslationDUJINLABS 전문 번역 + 해설

요약·해설과 원문, 전문 번역을 서로 분리했습니다. API 이름, symbol, source path는 원문 표기를 사용합니다.

1. 요약·해설

원문의 핵심 논리와 kernel programming 관점의 보충 설명입니다. 아래의 전문 번역과는 별도로 작성했습니다.

요약과 해설

suspend-flows.rst:1-270

Suspend flow는 외부 활동을 단계적으로 차단하고 resume flow는 이를 역순에 가깝게 복구합니다. S2Idle은 armed IRQ와 CPU idle state를 사용하고, platform-dependent suspend는 CPU hotplug와 firmware hook까지 사용합니다.

Device callback은 suspend와 resume에서 각각 네 phase로 나뉩니다. Runtime PM과 IRQ handler의 활성 시점이 phase 경계에 묶여 있으므로 driver callback 순서를 바꾸면 안 됩니다.

흐름핵심 순서
S2Idle suspendNotifier → task freeze → device/IRQ suspend → tick·timekeeping freeze
S2Idle resumeTimekeeping/tick → device/IRQ → task thaw → notifier
Platform suspendS2Idle 앞단 + nonboot CPU offline → core suspend → platform power removal
Platform resumePlatform wakeup → core → CPU online → device/IRQ → task → notifier
Device suspend phases`prepare`, `suspend`, `late suspend`, `noirq suspend`
Device resume phases`noirq resume`, `early resume`, `resume`, `complete`
WakeupS2Idle은 armed IRQ, platform suspend는 platform-specific wakeup source
핵심 제약Platform firmware hook 실행 전 one-CPU configuration이 필요할 수 있음

2. 영어 원문 전체

번역 기준이 된 Linux v6.18.37 원문입니다. 줄 번호는 이 버전의 파일 좌표입니다.

원문 전체 펼치기
1 .. SPDX-License-Identifier: GPL-2.0
2 .. include:: <isonum.txt>
3
4 =========================
5 System Suspend Code Flows
6 =========================
7
8 :Copyright: |copy| 2020 Intel Corporation
9
10 :Author: Rafael J. Wysocki <[email protected]>
11
12 At least one global system-wide transition needs to be carried out for the
13 system to get from the working state into one of the supported
14 :doc:`sleep states <sleep-states>`. Hibernation requires more than one
15 transition to occur for this purpose, but the other sleep states, commonly
16 referred to as *system-wide suspend* (or simply *system suspend*) states, need
17 only one.
18
19 For those sleep states, the transition from the working state of the system into
20 the target sleep state is referred to as *system suspend* too (in the majority
21 of cases, whether this means a transition or a sleep state of the system should
22 be clear from the context) and the transition back from the sleep state into the
23 working state is referred to as *system resume*.
24
25 The kernel code flows associated with the suspend and resume transitions for
26 different sleep states of the system are quite similar, but there are some
27 significant differences between the :ref:`suspend-to-idle <s2idle>` code flows
28 and the code flows related to the :ref:`suspend-to-RAM <s2ram>` and
29 :ref:`standby <standby>` sleep states.
30
31 The :ref:`suspend-to-RAM <s2ram>` and :ref:`standby <standby>` sleep states
32 cannot be implemented without platform support and the difference between them
33 boils down to the platform-specific actions carried out by the suspend and
34 resume hooks that need to be provided by the platform driver to make them
35 available. Apart from that, the suspend and resume code flows for these sleep
36 states are mostly identical, so they both together will be referred to as
37 *platform-dependent suspend* states in what follows.
38
39
40 .. _s2idle_suspend:
41
42 Suspend-to-idle Suspend Code Flow
43 =================================
44
45 The following steps are taken in order to transition the system from the working
46 state to the :ref:`suspend-to-idle <s2idle>` sleep state:
47
48 1. Invoking system-wide suspend notifiers.
49
50 Kernel subsystems can register callbacks to be invoked when the suspend
51 transition is about to occur and when the resume transition has finished.
52
53 That allows them to prepare for the change of the system state and to clean
54 up after getting back to the working state.
55
56 2. Freezing tasks.
57
58 Tasks are frozen primarily in order to avoid unchecked hardware accesses
59 from user space through MMIO regions or I/O registers exposed directly to
60 it and to prevent user space from entering the kernel while the next step
61 of the transition is in progress (which might have been problematic for
62 various reasons).
63
64 All user space tasks are intercepted as though they were sent a signal and
65 put into uninterruptible sleep until the end of the subsequent system resume
66 transition.
67
68 The kernel threads that choose to be frozen during system suspend for
69 specific reasons are frozen subsequently, but they are not intercepted.
70 Instead, they are expected to periodically check whether or not they need
71 to be frozen and to put themselves into uninterruptible sleep if so. [Note,
72 however, that kernel threads can use locking and other concurrency controls
73 available in kernel space to synchronize themselves with system suspend and
74 resume, which can be much more precise than the freezing, so the latter is
75 not a recommended option for kernel threads.]
76
77 3. Suspending devices and reconfiguring IRQs.
78
79 Devices are suspended in four phases called *prepare*, *suspend*,
80 *late suspend* and *noirq suspend* (see :ref:`driverapi_pm_devices` for more
81 information on what exactly happens in each phase).
82
83 Every device is visited in each phase, but typically it is not physically
84 accessed in more than two of them.
85
86 The runtime PM API is disabled for every device during the *late* suspend
87 phase and high-level ("action") interrupt handlers are prevented from being
88 invoked before the *noirq* suspend phase.
89
90 Interrupts are still handled after that, but they are only acknowledged to
91 interrupt controllers without performing any device-specific actions that
92 would be triggered in the working state of the system (those actions are
93 deferred till the subsequent system resume transition as described
94 `below <s2idle_resume_>`_).
95
96 IRQs associated with system wakeup devices are "armed" so that the resume
97 transition of the system is started when one of them signals an event.
98
99 4. Freezing the scheduler tick and suspending timekeeping.
100
101 When all devices have been suspended, CPUs enter the idle loop and are put
102 into the deepest available idle state. While doing that, each of them
103 "freezes" its own scheduler tick so that the timer events associated with
104 the tick do not occur until the CPU is woken up by another interrupt source.
105
106 The last CPU to enter the idle state also stops the timekeeping which
107 (among other things) prevents high resolution timers from triggering going
108 forward until the first CPU that is woken up restarts the timekeeping.
109 That allows the CPUs to stay in the deep idle state relatively long in one
110 go.
111
112 From this point on, the CPUs can only be woken up by non-timer hardware
113 interrupts. If that happens, they go back to the idle state unless the
114 interrupt that woke up one of them comes from an IRQ that has been armed for
115 system wakeup, in which case the system resume transition is started.
116
117
118 .. _s2idle_resume:
119
120 Suspend-to-idle Resume Code Flow
121 ================================
122
123 The following steps are taken in order to transition the system from the
124 :ref:`suspend-to-idle <s2idle>` sleep state into the working state:
125
126 1. Resuming timekeeping and unfreezing the scheduler tick.
127
128 When one of the CPUs is woken up (by a non-timer hardware interrupt), it
129 leaves the idle state entered in the last step of the preceding suspend
130 transition, restarts the timekeeping (unless it has been restarted already
131 by another CPU that woke up earlier) and the scheduler tick on that CPU is
132 unfrozen.
133
134 If the interrupt that has woken up the CPU was armed for system wakeup,
135 the system resume transition begins.
136
137 2. Resuming devices and restoring the working-state configuration of IRQs.
138
139 Devices are resumed in four phases called *noirq resume*, *early resume*,
140 *resume* and *complete* (see :ref:`driverapi_pm_devices` for more
141 information on what exactly happens in each phase).
142
143 Every device is visited in each phase, but typically it is not physically
144 accessed in more than two of them.
145
146 The working-state configuration of IRQs is restored after the *noirq* resume
147 phase and the runtime PM API is re-enabled for every device whose driver
148 supports it during the *early* resume phase.
149
150 3. Thawing tasks.
151
152 Tasks frozen in step 2 of the preceding `suspend <s2idle_suspend_>`_
153 transition are "thawed", which means that they are woken up from the
154 uninterruptible sleep that they went into at that time and user space tasks
155 are allowed to exit the kernel.
156
157 4. Invoking system-wide resume notifiers.
158
159 This is analogous to step 1 of the `suspend <s2idle_suspend_>`_ transition
160 and the same set of callbacks is invoked at this point, but a different
161 "notification type" parameter value is passed to them.
162
163
164 Platform-dependent Suspend Code Flow
165 ====================================
166
167 The following steps are taken in order to transition the system from the working
168 state to platform-dependent suspend state:
169
170 1. Invoking system-wide suspend notifiers.
171
172 This step is the same as step 1 of the suspend-to-idle suspend transition
173 described `above <s2idle_suspend_>`_.
174
175 2. Freezing tasks.
176
177 This step is the same as step 2 of the suspend-to-idle suspend transition
178 described `above <s2idle_suspend_>`_.
179
180 3. Suspending devices and reconfiguring IRQs.
181
182 This step is analogous to step 3 of the suspend-to-idle suspend transition
183 described `above <s2idle_suspend_>`_, but the arming of IRQs for system
184 wakeup generally does not have any effect on the platform.
185
186 There are platforms that can go into a very deep low-power state internally
187 when all CPUs in them are in sufficiently deep idle states and all I/O
188 devices have been put into low-power states. On those platforms,
189 suspend-to-idle can reduce system power very effectively.
190
191 On the other platforms, however, low-level components (like interrupt
192 controllers) need to be turned off in a platform-specific way (implemented
193 in the hooks provided by the platform driver) to achieve comparable power
194 reduction.
195
196 That usually prevents in-band hardware interrupts from waking up the system,
197 which must be done in a special platform-dependent way. Then, the
198 configuration of system wakeup sources usually starts when system wakeup
199 devices are suspended and is finalized by the platform suspend hooks later
200 on.
201
202 4. Disabling non-boot CPUs.
203
204 On some platforms the suspend hooks mentioned above must run in a one-CPU
205 configuration of the system (in particular, the hardware cannot be accessed
206 by any code running in parallel with the platform suspend hooks that may,
207 and often do, trap into the platform firmware in order to finalize the
208 suspend transition).
209
210 For this reason, the CPU offline/online (CPU hotplug) framework is used
211 to take all of the CPUs in the system, except for one (the boot CPU),
212 offline (typically, the CPUs that have been taken offline go into deep idle
213 states).
214
215 This means that all tasks are migrated away from those CPUs and all IRQs are
216 rerouted to the only CPU that remains online.
217
218 5. Suspending core system components.
219
220 This prepares the core system components for (possibly) losing power going
221 forward and suspends the timekeeping.
222
223 6. Platform-specific power removal.
224
225 This is expected to remove power from all of the system components except
226 for the memory controller and RAM (in order to preserve the contents of the
227 latter) and some devices designated for system wakeup.
228
229 In many cases control is passed to the platform firmware which is expected
230 to finalize the suspend transition as needed.
231
232
233 Platform-dependent Resume Code Flow
234 ===================================
235
236 The following steps are taken in order to transition the system from a
237 platform-dependent suspend state into the working state:
238
239 1. Platform-specific system wakeup.
240
241 The platform is woken up by a signal from one of the designated system
242 wakeup devices (which need not be an in-band hardware interrupt) and
243 control is passed back to the kernel (the working configuration of the
244 platform may need to be restored by the platform firmware before the
245 kernel gets control again).
246
247 2. Resuming core system components.
248
249 The suspend-time configuration of the core system components is restored and
250 the timekeeping is resumed.
251
252 3. Re-enabling non-boot CPUs.
253
254 The CPUs disabled in step 4 of the preceding suspend transition are taken
255 back online and their suspend-time configuration is restored.
256
257 4. Resuming devices and restoring the working-state configuration of IRQs.
258
259 This step is the same as step 2 of the suspend-to-idle suspend transition
260 described `above <s2idle_resume_>`_.
261
262 5. Thawing tasks.
263
264 This step is the same as step 3 of the suspend-to-idle suspend transition
265 described `above <s2idle_resume_>`_.
266
267 6. Invoking system-wide resume notifiers.
268
269 This step is the same as step 4 of the suspend-to-idle suspend transition
270 described `above <s2idle_resume_>`_.
271

3. 한국어 전문 번역

영어 원문의 문단 순서와 의미를 유지한 전체 번역입니다. 코드, 함수명, symbol과 URL은 원문 표기를 유지합니다.

System suspend code flow 개요

1-39

이 문서는 `SPDX-License-Identifier: GPL-2.0`을 따르고 `<isonum.txt>`를 포함합니다. 저작권은 2020 Intel Corporation에 있으며, 작성자는 Rafael J. Wysocki `<[email protected]>`입니다.

System이 working state에서 지원되는 sleep state 중 하나로 이동하려면 적어도 한 번의 global system-wide transition이 필요합니다. Hibernation에는 둘 이상의 transition이 필요하지만, 일반적으로 `system-wide suspend` 또는 간단히 `system suspend` state라고 부르는 다른 sleep state에는 한 번만 필요합니다.

이 sleep state들에서 working state로부터 목표 sleep state로 가는 transition 역시 `system suspend`라고 부릅니다. 대부분 문맥으로 state 자체와 transition 중 어느 뜻인지 구분할 수 있습니다. Sleep state에서 working state로 돌아오는 transition은 `system resume`이라고 합니다.

System의 여러 sleep state에 대한 suspend와 resume kernel code flow는 상당히 비슷합니다. 다만 suspend-to-idle의 flow와 suspend-to-RAM 및 standby의 flow 사이에는 중요한 차이가 있습니다.

Suspend-to-RAM과 Standby는 platform 지원 없이는 구현할 수 없습니다. 둘의 차이는 platform driver가 이 상태들을 제공하기 위해 구현해야 하는 suspend/resume hook의 platform-specific action으로 귀결됩니다. 그 밖의 suspend와 resume flow는 거의 같으므로 이하에서는 둘을 함께 `platform-dependent suspend` state라고 부릅니다.

Suspend-to-Idle suspend flow

40-117

Working state에서 Suspend-to-Idle sleep state로 전환할 때 다음 단계를 순서대로 수행합니다.

1. `system-wide suspend notifiers`를 호출합니다. Kernel subsystem은 suspend transition 직전과 resume transition 완료 뒤에 호출될 callback을 등록할 수 있습니다. 이를 통해 system state 변경을 준비하고 working state로 돌아온 뒤 정리할 수 있습니다.

2. Task를 freeze합니다. 주된 목적은 userspace에 직접 노출된 MMIO region이나 I/O register를 통한 검증되지 않은 hardware access를 막고, 다음 transition 단계가 진행되는 동안 userspace가 kernel에 진입하지 못하게 하는 것입니다.

모든 user space task를 signal을 받은 것처럼 가로채 이후 system resume transition이 끝날 때까지 `uninterruptible sleep`에 둡니다. 특정 이유로 system suspend 중 freeze되기를 선택한 kernel thread는 그다음에 freeze되지만 가로채지는 않습니다. 대신 주기적으로 freeze 필요 여부를 확인하고 필요하면 스스로 uninterruptible sleep에 들어가야 합니다.

Kernel thread는 kernel space의 locking과 다른 concurrency control을 사용해 system suspend/resume과 더 정밀하게 동기화할 수 있으므로, kernel thread에는 freezer 방식이 권장되지 않습니다.

3. Device를 suspend하고 IRQ를 재구성합니다. Device suspend는 `prepare`, `suspend`, `late suspend`, `noirq suspend`의 네 phase로 진행됩니다. 각 phase의 정확한 동작은 `driverapi_pm_devices`를 참조하십시오. 모든 device를 각 phase에서 방문하지만 물리적으로 접근하는 phase는 대개 두 개 이하입니다.

`late suspend` phase 동안 모든 device에서 runtime PM API를 비활성화합니다. `noirq suspend` phase 전에 high-level `action` interrupt handler 호출을 차단합니다. 이후에도 interrupt 자체는 처리하지만, working state에서 실행할 device-specific action 없이 interrupt controller에서 acknowledge만 합니다. 해당 action은 뒤따르는 system resume transition까지 미룹니다.

System wakeup device와 연결된 IRQ를 `armed` 상태로 만들어 그중 하나가 event를 signal하면 system resume transition을 시작하게 합니다.

4. Scheduler tick을 freeze하고 timekeeping을 suspend합니다. 모든 device가 suspend되면 CPU는 idle loop에 들어가 가장 깊은 available idle state로 전환됩니다. 각 CPU는 자신의 scheduler tick을 freeze해 다른 interrupt source가 CPU를 깨울 때까지 tick과 관련된 timer event가 발생하지 않게 합니다.

마지막으로 idle state에 들어가는 CPU는 timekeeping도 멈춥니다. 이로써 먼저 깨어난 CPU가 timekeeping을 다시 시작할 때까지 high resolution timer를 포함한 timer가 trigger되지 않습니다. CPU가 한 번에 비교적 오랫동안 deep idle state에 머물 수 있게 됩니다.

이 시점부터 CPU는 non-timer hardware interrupt로만 깨어날 수 있습니다. CPU를 깨운 interrupt가 system wakeup용으로 armed된 IRQ가 아니면 다시 idle state로 돌아갑니다. Armed IRQ에서 왔다면 system resume transition을 시작합니다.

Suspend-to-Idle suspend 순서
System-wide suspend notifiersFreeze user tasks and participating kernel threadsDevice prepare → suspend → late → noirq; arm wakeup IRQsFreeze scheduler tick and timekeepingCPUs remain in deepest available idle state

Global notification에서 시작해 task와 device를 멈추고 마지막에 CPU tick과 timekeeping을 freeze합니다.

Suspend-to-Idle resume flow

118-163

Suspend-to-Idle sleep state에서 working state로 전환할 때 다음 단계를 순서대로 수행합니다.

1. Timekeeping을 resume하고 scheduler tick을 unfreeze합니다. Non-timer hardware interrupt로 CPU 하나가 깨어나면 앞선 suspend transition의 마지막 단계에서 들어간 idle state를 떠납니다. 다른 CPU가 먼저 재시작하지 않았다면 timekeeping을 재시작하고 해당 CPU의 scheduler tick을 unfreeze합니다. CPU를 깨운 interrupt가 system wakeup용으로 armed되어 있었다면 system resume transition이 시작됩니다.

2. Device를 resume하고 IRQ의 working-state configuration을 복구합니다. Device resume은 `noirq resume`, `early resume`, `resume`, `complete`의 네 phase로 진행됩니다. 세부 동작은 `driverapi_pm_devices`를 참조하십시오. 모든 device를 각 phase에서 방문하지만 물리적으로 접근하는 phase는 대개 두 개 이하입니다.

`noirq resume` phase 뒤 IRQ의 working-state configuration을 복구하고, `early resume` phase 동안 driver가 지원하는 모든 device에서 runtime PM API를 다시 활성화합니다.

3. Task를 thaw합니다. 앞선 suspend transition의 2단계에서 freeze된 task를 깨워 당시 들어간 uninterruptible sleep에서 빠져나오게 하고, user space task가 kernel을 나갈 수 있게 합니다.

4. `system-wide resume notifiers`를 호출합니다. Suspend flow 1단계와 같은 callback 집합을 호출하지만 서로 다른 `notification type` parameter 값을 전달합니다.

Suspend-to-Idle resume 순서
Resume timekeeping and unfreeze scheduler tickDevice noirq → early → resume → complete; restore IRQsThaw tasksSystem-wide resume notifiers

Wakeup IRQ가 resume을 시작하면 suspend 때의 제어를 역방향으로 복구합니다.

Platform-dependent suspend flow

164-232

Working state에서 platform-dependent suspend state로 전환할 때 다음 단계를 순서대로 수행합니다.

1. `system-wide suspend notifiers`를 호출합니다. Suspend-to-Idle suspend transition의 1단계와 같습니다.

2. Task를 freeze합니다. Suspend-to-Idle suspend transition의 2단계와 같습니다.

3. Device를 suspend하고 IRQ를 재구성합니다. Suspend-to-Idle의 3단계와 비슷하지만 system wakeup용 IRQ arming은 일반적으로 platform에 직접 영향을 주지 않습니다.

모든 CPU가 충분히 깊은 idle state에 있고 모든 I/O device가 low-power state에 들어가면 platform 내부적으로 매우 깊은 low-power state에 진입할 수 있는 platform도 있습니다. 이런 platform에서는 Suspend-to-Idle만으로도 system power를 효과적으로 줄일 수 있습니다.

다른 platform에서는 비슷한 power 절감을 얻으려면 interrupt controller 같은 low-level component를 platform-specific 방식으로 꺼야 합니다. 이 방식은 platform driver가 제공하는 hook에 구현됩니다.

그렇게 하면 보통 in-band hardware interrupt로 system을 깨울 수 없으므로 platform-dependent wakeup 방식을 사용해야 합니다. System wakeup source 구성은 대개 system wakeup device를 suspend할 때 시작하고, 나중에 platform suspend hook이 마무리합니다.

4. Non-boot CPU를 비활성화합니다. 일부 platform에서는 suspend hook을 one-CPU configuration에서 실행해야 합니다. 특히 platform firmware로 trap해 suspend transition을 마무리할 수 있는 platform suspend hook과 병렬로 실행되는 code가 hardware에 접근해서는 안 될 수 있습니다.

이 때문에 CPU offline/online, 즉 CPU hotplug framework로 boot CPU 하나를 제외한 모든 CPU를 offline으로 만듭니다. Offline된 CPU는 보통 deep idle state로 들어갑니다. 해당 CPU에 있던 모든 task를 다른 곳으로 migrate하고 모든 IRQ를 유일하게 online으로 남은 CPU로 reroute합니다.

5. Core system component를 suspend합니다. 앞으로 power를 잃을 수 있도록 core system component를 준비하고 timekeeping을 suspend합니다.

6. Platform-specific power removal을 수행합니다. RAM 내용을 보존하기 위한 memory controller와 RAM, 그리고 system wakeup용으로 지정된 일부 device를 제외한 모든 system component의 power를 제거해야 합니다. 많은 경우 control을 platform firmware에 넘겨 필요한 suspend transition 마무리를 맡깁니다.

Platform-dependent suspend 순서
System-wide suspend notifiersFreeze tasksSuspend devices and configure platform wakeup sourcesOffline every non-boot CPU; reroute tasks and IRQsSuspend core system components and timekeepingPlatform-specific power removal

S2Idle 공통 앞단 뒤에 CPU hotplug, core suspend, firmware 기반 power removal이 이어집니다.

Platform-dependent resume flow

233-270

Platform-dependent suspend state에서 working state로 전환할 때 다음 단계를 순서대로 수행합니다.

1. Platform-specific system wakeup을 수행합니다. 지정된 system wakeup device의 signal이 platform을 깨웁니다. 이 signal은 in-band hardware interrupt일 필요가 없습니다. 이후 control이 kernel로 돌아오며, kernel이 control을 다시 얻기 전에 platform firmware가 working configuration을 복구해야 할 수도 있습니다.

2. Core system component를 resume합니다. Core component의 suspend-time configuration을 복구하고 timekeeping을 resume합니다.

3. Non-boot CPU를 다시 활성화합니다. 앞선 suspend transition 4단계에서 비활성화한 CPU를 online으로 되돌리고 suspend-time configuration을 복구합니다.

4. Device를 resume하고 IRQ의 working-state configuration을 복구합니다. Suspend-to-Idle resume transition의 2단계와 같습니다.

5. Task를 thaw합니다. Suspend-to-Idle resume transition의 3단계와 같습니다.

6. `system-wide resume notifiers`를 호출합니다. Suspend-to-Idle resume transition의 4단계와 같습니다.

Platform-dependent resume 순서
Platform-specific system wakeupResume core system components and timekeepingBring non-boot CPUs onlineResume devices and restore IRQ configurationThaw tasksSystem-wide resume notifiers

Platform wakeup 뒤 core와 CPU를 먼저 복구하고 device, task, notifier를 차례로 되돌립니다.