Sunteți pe pagina 1din 134

Process Synchronization

Part I

Operating System Concepts – 8th Edition, Modified by M.Rebaudengo – 2017 Silberschatz, Galvin and Gagne ©2009
Concurrency
The system must support concurrent execution of threads
Scheduling:
 Deals with execution of “unrelated” threads
Concurrency:
 Deals with execution of “related” threads

Why is it necessary?
Cooperation: One thread may need to wait for the result of some operation
done by another thread
e.g. “Calculate Average” must wait until all “data reads” are completed
Competition: Several threads may compete for exclusive use of resources
e.g. two threads trying to increment the value in a memory location

Operating System Concepts – 8th Edition 6.2 Silberschatz, Galvin and Gagne ©2009
Competition and Cooperation
Competition
Processes compete for resources
Each process could exist without the other

Cooperation
Each process is aware of the other
Processes Synchronization
Exchange information with one another
 Shared memory
 Message passing

Operating System Concepts – 8th Edition 6.3 Silberschatz, Galvin and Gagne ©2009
Resources
An object, necessary to a task in order to execute
Hardware resources:
 Co-processor
 I/O system (e.g., printer, disks)
 memory
 network
Software resources:
 buffer memory space
 portion of code source.

Operating System Concepts – 8th Edition 6.4 Silberschatz, Galvin and Gagne ©2009
Mutual Exclusion
Critical resource: a resource not shareable for which sharing by the threads
must be controlled by the system
Critical section (or critical region) of a program: a part of a program where
access to a critical resource occurs
If one thread is going to use a shared resource (critical resource)
a file
a variable
printer
register, etc
the other thread must be excluded from using the same resource

Operating System Concepts – 8th Edition 6.5 Silberschatz, Galvin and Gagne ©2009
Process Interaction
Processes unaware of each other: when several tasks want to obtain a resource,
they enter in competition.
independent processes not working together
The OS must resolve the competition for resources
 I/O, memory, printer, tape drive, etc.
Each process should leave the state of any resource that it uses unaffected
Issues involved:
 Mutual exclusion
– The resource being competed for is a critical resource
– The portion of program in each process that uses the critical resource is
a critical section
– At any time, only one program is allowed to be in its critical section.
 Deadlock:
– a deadlock is a state in which each member of a group of actions, is
waiting for some other member to release a resource
 Starvation:
– starvation is a problem encountered where a process is
perpetually denied necessary resources to process its work.

Operating System Concepts – 8th Edition 6.6 Silberschatz, Galvin and Gagne ©2009
Process Interaction (cont.)
Processes indirectly aware of each other (cooperation by sharing)
shared access to some object
 shared variables, files, or databases
 Processes may use and update the shared data without reference to
other process, but know that other processes may have access to
the same data.
Issues involved
 maintenance of data integrity
 Since data are stored in resources (devices, memory), the control
problems of mutual exclusion, deadlock, and starvation are still
present.
– Mutual exclusion applies only to writing, not reading of data.
 Data coherence
– Example: a = b must be enforced in the following two processes:
– P1: a := a + 1;
b := b + 1;
P2: b := 2 * b; (Cont.)
Operating System Concepts – 8th Edition a := 2 * a; 6.7 Silberschatz, Galvin and Gagne ©2009
Process interaction (cont.)
If the traces of P1 and P2 are as below, a = b is not enforced.
1. a := a + 1;
2. b := 2 * b;
3. b := b + 1;
4. a := 2 * a;
The solution is to put the instructions of each process in a critical section.

Operating System Concepts – 8th Edition 6.8 Silberschatz, Galvin and Gagne ©2009
Process interaction (cont.)
Processes directly aware of each other (cooperation by communication)
Interprocess communication exists.
Sending and receiving of messages are involved.
Issues involved
 no shared object, hence no mutual exclusion
 The problems of deadlock and starvation are still present.
– deadlock: two processes may be blocked, waiting for a message
from the other.
– starvation: three processes are involved in communication, but
two of them exchange information repeatedly that the third one
waits indefinitely for its turn.

Operating System Concepts – 8th Edition 6.9 Silberschatz, Galvin and Gagne ©2009
Example: Producer-Consumer Problem
Paradigm for cooperating processes
producer process produces information that is consumed by a
consumer process later
Since a producer and a consumer can work at different speeds, a
buffer is needed where the producer can temporarily store data that
can be retrieved by the consumer at a more appropriate speed

Producer buffer Consumer

An integer count keeps track of the number of full buffers.


Initially, count is set to 0.
It is incremented by the producer after it produces a new buffer
It is decremented by the consumer after it consumes a buffer.

Operating System Concepts – 8th Edition 6.10 Silberschatz, Galvin and Gagne ©2009
Bounded-Buffer
Data shared by the producer and the consumer
#define BUFFER_SIZE 10
typedef struct {
. . .
} item;

item buffer[BUFFER_SIZE];
int in = 0;
int out = 0;
Circular Array:
in points to the next free position in the buffer
out points to the first full position in the buffer

Operating System Concepts – 8th Edition 6.11 Silberschatz, Galvin and Gagne ©2009
Producer
out
while (true) {

/* produce an item and put in nextProduced */


while (count == BUFFER_SIZE)
; // do nothing In

buffer [in] = nextProduced;


in = (in + 1) % BUFFER_SIZE;
count++;
}

Operating System Concepts – 8th Edition 6.12 Silberschatz, Galvin and Gagne ©2009
Consumer
out

