工作者线程不断执行,从work_poll结构中卸下一个work, 然后进入函数process_one_work
来执行这个work.
process_one_work(struct worker *worker, struct work_struct *work)
下面一行行代码分析下:
首先,struct pool_workqueue *pwq = get_work_pwq(work);
我们知道了,原来,work_struct 结构体中一直有个域指向了pool_workqueue.得到pwq结构体是为了得到workqueue,[ by pwq->wq], pwq中有许多属于锁啊,包括是不是绑定在CPU上啊这些信息, 都是在处理一个任务的时候需要的
struct worker_pool *pool = worker->pool;
每一个worker对应着一个池子,worker_pool,
[一个work可能要被多个线程执行,什么情况下会如此呢?]
然后把当前的工作, 加入到woker->hentry的哈希表中
pool->busy_hash是一个哈希表struct hlist_head name[1 << (bits)], 这是个开链的哈希表,
把这个worker链到这个woker_pool上的哈希表上
[看来,并不是一个work_poll对应这一个worker, 多个线程对应着一个worker_poll, 这样设计有其合理性啊,因为如果系统当前比较空闲,但是就是有大量的工作被挂载了当前的work_pool上面, 这样的话, 我们就要多个线程来执行啊]
对于UNBOUND的线程来说,一个work_poll对应着多个worker线程看来是很正常的事情.
然后就是对worker->current_work设置:
worker->current_work = work;
worker->current_func = work->func;
worker->current_pwq = pwq;
然后最重要的一件事情就是worker->current_func(work);
这里就是调用实际的工作函数了:
比如wb_workfn了!