linux2.6进程管理

来源:互联网 发布:香港国际网络电视台 编辑:程序博客网 时间:2024/05/17 03:20

                                                    linux2.6进程管理

                                        作者  :流氓虫

                                                    http://blog.csdn.net/xph23/archive/2010/12/04/6054991.aspx

  内核中把进程存放在叫做任务队列的双向循环链表中,链表中的每一线都是task_struct,成为进程描述符,从cpu的角度来看,一个task_struct描述了这个进程的所有信息,包括进程号,优先级,它打开的文件,进程的地址空间,挂起的信号,进程的状态等等,通过current宏可以查到当前正在运行的进程的进程描述符,

       一个正在运行的操作系统会有很多进程争取处理器有限的时间资源,内核是如何进行管理的呢?

       内核是通过调度程序进行管理的, 调度程序时内核的非常重要的部分,他负责选择下一个要运行的进程,调度程序可以看做是可运行态进程之间分配有限处理器时间资源的代码,只有 通过调度程序的合理调度,系统资源才能最大限度的发挥作用,多进程才会有并发执行的效果。

      调度程序中最基本的数据结构式运行队列(runqueue),他定义在kernel/sched.c中,由结构runqueue表示,可执行队列是一个链表,是给定处理器上的可执行进程的链表,每个处理器一个,每个可投入运行的进程都唯一的归属于一个可执行队列,此外,可执行队列还包含每个处理器的调度信息,可执行队列是每个处理器最重要的数据结构。内核通过可执行队列队进程进行调度。

      用于获取给定可执行队列的宏定义:

  cpu_rq(processor): 用于返回给定处理器的可执行队列的指针。

  this_rq():                  用于返回当前处理器的可执行队列。

  task_rq():                 返回给定任务所在队列的指针。

在对可执行队列进行操作之前,应该要锁住他,因为每个处理器唯一的对应着一个可执行队列,所以很少出现一个处理器需要锁住其他处理器可执行队列的情况,但还是有。在其拥有者读取或者改写队列成员的时候,可执行队列包含的锁用来防止队列被其他代码改动,锁住摸个队列的最常见情形发生一个特定的任务在运行队列上执行时,可以用以下两个函数进行

task_rq_lock()

task_rq_unlock()

也可以用this_rq_lock()来锁住当前的可执行队列,用this_rq_unlock(struct runqueue *rq)释放给定队列上的锁。

 

 

优先级数组:

   每个运行队列都有两个优先级数组,一个活跃的,一个过期的,优先级数组在kernel/sched.c中被定义,他是prio_array类型的结构体

优先级数组可以使得每个运行处理器的每一种优先级都包含一个相应的队列,而这些队列包含对应优先级上的可以执行进程链表。优先级数组还拥有一个优先级位图,当需要查找当前系统内拥有最高优先级的可执行进程时,它可以帮助提高效率,

 struct prio_array{

int nr_active; /*任务数目*/

unsigned long bitmap[BITMAP_SIZE];/*优先级位图*/

struct list_head;/*优先级队列*/

};

之所以为每个处理器维护两个优先级数组,即活动数组和过期数组,活动数组 内的可执行队列上的进程都还有剩余时间片,而过期数组内的可执行队列上的进程都已经耗尽了时间片,都一个进程的时间片被耗尽的时候,就会被移动到过期数组,分配两个优先级数组对重新计算时间片很有帮助,这样,他就不会像其他的很多操作系统一样用现实的方法重新计算每个进程的时间片。他只需要在活动和过期数组间进行切换即可,

}

 

参考文献:linux内核设计与实现

原创粉丝点击