while (true) {
while (count == 0)
; // do nothing
nextConsumed = buffer[out];
In
out = (out + 1) % BUFFER_SIZE;
count--;

/* consume the item in nextConsumed


}

Operating System Concepts – 8th Edition 6.13 Silberschatz, Galvin and Gagne ©2009
Race Conditions
A race condition occurs when multiple processes are trying to do
something with shared data and the final outcome depends on the order
in which the processes run.

When two or more processes/threads are executing concurrently, the


result can depend on how the two instruction streams are interleaved.

Race conditions may cause:


undesired computation results.
bugs which are hard to reproduce!

Operating System Concepts – 8th Edition 6.14 Silberschatz, Galvin and Gagne ©2009
Race Condition

Race condition: The outcome of concurrent thread execution depends


on the particular order in which the access takes place.

count++ could be implemented as


register1 := count
register1 := register1 + 1
count := register1
count-- could be implemented as
register2 := count
register2 := register2 - 1
count := register2
Consider this execution interleaving with “count = 5” initially:
T0: producer execute register1 := count {register1 = 5}
T1: producer execute register1 := register1 + 1 {register1 = 6}
T2: consumer execute register2 := count {register2 = 5}
T3: consumer execute register2 := register2 - 1 {register2 = 4}
T4: producer execute count := register1 {count = 6}
T5: consumer execute count := register2 {count = 4}

To prevent race conditions, concurrent processes must be synchronized.

Operating System Concepts – 8th Edition 6.15 Silberschatz, Galvin and Gagne ©2009
Critical Section
In case of a set of n cooperating processes, competing to use some
shared data, the code segment, in which the shared data is accessed, is
called critical section.

Operating System Concepts – 8th Edition 6.16 Silberschatz, Galvin and Gagne ©2009
Critical-Section Problem
do {
entry section
critical section
exit section
remainder section
} while (TRUE);
A Critical Section environment contains:
Entry Section: code requesting entry into the critical section.
Critical Section: code in which only one process can execute at any one
time.
Exit Section: the end of the critical section, releasing or allowing others in.
Remainder Section: rest of the code after the critical section.
Operating System Concepts – 8th Edition 6.17 Silberschatz, Galvin and Gagne ©2009
Solution to Critical-Section Problem
The critical section must enforce all 3 of the
following rules:
1. Mutual Exclusion - If process Pi is
executing in its critical section, then no When coming and entering CS
other processes can be executing in their
critical sections
2. Progress - If no process is executing in its
critical section and there exist some 3. Delta time exists
processes that wish to enter their critical
section, then the selection of the processes
that will enter the critical section next 2. Pick up a process to enter
cannot be postponed indefinitely
3. Bounded Waiting - A bound must exist Critical Section
on the number of times that other
processes are allowed to enter their critical
sections after a process has made a
1. only one process
request to enter its critical section and
before that request is granted.

Speed and Number of CPUs: No assumption may


be made about speeds or number of CPUs. When exiting from CS

Operating System Concepts – 8th Edition 6.18 Silberschatz, Galvin and Gagne ©2009
Concurrency requirements
Among all threads that have CSs for the same resource
Only one thread at a time is allowed into its CS
It must not be possible for a thread requiring access to a CS to be
delayed indefinitely
no deadlock
no starvation
When no thread is in a CS, any thread requesting entry to the CS
must be granted permission without delay
No assumptions are made about the relative thread speeds or
number of processors.
A thread remains inside its CS for a finite time only.

Operating System Concepts – 8th Edition 6.19 Silberschatz, Galvin and Gagne ©2009
Comments
Deadlock (all processes are blocked) represents a violation of
progress
Starvation (a process never enters in CS) represents a violation of
bounded waiting.

Operating System Concepts – 8th Edition 6.20 Silberschatz, Galvin and Gagne ©2009
Other ways to report the rules
Requirements for critical section problem
Safety (aka mutual exclusion): only one process/thread at a time inside CS
Liveness (aka progress): if nobody has access and somebody wants to get in,
somebody gets in
No starvation (aka bounded waiting): if you want to get in, you will eventually get
in

Operating System Concepts – 8th Edition 6.21 Silberschatz, Galvin and Gagne ©2009
Desirable properties
Critical section problem requires some additional properties:
Efficiency: can get into CS in relatively few instructions
Low load: waiting for CS does not waste resources
Fairness: if you want in, nobody else gets in ahead of you twice (i.e., if two
threads are both trying to enter a critical section, they have equal chances of
success, or one has an initial priority, but for the second time the priority is
inverted).

Operating System Concepts – 8th Edition 6.22 Silberschatz, Galvin and Gagne ©2009
Types of solutions

Software solutions
algorithms whose correctness does not rely on any other assumptions
Hardware solutions
rely on some special machine instructions
Operating System solutions
provide some functions and data structures to the programmer

Operating System Concepts – 8th Edition 6.23 Silberschatz, Galvin and Gagne ©2009
Software solutions

Operating System Concepts – 8th Edition 6.24 Silberschatz, Galvin and Gagne ©2009
Critical section problem
Here’s an example of a simple piece of code containing the components
required in a critical section.
i is the current process, j the "other" process
The variable turn indicates whose turn it is to enter the critical section.

do {
Entry Section
while ( turn ^= i );
/* critical section */ Critical Section
turn = j;
/* remainder section */ Exit Section
} while(TRUE);
Remainder Section

Operating System Concepts – 8th Edition 6.25 Silberschatz, Galvin and Gagne ©2009
Algorithm 0
Solving the problem
Shared variables:
char inside; boolean variable
initially inside = 0

do {
while (inside) continue;
inside = true;
critical section
inside = false; Code is unsafe: thread 0 could finish the while
reminder section test when inside is false, but then 1 might check
before thread 0 can set inside to true!
} while (1);
Now ask:
Is this Mutual Exclusion? Progress? Bounded waiting?

Operating System Concepts – 8th Edition 6.26 Silberschatz, Galvin and Gagne ©2009
Algorithm 1
Shared Pointer to Active Process

Shared variables:
int turn;
initially turn = 0
turn = i  Pi can enter its critical section
Process Pi
do {
while (turn != i) ;
critical section
turn = j;
reminder section
} while (1);
Satisfies mutual exclusion, but not progress
Pi, Pj, Pi, Pj… strict alternation of processes
Pi leaves, Pj busy with long I/O, Pi comes back to CS-entry;
No one in the CS, but Pi has to wait until Pj to come to the CS
What if Pj never comes back to CS ?

Operating System Concepts – 8th Edition 6.27 Silberschatz, Galvin and Gagne ©2009
Boolean Array Algorithm 2

FLAG FOR EACH PROCESS GIVES STATE:


Each process maintains a flag indicating that it wants to get into the
critical section. It checks the flag of the other process and doesn’t
enter the critical section if that other process wants to get in.
Shared variables
boolean flag[2];
initially flag [0] = flag [1] = false.
flag [i] = true  Pi ready to enter its critical section

do {
flag[i] = true; Are the three Critical
while (flag[j]) ; Section Requirements Met?
critical section
flag [i] = false;
remainder section
} while (1);

Operating System Concepts – 8th Edition 6.28 Silberschatz, Galvin and Gagne ©2009
Boolean Array Algorithm 2

Satisfies mutual exclusion, but not progress requirement.


Pi Pj
do { do {
flag[i] = true; flag[j] = true;
while (flag[j]) ; while (flag[i]) ;
critical section critical section
flag [i] = false; flag [j] = false;
remainder section remainder section
} while (1); } while (1);

Pi: sets flag[i] to true


Pj: sets flag[j] to true
Indefinite wait: deadlock

Algorithm depends on the exact timing of the two processes

