1:初始化第一步:分配各项数据结构及系统workqueue
/**
-
workqueue_init_early - early init for workqueue subsystem
-
This is the first half of two-staged workqueue subsystem initialization
-
and invoked as soon as the bare basics - memory allocation, cpumasks and
-
idr are up. It sets up all the data structures and system workqueues
-
and allows early boot code to create workqueues and queue/cancel work
-
items. Actual work item execution starts only after kthreads can be
-
created and scheduled right before early initcalls.
/
int __init workqueue_init_early(void)
/ initialize CPU pools /
for_each_possible_cpu(cpu) //每个cpu
for_each_cpu_worker_pool(pool, cpu) //每个cpu的worker_pool
init_worker_pool(pool)
…
pool->flags |= POOL_DISASSOCIATED; //worker_pool未链接标记
…
pool->refcnt = 1;
/ shouldn’t fail above this point */
pool->attrs = alloc_workqueue_attrs(GFP_KERNEL);pool->cpu = cpu; cpumask_copy(pool->attrs->cpumask, cpumask_of(cpu)); pool->attrs->nice = std_nice[i++]; pool->node = cpu_to_node(cpu); worker_pool_assign_id(pool) ret = idr_alloc(&worker_pool_idr, pool, 0, WORK_OFFQ_POOL_NONE, GFP_KERNEL); pool->id = ret
/* create default unbound and ordered wq attrs */
for (i = 0; i < NR_STD_WORKER_POOLS; i++) //system中各有2个,分普通级和优先级