Consider the following Barrier method to implement synchronization :
void barrier
{
P(s);
process_arrived++;
V(s);
while(process_arrived != 3);
P(s);
process_left++;
if(process_left == 3)
{
process_Arrived = 0;
process_left = 0;
}
V(s);
}
It is known that this code does not work because of a flaw, but I am not able to find the flaw.
The problem is with the condition : if (process_left == 3)
It may lead to deadlock if two barrier invocations are used in immediate succession.
Initially, process_arrived and process_left will be '0'.
When a process arrives, it increments process_arrived and waits till maximum number of processes have arrived. After that processes are allowed to leave.
Consider the following scenario:
P1 comes and waits till process_arrived becomes 3 ( currently process_arrived = 1)
P2 comes and waits till process_arrived becomes 3 ( currently process_Arrived = 2)
Now P3 comes for execution. The condition in while loop fails and executes further, making process_left = 1 and again enters the function immediately.
It makes process_Arrived = 4 and waits in while loop.
P2 gets a chance to execute makes process_left = 2 and leaves.
P1 executes further and finds that process_left = 3, thereby making both process_arrived and process_left = 0. (Remember that P3 has already entered and is waiting at the barrier, so here a count is lost)
P1 again executes , makes process_arrived = 1 and waits.
P2 also executes again. makes process_arrived = 2 and waits.
Now every process will wait for ever. Hence a deadlock has occurred.