Operating System Concepts – 8th Edition 6.29 Silberschatz, Galvin and Gagne ©2009
Peterson’s Solution Algorithm 3

Two-process solution
Assume that the LOAD and STORE instructions are
atomic (they cannot be interrupted).
The two processes share two variables:
int turn;
Boolean flag[2]
The variable turn indicates whose turn it is to enter the
critical section.
The flag array is used to indicate if a process is ready to
enter the critical section. flag[i] = true implies that
process Pi is ready.

Operating System Concepts – 8th Edition 6.30 Silberschatz, Galvin and Gagne ©2009
Peterson’s Solution: algorithm for Process Pi
Algorithm 3
do {
flag[i] = TRUE;
turn = j;
while (flag[j] && turn == j);
critical section
flag[i] = FALSE;
remainder section
} while (TRUE);

Operating System Concepts – 8th Edition 6.31 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct

1. Mutual exclusion is preserved


2. The progress requirement is satisfied.
3. The bounded waiting requirement is met.

Operating System Concepts – 8th Edition 6.32 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct
1. Mutual exclusion is preserved

do { do {
flag[i] = TRUE; flag[j] = TRUE;
turn = j; turn = i;
while (flag[j] && turn == j); while (flag[i] && turn == i);
critical section critical section
flag[i] = FALSE; flag[j] = FALSE;
remainder section remainder section
} while (TRUE); } while (TRUE);

Operating System Concepts – 8th Edition 6.33 Silberschatz, Galvin and Gagne ©2009
Proof of correctness

Mutual exclusion is preserved:


P0 and P1 are both in CS
only if
– flag[0] = flag[1] = true
and only if
– turn = i for each Pi (impossible)

Operating System Concepts – 8th Edition 6.34 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct
2. Is the progress requirement satisfied ?
Pj stuck at this point
do { do {
flag[i] = TRUE; flag[j] = TRUE;
turn = j; turn = i;
while (flag[j] && turn == j); while (flag[i] && turn == i);
critical section critical section
flag[i] = FALSE; flag[j] = FALSE;
remainder section remainder section
} while (TRUE); } while (TRUE);

Operating System Concepts – 8th Edition 6.35 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct
2.1 The progress requirement is satisfied.

do { do {
flag[i] = TRUE; flag[j] = TRUE;
turn = j; turn = i;
while (flag[j] && turn == j); while (flag[i] && turn == i);
critical section critical section
flag[i] = FALSE; flag[j] = FALSE;
remainder section remainder section
} while (TRUE); } while (TRUE);

flag[i] = false  Pj can enter


Operating System Concepts – 8th Edition 6.36 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct
2.2 Is the progress requirement is satisfied ?

do { do {
flag[i] = TRUE; flag[j] = TRUE;
turn = j; turn = i;
while (flag[j] && turn == j); while (flag[i] && turn == i);
critical section critical section
flag[i] = FALSE; flag[j] = FALSE;
remainder section remainder section
} while (TRUE); } while (TRUE);

Operating System Concepts – 8th Edition 6.37 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct
2.2.1 The progress requirement is satisfied.

do { do {
flag[i] = TRUE; flag[j] = TRUE;
turn = j; turn = i;
while (flag[j] && turn == j); while (flag[i] && turn == i);
critical section critical section
flag[i] = FALSE; flag[j] = FALSE;
remainder section remainder section
} while (TRUE); } while (TRUE);

turn = j  Pj can enter


Operating System Concepts – 8th Edition 6.38 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct
2.2.2 Is the progress requirement is satisfied ?

do { do {
flag[i] = TRUE; flag[j] = TRUE;
turn = j; turn = i;
while (flag[j] && turn == j); while (flag[i] && turn == i);
critical section critical section
flag[i] = FALSE; flag[j] = FALSE;
remainder section remainder section
} while (TRUE); } while (TRUE);

turn = i  Pi can enter


Operating System Concepts – 8th Edition 6.39 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct
2.2.2.a The progress requirement is satisfied.

do { do {
flag[i] = TRUE; flag[j] = TRUE;
turn = j; turn = i;
while (flag[j] && turn == j); while (flag[i] && turn == i);
critical section critical section
flag[i] = FALSE; flag[j] = FALSE;
remainder section remainder section
} while (TRUE); } while (TRUE);

flag[i] = false  Pj can enter


Operating System Concepts – 8th Edition 6.40 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct
2.2.3 The progress requirement is satisfied.

do { do {
flag[i] = TRUE; flag[j] = TRUE;
turn = j; turn = i;
while (flag[j] && turn == j); while (flag[i] && turn == i);
critical section critical section
flag[i] = FALSE; flag[j] = FALSE;
remainder section remainder section
} while (TRUE); } while (TRUE);

turn = j  Pj can enter

Operating System Concepts – 8th Edition 6.41 Silberschatz, Galvin and Gagne ©2009
Prove this algorithm is correct
3. The bounded waiting requirement is met

do { do {
flag[i] = TRUE; flag[j] = TRUE;
turn = j; turn = i;
while (flag[j] && turn == j); while (flag[i] && turn == i);
critical section critical section
flag[i] = FALSE; flag[j] = FALSE;
remainder section remainder section
} while (TRUE); } while (TRUE);

Pi will enter the CS after at most one entry by Pj

Operating System Concepts – 8th Edition 6.42 Silberschatz, Galvin and Gagne ©2009
Drawbacks of software solutions
Processes that are requesting to enter in their critical section are busy
waiting (consuming processor time needlessly)
If CSs are long, it would be more efficient to block processes that are
waiting.

Operating System Concepts – 8th Edition 6.43 Silberschatz, Galvin and Gagne ©2009
Hardware Synchronization

Operating System Concepts – 8th Edition 6.44 Silberschatz, Galvin and Gagne ©2009
Hardware Synchronization
Any solution to the critical-section problem requires a
simple tool – a lock.
Race conditions are prevented by requiring that critical
regions be protected by locks

do {
acquire lock
critical section
release lock
remainder section
} while (TRUE);
Operating System Concepts – 8th Edition 6.45 Silberschatz, Galvin and Gagne ©2009
Solution to Critical-section Problem Using Locks

Lock: prevents someone from doing something


Lock before entering critical section and
before accessing shared data
Unlock when leaving, after accessing shared data
Wait if locked: all synchronization involves waiting.

Operating System Concepts – 8th Edition 6.46 Silberschatz, Galvin and Gagne ©2009
Hardware Synchronization
Many systems provide hardware support for critical section code
Uniprocessors – could disable interrupts
Currently running code would execute without preemption
Generally too inefficient on multiprocessor systems
Modern machines provide special atomic hardware instructions
 Atomic = non-interruptable

