信号量机制
Posted 杀手不太冷!
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了信号量机制相关的知识,希望对你有一定的参考价值。
信号量机制
知识总览图
引子
信号量机制定义
P就相当于wait就相当于wait(S),意思是进入区的检查和上锁原语操作;
V就相当于signal就相当于signal(S),意思是退出区的解锁原语操作;
信号量机制–整型信号量
首先要知道什么叫做"忙等"和"让权等待"?
忙等待:如果进程不能访问临界区,那么此进程会一直占用CPU,一直申请进入临界区操作,直到申请成功。
让权等待:如果进程不能访问临界区,即申请临界区失败,那么会主动的阻塞,让出CPU,如sleep()睡眠进程其实就是一种让权等待,当进程访问临界区失败时,睡眠的进程会sleep一段时间,醒来后继续运行。
下图中:
wait方法是一个原语,里面的代码会一气呵成的执行,中间不允许被打断;while(S<=0)此句代码是检查临界区是否可以访问,如果S>0,那么循环是不满足条件的,这个时候进程是可以访问临界区的,S=S-1是给临界区上锁,S本来等于1,这个时候P0进程是可以访问临界区的,但是在上锁之后,S就变成了0,这个时候其它的进程如P1就不可以访问临界区了,因为执行while(S<=0)语句时会发生死循环,这和双标志先检查法逻辑是相同的,但是不同的是,这里因为用到了wait原语,检查和上锁是一气呵成的,中间不允许被打断,这就避免了在双标志先检查法中并发、异步导致的问题;但是整型信号量这种方式不满足让权等待,即如果一个进程访问临界区失败的话,会一直执行while循环语句,进入忙等,而不会主动的放弃CPU的使用权。
上图中如果进程P0执行了wait操作之后,那么其他的进程都会卡在wait原语中的while循环的地方,一直循环,无法进入临界区。
信号量机制–记录型信号量
上图中的value就代表剩余资源的数目,比如资源是打印机,并且只有1个打印机,那么value的初始值就是1,假如只有一个线程A,那么线程A执行wait操作,先执行S.value–,之后value的值变成了0,然后执行if(S.value<0)不满足条件,因此线程A不会阻塞;假如有两个进程,进程A和进程B,进程A先执行wait原语,之后value的值变成了0,然后线程B执行wait原语,这个时候value的值变成-1,因为if条件满足,所以线程B会执行block(S.L),然后线程B会被放入到L这个等待队列中,这样就满足了“让权等待”;等到线程A执行signal退出区的解锁原语,会先让s.value++,然后value此时的值为0,但是初始值value的值等于1有一台打印设备,现在为什么变成0了呢?就是因为有另外一个线程执行了wait原语操作,让value的值减去了1。并且这个线程现在肯定是在L阻塞队列中,所以如果value的值小于等于0,那么肯定说明L阻塞队列中存在被阻塞的进程,我们需要把它主动唤醒,而wakeup(S.L)的作用就是主动唤醒L队列中的一个进程。
下面是一个记录型信号量的例子:
假设某计算机系统中有2台打印机,如下图:
然后CPU切换到了P1进程,如下图:
接着CPU切换到了P2进程,如下图:
接着CPU切换到了P3进程,如下图:
接着CPU执行P0进程的sinnal(S)退出区的解锁原语,这个时候,剩余资源数会加一,所以value会变成-1,然后会唤醒等待队列的链表头部的进程也即是P2,最后会把打印机资源分配给P2进程,如下图:
记录型信号量的简单总结,如下图:
以上是关于信号量机制的主要内容,如果未能解决你的问题,请参考以下文章
操作系统 王道考研2019 第二章:进程管理 -- 信号量机制(整型 / 记录型信号量)原语P / V操作用信号量机制实现进程互斥同步前驱关系