diff options
Diffstat (limited to 'kernel/workqueue.c')
-rw-r--r-- | kernel/workqueue.c | 73 |
1 files changed, 0 insertions, 73 deletions
diff --git a/kernel/workqueue.c b/kernel/workqueue.c index a981add58fb9..ea422254f8bf 100644 --- a/kernel/workqueue.c +++ b/kernel/workqueue.c | |||
@@ -98,79 +98,6 @@ static inline void *get_wq_data(struct work_struct *work) | |||
98 | return (void *) (atomic_long_read(&work->data) & WORK_STRUCT_WQ_DATA_MASK); | 98 | return (void *) (atomic_long_read(&work->data) & WORK_STRUCT_WQ_DATA_MASK); |
99 | } | 99 | } |
100 | 100 | ||
101 | static int __run_work(struct cpu_workqueue_struct *cwq, struct work_struct *work) | ||
102 | { | ||
103 | int ret = 0; | ||
104 | unsigned long flags; | ||
105 | |||
106 | spin_lock_irqsave(&cwq->lock, flags); | ||
107 | /* | ||
108 | * We need to re-validate the work info after we've gotten | ||
109 | * the cpu_workqueue lock. We can run the work now iff: | ||
110 | * | ||
111 | * - the wq_data still matches the cpu_workqueue_struct | ||
112 | * - AND the work is still marked pending | ||
113 | * - AND the work is still on a list (which will be this | ||
114 | * workqueue_struct list) | ||
115 | * | ||
116 | * All these conditions are important, because we | ||
117 | * need to protect against the work being run right | ||
118 | * now on another CPU (all but the last one might be | ||
119 | * true if it's currently running and has not been | ||
120 | * released yet, for example). | ||
121 | */ | ||
122 | if (get_wq_data(work) == cwq | ||
123 | && work_pending(work) | ||
124 | && !list_empty(&work->entry)) { | ||
125 | work_func_t f = work->func; | ||
126 | cwq->current_work = work; | ||
127 | list_del_init(&work->entry); | ||
128 | spin_unlock_irqrestore(&cwq->lock, flags); | ||
129 | |||
130 | if (!test_bit(WORK_STRUCT_NOAUTOREL, work_data_bits(work))) | ||
131 | work_release(work); | ||
132 | f(work); | ||
133 | |||
134 | spin_lock_irqsave(&cwq->lock, flags); | ||
135 | cwq->current_work = NULL; | ||
136 | ret = 1; | ||
137 | } | ||
138 | spin_unlock_irqrestore(&cwq->lock, flags); | ||
139 | return ret; | ||
140 | } | ||
141 | |||
142 | /** | ||
143 | * run_scheduled_work - run scheduled work synchronously | ||
144 | * @work: work to run | ||
145 | * | ||
146 | * This checks if the work was pending, and runs it | ||
147 | * synchronously if so. It returns a boolean to indicate | ||
148 | * whether it had any scheduled work to run or not. | ||
149 | * | ||
150 | * NOTE! This _only_ works for normal work_structs. You | ||
151 | * CANNOT use this for delayed work, because the wq data | ||
152 | * for delayed work will not point properly to the per- | ||
153 | * CPU workqueue struct, but will change! | ||
154 | */ | ||
155 | int fastcall run_scheduled_work(struct work_struct *work) | ||
156 | { | ||
157 | for (;;) { | ||
158 | struct cpu_workqueue_struct *cwq; | ||
159 | |||
160 | if (!work_pending(work)) | ||
161 | return 0; | ||
162 | if (list_empty(&work->entry)) | ||
163 | return 0; | ||
164 | /* NOTE! This depends intimately on __queue_work! */ | ||
165 | cwq = get_wq_data(work); | ||
166 | if (!cwq) | ||
167 | return 0; | ||
168 | if (__run_work(cwq, work)) | ||
169 | return 1; | ||
170 | } | ||
171 | } | ||
172 | EXPORT_SYMBOL(run_scheduled_work); | ||
173 | |||
174 | static void insert_work(struct cpu_workqueue_struct *cwq, | 101 | static void insert_work(struct cpu_workqueue_struct *cwq, |
175 | struct work_struct *work, int tail) | 102 | struct work_struct *work, int tail) |
176 | { | 103 | { |