屏蔽了具体的调度算法,具体的调度算法在冰山之下
schedule
=>preempt_disable();
=>cpu = smp_processor_id();
rq = cpu_rq(cpu);
rcu_sched_qs(cpu);
prev = rq->curr;
switch_count = &prev->nivcsw;
=>if (prev->state && !(preempt_count() & PREEMPT_ACTIVE)) {
if (unlikely(signal_pending_state(prev->state, prev)))
prev->state = TASK_RUNNING;
else
deactivate_task(rq, prev, 1);//prev进程出队列
switch_count = &prev->nvcsw;
}
=>put_prev_task(rq, prev);//重新入队列,在红黑树的位置可能不在以前的位置了
=>next = pick_next_task(rq);//选择最左节点作为下一次调度的进程next
=>if (likely(prev != next)) {//prev和next不是同一进程则调度之
sched_info_switch(prev, next);
perf_event_task_sched_out(prev, next);
rq->nr_switches++;
rq->curr = next;
++*switch_count;
context_switch(rq, prev, next); /* unlocks the rq */
/*
* the context switch might have flipped the stack from under
* us, hence refresh the local variables.
*/
cpu = smp_processor_id();
rq = cpu_rq(cpu);
}
=>preempt_enable_no_resched();
参考文章
linux schedule 理解
https://blog.csdn.net/prike/article/details/79002717