OS 2.4.2 硬件同步机制
写在前面
自己看课本做的一点记录。
教材是西安电子科技大学出版社的《计算机操作系统》(第四版),汤小丹等人编著。
为什么不用软件
解决进程互斥进入临界区的问题,如果用软件方法:可以实现,但有一定难度,而且有局限性。
硬件方法
1.关中断
原文
在进入锁测试之前关闭中断,直到完成锁测试并上锁之后才能打开中断。这样,进程在临界区执行期间,计算机系统不响应中断,从而不会引发调度,也就不会发生进程或线程切换。
理解
这段有点抽象。“测试锁的开关状态”之前,就需要暂停“中断”这种操作,直到锁被测试并被关上为止。在“测试锁的开关状态”这个过程中,要保证此过程不被其他方式打断。
缺点
- 滥用会导致严重后果(什么严重后果让我上课后问一下)
- 时间过长影响系统效率(限制处理器交叉执行程序的能力)
- 不适用于多CPU系统(不能保证其他处理器不执行相同的临界段代码)
2.利用Test-and-Set指令实现互斥
ts代码
TS指令
boolean TS(boolean *lock)//*lock=FALSE时,表示资源空闲;*lock=TRUE时,资源正被使用
{
//一个布尔型数据
boolean old;
//存放原*lock值
old = *lock;
//置*lock为真
*lock = TRUE;
//返回以前lock的状态值
return old;
}
诚实地说,我前两遍没太搞懂ts语句的意义,发现一步步分析会有助于理解。函数意义理解如下:
lock为false时,置old为false,置lock内容为true。
这意思应该是说,当资源空闲的时候执行此代码,即是用old标记此时的状态(此时是空闲),再置lock为忙,向外返回的状态是old(空闲状态)。
lock为true时,置old为true,置lock内容为true。
经过这段代码的一顿操作,lock值也没有从false到true的变化,只不过是向外返回的状态是“被占用”。
先假设有一个场景吧:
临界资源一直被其他进程占用,不断试探临界资源之后,才终于为自己这个进程所有。
根据自己的理解分析那么一下下:资源被其他进程占用的时候,old都是true。直到其他进程结束对临界资源的使用,old变成了false,本进程才发现ts语句返回的结果是false,这时候就能进入临界区代码了。
来看看课本上的使用场景
do{
...
//TS指令测试lock值
while TS(&lock);
//只要ts语句返回是true,那么仍旧进行...内的代码执行?
//而ts语句返回一旦改变,就能够跳出do-while循环,进入自己的操作,也就是开始临界区代码执行。
//迎来了临界区代码
cirtical section;
//执行结束,开锁!
lock=FALSE;
//剩余区
remainder section;
}while(TRUE);
3.利用Swap指令实现进程互斥
swap代码
没啥新颖的,就是传统swap。
void swap(boolean *a,boolean *b)
{
boolean temp;
temp = *a;
*a = *b;
*b = temp;
}
这个简单的swap如何实现进程互斥呢?
看下原文:
给每个临界资源设置一个全局的布尔变量lock,初值是false,在每个进程中再利用一个局部变量key。
意思就是给资源和进程都配个锁和钥匙呗?
看下实现代码:
do{
//钥匙永远是true
key=true;
//直到钥匙变成false之前都进行与lock的交换
//某一次循环中,若lock为false,那么key就会由true变成false
//若lock为true,那么key还是true,不会改变
do{
swap(&lock,&key);
}while(key != false);
//临界区代码
critical section;
//解锁
lock = false;
//剩余区
remainder section;
}while(true);
和TS的区别?
有那么点意思了,配合ts指令进行理解,发现这也是一种倒换,只不过,给每个资源都配上了一个锁,每个进程都配上了一把钥匙,而非用临时变量观察占用状态是否发生转换。
后记
本来想多写一点的,没想到时间不太够用,必须要投入到计组复盘大业中了!
下一篇写信号量机制,想和经典同步问题一起介绍~