Semaphore usage generally falls into two classes:
Whenever possible, cast problems into the first class. This usually can be done.
Unfortunately, sometimes a resource is shared by different classes of users; that is, they use the resource in different ways. Potentially the different kinds of usage interact. For example, consider a shared database with readers and writers. It is safe for any number of readers to access the database simultaneously, but each writer must have exclusive access. Example: checking account (statement-generators are readers, tellers are writers).
AW is always 0 or 1. AR and AW may not both be non-zero.
| Reader Process: | Writer Process: |
|---|---|
StartRead ()
{
Lock.P();
if ((AW+WW) == 0) {
OKToRead.V();
AR++;
} else {
WR++;
}
Lock.V();
OKToRead.P();
}
|
StartWrite ()
{
Lock.P();
if ((AW+AR+WW) == 0) {
OKToWrite.V();
AW++;
} else {
WW++;
}
Lock.V();
OKToWrite.P();
}
|
EndRead ()
{
Lock.P();
AR--;
if ((AR == 0) and (WW > 0)) {
OKToWrite.V();
AW++;
WW--;
}
Lock.V();
}
|
EndWrite ()
Lock.P();
AW--;
if (WW>0) {
OKToWrite.V();
AW++;
WW--;
} else {
while (WR>0) {
OKToRead.V();
AR++;
WR--;
}
}
Lock.V();
}
|
main ();
{
StartRead();
// --read the necessary data--
EndRead();
}
|
main ();
{
StartWrite();
// --write the necessary data--
EndWrite();
}
|
Examples:
Questions: