1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135
| 2114
2128 static void process_one_work(struct worker *worker, struct work_struct *work) 2129 __releases(&pool->lock) 2130 __acquires(&pool->lock) 2131 { 2132 struct pool_workqueue *pwq = get_work_pwq(work); 2133 struct worker_pool *pool = worker->pool; 2134 bool cpu_intensive = pwq->wq->flags & WQ_CPU_INTENSIVE; 2135 int work_color; 2136 struct worker *collision; 2137 #ifdef CONFIG_LOCKDEP 2138
2145 struct lockdep_map lockdep_map; 2146 2147 lockdep_copy_map(&lockdep_map, &work->lockdep_map); 2148 #endif 2149
2154 WARN_ON_ONCE(!(worker->flags & WORKER_UNBOUND) && 2155 !(pool->flags & POOL_DISASSOCIATED) && 2156 raw_smp_processor_id() != pool->cpu); 2157 2158
2164 collision = find_worker_executing_work(pool, work); 2165 if (unlikely(collision)) { 2166 move_linked_works(work, &collision->scheduled, NULL); 2167 return; 2168 } 2169 2170 2171 debug_work_deactivate(work); 2172 hash_add(pool->busy_hash, &worker->hentry, (unsigned long)work); 2173 worker->current_work = work; 2174 worker->current_func = work->func; 2174 worker->current_func = work->func; 2175 worker->current_pwq = pwq; 2176 work_color = get_work_color(work); 2177 2178 list_del_init(&work->entry); 2179 2180
2184 if (unlikely(cpu_intensive)) 2185 worker_set_flags(worker, WORKER_CPU_INTENSIVE, true); 2186 2187
2191 if ((worker->flags & WORKER_UNBOUND) && need_more_worker(pool)) 2192 wake_up_worker(pool); 2193 2194
2200 set_work_pool_and_clear_pending(work, pool->id); 2201 2202 spin_unlock_irq(&pool->lock); 2203 2204 lock_map_acquire_read(&pwq->wq->lockdep_map); 2205 lock_map_acquire(&lockdep_map); 2206 trace_workqueue_execute_start(work); 2207 worker->current_func(work); 2208
2212 trace_workqueue_execute_end(work); 2213 lock_map_release(&lockdep_map); 2214 lock_map_release(&pwq->wq->lockdep_map); 2215 2216 if (unlikely(in_atomic() || lockdep_depth(current) > 0)) { 2217 pr_err("BUG: workqueue leaked lock or atomic: %s/0x%08x/%d\n" 2218 " last function: %pf\n", 2219 current->comm, preempt_count(), task_pid_nr(current), 2220 worker->current_func); 2221 debug_show_held_locks(current); 2222 dump_stack(); 2223 } 2224 2225
2232 cond_resched(); 2233 2234 spin_lock_irq(&pool->lock); 2235 2236 2237 if (unlikely(cpu_intensive)) 2238 worker_clr_flags(worker, WORKER_CPU_INTENSIVE); 2239 2240 2241 hash_del(&worker->hentry); 2242 worker->current_work = NULL; 2243 worker->current_func = NULL; 2244 worker->current_pwq = NULL; 2245 worker->desc_valid = false; 2246 pwq_dec_nr_in_flight(pwq, work_color); 2247 }
|