《操作系统概念(原书第9版)》
第6章 同步
6.6 信号量
例题
1.已知生产者、消费者问题的代码:
生产者:
Producer () {
while (true) {
/* produce an item and
put in nextProduced */
while (count == BUF_SIZE)
; // do nothing
buffer [in] = nextProduced;
in = (in + 1) % BUF_SIZE;
count++;
}
}
消费者:
Consumer () {
while (true) {
while (count == 0)
; // do nothing
nextConsumed = buffer[out];
out = (out + 1) % BUF_SIZE;
count--;
/* consume the item in
nextConsumed */
}
}
请使用信号量(semaphore),修改现有代码,实现生产者和消费者可能会引起资源竞争的代码的互斥,并分析该实现是否正确、是否会发生死锁(8’)。
答:
Semaphore full = 0;
Semaphore empty = BUF_SIZE;
Semaphore mutex = 1; // 初始化1分
生产者:
Producer () {
while (true) {
/* produce an item and
put in nextProduced */
Wait (empty);
Wait (mutex);
buffer [in] = nextProduced;
in = (in + 1) % BUF_SIZE;
count++;
Signal (mutex);
Signal (ful);
}
}
消费者:
Consumer () {
while (true) {
Wait (full);
Wait (mutex);
nextConsumed = buffer[out];
out = (out + 1) % BUF_SIZE;
count--;
Signal (mutex);
Signal (empty);
/* consume the item in
nextConsumed */
}
}
初始化1分,程序基本正确3分,给了分析1分。
2.有一阅览室,共有100个座位。读者进入时必须先在一张登记表上登记,该表为每一座位列表目,包括座号和读者姓名。读者离开时要消掉登记内容。试用P、V操作描述读者进程的同步结构。
答:
var
mutex : semaphere; 信号量,用于互斥
full : semaphere; 信号量,用于同步
table : array 0..n-1 of item; 登记表
procedure reader; 读者进程
begin
P(full);
P(mutex);
Register_name(table);
V(mutex);
Reading;
P(mutex);
Delet_name(table);
V(mutex);
V(full)
end;
3.生产围棋的工人不小心将相等数量的黑子和白子混合装在一个盒子里。现要用自动分拣系统将黑子和白子分开,该系统由两个并发执行的进程Pa和Pb组成。系统功能如下:Pa专拣黑子,Pb专拣白子;每次都只能拣一个子,当一个进程拣子时,不允许另一个进程去拣子;当一个进程拣子后,必须让另一个进程进行拣子。试解答以下问题,实现对两个拣子并发进程进行描述:
- 写出对信号量的定义及其初值的设置。(3分)
- 利用所定义的信号量,采用P、V操作,描述两个进程拣子的并发过程。(7分)
答案:(仅供参考)
- 信号量及其初值:
同步信号量 int S1; 初值为1,允许拣黑子,如果为0,表示不允许拣黑子。
int S2; 初值为1,允许拣白子,如果为0,表示不允许拣白子。
互斥信号量 int mutex; 初值为1,允许进入盒子临界空间进行拣子,如果为0,表示不允许进入盒子临界区。
- 并发过程描述:
main()
{
Semaphore S1,mutex,S2;
S1=1; mutex=1; S2=0;
Cobegin
processPa();
processPb();
Coend
}
processPa()
{
while (1)
{
P(S1);
P(mutex);
拣黑子;
V(mutex);
V(S2);
}
}
processPb()
{
while (1)
{
P(S2);
P(mutex);
拣白子;
V(mutex);
V(S1);
}
}
4.有一个桥如图所示,桥上的车流如箭头所示。桥上不允许两车交会,但允许同方向多辆车依次通行(即桥上可以有多个同方向的车)。请用P、V操作实现交通管理以防止桥上拥塞的程序。
答案
由于桥上不允许两车相会,故桥应该被互斥访问,而同一方向上允许多辆车依次通过,即临界区允许多个实例访问。用一个信号量来互斥访问临界区。由于不能允许某一个方向的车完全“控制”桥,应保证最多某一个方向上连续通过一定数量的车后,必须让另外一个方向的车通过。用另外两个信号量来实现这个。
故:
设smutex用来控制从南向北车辆数量s的互斥信号量
nmutex用来控制从南向北车辆数量n的互斥信号量
wait用来控制会车的互斥访问