Operating System Concepts – 8th Edition 6.47 Silberschatz, Galvin and Gagne ©2009
Critical Section Access - Disabling Interrupts

One way to provide mutual exclusion is to disable interrupts (and thus


context switching), but
It cannot be done for long (or some interrupts will be lost)
User processes are not allowed to do that
I/O may be needed while in a critical section (and it will never be
completed with interrupts disabled)
It disables even time interrupts, thus not allowing preemption
It does not work in a multi-processor system, anyway!

Operating System Concepts – 8th Edition 6.48 Silberschatz, Galvin and Gagne ©2009
Interrupt Disabling
If it is guaranteed that no interrupt occurs while a thread is in the CS,
then no other thread can enter the same CS

Process Pi:
repeat
disable interrupts
critical section
enable interrupts
remainder section
forever

Operating System Concepts – 8th Edition 6.49 Silberschatz, Galvin and Gagne ©2009
Hardware solutions: interrupt disabling

On a uniprocessor: no overlapping of execution


Therefore, if a process doesn’t get interrupted in its CS, mutual exclusion
is guaranteed
Degrades efficiency because processor cannot interleave threads when
interrupts are disabled
Simplest solution
but it is not desirable to give a thread the power of controlling
interrupts
On a multiprocessor: mutual exclusion is not preserved
Generally not an acceptable solution.

Operating System Concepts – 8th Edition 6.50 Silberschatz, Galvin and Gagne ©2009
Hardware lock

The hardware lock is done with a binary flag which indicates if the resource
is free or not

Each task will test the flag before using the resource: if it is already used by
another task, it will do an active wait.

Operating System Concepts – 8th Edition 6.51 Silberschatz, Galvin and Gagne ©2009
Hardware lock functioning
If the resource is free, the task will set the flag «busy» before using the
resource and will set it again «free» after finishing the job with the resource
It is necessary to have a means to test and set this flag in an indivisible (or
atomic) way
Processors usually have a «TEST and SET» instruction allowing to test and
set/reset a memory location in an atomic way
Examples:
 Test & Set (most architectures)
 Exchange (Pentium)
 Compare & Swap (68K, Sparc).

Operating System Concepts – 8th Edition 6.52 Silberschatz, Galvin and Gagne ©2009
Atomic Operations
Atomic Operation: an operation that always runs to completion (without
interruption) or not at all
It is indivisible: it cannot be stopped in the middle and its state cannot be
modified by someone else in the middle
On most machines, memory references and assignments (i.e. loads and
stores) of words are atomic
For Hardware Lock:
Atomically read old value, write new value

Operating System Concepts – 8th Edition 6.53 Silberschatz, Galvin and Gagne ©2009
Test and set
We assume the existence of a shared “lock” variable
int lock = 0; // shared
Will only have two possible values
0 meaning nobody is inside the critical section
1 meaning somebody has entered the critical section

Operating System Concepts – 8th Edition 6.54 Silberschatz, Galvin and Gagne ©2009
Test and Set

Atomic operation:
Test the value of a flag (lock)
If it is set
 leave it (and wait until it is reset by another)
Else
 set it (as saying "I’ll enter CS")
Example:
while ( testAndSet( lock ) == true )
;
// I’ll enter CS.

Operating System Concepts – 8th Edition 6.55 Silberschatz, Galvin and Gagne ©2009
Test And Set Instruction
Definition:

boolean TestAndSet (boolean *target)


{
boolean rv = *target;
*target = TRUE;
return rv:
}
if target ==1 (locked), target stays 1 and return 1, “wait”
if target ==0 (unlocked), set target to 1 (lock door), return 0, and “enter
CS”

Operating System Concepts – 8th Edition 6.56 Silberschatz, Galvin and Gagne ©2009
Solution using TestAndSet

Shared data:
boolean lock = false;
// if lock == 0, door open, if lock == 1, door locked

Solution (Mutual-Exclusion):
do {
while ( TestAndSet (& lock ))
; // do nothing
// critical section
lock = FALSE;
// remainder section
} while (TRUE);

Operating System Concepts – 8th Edition 6.57 Silberschatz, Galvin and Gagne ©2009
TSL Instruction (Test and Set Lock)
acquire_lock: TSL REGISTER,LOCK
CMP REGISTER, 0
JNE acquire_lock
RET

Release_lock: MOV LOCK, 0


RET

Operating System Concepts – 8th Edition 6.58 Silberschatz, Galvin and Gagne ©2009
Compare and swap
Compare-and-swap (CAS) is an atomic instruction used in multithreading to
achieve synchronization.
It compares the contents of a memory location to a given value and, only if
they are the same, it modifies the contents of that memory location to a new
given value.
This is done in a single atomic operation.

Operating System Concepts – 8th Edition 6.59 Silberschatz, Galvin and Gagne ©2009
cmpxchg instruction

X86 instruction
Syntax:
cmpxchg source, destination
Behavior:
The instruction uses an implicit operand which is the accumulator
register (EAX)
The instruction compares the accumulator with the destination operand
then:
 if (accumulator == destination)
– ZF = 1
– destination = source
 else
– ZF = 0
– accumulator = destination

Operating System Concepts – 8th Edition 6.60 Silberschatz, Galvin and Gagne ©2009
cmpxchg instruction: example
enter _section:
mov eax, 0
mov ebx, 1
lock cmpxchg ebx, my_lock
jne enter_section

Leave_section:
mov my_lock, 0

Note:
lock is a prefix that causes the CPU to block the access to the bus

while the instruction is not completed.

Operating System Concepts – 8th Edition 6.61 Silberschatz, Galvin and Gagne ©2009
Busy Waiting (“Spinning”)
Busy-Waiting: thread consumes cycles while waiting

void acquire() {
while (testset(value))
;
}

void release() {
value = 0;
}
spin-lock

Operating System Concepts – 8th Edition 6.62 Silberschatz, Galvin and Gagne ©2009
Busy waiting
Busy waits waste CPU cycles:
Generate unnecessary context switches
Slow down the progress of other processes

Operating System Concepts – 8th Edition 6.63 Silberschatz, Galvin and Gagne ©2009
Priority inversion
A high priority process doing a busy wait may prevent a lower priority
process to do its work and leave its critical region.

Operating System Concepts – 8th Edition 6.64 Silberschatz, Galvin and Gagne ©2009
Starvation is possible
When a process leaves a critical section and more than one process is
waiting, the selection of a waiting process is arbitrary. Thus, some process
could indefinitely be denied access.

Operating System Concepts – 8th Edition 6.65 Silberschatz, Galvin and Gagne ©2009
Deadlock is possible
Consider the following scenario:
Process P1 executes the special instruction and enters its critical
section
P1 is then interrupted to give the processor to process P2, which has
higher priority
If P2 now attempts to use the same resource as P1, it will be denied
access because of mutual exclusion mechanism. Thus, it will go into a
busy waiting loop
However, P1 will never be dispatched because it is of lower priority than
another ready process P2.

Operating System Concepts – 8th Edition 6.66 Silberschatz, Galvin and Gagne ©2009
Properties of machine instructions
Advantages:
Applicable to any number of processes
Machine can receive interrupts
Can be used on single as well as multiple processor machines sharing
main memory
Simple and easy to verify
Disadvantages:
Busy Waiting
Starvation
Deadlock.

Operating System Concepts – 8th Edition 6.67 Silberschatz, Galvin and Gagne ©2009
Operating System solutions

Operating System Concepts – 8th Edition 6.68 Silberschatz, Galvin and Gagne ©2009
Semaphores
The hardware-based solutions for the CS problem are complex for
application programmers to use
To overcome this difficulty, a synchronization tool, called semaphore, has
been proposed
Proposed by Dijkstra (1965)
Semaphores do not require busy waiting
Semaphore S – integer variable
Two standard operations modify S:
wait() and signal()
Originally called Edsger W. Dijkstra (1930-2002)

 P(): (from the Dutch probeer te verlagen: “try to decrease”, Wait


(Busy wait or sleep) if the resource is not available)
 V(): (from the Dutch verhogen = to increment, free the resource).

Operating System Concepts – 8th Edition 6.69 Silberschatz, Galvin and Gagne ©2009
Semaphore Definition
A semaphore S is a shared variable (protected by the OS) that can be used
by processes to send and receive signals
The following operations apply:
Initialize(S): S has to be initialized
Wait(S)
Signal(S)
OS must guarantee that each of these operations are atomic.
It must be impossible for two processes to execute them
simultaneously.
The assembly language statements that implement these operations will
never be interleaved.

Operating System Concepts – 8th Edition 6.70 Silberschatz, Galvin and Gagne ©2009
Semaphores
Can only be accessed via two atomic operations
wait (S) {
while S <= 0
; // no-op
S--;
}
signal (S) {
S++;
}

Operating System Concepts – 8th Edition 6.71 Silberschatz, Galvin and Gagne ©2009
Types of Semaphores

Counting semaphore – integer value can range over an


unrestricted domain

Binary semaphore – integer value can range only between 0


and 1

Operating System Concepts – 8th Edition 6.72 Silberschatz, Galvin and Gagne ©2009
Binary Semaphore
Integer value can range only between 0 and 1:
Also known as mutex locks as they are locks that provide
mutual exclusion.
We can use binary semaphore to deal with the CS problem for
multiple processes.
The n processes share a semaphore, mutex, initialized to 1

Operating System Concepts – 8th Edition 6.73 Silberschatz, Galvin and Gagne ©2009
Semaphores
The semaphore used by railroads indicates whether the train can
proceed. When it’s lowered (a), an oncoming train is expected. If it
is raised (b), the train can continue.

a) Stop b) All Clear

Operating System Concepts – 8th Edition 6.74 Silberschatz, Galvin and Gagne ©2009
Using semaphores
Semaphores can be used for mutual exclusion
Semaphore value initialized to 1
Wait on entry to critical section
Signal on exit from critical section

Operating System Concepts – 8th Edition 6.75 75


Silberschatz, Galvin and Gagne ©2009
Mutual-Exclusion Implementation with semaphores

Provides mutual exclusion (for Process Pi)


Semaphore mutex; // initialized to 1
do {
wait (mutex);
// Critical Section
signal (mutex);
// remainder section
} while (TRUE);

Operating System Concepts – 8th Edition 6.76 Silberschatz, Galvin and Gagne ©2009
Using Semaphores for Mutex

semaphore mutex = 1 -- unlocked

1 repeat 1 repeat
2 wait(mutex); 2 wait(mutex);
3 critical section 3 critical section
4 signal(mutex); 4 signal(mutex);
5 remainder section 5 remainder section
6 until FALSE 6 until FALSE

Thread A Thread B

Operating System Concepts – 8th Edition 6.77 Silberschatz, Galvin and Gagne ©2009
Using Semaphores for Mutex

semaphore mutex = 0 -- locked

1 repeat 1 repeat
2 wait(mutex); 2 wait(mutex);
3 critical section 3 critical section
4 signal(mutex); 4 signal(mutex);
5 remainder section 5 remainder section
6 until FALSE 6 until FALSE

Thread A Thread B

Operating System Concepts – 8th Edition 6.78 Silberschatz, Galvin and Gagne ©2009
Using Semaphores for Mutex

semaphore mutex = 0 --locked

1 repeat 1 repeat
2 wait(mutex); 2 wait(mutex);
3 critical section 3 critical section
4 signal(mutex); 4 signal(mutex);
5 remainder section 5 remainder section
6 until FALSE 6 until FALSE

Thread A Thread B

Operating System Concepts – 8th Edition 6.79 Silberschatz, Galvin and Gagne ©2009
Using Semaphores for Mutex

semaphore mutex = 0 -- locked

1 repeat 1 repeat
2 wait(mutex); 2 wait(mutex);
3 critical section 3 critical section
4 signal(mutex); 4 signal(mutex);
5 remainder section 5 remainder section
6 until FALSE 6 until FALSE

Thread A Thread B

Operating System Concepts – 8th Edition 6.80 Silberschatz, Galvin and Gagne ©2009
Using Semaphores for Mutex

semaphore mutex = 0 -- locked

1 repeat 1 repeat
2 wait(mutex); 2 wait(mutex);
3 critical section 3 critical section
4 signal(mutex); 4 signal(mutex);
5 remainder section 5 remainder section
6 until FALSE 6 until FALSE

Thread A Thread B

Operating System Concepts – 8th Edition 6.81 Silberschatz, Galvin and Gagne ©2009
Using Semaphores for Mutex

semaphore mutex = 1 -- unlocked This thread can


now be released!

1 repeat 1 repeat
2 wait(mutex); 2 wait(mutex);
3 critical section 3 critical section
4 signal(mutex); 4 signal(mutex);
5 remainder section 5 remainder section
6 until FALSE 6 until FALSE

Thread A Thread B

Operating System Concepts – 8th Edition 6.82 Silberschatz, Galvin and Gagne ©2009
Using Semaphores for Mutex

