aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/kthread.c
diff options
context:
space:
mode:
authorMauro Carvalho Chehab <mchehab@redhat.com>2012-10-17 08:32:49 -0400
committerMauro Carvalho Chehab <mchehab@redhat.com>2012-10-17 08:32:49 -0400
commit214e2ca2b82d335935a861c253fe94c61ad77aad (patch)
treeeee42ff74d10470789d919b8499737ad0e919360 /kernel/kthread.c
parent1fdead8ad31d3aa833bc37739273fcde89ace93c (diff)
parentddffeb8c4d0331609ef2581d84de4d763607bd37 (diff)
Merge tag 'v3.7-rc1' into staging/for_v3.8
Linux 3.7-rc1 * tag 'v3.7-rc1': (9579 commits) Linux 3.7-rc1 x86, boot: Explicitly include autoconf.h for hostprogs perf: Fix UAPI fallout ARM: config: make sure that platforms are ordered by option string ARM: config: sort select statements alphanumerically UAPI: (Scripted) Disintegrate include/linux/byteorder UAPI: (Scripted) Disintegrate include/linux UAPI: Unexport linux/blk_types.h UAPI: Unexport part of linux/ppp-comp.h perf: Handle new rbtree implementation procfs: don't need a PATH_MAX allocation to hold a string representation of an int vfs: embed struct filename inside of names_cache allocation if possible audit: make audit_inode take struct filename vfs: make path_openat take a struct filename pointer vfs: turn do_path_lookup into wrapper around struct filename variant audit: allow audit code to satisfy getname requests from its names_list vfs: define struct filename and have getname() return it btrfs: Fix compilation with user namespace support enabled userns: Fix posix_acl_file_xattr_userns gid conversion userns: Properly print bluetooth socket uids ...
Diffstat (limited to 'kernel/kthread.c')
-rw-r--r--kernel/kthread.c186
1 files changed, 167 insertions, 19 deletions
diff --git a/kernel/kthread.c b/kernel/kthread.c
index b579af57ea10..29fb60caecb5 100644
--- a/kernel/kthread.c
+++ b/kernel/kthread.c
@@ -16,6 +16,7 @@
16#include <linux/mutex.h> 16#include <linux/mutex.h>
17#include <linux/slab.h> 17#include <linux/slab.h>
18#include <linux/freezer.h> 18#include <linux/freezer.h>
19#include <linux/ptrace.h>
19#include <trace/events/sched.h> 20#include <trace/events/sched.h>
20 21
21static DEFINE_SPINLOCK(kthread_create_lock); 22static DEFINE_SPINLOCK(kthread_create_lock);
@@ -37,11 +38,20 @@ struct kthread_create_info
37}; 38};
38 39
39struct kthread { 40struct kthread {
40 int should_stop; 41 unsigned long flags;
42 unsigned int cpu;
41 void *data; 43 void *data;
44 struct completion parked;
42 struct completion exited; 45 struct completion exited;
43}; 46};
44 47
48enum KTHREAD_BITS {
49 KTHREAD_IS_PER_CPU = 0,
50 KTHREAD_SHOULD_STOP,
51 KTHREAD_SHOULD_PARK,
52 KTHREAD_IS_PARKED,
53};
54
45#define to_kthread(tsk) \ 55#define to_kthread(tsk) \
46 container_of((tsk)->vfork_done, struct kthread, exited) 56 container_of((tsk)->vfork_done, struct kthread, exited)
47 57
@@ -52,13 +62,29 @@ struct kthread {
52 * and this will return true. You should then return, and your return 62 * and this will return true. You should then return, and your return
53 * value will be passed through to kthread_stop(). 63 * value will be passed through to kthread_stop().
54 */ 64 */
55int kthread_should_stop(void) 65bool kthread_should_stop(void)
56{ 66{
57 return to_kthread(current)->should_stop; 67 return test_bit(KTHREAD_SHOULD_STOP, &to_kthread(current)->flags);
58} 68}
59EXPORT_SYMBOL(kthread_should_stop); 69EXPORT_SYMBOL(kthread_should_stop);
60 70
61/** 71/**
72 * kthread_should_park - should this kthread park now?
73 *
74 * When someone calls kthread_park() on your kthread, it will be woken
75 * and this will return true. You should then do the necessary
76 * cleanup and call kthread_parkme()
77 *
78 * Similar to kthread_should_stop(), but this keeps the thread alive
79 * and in a park position. kthread_unpark() "restarts" the thread and
80 * calls the thread function again.
81 */
82bool kthread_should_park(void)
83{
84 return test_bit(KTHREAD_SHOULD_PARK, &to_kthread(current)->flags);
85}
86
87/**
62 * kthread_freezable_should_stop - should this freezable kthread return now? 88 * kthread_freezable_should_stop - should this freezable kthread return now?
63 * @was_frozen: optional out parameter, indicates whether %current was frozen 89 * @was_frozen: optional out parameter, indicates whether %current was frozen
64 * 90 *
@@ -96,6 +122,24 @@ void *kthread_data(struct task_struct *task)
96 return to_kthread(task)->data; 122 return to_kthread(task)->data;
97} 123}
98 124
125static void __kthread_parkme(struct kthread *self)
126{
127 __set_current_state(TASK_INTERRUPTIBLE);
128 while (test_bit(KTHREAD_SHOULD_PARK, &self->flags)) {
129 if (!test_and_set_bit(KTHREAD_IS_PARKED, &self->flags))
130 complete(&self->parked);
131 schedule();
132 __set_current_state(TASK_INTERRUPTIBLE);
133 }
134 clear_bit(KTHREAD_IS_PARKED, &self->flags);
135 __set_current_state(TASK_RUNNING);
136}
137
138void kthread_parkme(void)
139{
140 __kthread_parkme(to_kthread(current));
141}
142
99static int kthread(void *_create) 143static int kthread(void *_create)
100{ 144{
101 /* Copy data: it's on kthread's stack */ 145 /* Copy data: it's on kthread's stack */
@@ -105,9 +149,10 @@ static int kthread(void *_create)
105 struct kthread self; 149 struct kthread self;
106 int ret; 150 int ret;
107 151
108 self.should_stop = 0; 152 self.flags = 0;
109 self.data = data; 153 self.data = data;
110 init_completion(&self.exited); 154 init_completion(&self.exited);
155 init_completion(&self.parked);
111 current->vfork_done = &self.exited; 156 current->vfork_done = &self.exited;
112 157
113 /* OK, tell user we're spawned, wait for stop or wakeup */ 158 /* OK, tell user we're spawned, wait for stop or wakeup */
@@ -117,9 +162,11 @@ static int kthread(void *_create)
117 schedule(); 162 schedule();
118 163
119 ret = -EINTR; 164 ret = -EINTR;
120 if (!self.should_stop)
121 ret = threadfn(data);
122 165
166 if (!test_bit(KTHREAD_SHOULD_STOP, &self.flags)) {
167 __kthread_parkme(&self);
168 ret = threadfn(data);
169 }
123 /* we can't just return, we must preserve "self" on stack */ 170 /* we can't just return, we must preserve "self" on stack */
124 do_exit(ret); 171 do_exit(ret);
125} 172}
@@ -172,8 +219,7 @@ static void create_kthread(struct kthread_create_info *create)
172 * Returns a task_struct or ERR_PTR(-ENOMEM). 219 * Returns a task_struct or ERR_PTR(-ENOMEM).
173 */ 220 */
174struct task_struct *kthread_create_on_node(int (*threadfn)(void *data), 221struct task_struct *kthread_create_on_node(int (*threadfn)(void *data),
175 void *data, 222 void *data, int node,
176 int node,
177 const char namefmt[], 223 const char namefmt[],
178 ...) 224 ...)
179{ 225{
@@ -210,6 +256,13 @@ struct task_struct *kthread_create_on_node(int (*threadfn)(void *data),
210} 256}
211EXPORT_SYMBOL(kthread_create_on_node); 257EXPORT_SYMBOL(kthread_create_on_node);
212 258
259static void __kthread_bind(struct task_struct *p, unsigned int cpu)
260{
261 /* It's safe because the task is inactive. */
262 do_set_cpus_allowed(p, cpumask_of(cpu));
263 p->flags |= PF_THREAD_BOUND;
264}
265
213/** 266/**
214 * kthread_bind - bind a just-created kthread to a cpu. 267 * kthread_bind - bind a just-created kthread to a cpu.
215 * @p: thread created by kthread_create(). 268 * @p: thread created by kthread_create().
@@ -226,14 +279,112 @@ void kthread_bind(struct task_struct *p, unsigned int cpu)
226 WARN_ON(1); 279 WARN_ON(1);
227 return; 280 return;
228 } 281 }
229 282 __kthread_bind(p, cpu);
230 /* It's safe because the task is inactive. */
231 do_set_cpus_allowed(p, cpumask_of(cpu));
232 p->flags |= PF_THREAD_BOUND;
233} 283}
234EXPORT_SYMBOL(kthread_bind); 284EXPORT_SYMBOL(kthread_bind);
235 285
236/** 286/**
287 * kthread_create_on_cpu - Create a cpu bound kthread
288 * @threadfn: the function to run until signal_pending(current).
289 * @data: data ptr for @threadfn.
290 * @cpu: The cpu on which the thread should be bound,
291 * @namefmt: printf-style name for the thread. Format is restricted
292 * to "name.*%u". Code fills in cpu number.
293 *
294 * Description: This helper function creates and names a kernel thread
295 * The thread will be woken and put into park mode.
296 */
297struct task_struct *kthread_create_on_cpu(int (*threadfn)(void *data),
298 void *data, unsigned int cpu,
299 const char *namefmt)
300{
301 struct task_struct *p;
302
303 p = kthread_create_on_node(threadfn, data, cpu_to_node(cpu), namefmt,
304 cpu);
305 if (IS_ERR(p))
306 return p;
307 set_bit(KTHREAD_IS_PER_CPU, &to_kthread(p)->flags);
308 to_kthread(p)->cpu = cpu;
309 /* Park the thread to get it out of TASK_UNINTERRUPTIBLE state */
310 kthread_park(p);
311 return p;
312}
313
314static struct kthread *task_get_live_kthread(struct task_struct *k)
315{
316 struct kthread *kthread;
317
318 get_task_struct(k);
319 kthread = to_kthread(k);
320 /* It might have exited */
321 barrier();
322 if (k->vfork_done != NULL)
323 return kthread;
324 return NULL;
325}
326
327/**
328 * kthread_unpark - unpark a thread created by kthread_create().
329 * @k: thread created by kthread_create().
330 *
331 * Sets kthread_should_park() for @k to return false, wakes it, and
332 * waits for it to return. If the thread is marked percpu then its
333 * bound to the cpu again.
334 */
335void kthread_unpark(struct task_struct *k)
336{
337 struct kthread *kthread = task_get_live_kthread(k);
338
339 if (kthread) {
340 clear_bit(KTHREAD_SHOULD_PARK, &kthread->flags);
341 /*
342 * We clear the IS_PARKED bit here as we don't wait
343 * until the task has left the park code. So if we'd
344 * park before that happens we'd see the IS_PARKED bit
345 * which might be about to be cleared.
346 */
347 if (test_and_clear_bit(KTHREAD_IS_PARKED, &kthread->flags)) {
348 if (test_bit(KTHREAD_IS_PER_CPU, &kthread->flags))
349 __kthread_bind(k, kthread->cpu);
350 wake_up_process(k);
351 }
352 }
353 put_task_struct(k);
354}
355
356/**
357 * kthread_park - park a thread created by kthread_create().
358 * @k: thread created by kthread_create().
359 *
360 * Sets kthread_should_park() for @k to return true, wakes it, and
361 * waits for it to return. This can also be called after kthread_create()
362 * instead of calling wake_up_process(): the thread will park without
363 * calling threadfn().
364 *
365 * Returns 0 if the thread is parked, -ENOSYS if the thread exited.
366 * If called by the kthread itself just the park bit is set.
367 */
368int kthread_park(struct task_struct *k)
369{
370 struct kthread *kthread = task_get_live_kthread(k);
371 int ret = -ENOSYS;
372
373 if (kthread) {
374 if (!test_bit(KTHREAD_IS_PARKED, &kthread->flags)) {
375 set_bit(KTHREAD_SHOULD_PARK, &kthread->flags);
376 if (k != current) {
377 wake_up_process(k);
378 wait_for_completion(&kthread->parked);
379 }
380 }
381 ret = 0;
382 }
383 put_task_struct(k);
384 return ret;
385}
386
387/**
237 * kthread_stop - stop a thread created by kthread_create(). 388 * kthread_stop - stop a thread created by kthread_create().
238 * @k: thread created by kthread_create(). 389 * @k: thread created by kthread_create().
239 * 390 *
@@ -250,16 +401,13 @@ EXPORT_SYMBOL(kthread_bind);
250 */ 401 */
251int kthread_stop(struct task_struct *k) 402int kthread_stop(struct task_struct *k)
252{ 403{
253 struct kthread *kthread; 404 struct kthread *kthread = task_get_live_kthread(k);
254 int ret; 405 int ret;
255 406
256 trace_sched_kthread_stop(k); 407 trace_sched_kthread_stop(k);
257 get_task_struct(k); 408 if (kthread) {
258 409 set_bit(KTHREAD_SHOULD_STOP, &kthread->flags);
259 kthread = to_kthread(k); 410 clear_bit(KTHREAD_SHOULD_PARK, &kthread->flags);
260 barrier(); /* it might have exited */
261 if (k->vfork_done != NULL) {
262 kthread->should_stop = 1;
263 wake_up_process(k); 411 wake_up_process(k);
264 wait_for_completion(&kthread->exited); 412 wait_for_completion(&kthread->exited);
265 } 413 }