本章讨论了Unix/Linux中的进程管理;
介绍了进程的概念;
多任务处理原则和多任务处理的基本系统,并给出了实例与代码,稍后将会实现之;
进程同步的概念与基本运行原理;
MT系统中的进程管理;
Unix/Linux系统进程的来源;
进程管理的系统调用;
I/O重定向和管道相关的内容。
多任务处理
计算机技术概念中的多任务处理指的是同时执行若干独立任务。无论是在多处理机系统还是单处理机系统都可以实现多任务处理。对于单处理机系统,多任务处理的实现依靠着多路复用技术,通过上下文的快速切换实现逻辑上的多任务并行处理。这种并行性被称为并发。
进程的概念
进程是对映像的执行。一个进程是一个对资源的动态利用的过程,系统内核通过一个独特的数据结构来表示,它被称为进程控制块PCB或任务控制块TCB。在本章中直接称之为PROC结构体。以下是PROC的一般定义:
其中,next是指向下一个PROC结构体的指针;
ksp字段是保存的堆栈指针,存储了放弃使用CPU的进程的上下文;
pid标识一个进程的ID编号;
ppid为父进程的编号;
status是进程的当前状态;
priority是进程的调度优先级;
kstack是进程执行时的堆栈。
多任务处理系统,简称MT,具有如下格式:
type.h文件,定义了系统常数和简单的PROC结构体:
/*********** type.h file ************/ #define NPROC 9 //numbers of PROC #define SSIZE 1024 //stack size = 4KB // PROC status #define FREE 0 #define READY 1 #define SLEEP 2 #define ZOMBIE 3 typedef struct proc{ struct proc *next; //next proc pointer int *ksp; //saved stack pointer int pid; //pid = 0 to NPROC-1 int ppid; //parent pid int status; //PROC status int priority; //scheduled priority int kstack [SSIZE]; //process stack }PROC;
ts.s文件,32汇编代码,用于实现上下文切换:
#-------------- ts.s file ---------------- .globl running,scheduler, tswitch tSwitch: SAVE: pushl %eax : pushl %ebx pushl %ecx pushl %edx pushl %ebp pushl %esi pushl %edi pushf1 movl running, Sebx mov1 # esp,4(%ebx) FIND: call scheduler RESUME: movl running,8ebx movl 4(%ebx),%esp popf1 popl %edi popl %esi popl %ebp popl %edx popl %ecx popl %ebx popl %eax ret # stack contents=|retPC|eax|ebx|ecx|edx|ebp|esi|edi|eflag| # -1 -2 -3 -4 -5 -6 -7 -8 -9
queue.c文件,可实现队列和链表操作函数:
/******************************* queue.c file *******************************/ int enqueue(PROC **queue,PROC *p) { PROC *q = *queue; if(q == 0 || p->priority> q->priority){ *queue = p; p->next = q; } else{ while(g->next && p->priority <= q->next->priority) q = q->next; p->next = q->next; q->next = p; } } PROC *dequeue (PROC **queue) { PROC *p = *queue; if (p) *queue =(*queue)->next; return p; } int printList(char *name,PROC *p) { printf("%s = ",name); while(p){ printf("[8d %d]->",p->pid,p->priority); p = p->next; } printf("NULL\n"); }
t.c文件,定义MT系统数据结构、系统初始化代码和进程管理函数:
/*********** t.c file of A Multitasking System ***********/ #include <stdio.h> #include "type.h" PROC proc[NPROC]; //NPROC PROCs PROC *freeList; //freeLists PROC *readyQueue; PROC *running; #include "queue.c" /*********************************************************** kfork() creats a child process and returns a chile pid, When scheduled to run , child PROC resumes to body; ***********************************************************/ int kfrok() {...} int kexit() //to exit {...} int do_kfork() {...} int do_switch() {...} int do_exit() {...} int body() //prcdess body function {...} int init() {...} int main() {...} int scheduler() {...}
睡眠模式
顾名思义,当进程需要某些当前没有的东西时就会进入睡眠模式,在PROC结构体添加event字段即可实现休眠功能:
typedef struct proc{ ... int event; int exitevent; struct proc *child; struct proc *sibling; struct proc *parent; ... }PROC
唤醒操作
当等待的东西准备好后,就需要等待者醒来,进行下一步操作,调用kwakeup()就可以唤醒进程。
进程终止
在操作系统中,进程会终结或死亡,即进程终止。进程终止有两种方式: