Semaphores A counting semaphore s consists of a private integer value - - PDF document

semaphores
SMART_READER_LITE
LIVE PREVIEW

Semaphores A counting semaphore s consists of a private integer value - - PDF document

Concurrent programming slides T.S. Norvell (c) 2001 Semaphores A counting semaphore s consists of a private integer value s.c (invariant s.c 0 ) and three operations executed with mutual exclusion w.r.t. the others. Abstract de


slide-1
SLIDE 1

Concurrent programming slides T.S. Norvell (c) 2001

Semaphores

A “counting semaphore” s consists of a private integer value

s.c (invariant s.c ≥ 0) and three operations executed with

mutual exclusion w.r.t. the others. Abstract deÞnition (initialize is called Þrst and once): proc initialize( i : int ) ; pre i >= 0 c := i end initialize proc acquire % AKA P wait until c > 0 c -= 1 end acquire proc release % AKA V c += 1 end release 9

slide-2
SLIDE 2

Concurrent programming slides T.S. Norvell (c) 2001

You can think of a semaphore as a bowl containing c pebbles.

  • acquire: Remove one pebble from the bowl
  • release: Add one pebble to the bowl

For mutual exclusion we use Global data and initialization: var s : semaphore ; s.initialize(1 ) ; acquire(i): s.acquire release(i): s.release 10

slide-3
SLIDE 3

Concurrent programming slides T.S. Norvell (c) 2001

Further Uses of Semaphores

We can also use semaphores to implement other forms of coordination. For example a single buffer Messenger module which mimics the Messenger monitor we saw earlier. module Messenger ; export send, receive var e : semaphore ; e.initialize( 1 ) var f : semaphore ; f.initialize( 0 ) var buffer : string % invariant e.c+f.c <= 1 proc send( message : string ) e.acquire buffer := message % crit. sect. f.release ; end send proc receive( var message : string ) f.acquire message := buffer % crit. sect. e.release ; end receive end Messenger % module 11

slide-4
SLIDE 4

Concurrent programming slides T.S. Norvell (c) 2001

Note: the invariant is true at all times after initialization. According to the invariants, there are three states of the semaphores:

  • e.c=1 and f.c=0: The buffer is empty. send may be entered,

but not receive

  • e.c=0 and f.c=1: The buffer is full. receive may be entered,

but nor send

  • e.c=0 and f.c=0: Then some thread is executing a critical
  • section. Other threads are locked out, of both send and

receive, ensuring mutual exclusion on the critical sections.

attack at dawn Buffer: pick up read drop off pick up write drop off receiver sender Buffer is full Buffer is empty

12

slide-5
SLIDE 5

Concurrent programming slides T.S. Norvell (c) 2001

Implementing semaphores

Of course semaphores can be implemented using monitors, but monitors are not always available. We look at how to implement semaphores using process states. Each semaphore is represented by a record with two Þelds:

  • s.count: int with abstraction relation:

if s.count >= 0 then s.c = s.count else s.c = 0

  • s.queue: a fair queue with invariant

if s.count < 0 then s.queue.length = −s.count else s.queue.length = 0 Each operation is executed with mutual exclusion w.r.t. the

  • thers

proc initialize( i : int ) ; pre i >= 0 count := i ; queue := theEmptyQueue end initialize 13

slide-6
SLIDE 6

Concurrent programming slides T.S. Norvell (c) 2001

In acquire, the thread loses mutual exclusion when it yields the CPU. proc acquire count -= 1 if count < 0 then put this thread on queue yield the CPU (enter the waiting state) end if end acquire proc release count += 1 if count <= 0 then remove a thread from queue and move that thread from waiting to the ready state end if end release Pro:

  • Multiple classes of critical sections.
  • No busy wait, and hence, good CPU utilization.

14

slide-7
SLIDE 7

Concurrent programming slides T.S. Norvell (c) 2001

Implementing Monitors

Now we can Þnally implement monitors. For each monitor m we need a semaphore m.s initialized to 1

  • To enter m, execute m.s.acquire
  • To exit m, execute m.s.release

For each condition variable c, declared within m, we need

  • an integer c.count initialized to 0. This counts the number
  • f waiting threads.
  • a semaphore c.s, initialized to 0.

wait c is implemented by c.count += 1 ; m.s.release ; c.s.acquire ; c.count -= 1 signal c is implemented by if c.count > 0 then c.s.release else m.s.release end if m.s.acquire empty(c) is implemented by c.count = 0 15

slide-8
SLIDE 8

Concurrent programming slides T.S. Norvell (c) 2001

Why this works

When a thread acquires m.s it acquires an obligation to release m.s some time in the future. This obligation can be fulÞlled either by exiting or by

  • signalling. Signalling may pass the obligation to a thread

waiting on c.s. Note:

  • c.count is protected by m.s
  • when a waiting thread is signaled, m.s.c remains 0
  • c.s.acquire may be initiated before or after c.s.release.
  • Invariant: At all times m.s.c+ P

c∈C c.s.c ≤ 1, where C is

the set of all conditions declared in monitor m.

  • Think of a single pebble being taken from a bowl, held for

a while, and then put into a bowl. 16

slide-9
SLIDE 9

Concurrent programming slides T.S. Norvell (c) 2001

Monitors vs. Semaphores

Semaphores and monitors have equal expressive power since: each can be implemented by the other (see the ResourceMonitor) So the question is: Which is easier to use and to reason about?

Furthermore, the quality of the language was now the subject of objective scientiÞc assessment, based on simplicity of the axioms and the guidance they give for program construction. The axiomatic method is a way to avoid the dogmatism and controversy that so often accompanies programming language design, particularly by committees. C.A.R. Hoare ‘Assertions: a personal perspective’

For mutual exclusion, monitors are more convenient as they pair-up acquisition of mutual exclusion with its release. For more complex coordination problems, monitors are easier to use since

  • Passing wait c indicates something is true right now —

namely the condition

  • Passing s.acquire indicates something happened in the past

— namely a release

  • Thus monitors allow the use of assertional reasoning

whereas semaphores seem to require the use of operational reasoning.. 17