1
2#ifndef _LINUX_SUSPEND_H
3#define _LINUX_SUSPEND_H
4
5#include <linux/swap.h>
6#include <linux/notifier.h>
7#include <linux/init.h>
8#include <linux/pm.h>
9#include <linux/mm.h>
10#include <linux/freezer.h>
11#include <asm/errno.h>
12
13#ifdef CONFIG_VT
14extern void pm_set_vt_switch(int);
15#else
16static inline void pm_set_vt_switch(int do_switch)
17{
18}
19#endif
20
21#ifdef CONFIG_VT_CONSOLE_SLEEP
22extern void pm_prepare_console(void);
23extern void pm_restore_console(void);
24#else
25static inline void pm_prepare_console(void)
26{
27}
28
29static inline void pm_restore_console(void)
30{
31}
32#endif
33
34typedef int __bitwise suspend_state_t;
35
36#define PM_SUSPEND_ON ((__force suspend_state_t) 0)
37#define PM_SUSPEND_TO_IDLE ((__force suspend_state_t) 1)
38#define PM_SUSPEND_STANDBY ((__force suspend_state_t) 2)
39#define PM_SUSPEND_MEM ((__force suspend_state_t) 3)
40#define PM_SUSPEND_MIN PM_SUSPEND_TO_IDLE
41#define PM_SUSPEND_MAX ((__force suspend_state_t) 4)
42
43enum suspend_stat_step {
44 SUSPEND_FREEZE = 1,
45 SUSPEND_PREPARE,
46 SUSPEND_SUSPEND,
47 SUSPEND_SUSPEND_LATE,
48 SUSPEND_SUSPEND_NOIRQ,
49 SUSPEND_RESUME_NOIRQ,
50 SUSPEND_RESUME_EARLY,
51 SUSPEND_RESUME
52};
53
54struct suspend_stats {
55 int success;
56 int fail;
57 int failed_freeze;
58 int failed_prepare;
59 int failed_suspend;
60 int failed_suspend_late;
61 int failed_suspend_noirq;
62 int failed_resume;
63 int failed_resume_early;
64 int failed_resume_noirq;
65#define REC_FAILED_NUM 2
66 int last_failed_dev;
67 char failed_devs[REC_FAILED_NUM][40];
68 int last_failed_errno;
69 int errno[REC_FAILED_NUM];
70 int last_failed_step;
71 enum suspend_stat_step failed_steps[REC_FAILED_NUM];
72};
73
74extern struct suspend_stats suspend_stats;
75
76static inline void dpm_save_failed_dev(const char *name)
77{
78 strlcpy(suspend_stats.failed_devs[suspend_stats.last_failed_dev],
79 name,
80 sizeof(suspend_stats.failed_devs[0]));
81 suspend_stats.last_failed_dev++;
82 suspend_stats.last_failed_dev %= REC_FAILED_NUM;
83}
84
85static inline void dpm_save_failed_errno(int err)
86{
87 suspend_stats.errno[suspend_stats.last_failed_errno] = err;
88 suspend_stats.last_failed_errno++;
89 suspend_stats.last_failed_errno %= REC_FAILED_NUM;
90}
91
92static inline void dpm_save_failed_step(enum suspend_stat_step step)
93{
94 suspend_stats.failed_steps[suspend_stats.last_failed_step] = step;
95 suspend_stats.last_failed_step++;
96 suspend_stats.last_failed_step %= REC_FAILED_NUM;
97}
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177struct platform_suspend_ops {
178 int (*valid)(suspend_state_t state);
179 int (*begin)(suspend_state_t state);
180 int (*prepare)(void);
181 int (*prepare_late)(void);
182 int (*enter)(suspend_state_t state);
183 void (*wake)(void);
184 void (*finish)(void);
185 bool (*suspend_again)(void);
186 void (*end)(void);
187 void (*recover)(void);
188};
189
190struct platform_s2idle_ops {
191 int (*begin)(void);
192 int (*prepare)(void);
193 void (*wake)(void);
194 void (*sync)(void);
195 void (*restore)(void);
196 void (*end)(void);
197};
198
199#ifdef CONFIG_SUSPEND
200extern suspend_state_t mem_sleep_current;
201extern suspend_state_t mem_sleep_default;
202
203
204
205
206
207extern void suspend_set_ops(const struct platform_suspend_ops *ops);
208extern int suspend_valid_only_mem(suspend_state_t state);
209
210extern unsigned int pm_suspend_global_flags;
211
212#define PM_SUSPEND_FLAG_FW_SUSPEND BIT(0)
213#define PM_SUSPEND_FLAG_FW_RESUME BIT(1)
214#define PM_SUSPEND_FLAG_NO_PLATFORM BIT(2)
215
216static inline void pm_suspend_clear_flags(void)
217{
218 pm_suspend_global_flags = 0;
219}
220
221static inline void pm_set_suspend_via_firmware(void)
222{
223 pm_suspend_global_flags |= PM_SUSPEND_FLAG_FW_SUSPEND;
224}
225
226static inline void pm_set_resume_via_firmware(void)
227{
228 pm_suspend_global_flags |= PM_SUSPEND_FLAG_FW_RESUME;
229}
230
231static inline void pm_set_suspend_no_platform(void)
232{
233 pm_suspend_global_flags |= PM_SUSPEND_FLAG_NO_PLATFORM;
234}
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256static inline bool pm_suspend_via_firmware(void)
257{
258 return !!(pm_suspend_global_flags & PM_SUSPEND_FLAG_FW_SUSPEND);
259}
260
261
262
263
264
265
266
267
268
269
270
271
272static inline bool pm_resume_via_firmware(void)
273{
274 return !!(pm_suspend_global_flags & PM_SUSPEND_FLAG_FW_RESUME);
275}
276
277
278
279
280
281
282
283
284
285
286
287
288static inline bool pm_suspend_no_platform(void)
289{
290 return !!(pm_suspend_global_flags & PM_SUSPEND_FLAG_NO_PLATFORM);
291}
292
293
294enum s2idle_states {
295 S2IDLE_STATE_NONE,
296 S2IDLE_STATE_ENTER,
297 S2IDLE_STATE_WAKE,
298};
299
300extern enum s2idle_states __read_mostly s2idle_state;
301
302static inline bool idle_should_enter_s2idle(void)
303{
304 return unlikely(s2idle_state == S2IDLE_STATE_ENTER);
305}
306
307extern bool pm_suspend_via_s2idle(void);
308extern void __init pm_states_init(void);
309extern void s2idle_set_ops(const struct platform_s2idle_ops *ops);
310extern void s2idle_wake(void);
311
312
313
314
315
316
317
318
319extern void arch_suspend_disable_irqs(void);
320
321
322
323
324
325
326
327
328extern void arch_suspend_enable_irqs(void);
329
330extern int pm_suspend(suspend_state_t state);
331#else
332#define suspend_valid_only_mem NULL
333
334static inline void pm_suspend_clear_flags(void) {}
335static inline void pm_set_suspend_via_firmware(void) {}
336static inline void pm_set_resume_via_firmware(void) {}
337static inline bool pm_suspend_via_firmware(void) { return false; }
338static inline bool pm_resume_via_firmware(void) { return false; }
339static inline bool pm_suspend_via_s2idle(void) { return false; }
340
341static inline void suspend_set_ops(const struct platform_suspend_ops *ops) {}
342static inline int pm_suspend(suspend_state_t state) { return -ENOSYS; }
343static inline bool idle_should_enter_s2idle(void) { return false; }
344static inline void __init pm_states_init(void) {}
345static inline void s2idle_set_ops(const struct platform_s2idle_ops *ops) {}
346static inline void s2idle_wake(void) {}
347#endif
348
349
350
351
352
353struct pbe {
354 void *address;
355 void *orig_address;
356 struct pbe *next;
357};
358
359
360extern void mark_free_pages(struct zone *zone);
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414struct platform_hibernation_ops {
415 int (*begin)(pm_message_t stage);
416 void (*end)(void);
417 int (*pre_snapshot)(void);
418 void (*finish)(void);
419 int (*prepare)(void);
420 int (*enter)(void);
421 void (*leave)(void);
422 int (*pre_restore)(void);
423 void (*restore_cleanup)(void);
424 void (*recover)(void);
425};
426
427#ifdef CONFIG_HIBERNATION
428
429extern void __register_nosave_region(unsigned long b, unsigned long e, int km);
430static inline void __init register_nosave_region(unsigned long b, unsigned long e)
431{
432 __register_nosave_region(b, e, 0);
433}
434static inline void __init register_nosave_region_late(unsigned long b, unsigned long e)
435{
436 __register_nosave_region(b, e, 1);
437}
438extern int swsusp_page_is_forbidden(struct page *);
439extern void swsusp_set_page_free(struct page *);
440extern void swsusp_unset_page_free(struct page *);
441extern unsigned long get_safe_page(gfp_t gfp_mask);
442extern asmlinkage int swsusp_arch_suspend(void);
443extern asmlinkage int swsusp_arch_resume(void);
444
445extern void hibernation_set_ops(const struct platform_hibernation_ops *ops);
446extern int hibernate(void);
447extern bool system_entering_hibernation(void);
448extern bool hibernation_available(void);
449asmlinkage int swsusp_save(void);
450extern struct pbe *restore_pblist;
451#else
452static inline void register_nosave_region(unsigned long b, unsigned long e) {}
453static inline void register_nosave_region_late(unsigned long b, unsigned long e) {}
454static inline int swsusp_page_is_forbidden(struct page *p) { return 0; }
455static inline void swsusp_set_page_free(struct page *p) {}
456static inline void swsusp_unset_page_free(struct page *p) {}
457
458static inline void hibernation_set_ops(const struct platform_hibernation_ops *ops) {}
459static inline int hibernate(void) { return -ENOSYS; }
460static inline bool system_entering_hibernation(void) { return false; }
461static inline bool hibernation_available(void) { return false; }
462#endif
463
464
465#define PM_HIBERNATION_PREPARE 0x0001
466#define PM_POST_HIBERNATION 0x0002
467#define PM_SUSPEND_PREPARE 0x0003
468#define PM_POST_SUSPEND 0x0004
469#define PM_RESTORE_PREPARE 0x0005
470#define PM_POST_RESTORE 0x0006
471
472extern struct mutex system_transition_mutex;
473
474#ifdef CONFIG_PM_SLEEP
475void save_processor_state(void);
476void restore_processor_state(void);
477
478
479extern int register_pm_notifier(struct notifier_block *nb);
480extern int unregister_pm_notifier(struct notifier_block *nb);
481extern void ksys_sync_helper(void);
482
483#define pm_notifier(fn, pri) { \
484 static struct notifier_block fn##_nb = \
485 { .notifier_call = fn, .priority = pri }; \
486 register_pm_notifier(&fn##_nb); \
487}
488
489
490extern bool events_check_enabled;
491extern unsigned int pm_wakeup_irq;
492extern suspend_state_t pm_suspend_target_state;
493
494extern bool pm_wakeup_pending(void);
495extern void pm_system_wakeup(void);
496extern void pm_system_cancel_wakeup(void);
497extern void pm_wakeup_clear(bool reset);
498extern void pm_system_irq_wakeup(unsigned int irq_number);
499extern bool pm_get_wakeup_count(unsigned int *count, bool block);
500extern bool pm_save_wakeup_count(unsigned int count);
501extern void pm_wakep_autosleep_enabled(bool set);
502extern void pm_print_active_wakeup_sources(void);
503
504extern void lock_system_sleep(void);
505extern void unlock_system_sleep(void);
506
507#else
508
509static inline int register_pm_notifier(struct notifier_block *nb)
510{
511 return 0;
512}
513
514static inline int unregister_pm_notifier(struct notifier_block *nb)
515{
516 return 0;
517}
518
519static inline void ksys_sync_helper(void) {}
520
521#define pm_notifier(fn, pri) do { (void)(fn); } while (0)
522
523static inline bool pm_wakeup_pending(void) { return false; }
524static inline void pm_system_wakeup(void) {}
525static inline void pm_wakeup_clear(bool reset) {}
526static inline void pm_system_irq_wakeup(unsigned int irq_number) {}
527
528static inline void lock_system_sleep(void) {}
529static inline void unlock_system_sleep(void) {}
530
531#endif
532
533#ifdef CONFIG_PM_SLEEP_DEBUG
534extern bool pm_print_times_enabled;
535extern bool pm_debug_messages_on;
536extern __printf(2, 3) void __pm_pr_dbg(bool defer, const char *fmt, ...);
537#else
538#define pm_print_times_enabled (false)
539#define pm_debug_messages_on (false)
540
541#include <linux/printk.h>
542
543#define __pm_pr_dbg(defer, fmt, ...) \
544 no_printk(KERN_DEBUG fmt, ##__VA_ARGS__)
545#endif
546
547#define pm_pr_dbg(fmt, ...) \
548 __pm_pr_dbg(false, fmt, ##__VA_ARGS__)
549
550#define pm_deferred_pr_dbg(fmt, ...) \
551 __pm_pr_dbg(true, fmt, ##__VA_ARGS__)
552
553#ifdef CONFIG_PM_AUTOSLEEP
554
555
556void queue_up_suspend_work(void);
557
558#else
559
560static inline void queue_up_suspend_work(void) {}
561
562#endif
563
564#ifdef CONFIG_ARCH_SAVE_PAGE_KEYS
565
566
567
568
569
570
571
572unsigned long page_key_additional_pages(unsigned long pages);
573int page_key_alloc(unsigned long pages);
574void page_key_free(void);
575void page_key_read(unsigned long *pfn);
576void page_key_memorize(unsigned long *pfn);
577void page_key_write(void *address);
578
579#else
580
581static inline unsigned long page_key_additional_pages(unsigned long pages)
582{
583 return 0;
584}
585
586static inline int page_key_alloc(unsigned long pages)
587{
588 return 0;
589}
590
591static inline void page_key_free(void) {}
592static inline void page_key_read(unsigned long *pfn) {}
593static inline void page_key_memorize(unsigned long *pfn) {}
594static inline void page_key_write(void *address) {}
595
596#endif
597
598#endif
599