感觉通过贴代码,写注释的方法来描述,往往不能很好的把大体框架,总是陷入代码的细节中,所以这次就少贴代码,只说代码流程。
在每个cpu的调度队列上都有一个migration_thread,该migration_thread负责在该队列负载不均衡的时候将该调度队列上的任务,“推送”到其他的cpu上去。该线程往往一般是处于休眠状态,当在load_balance函数中进行move_tasks失败时,就会将该线程唤醒,主动推送任务到其他cpu上。move_tasks有时候失败是因为要移动的任务当前正在执行,但是将migration_thread唤醒后,要移动的任务肯定不处于执行状态,所以再次移动就会成功。此外,migration_thread还负责处理进程迁移请求队列中的请求,下文有介绍。
在主调度器schedule中会判断当前CPU的rq上的进程个数是否为0,如果为0的话,说明该cpu即将处于空闲状态,就调用idle_balance函数,进行负载均衡,看这个cpu能否为其他的cpu分担负载。
idle_balance函数会按从低到高的顺序遍历该cpu所在的调度域,在每个调度域上执行函数load_balance_newidle,该函数和load_balance函数很类似,感觉最大的不同就是传递当前cpu空闲状态不同,idle总是等于CPU_NEWLY_IDLE。load_balance_newidle的流程如下:
1.调用find_busiest_group找出最忙的调度组。
2.如果找到最忙的调度组,则在最忙的调度组上调用find_busiest_queue,找出该组上最忙的cpu调度队列。
3.如果能够找到最忙的调度队列,而且调度队列中的任务个数不止1个,则调用move_tasks将最忙的调度队列上的一些任务移动到当前cpu的队列中,让这个即将处于idle状态的cpu帮最忙的cpu分担一些任务。
4.move_tasks移动任务成功还则罢了,否则,更新移动失败的