semaphore mutex = 0 -- locked

1 repeat 1 repeat
2 wait(mutex); 2 wait(mutex);
3 critical section 3 critical section
4 signal(mutex); 4 signal(mutex);
5 remainder section 5 remainder section
6 until FALSE 6 until FALSE

Thread A Thread B

Operating System Concepts – 8th Edition 6.83 Silberschatz, Galvin and Gagne ©2009
Counting semaphore
The concept of semaphore can be extended to the case where n
tasks can simultaneously access a resource controlled by the
semaphore
The initial value of the counter S determines the number of tasks
which will be able to cross the semaphore before being blocked
(number of tasks which can access simultaneously the critical
section)
To use a resource, wait()
To release a resource, signal()

Operating System Concepts – 8th Edition 6.84 Silberschatz, Galvin and Gagne ©2009
Sempahore usage
Counting semaphores are often used to control access to a number of
similar resources, such as disks, tape drives, CDs, etc.
We may have 8 disks available for allocation to processes and a
counting semaphore keeps track of the number remaining to allocate (if
any).
A semaphore is typically initialized to the number of resources available
Wait() decrements the semaphore;
Signal() increments the semaphore.
Presumably, if the value of the semaphore is ‘acceptable,’ the process
enters its critical section.
If count goes to 0, then no more of these resources are available and
the requesting process will likely block until the semaphore becomes
greater than 0.

Operating System Concepts – 8th Edition 6.85 Silberschatz, Galvin and Gagne ©2009
Shareable resource – Example

T1 T2

Access
Accès
Request
Requête RAM1 Request
Requête

RAM2
RAM3
Print = 3

Operating System Concepts – 8th Edition 6.86 Silberschatz, Galvin and Gagne ©2009
Semaphore Implementation
The main disadvantage of previous mutual-
exclusion solution is the busy waiting (CPU is
wasting).
This type of semaphore is called a spinlock.
To overcome this, we can use the concept of
block and wakeup operations.

Typedef struc {
int value;
struct process *list;
} semaphore

Operating System Concepts – 8th Edition 6.87 Silberschatz, Galvin and Gagne ©2009
Semaphore Implementation with no Busy waiting

With each semaphore there is an associated waiting queue. Each


semaphore has two data items:
value (of type integer) of the semaphore
pointer to a list of waiting processes (initially empty)
Two additional operations:
block – place the process invoking the operation on the
appropriate waiting queue.
wakeup – remove one of the processes in the waiting queue
and place it in the ready queue.

Operating System Concepts – 8th Edition 6.88 Silberschatz, Galvin and Gagne ©2009
Semaphore Implementation with no Busy waiting

Implementation of wait:
wait (semaphore *S) {
S->value--;
if (S->value < 0) {
add this process to S->list;
block();
}
}

Operating System Concepts – 8th Edition 6.89 Silberschatz, Galvin and Gagne ©2009
Semaphore Implementation with no Busy waiting

Note that the semaphore value may be negative.


Its magnitude is the number of processes waiting on that
semaphore.
The list of waiting processes can be easily implemented
by a link field in each process control block (PCB).

Operating System Concepts – 8th Edition 6.90 Silberschatz, Galvin and Gagne ©2009
Semaphore Implementation with no Busy waiting

Implementation of signal:
signal (semaphore *S) {
S->value++;
if (S->value <= 0) {
remove a process P from S->list;
wakeup(P);
}
}

Operating System Concepts – 8th Edition 6.91 Silberschatz, Galvin and Gagne ©2009
Semaphores: observations, I.

What does S.count represent?


if S.value >=0: the number of processes that can execute
wait(S) without being blocked = S.count (not > 1 for mutual
exclusion)
if S.value<0: the number of processes waiting on S is = |S.value|
P and V Must Be Indivisible
Semaphore operations must be indivisible, or atomic.
Once OS begins either a P or V operation, it cannot be interrupted until
it is completed.
P operation must be indivisible; otherwise there is no guarantee that
two processes won’t try to test P at the “same” time and both find it
equal to 1.
P(S): S->value--;
if (S->value < 0) {
add this process to S->list;
block(); }
Two V operations executed at the same time could unblock two
processes, leading to two processes in their critical sections
concurrently.
V(S): S->value++;
if (S->value <= 0) {
remove a process P from S->list;
wakeup(P); }

Operating System Concepts – 8th Edition 6.93 Silberschatz, Galvin and Gagne ©2009
Semaphores: observations, II.

Atomicity and mutual exclusion:


no 2 process can be in wait(S) or signal(S) (on the same S) at
the same time (even with multiple CPUs)
the blocks of code defining wait(S) and signal(S) are, in fact,
critical sections
Semaphores: observations, II.
The critical sections defined by wait(S) and signal(S) are very short:
typically 10 instructions
Solutions:
uniprocessor: disable interrupts during these operations (i.e., for a very
short period). This does not work on a multiprocessor machine.
multiprocessor: use previous software or hardware schemes. The
amount of busy waiting should be small.

The order in which processes are awakened depends on the CPU


scheduling algorithm (not always FCFS)
Semaphores
Advantages
OS guarantees that Wait and Signal are atomic
Programmer does not need to worry about interleaving within the entry
and exit sections.
No spin locks
Semaphores are machine-independent
They are simple but very general
They work with any number of processes
We can have as many critical regions as we want by assigning a
different semaphore to each critical region
OS designer must use the features of the hardware to provide semaphores.

Operating System Concepts – 8th Edition 6.96 Silberschatz, Galvin and Gagne ©2009
State transition diagram
The state transition diagram for a job in an operating system that provides a
semaphore

New state: waiting


for a semaphore

Operating System Concepts – 8th Edition 6.97 Silberschatz, Galvin and Gagne ©2009
Process States

time-out

running ready
ready_queue

dispatch

Operating System Concepts – 8th Edition 6.98 Silberschatz, Galvin and Gagne ©2009
Process States

time-out

running ready
ready_queue

wait(si) dispatch

blocked
wait-queues

s1 ... sn
...

...
Operating System Concepts – 8th Edition 6.99 Silberschatz, Galvin and Gagne ©2009
Process States

time-out

running ready
ready_queue

wait(si) dispatch

blocked
wait-queues

s1 ... sn
...

...
Operating System Concepts – 8th Edition 6.100 Silberschatz, Galvin and Gagne ©2009
Process States
A running process calls signal(si).

time-out

running ready
ready_queue

wait(si) dispatch
signal(si)
blocked
wait-queues

s1 ... sn
...

