monitor guardaroba_russo
{
Ritira = 0; Consegna = 1; Prendi = 2;
queue waiting[2] = {0, 0};
queue all;
condition ok[3];
count = 0;
waitingAny = False; waitingMax = False;
output;
// Cancella la prima occorrenza di <Ritira> nella coda <all>
deleteRitira();
item prendi()
{
if (count == MAX)
{
if (waiting[Ritira].Count == 0)
{
waitingMax = True;
ok[Prendi].wait();
}
return waiting[Ritira].dequeue();
}
else
{
if (all.Count == 0)
{
waitingAny = True;
ok[Prendi].wait();
waitingAny = False;
}
return waiting[all.read()].dequeue();
}
}
dai(item x)
{
if (waitingMax)
{
waitingMax = False;
deleteRitira();
output = x;
// Se il dipendente e' stato riattivato tramite signal, la seguente va a vuoto
ok[Ritira].signal();
}
else
{
output = x;
// Se il dipendente e' stato riattivato tramite signal, la seguente va a vuoto
ok[all.dequeue()].signal();
}
}
contrassegno consegna(giacca g)
{
all.enqueue(Consegna);
waiting[Consegna].enqueue(g);
if (waitingAny)
ok[Prendi].signal();
else
ok[Consegna].wait();
count++;
return output;
}
giacca ritira(contrassegno c)
{
all.enqueue(Ritira);
waiting[Ritira].enqueue(c);
if (waitingAny || waitingMax)
ok[Prendi].signal();
else
ok[Ritira].wait();
count--;
return output;
}
}
shared lock = 0;
process P
{
int vp;
while (True)
{
do
{
vp = 1;
lock += 1;
F(lock, vp);
} while(vp);
// <critical section>
lock = 0;
// </critical section>
}
}