Chapter 3.2
Chapter 3.2
Process Management
Outline
Process Synchronization:
Deadlocks:
Process Synchronization
• Processes can execute concurrently
– May be interrupted at any time, partially completing execution
problem that fills all the buffers. We can do so by having an integer counter
that keeps track of the number of full buffers. Initially, counter is set to 0.
register1 = counter
register1 = register1 + 1
counter = register1
do {
Assume that the load and store machine-language instructions are atomic;
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
do {
flag[i] = true;
turn = j;
while (flag[j] && turn = = j);
critical section
flag[i] = false;
remainder section
} while (true);
Peterson’s Solution (Cont.)
do {
acquire lock
critical section
release lock
remainder section
} while (TRUE);
test_and_set Instruction
Definition:
boolean test_and_set (boolean *target)
{
boolean rv = *target;
*target = TRUE;
return rv:
}
1. Executed atomically
2. Returns the original value of passed parameter
3. Set the new value of passed parameter to
“TRUE”.
Solution using test_and_set()
Shared Boolean variable lock, initialized to FALSE
Solution:
do {
while (test_and_set(&lock))
; /* do nothing */
/* critical section */
lock = false;
/* remainder section */
} while (true);
compare_and_swap Instruction
Definition:
int compare _and_swap(int *value, int expected, int new_value) {
int temp = *value;
if (*value == expected)
*value = new_value;
return temp;
}
1. Executed atomically
2. Returns the original value of passed parameter
“value”
3. Set the variable “value” the value of the passed
parameter “new_value” but only if “value”
==“expected”. That is, the swap takes place only
under this condition.
Solution using compare_and_swap
application programmers
OS designers build software tools to solve critical section problem
Protect a critical section by first acquire() a lock then release() the lock
Boolean variable indicating if lock is available or not
wait(semaphore *S) {
S->value--;
if (S->value < 0) {
add this process to S->list;
block();
}
}
signal(semaphore *S) {
S->value++;
if (S->value <= 0) {
remove a process P from S->list;
wakeup(P);
}
}
Deadlock and Starvation
• Deadlock – two or more processes are waiting
indefinitely for an event that can be caused by only
one of the waiting processes
• Let S and Q be two semaphores initialized to 1
P0 P1
wait(S); wait(Q);
wait(Q); wait(S);
... ...
signal(S); signal(Q);
signal(Q); signal(S);
• Starvation – indefinite blocking
– A process may never be removed from the semaphore queue
in which it is suspended
• Priority Inversion – Scheduling problem when lower-priority process
holds a lock needed by higher-priority process
– Solved via priority-inheritance protocol
Classical Problems of Synchronization
do {
...
/* produce an item in next_produced */
...
wait(empty);
wait(mutex);
...
/* add next produced to the buffer */
...
signal(mutex);
signal(full);
} while (true);
Bounded Buffer Problem (Cont.)
The structure of the consumer process
Do {
wait(full);
wait(mutex);
...
/* remove an item from buffer to next_consumed */
...
signal(mutex);
signal(empty);
...
/* consume the item in next consumed */
...
} while (true);
Readers-Writers Problem
• A data set is shared among a number of concurrent processes
– Readers – only read the data set; they do not perform any updates
– Writers – can both read and write
• Problem – allow multiple readers to read at the same time
– Only one single writer can access the shared data at the same time
• Several variations of how readers and writers are considered
– all involve some form of priorities
• Shared Data
– Data set
– Semaphore rw_mutex initialized to 1
– Semaphore mutex initialized to 1
– Integer read_count initialized to 0
Readers-Writers Problem (Cont.)
do {
wait(rw_mutex);
...
/* writing is performed */
...
signal(rw_mutex);
} while (true);
Readers-Writers Problem (Cont.)
• The structure of a reader process
do {
wait(mutex);
read_count++;
if (read_count == 1)
wait(rw_mutex);
signal(mutex);
...
/* reading is performed */
...
wait(mutex);
read count--;
if (read_count == 0)
signal(rw_mutex);
signal(mutex);
} while (true);
Readers-Writers Problem Variations
locks
Dining-Philosophers Problem
// eat
signal (chopstick[i] );
signal (chopstick[ (i + 1) % 5] );
// think
} while (TRUE);
• Deadlock handling
– Allow at most 4 philosophers to be sitting
simultaneously at the table.
– Allow a philosopher to pick up the forks only if
both are available (picking must be done in a
critical section.
– Use an asymmetric solution -- an odd-numbered
philosopher picks up first the left chopstick and
then the right chopstick. Even-numbered
philosopher picks up first the right chopstick and
then the left chopstick.
Problems with Semaphores
monitor monitor-name
{
// shared variable declarations
procedure P1 (…) { …. }
• condition x, y;
initialization_code() {
for (int i = 0; i < 5; i++)
state[i] = THINKING;
}
}
Solution to Dining Philosophers (Cont.)
DiningPhilosophers.pickup(i);
EAT
DiningPhilosophers.putdown(i);
• Variables
if (x_count > 0) {
next_count++;
signal(x_sem);
wait(next);
next_count--;
}
Resuming Processes within a Monitor
R.acquire(t);
...
access the resurce;
...
R.release;
• Solaris
• Windows
• Linux
• Pthreads
Solaris Synchronization
• Implements a variety of locks to support multitasking,
multithreading (including real-time threads), and
multiprocessing
• Uses adaptive mutexes for efficiency when protecting data
from short code segments
– Starts as a standard semaphore spin-lock
– If lock held, and by a thread running on another CPU, spins
– If lock held by non-run-state thread, block and sleep waiting for signal of lock being released
• Transactional Memory
• OpenMP
void update()
{
/* read/write memory */
}
OpenMP
• OpenMP is a set of compiler directives and
API that support parallel progamming.
maintain state.
64
Deadlock Characterization
Deadlock can arise if four conditions hold simultaneously.
• Circular wait: there exists a set {P0, P1, …, Pn} of waiting processes such
resource that is held by P2, …, Pn–1 is waiting for a resource that is held
66
DEADLOCK
2. DEADLOCK DETECTION AND RECOVERY
The system lets deadlocks to occur, tries to detect when this happens,
and then takes some action to recover after the fact
Deadlock Detection with One Resource of Each Type
68
DEADLOCK
4. DEADLOCK AVOIDANCE
• Two approaches:
– Process initiation denial
• Do not start a process if its demands might lead
to deadlock
– Resource allocation denial (Banker’s
algorithm
• Do not grant an incremental resource request
to a process if this allocation might lead to
deadlock
69
DEADLOCK
5. DEADLOCK PREVENTION
71
DEADLOCK
5. DEADLOCK PREVENTION
• Attacking the No Preemption Condition
• If a process has been assigned the printer and is in the
middle of printing its output, forcibly taking away the
printer because a needed plotter is not available is
tricky at best and impossible at worst
• Attacking the Circular Wait Condition
• circular wait can be eliminated in several ways:
• a process is entitled only to a single resource at any moment
• provide a global numbering of all the resources, all requests
must be made in numerical order
• E.g 1. Printer, 2. Tape, 3. Scanner
• A process can request a printer and then a tape, but not the
reverse.
72
End
73