...
Operating System Concepts – 8th Edition 6.101 Silberschatz, Galvin and Gagne ©2009
Binary Semaphores
wait(S):

if (S.value == 0) {
add this process to S.L;
block();
}

signal(S):

if (queue is not empty)


{
remove a process from S.L;
wakeup();
}
else S.value = 1;

Operating System Concepts – 8th Edition 6.102 Silberschatz, Galvin and Gagne ©2009
Critical Section for n Processes

Operating System Concepts – 8th Edition 6.103 Silberschatz, Galvin and Gagne ©2009
Semaphores
There is a wait-queue s
associated with each
semaphore.

s=2
Process 1 Process 2 Process 3 Process 4

s
P(s) P(s) P(s) P(s)
CS1 CS2 CS3 CS4
V(s) V(s) V(s) V(s)
Program1 Program2 Program3 Program4

Operating System Concepts – 8th Edition 6.104 Silberschatz, Galvin and Gagne ©2009
Semaphores

s=1
Process 1 Process 2 Process 3 Process 4

s
P(s) P(s) P(s) P(s)
CS1 CS2 CS3 CS4
V(s) V(s) V(s) V(s)
Program1 Program2 Program3 Program4

Operating System Concepts – 8th Edition 6.105 Silberschatz, Galvin and Gagne ©2009
Semaphores

s=0
Process 1 Process 2 Process 3 Process 4

s
P(s) P(s) P(s) P(s)
CS1 CS2 CS3 CS4
V(s) V(s) V(s) V(s)
Program1 Program2 Program3 Program4

Operating System Concepts – 8th Edition 6.106 Silberschatz, Galvin and Gagne ©2009
Semaphores

s = -1
Process 1 Process 2 Process 3 Process 4

s
P(s) P(s) P(s) P(s)
CS1 CS2 CS3 CS4
V(s) V(s) V(s) V(s)
Program1 Program2 Program3 Program4 Process 3

Operating System Concepts – 8th Edition 6.107 Silberschatz, Galvin and Gagne ©2009
Semaphores

s = -2
Process 1 Process 2 Process 3 Process 4

s
P(s) P(s) P(s) P(s)
CS1 CS2 CS3 CS4
V(s) V(s) V(s) V(s)
Program1 Program2 Program3 Program4 Process 43

Process 3

Operating System Concepts – 8th Edition 6.108 Silberschatz, Galvin and Gagne ©2009
Semaphores

s = -1
Process 1 Process 2 Process 3 Process 4

s
P(s) P(s) P(s) P(s)
CS1 CS2 CS3 CS4
V(s) V(s) V(s) V(s)
Program1 Program2 Program3 Program4 Process 4

Operating System Concepts – 8th Edition 6.109 Silberschatz, Galvin and Gagne ©2009
Semaphores

s=0
Process 1 Process 2 Process 3 Process 4

s
P(s) P(s) P(s) P(s)
CS1 CS2 CS3 CS4
V(s) V(s) V(s) V(s)
Program1 Program2 Program3 Program4 Process 4

Operating System Concepts – 8th Edition 6.110 Silberschatz, Galvin and Gagne ©2009
Semaphores

s=1
Process 1 Process 2 Process 3 Process 4

s
P(s) P(s) P(s) P(s)
CS1 CS2 CS3 CS4
V(s) V(s) V(s) V(s)
Program1 Program2 Program3 Program4

Operating System Concepts – 8th Edition 6.111 Silberschatz, Galvin and Gagne ©2009
Semaphores

s=2
Process 1 Process 2 Process 3 Process 4

s
P(s) P(s) P(s) P(s)
CS1 CS2 CS3 CS4
V(s) V(s) V(s) V(s)
Program1 Program2 Program3 Program4

Operating System Concepts – 8th Edition 6.112 Silberschatz, Galvin and Gagne ©2009
Deadlock
Semaphores provide synchronization, but can introduce more complicated
higher level problems like deadlock
two processes deadlock when each wants a resource that has been
locked by the other process
e.g. P1 wants resource R2 locked by process P2 with semaphore S2,
while P2 wants resource R1 locked by process P1 with semaphore S1

Operating System Concepts – 8th Edition 6.113 Silberschatz, Galvin and Gagne ©2009
Deadlock
Deadlock – two or more processes are waiting indefinitely for an event (a signal
operation) that can be caused by only one of the waiting processes
Let S and Q be two semaphores initialized to 1
P0 P1
1 wait(S); wait(Q); 2
3 wait(Q); wait(S); 4
CS CS
signal(S); signal(Q);
signal(Q); signal(S);

If P0 waits on S and P1 waits on Q, simultaneously, then if P0 waits on Q, it will wait


indefinitely for P1 to signal Q

Sequence 1, 2, 3, 4 causes deadlock


But sequence 1, 3, 2, 4 will not deadlock.

Operating System Concepts – 8th Edition 6.114 Silberschatz, Galvin and Gagne ©2009
Deadlock
In the previous example,
Each process will sleep on the other process’s semaphore
the signal() signalling statements will never get executed, so there is no
way to wake up the two processes from within those two processes
there is no rule prohibiting an application programmer from wait()’ing Q
before S, or vice versa - the application programmer won’t have
enough information to decide on the proper order
in general, with N processes sharing N semaphores, the potential for
deadlock grows.

Operating System Concepts – 8th Edition 6.115 Silberschatz, Galvin and Gagne ©2009
Weakness of Semaphores
Semaphores provide a convenient and effective mechanism for process
synchronization.
However, incorrect use may result in timing errors.

signal(mutex); wait(mutex);
... incorrect order
...
critical section (not mutual exclusive)
critical section
... ...
wait(mutex); forgotten

wait(mutex); ...
typing error
... critical section
(deadlock)
critical section ...
... signal(mutex);
wait(mutex);
Operating System Concepts – 8th Edition 6.116 Silberschatz, Galvin and Gagne ©2009
Starvation
Starvation – indefinite blocking. A process may never be
removed from the semaphore queue in which it is suspended:
if the waiting queues are implemented in LIFO order.

Operating System Concepts – 8th Edition 6.117 Silberschatz, Galvin and Gagne ©2009
Implementation of semaphores

Any software schemes, such as Peterson’s algorithm, can be used


to implement semaphores. However, the busy-waiting in each of
them imposes a large overhead.
Recall that the Peterson’s algorithm discussed above involves
only two processes. Generalizing this algorithm for n processes
to implement general semaphores has a large overhead.
Hardware implementation based on
test and set instruction
the busy-waiting in the V() and P() operations are relatively
short
disabling interrupts
there is no wait loop, but this approach works only on a
single processor system.

