aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/linux/freezer.h3
-rw-r--r--kernel/cgroup_freezer.c7
-rw-r--r--kernel/freezer.c31
-rw-r--r--kernel/power/process.c2
-rw-r--r--mm/oom_kill.c2
5 files changed, 18 insertions, 27 deletions
diff --git a/include/linux/freezer.h b/include/linux/freezer.h
index d02b78448b0f..ba4f512d2938 100644
--- a/include/linux/freezer.h
+++ b/include/linux/freezer.h
@@ -45,7 +45,7 @@ static inline bool should_send_signal(struct task_struct *p)
45} 45}
46 46
47/* Takes and releases task alloc lock using task_lock() */ 47/* Takes and releases task alloc lock using task_lock() */
48extern int thaw_process(struct task_struct *p); 48extern void __thaw_task(struct task_struct *t);
49 49
50extern bool __refrigerator(bool check_kthr_stop); 50extern bool __refrigerator(bool check_kthr_stop);
51extern int freeze_processes(void); 51extern int freeze_processes(void);
@@ -178,7 +178,6 @@ static inline int frozen(struct task_struct *p) { return 0; }
178static inline int freezing(struct task_struct *p) { return 0; } 178static inline int freezing(struct task_struct *p) { return 0; }
179static inline void set_freeze_flag(struct task_struct *p) {} 179static inline void set_freeze_flag(struct task_struct *p) {}
180static inline void clear_freeze_flag(struct task_struct *p) {} 180static inline void clear_freeze_flag(struct task_struct *p) {}
181static inline int thaw_process(struct task_struct *p) { return 1; }
182 181
183static inline bool __refrigerator(bool check_kthr_stop) { return false; } 182static inline bool __refrigerator(bool check_kthr_stop) { return false; }
184static inline int freeze_processes(void) { return -ENOSYS; } 183static inline int freeze_processes(void) { return -ENOSYS; }
diff --git a/kernel/cgroup_freezer.c b/kernel/cgroup_freezer.c
index 5e828a2ca8e6..a6d405a86ee0 100644
--- a/kernel/cgroup_freezer.c
+++ b/kernel/cgroup_freezer.c
@@ -130,7 +130,7 @@ struct cgroup_subsys freezer_subsys;
130 * write_lock css_set_lock (cgroup iterator start) 130 * write_lock css_set_lock (cgroup iterator start)
131 * task->alloc_lock 131 * task->alloc_lock
132 * read_lock css_set_lock (cgroup iterator start) 132 * read_lock css_set_lock (cgroup iterator start)
133 * task->alloc_lock (inside thaw_process(), prevents race with refrigerator()) 133 * task->alloc_lock (inside __thaw_task(), prevents race with refrigerator())
134 * sighand->siglock 134 * sighand->siglock
135 */ 135 */
136static struct cgroup_subsys_state *freezer_create(struct cgroup_subsys *ss, 136static struct cgroup_subsys_state *freezer_create(struct cgroup_subsys *ss,
@@ -300,9 +300,8 @@ static void unfreeze_cgroup(struct cgroup *cgroup, struct freezer *freezer)
300 struct task_struct *task; 300 struct task_struct *task;
301 301
302 cgroup_iter_start(cgroup, &it); 302 cgroup_iter_start(cgroup, &it);
303 while ((task = cgroup_iter_next(cgroup, &it))) { 303 while ((task = cgroup_iter_next(cgroup, &it)))
304 thaw_process(task); 304 __thaw_task(task);
305 }
306 cgroup_iter_end(cgroup, &it); 305 cgroup_iter_end(cgroup, &it);
307 306
308 freezer->state = CGROUP_THAWED; 307 freezer->state = CGROUP_THAWED;
diff --git a/kernel/freezer.c b/kernel/freezer.c
index b83c30e9483a..c851d588e29f 100644
--- a/kernel/freezer.c
+++ b/kernel/freezer.c
@@ -145,18 +145,8 @@ void cancel_freezing(struct task_struct *p)
145 } 145 }
146} 146}
147 147
148static int __thaw_process(struct task_struct *p)
149{
150 if (frozen(p)) {
151 p->flags &= ~PF_FROZEN;
152 return 1;
153 }
154 clear_freeze_flag(p);
155 return 0;
156}
157
158/* 148/*
159 * Wake up a frozen process 149 * Wake up a frozen task
160 * 150 *
161 * task_lock() is needed to prevent the race with refrigerator() which may 151 * task_lock() is needed to prevent the race with refrigerator() which may
162 * occur if the freezing of tasks fails. Namely, without the lock, if the 152 * occur if the freezing of tasks fails. Namely, without the lock, if the
@@ -164,15 +154,18 @@ static int __thaw_process(struct task_struct *p)
164 * refrigerator() could call frozen_process(), in which case the task would be 154 * refrigerator() could call frozen_process(), in which case the task would be
165 * frozen and no one would thaw it. 155 * frozen and no one would thaw it.
166 */ 156 */
167int thaw_process(struct task_struct *p) 157void __thaw_task(struct task_struct *p)
168{ 158{
159 bool was_frozen;
160
169 task_lock(p); 161 task_lock(p);
170 if (__thaw_process(p) == 1) { 162 was_frozen = frozen(p);
171 task_unlock(p); 163 if (was_frozen)
172 wake_up_process(p); 164 p->flags &= ~PF_FROZEN;
173 return 1; 165 else
174 } 166 clear_freeze_flag(p);
175 task_unlock(p); 167 task_unlock(p);
176 return 0; 168
169 if (was_frozen)
170 wake_up_process(p);
177} 171}
178EXPORT_SYMBOL(thaw_process);
diff --git a/kernel/power/process.c b/kernel/power/process.c
index addbbe5531bc..fe2787207f00 100644
--- a/kernel/power/process.c
+++ b/kernel/power/process.c
@@ -186,7 +186,7 @@ static void thaw_tasks(bool nosig_only)
186 if (cgroup_freezing_or_frozen(p)) 186 if (cgroup_freezing_or_frozen(p))
187 continue; 187 continue;
188 188
189 thaw_process(p); 189 __thaw_task(p);
190 } while_each_thread(g, p); 190 } while_each_thread(g, p);
191 read_unlock(&tasklist_lock); 191 read_unlock(&tasklist_lock);
192} 192}
diff --git a/mm/oom_kill.c b/mm/oom_kill.c
index 76f2c5ae908e..3134ee2fb2e8 100644
--- a/mm/oom_kill.c
+++ b/mm/oom_kill.c
@@ -328,7 +328,7 @@ static struct task_struct *select_bad_process(unsigned int *ppoints,
328 */ 328 */
329 if (test_tsk_thread_flag(p, TIF_MEMDIE)) { 329 if (test_tsk_thread_flag(p, TIF_MEMDIE)) {
330 if (unlikely(frozen(p))) 330 if (unlikely(frozen(p)))
331 thaw_process(p); 331 __thaw_task(p);
332 return ERR_PTR(-1UL); 332 return ERR_PTR(-1UL);
333 } 333 }
334 if (!p->mm) 334 if (!p->mm)