aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/linux/workqueue.h2
-rw-r--r--kernel/workqueue.c38
2 files changed, 25 insertions, 15 deletions
diff --git a/include/linux/workqueue.h b/include/linux/workqueue.h
index 957c21c16d62..9bca3539a1e5 100644
--- a/include/linux/workqueue.h
+++ b/include/linux/workqueue.h
@@ -63,6 +63,8 @@ extern void destroy_workqueue(struct workqueue_struct *wq);
63 63
64extern int FASTCALL(queue_work(struct workqueue_struct *wq, struct work_struct *work)); 64extern int FASTCALL(queue_work(struct workqueue_struct *wq, struct work_struct *work));
65extern int FASTCALL(queue_delayed_work(struct workqueue_struct *wq, struct work_struct *work, unsigned long delay)); 65extern int FASTCALL(queue_delayed_work(struct workqueue_struct *wq, struct work_struct *work, unsigned long delay));
66extern int queue_delayed_work_on(int cpu, struct workqueue_struct *wq,
67 struct work_struct *work, unsigned long delay);
66extern void FASTCALL(flush_workqueue(struct workqueue_struct *wq)); 68extern void FASTCALL(flush_workqueue(struct workqueue_struct *wq));
67 69
68extern int FASTCALL(schedule_work(struct work_struct *work)); 70extern int FASTCALL(schedule_work(struct work_struct *work));
diff --git a/kernel/workqueue.c b/kernel/workqueue.c
index 59f0b42bd89e..8fbef7008a7e 100644
--- a/kernel/workqueue.c
+++ b/kernel/workqueue.c
@@ -148,6 +148,27 @@ int fastcall queue_delayed_work(struct workqueue_struct *wq,
148 return ret; 148 return ret;
149} 149}
150 150
151int queue_delayed_work_on(int cpu, struct workqueue_struct *wq,
152 struct work_struct *work, unsigned long delay)
153{
154 int ret = 0;
155 struct timer_list *timer = &work->timer;
156
157 if (!test_and_set_bit(0, &work->pending)) {
158 BUG_ON(timer_pending(timer));
159 BUG_ON(!list_empty(&work->entry));
160
161 /* This stores wq for the moment, for the timer_fn */
162 work->wq_data = wq;
163 timer->expires = jiffies + delay;
164 timer->data = (unsigned long)work;
165 timer->function = delayed_work_timer_fn;
166 add_timer_on(timer, cpu);
167 ret = 1;
168 }
169 return ret;
170}
171
151static void run_workqueue(struct cpu_workqueue_struct *cwq) 172static void run_workqueue(struct cpu_workqueue_struct *cwq)
152{ 173{
153 unsigned long flags; 174 unsigned long flags;
@@ -411,21 +432,7 @@ int fastcall schedule_delayed_work(struct work_struct *work, unsigned long delay
411int schedule_delayed_work_on(int cpu, 432int schedule_delayed_work_on(int cpu,
412 struct work_struct *work, unsigned long delay) 433 struct work_struct *work, unsigned long delay)
413{ 434{
414 int ret = 0; 435 return queue_delayed_work_on(cpu, keventd_wq, work, delay);
415 struct timer_list *timer = &work->timer;
416
417 if (!test_and_set_bit(0, &work->pending)) {
418 BUG_ON(timer_pending(timer));
419 BUG_ON(!list_empty(&work->entry));
420 /* This stores keventd_wq for the moment, for the timer_fn */
421 work->wq_data = keventd_wq;
422 timer->expires = jiffies + delay;
423 timer->data = (unsigned long)work;
424 timer->function = delayed_work_timer_fn;
425 add_timer_on(timer, cpu);
426 ret = 1;
427 }
428 return ret;
429} 436}
430 437
431/** 438/**
@@ -622,6 +629,7 @@ void init_workqueues(void)
622EXPORT_SYMBOL_GPL(__create_workqueue); 629EXPORT_SYMBOL_GPL(__create_workqueue);
623EXPORT_SYMBOL_GPL(queue_work); 630EXPORT_SYMBOL_GPL(queue_work);
624EXPORT_SYMBOL_GPL(queue_delayed_work); 631EXPORT_SYMBOL_GPL(queue_delayed_work);
632EXPORT_SYMBOL_GPL(queue_delayed_work_on);
625EXPORT_SYMBOL_GPL(flush_workqueue); 633EXPORT_SYMBOL_GPL(flush_workqueue);
626EXPORT_SYMBOL_GPL(destroy_workqueue); 634EXPORT_SYMBOL_GPL(destroy_workqueue);
627 635