Operating System Concepts – 8th Edition 6.118 Silberschatz, Galvin and Gagne ©2009
Implementing a binary semaphore by TAS

type semaphore = record


value, flag: integer; 0
L: list of process;
end;

Initial values:
• S.value = 1
• S.flag = 0
• S.L = NULL
wait(S): signal(S):
repeat until test-and-set(S.flag) repeat until test-and-set(S.flag)
if (S.value == 0) {
if (queue is not empty)
add this process to S.L;
{
sleep & S.flag=0;
wakeup();
}
/* change its state from blocked to
else
ready; */
{
}
S.value = 0; else S.value = 1;
S.flag=0;
S.flag=0
}
Operating System Concepts – 8th Edition 6.119 Silberschatz, Galvin and Gagne ©2009
Implementing a counting semaphore by TAS
type semaphore = record
value, flag: integer;
L: list of process; -3
end;

Initial values:
• S.value = 1
• S.flag = 0
• S.L = NULL

wait(S): signal(S):
repeat until test-and-set(S.flag) repeat until test-and-set(S.flag)
S.value--; S.value++;
if (S.value < 0) { if (S.value <= 0) {
add this process to S.L; remove a process P from S.L;
sleep & S.flag=0; wakeup(P);
} }
else S.flag=0
S.flag=0

Operating System Concepts – 8th Edition 6.120 Silberschatz, Galvin and Gagne ©2009
Synchronization with Semaphores (I)

We can use semaphores for synchronizing processes in an arbitrary fashion


enforcing order of access between two processes
Suppose there are two processes P1 and P2, where P1 contains code
C1 and P2 contains code C2
Want to ensure that code C1 executes before code C2
Use semaphores to synchronize the order of execution of the two
processes

Semaphore S=0; // initial value of semaphore = 0

Process P1: Process P2:

C1; // execute C1 wait(S); // P() the semaphore


signal(S); // V() the semaphore C2; // execute C2

Operating System Concepts – 8th Edition 6.121 Silberschatz, Galvin and Gagne ©2009
Synchronization with Semaphores (I) (cont.)

In the previous example there are two cases:


if P1 executes first, then
 C1 will execute first, then P1 will V() the semaphore, increasing its
value to 1
 Later, when P2 executes, it will call wait(S), which will decrement the
semaphore to 0 followed by execution of C2
 Thus C1 executes before C2
If P2 executes first, then
 P2 will block on the semaphore, which is equal to 0, so that C2 will
not be executed yet
 Later, when P1 executes, it will run through C1, then V() the
semaphore
 This awakens P2, which then executes C2
 Thus C1 executes before C2.

Operating System Concepts – 8th Edition 6.122 Silberschatz, Galvin and Gagne ©2009
Thread 1 First

Operating System Concepts – 8th Edition 6.123 Silberschatz, Galvin and Gagne ©2009
Thread 2 First

Operating System Concepts – 8th Edition 6.124 Silberschatz, Galvin and Gagne ©2009
Synchronization with Semaphores (II)
In this case, the semaphore is used to exchange
synchronization signals among processes, as opposed to
solving the strict critical section problem.
P(s1) will not Execute
semaphore s1 = 0; Until V(s1) sets s1 to 1
semaphore s2 = 0; x Written Before Read

proc_A { proc_B {
while(TRUE) { while(TRUE) {
compute A1; // wait for signal from proc_B
write(x); P(s1);
V(s1); //signal proc_B read(x);
compute A2; compute B1;
// wait for signal from proc_B write(z);
P(s2); V(s2); //signal proc_A
read(z); compute B2;
} }
P(s2) will not Execute }
}
Until V(s2) sets s2 to 1
y Written Before Read
Operating System Concepts – 8th Edition 6.125 Silberschatz, Galvin and Gagne ©2009
Exercise 2
Three processes P1; P2; P3

semaphores s1 = 1, s2 = 0;
P1 P2 P3

P(s1); P(s2); P(s2);


A B C
V(s2); V(s2); V(s1);

Which execution orderings of A, B, C, are possible?

Operating System Concepts – 8th Edition 6.126 Silberschatz, Galvin and Gagne ©2009
Solution
3 processes P1; P2; P3

semaphores s1 = 1, s2 = 0;

P1 P2 P3

P(s1); P(s2); P(s2); B


A B C
V(s2); V(s2); V(s1);
A

Operating System Concepts – 8th Edition 6.127 Silberschatz, Galvin and Gagne ©2009
Exercise 3

There are three processes, each produces balls of some


color (e.g. Red, Green, Blue)
Sequencing required:
Red ball followed by Green followed by Blue and so-
on.

Operating System Concepts – 8th Edition 6.128 Silberschatz, Galvin and Gagne ©2009
Solution
Solution:

Semaphore s1 = 1;
Semaphore s2 = 0;
Semaphore s3 = 0;

Procedure RED_Generator() Procedure GREEN_Generator() Procedure BLUE_Generator()


{ { {
do do do
{ { {
wait(s1); wait(s2); wait(s3);

generate(RedBall); generate(GreenBall); generate(BlueBall);

signal(s2) signal(s3) signal(s1)


} } }
while (true); while (true); while (true);
} } }
Operating System Concepts – 8th Edition 6.129 Silberschatz, Galvin and Gagne ©2009
Setting up a rendezvous (I)
To force two processes to wait for each other, we need two semaphores
both initialized at 0
semaphore waitforfirst = 0;
semaphore waitforsecond = 0;

Operating System Concepts – 8th Edition 6.130 Silberschatz, Galvin and Gagne ©2009
Setting up a rendezvous (II)
When the first process is ready, it will do
V(&waitforfirst);
P(&waitforsecond);

When the second process is ready, it will do


V(&waitforsecond);
P(&waitforfirst);

Operating System Concepts – 8th Edition 6.131 Silberschatz, Galvin and Gagne ©2009
Setting up a rendezvous (III)
What will happen if the first process does
P(&waitforsecond);
V(&waitforfirst);

and the second process does


P(&waitforfirst);
V(&waitforsecond);

We will have a deadlock

Operating System Concepts – 8th Edition 6.132 Silberschatz, Galvin and Gagne ©2009
Home Work 1
Write the code to guarantee the following graph of precedences

Operating System Concepts – 8th Edition 6.133 Silberschatz, Galvin and Gagne ©2009
Home Work 2
Write the code to guarantee the following graph of precedences

A D

Operating System Concepts – 8th Edition 6.134 Silberschatz, Galvin and Gagne ©2009

S-ar putea să vă placă și