diff options
Diffstat (limited to 'include/linux/freezer.h')
-rw-r--r-- | include/linux/freezer.h | 108 |
1 files changed, 38 insertions, 70 deletions
diff --git a/include/linux/freezer.h b/include/linux/freezer.h index a5386e3ee756..09570ac22be6 100644 --- a/include/linux/freezer.h +++ b/include/linux/freezer.h | |||
@@ -5,71 +5,58 @@ | |||
5 | 5 | ||
6 | #include <linux/sched.h> | 6 | #include <linux/sched.h> |
7 | #include <linux/wait.h> | 7 | #include <linux/wait.h> |
8 | #include <linux/atomic.h> | ||
8 | 9 | ||
9 | #ifdef CONFIG_FREEZER | 10 | #ifdef CONFIG_FREEZER |
11 | extern atomic_t system_freezing_cnt; /* nr of freezing conds in effect */ | ||
12 | extern bool pm_freezing; /* PM freezing in effect */ | ||
13 | extern bool pm_nosig_freezing; /* PM nosig freezing in effect */ | ||
14 | |||
10 | /* | 15 | /* |
11 | * Check if a process has been frozen | 16 | * Check if a process has been frozen |
12 | */ | 17 | */ |
13 | static inline int frozen(struct task_struct *p) | 18 | static inline bool frozen(struct task_struct *p) |
14 | { | 19 | { |
15 | return p->flags & PF_FROZEN; | 20 | return p->flags & PF_FROZEN; |
16 | } | 21 | } |
17 | 22 | ||
18 | /* | 23 | extern bool freezing_slow_path(struct task_struct *p); |
19 | * Check if there is a request to freeze a process | ||
20 | */ | ||
21 | static inline int freezing(struct task_struct *p) | ||
22 | { | ||
23 | return test_tsk_thread_flag(p, TIF_FREEZE); | ||
24 | } | ||
25 | |||
26 | /* | ||
27 | * Request that a process be frozen | ||
28 | */ | ||
29 | static inline void set_freeze_flag(struct task_struct *p) | ||
30 | { | ||
31 | set_tsk_thread_flag(p, TIF_FREEZE); | ||
32 | } | ||
33 | 24 | ||
34 | /* | 25 | /* |
35 | * Sometimes we may need to cancel the previous 'freeze' request | 26 | * Check if there is a request to freeze a process |
36 | */ | 27 | */ |
37 | static inline void clear_freeze_flag(struct task_struct *p) | 28 | static inline bool freezing(struct task_struct *p) |
38 | { | ||
39 | clear_tsk_thread_flag(p, TIF_FREEZE); | ||
40 | } | ||
41 | |||
42 | static inline bool should_send_signal(struct task_struct *p) | ||
43 | { | 29 | { |
44 | return !(p->flags & PF_FREEZER_NOSIG); | 30 | if (likely(!atomic_read(&system_freezing_cnt))) |
31 | return false; | ||
32 | return freezing_slow_path(p); | ||
45 | } | 33 | } |
46 | 34 | ||
47 | /* Takes and releases task alloc lock using task_lock() */ | 35 | /* Takes and releases task alloc lock using task_lock() */ |
48 | extern int thaw_process(struct task_struct *p); | 36 | extern void __thaw_task(struct task_struct *t); |
49 | 37 | ||
50 | extern void refrigerator(void); | 38 | extern bool __refrigerator(bool check_kthr_stop); |
51 | extern int freeze_processes(void); | 39 | extern int freeze_processes(void); |
52 | extern int freeze_kernel_threads(void); | 40 | extern int freeze_kernel_threads(void); |
53 | extern void thaw_processes(void); | 41 | extern void thaw_processes(void); |
54 | 42 | ||
55 | static inline int try_to_freeze(void) | 43 | static inline bool try_to_freeze(void) |
56 | { | 44 | { |
57 | if (freezing(current)) { | 45 | might_sleep(); |
58 | refrigerator(); | 46 | if (likely(!freezing(current))) |
59 | return 1; | 47 | return false; |
60 | } else | 48 | return __refrigerator(false); |
61 | return 0; | ||
62 | } | 49 | } |
63 | 50 | ||
64 | extern bool freeze_task(struct task_struct *p, bool sig_only); | 51 | extern bool freeze_task(struct task_struct *p); |
65 | extern void cancel_freezing(struct task_struct *p); | 52 | extern bool set_freezable(void); |
66 | 53 | ||
67 | #ifdef CONFIG_CGROUP_FREEZER | 54 | #ifdef CONFIG_CGROUP_FREEZER |
68 | extern int cgroup_freezing_or_frozen(struct task_struct *task); | 55 | extern bool cgroup_freezing(struct task_struct *task); |
69 | #else /* !CONFIG_CGROUP_FREEZER */ | 56 | #else /* !CONFIG_CGROUP_FREEZER */ |
70 | static inline int cgroup_freezing_or_frozen(struct task_struct *task) | 57 | static inline bool cgroup_freezing(struct task_struct *task) |
71 | { | 58 | { |
72 | return 0; | 59 | return false; |
73 | } | 60 | } |
74 | #endif /* !CONFIG_CGROUP_FREEZER */ | 61 | #endif /* !CONFIG_CGROUP_FREEZER */ |
75 | 62 | ||
@@ -118,23 +105,6 @@ static inline int freezer_should_skip(struct task_struct *p) | |||
118 | } | 105 | } |
119 | 106 | ||
120 | /* | 107 | /* |
121 | * Tell the freezer that the current task should be frozen by it | ||
122 | */ | ||
123 | static inline void set_freezable(void) | ||
124 | { | ||
125 | current->flags &= ~PF_NOFREEZE; | ||
126 | } | ||
127 | |||
128 | /* | ||
129 | * Tell the freezer that the current task should be frozen by it and that it | ||
130 | * should send a fake signal to the task to freeze it. | ||
131 | */ | ||
132 | static inline void set_freezable_with_signal(void) | ||
133 | { | ||
134 | current->flags &= ~(PF_NOFREEZE | PF_FREEZER_NOSIG); | ||
135 | } | ||
136 | |||
137 | /* | ||
138 | * Freezer-friendly wrappers around wait_event_interruptible(), | 108 | * Freezer-friendly wrappers around wait_event_interruptible(), |
139 | * wait_event_killable() and wait_event_interruptible_timeout(), originally | 109 | * wait_event_killable() and wait_event_interruptible_timeout(), originally |
140 | * defined in <linux/wait.h> | 110 | * defined in <linux/wait.h> |
@@ -152,47 +122,45 @@ static inline void set_freezable_with_signal(void) | |||
152 | #define wait_event_freezable(wq, condition) \ | 122 | #define wait_event_freezable(wq, condition) \ |
153 | ({ \ | 123 | ({ \ |
154 | int __retval; \ | 124 | int __retval; \ |
155 | do { \ | 125 | for (;;) { \ |
156 | __retval = wait_event_interruptible(wq, \ | 126 | __retval = wait_event_interruptible(wq, \ |
157 | (condition) || freezing(current)); \ | 127 | (condition) || freezing(current)); \ |
158 | if (__retval && !freezing(current)) \ | 128 | if (__retval || (condition)) \ |
159 | break; \ | 129 | break; \ |
160 | else if (!(condition)) \ | 130 | try_to_freeze(); \ |
161 | __retval = -ERESTARTSYS; \ | 131 | } \ |
162 | } while (try_to_freeze()); \ | ||
163 | __retval; \ | 132 | __retval; \ |
164 | }) | 133 | }) |
165 | 134 | ||
166 | |||
167 | #define wait_event_freezable_timeout(wq, condition, timeout) \ | 135 | #define wait_event_freezable_timeout(wq, condition, timeout) \ |
168 | ({ \ | 136 | ({ \ |
169 | long __retval = timeout; \ | 137 | long __retval = timeout; \ |
170 | do { \ | 138 | for (;;) { \ |
171 | __retval = wait_event_interruptible_timeout(wq, \ | 139 | __retval = wait_event_interruptible_timeout(wq, \ |
172 | (condition) || freezing(current), \ | 140 | (condition) || freezing(current), \ |
173 | __retval); \ | 141 | __retval); \ |
174 | } while (try_to_freeze()); \ | 142 | if (__retval <= 0 || (condition)) \ |
143 | break; \ | ||
144 | try_to_freeze(); \ | ||
145 | } \ | ||
175 | __retval; \ | 146 | __retval; \ |
176 | }) | 147 | }) |
148 | |||
177 | #else /* !CONFIG_FREEZER */ | 149 | #else /* !CONFIG_FREEZER */ |
178 | static inline int frozen(struct task_struct *p) { return 0; } | 150 | static inline bool frozen(struct task_struct *p) { return false; } |
179 | static inline int freezing(struct task_struct *p) { return 0; } | 151 | static inline bool freezing(struct task_struct *p) { return false; } |
180 | static inline void set_freeze_flag(struct task_struct *p) {} | ||
181 | static inline void clear_freeze_flag(struct task_struct *p) {} | ||
182 | static inline int thaw_process(struct task_struct *p) { return 1; } | ||
183 | 152 | ||
184 | static inline void refrigerator(void) {} | 153 | static inline bool __refrigerator(bool check_kthr_stop) { return false; } |
185 | static inline int freeze_processes(void) { return -ENOSYS; } | 154 | static inline int freeze_processes(void) { return -ENOSYS; } |
186 | static inline int freeze_kernel_threads(void) { return -ENOSYS; } | 155 | static inline int freeze_kernel_threads(void) { return -ENOSYS; } |
187 | static inline void thaw_processes(void) {} | 156 | static inline void thaw_processes(void) {} |
188 | 157 | ||
189 | static inline int try_to_freeze(void) { return 0; } | 158 | static inline bool try_to_freeze(void) { return false; } |
190 | 159 | ||
191 | static inline void freezer_do_not_count(void) {} | 160 | static inline void freezer_do_not_count(void) {} |
192 | static inline void freezer_count(void) {} | 161 | static inline void freezer_count(void) {} |
193 | static inline int freezer_should_skip(struct task_struct *p) { return 0; } | 162 | static inline int freezer_should_skip(struct task_struct *p) { return 0; } |
194 | static inline void set_freezable(void) {} | 163 | static inline void set_freezable(void) {} |
195 | static inline void set_freezable_with_signal(void) {} | ||
196 | 164 | ||
197 | #define wait_event_freezable(wq, condition) \ | 165 | #define wait_event_freezable(wq, condition) \ |
198 | wait_event_interruptible(wq, condition) | 166 | wait_event_interruptible(wq, condition) |