操作系统笔记四 进程管理进程同步
Posted Lora青蛙
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了操作系统笔记四 进程管理进程同步相关的知识,希望对你有一定的参考价值。
(笔记根据王道、天勤参考书及视频总结)
进程同步的基本概念
进程同步:在多道程序环境下,进程是并发执行的,不同进程之间存在着不同的相互制约关系。
临界资源
多道程序系统中存在许多进程,它们共享各种资源,然而有很多资源一次只能供一个进程使用。一次仅允许一个进程使用的资源称为临界资源。许多物理设备都属于临界资源,如输入机、打印机、磁带机等。
对临界资源的访问,必须互斥地进行,在每个进程中,访问临界资源的那段代码称为临界区。
// 为了保证临界资源的正确使用,可以将临界资源的访问分为4个部分
do {
entry section; // 进入区(检查进程是否可以进入临界区)
critical section; // 临界区(访问临界资源的那段代码)
exit section; // 退出区(清除正在访问临界区的标志)
remainder section;// 剩余区(剩余代码)
} while(true)
同步
互斥
区分互斥和同步只需记住,只要是同类进程即为互斥关系,不同类进程即为同步关系,例如消费者和消费者就是互斥关系,消费者和生产者就是同步关系。
实现临界区互斥的基本方法
1.软件实现方法
在进入区设置和检查一些标志来表明是否有进程在临界区中,如果已有进程在临界区,则在进入区通过循环检查进行等待,进程离开临界区后则在退出区修改标志。
算法一:单标志法(违背“空闲让进”)
该算法设置一个公用整型变量turn,用于指示被允许进入临界区的进程编号,即若turn = 0 ,则允许p0 进程进入临界区。该算法可确保每次只允许一个进程进入临界区。但两个进程必须交换进入临界区,如果某个进程不再进入临界区了,那么另一个进程也将无法进入临界区(违背“空闲让进”)。这样很容易造成资源利用不充分。
若p0顺利进入临界区并从临界区离开,那么此时临界区是空闲的,但p1 并没有进入临界区的打算,turn = 1 一直成立,p0 就无法再次进入临界区了(一直被 while 死循环困住)。
算法二:双标志法先检查(违背“忙则等待”)
该算法的基本思想是在每一个进程访问临界区资源之前,先查看一下临界区资源是否正被访问,若正被访问,该进程需等待;否则,进程才进入自己自己的临界区。为此,设置一个数据 flag[ i ] ,如第i个元素值为 FALSE ,表示Pi进程未进入临界区,值为 TRUE ,表示Pi进程进入临界区。
优点:不用交替进入,可连续使用。
缺点:Pi 进程和 Pj进程可能同时进入临界区。 检查和修改操作不能一次进行。
算法三:双标志法后检查(会导致“饥饿”现象)
算法二是先检查对方进程状态标志后,再置自己的标志,由于在检查和放置中可插入另一个进程到达时的检测操作,会造成两个进程在分别检查后,同时进入临界区。为此,算法三采用先设置自己标志为 TRUE 后,再检测对方状态标志,若对方标志位 TRUE,则进程等待;否则进入临界区。
当两个进程几乎同时都想进入临界区时,它们分别将自己的标志值 flag 设置为 TRUE ,并且同时检测对方的状态(执行 while 语句),发现对方也要进入临界区,于是双方互相谦让,结果谁也进不了临界区,从而导致“饥饿”现象。
算法四:Peterson’s Algorithm(皮特森算法:单标志法和双标志法后检查的结合)
为了防止两个进程为进入临界区而无限期等待,又设置变量 turn ,,每个进程在设置自己标志后再设置 turn 标志。这时,再同时检测另一个进程状态标志和不允许进入标志,这样可以保证当进程同时要求进入临界区,只允许一个进程进入临界区。
具体如下:考虑进程 Pi ,一旦它设置 flag[ i ] = true ,表示它想要进入临界区,同时 turn = j ,此时如果进程 Pj 已经在临界区中,则符合进程Pi 的while循环条件,则Pi 不能进入临界区。而如果 Pj 进程没要进入临界区,即 flag[ j ] = FALSE ,循环条件不符合,则 Pi 进程可以顺利进入,反之亦然,本算法的基本思想是:算法一和算法三的结合。利用 flag 解决临界资源的互斥访问,而利用 turn 解决“饥饿”现象。
2.硬件实现方法
计算机提供了特殊的硬件指令,允许对一个字中的内容进行检测和修正,或者是对两个字的内容进行交换等。通过硬件支持实现临界区问题的低级方法或称为元方法。
(1)中断屏蔽方法
(2)硬件指令方法
信号量
P操作相当于申请资源,V操作相当于释放资源。
信号量的分类
1.整型信号量
2.记录型信号量
在整型信号量机制中的wait操作,只要是信号量S<=0,就会不断测试。因此,该机制并未遵循“让权等待”准则,而是使进程处于“忙等”状态。记录型信号量机制则是一种不存在“忙等”现象的进程同步机制。
但在采取了“让权等待”的策略后,又会出现多个进程等待访问同一个临界资源的情况。为此,在信号量机制中,除了需要一个用于代表资源数目的整型变量value外,还应该增加一个进程链表指针L,用于链接上述的所有等待进程。记录型信号量是由于它采用了记录型的数据结构而得名的。
当 S.value<0时,表示该类资源已分配完毕,因此进程应调用block原语,进行自我阻塞,放弃处理机,并插入到信号量链表S.L 中。该机制遵循了“让权等待”准则。此时 S.value 的绝对值表示在该信号量链表中已阻塞进程的数目
若加1后仍是S.value≤0,则表示在该信号量链表中,仍有等待该资源的进程被阻塞,故还应调用wakeup原语,将S.L链表中的第一个等待进程唤醒
注意边界条件,小于等于0,意思就是只要之前有等待的进程,加一后可以满足一个等待进程的资源请求,所以就唤醒一个等待进程。
如果S.value的初值为1,表示只允许一个进程访问临界资源,此时的信号量转化为互斥信号量,用于进程互斥。
信号量的应用
经典同步问题
进程同步问题历来是操作系统考核的重点,基本以三种经典同步习题及其衍生问题为主要考察内容。
生产者-消费者问题
生产者-消费者问题是著名的进程同步问题。它描述的是一组生产者向一组消费者提供产品,他们共享一个有界缓冲区,生产者向其中投入产品,消费者从中取走产品。
这个问题是许多相互合作进程的一种抽象。如,在输入时,输入进程是生产者,计算进程是消费者;在输出时,计算进程是生产者,打印进程是消费者。
为解决这一问题,应当设置两个同步信号量:
一个说明空缓冲区数目,用empty表示,初值为有界缓冲区大小n;
另一个说明满缓冲区数目(即产品数目),用full表示,初值为0。
此外,还需要设置一个互斥信号量mutex,初值为1,以保证多个生产者或者消费者互斥地访问缓冲池。
Semaphore full=0;//满缓冲区数目
Semaphore empty=n;//空缓冲区数目
Semaphore mutex=1;//对有界缓冲区进行操作的互斥信号量
Producer()
{
while(true)
{
Produce an item put in nextp;//nextp为临时缓冲区
P(empty);//申请一个空缓冲区
P(mutex);//申请使用缓冲池
将产品放入缓冲池
V(mutex);//缓冲池使用完毕,释放互斥信号量
V(full);//增加一个满缓冲区
}
}
Consumer()
{
while(true)
P(full);//申请一个满缓冲区
P(mutex);//申请使用缓冲池
取出产品
V(mutex);//缓冲池使用完毕,释放互斥信号量
V(empty);//增加一个空缓冲区
Consumer the item in nextc;//消费掉产品
}
}
特别注意:
P(full)/P(empty)与P(mutex)的顺序不可颠倒,必须先对资源信号量进行P操作,再对互斥信号量进行P操作,否则会导致死锁。
读者-写者问题
待梳理
哲学家进餐问题
理发师问题
管程
以上是关于操作系统笔记四 进程管理进程同步的主要内容,如果未能解决你的问题,请参考以下文章