home *** CD-ROM | disk | FTP | other *** search
-
-
- Here is the complete text for the DIning Philosopher's example written in
- the Turing Plus programming language.
- Stephen Perelgut
- ------------------------- Dining Philosophers --------------------------
- randomize % re-initialize the random number generator each run
- const *numPhilosophers := 5 % maximum number of philosophers
-
- monitor Table % mutually exclusive access to forks
- export unqualified GetFork,
- unqualified GiveFork
-
- var ForkInUse : array 1..numPhilosophers of boolean % indicate fork in use
- for i : 1..numPhilosophers
- /* initially all forks are free */
- ForkInUse(i) := false
- end for
-
- var ForkQueue : array 1..numPhilosophers of condition
-
- /* Each philosopher brings one fork to the table and needs
- * two forks to eat. GetFork accesses the specified fork
- * by seeing if it is in use (and waiting for it to be freed
- * if it is in use) and then marking it as being used. GiveFork
- * marks a fork as being available again and signals someone
- * waiting for that fork that it is now available
- */
-
- procedure GetFork(Fork: 1..numPhilosophers)
- post ForkInUse(Fork)
-
- if ForkInUse(Fork) then
- wait ForkQueue(Fork)
- end if
- assert not ForkInUse(Fork)
- ForkInUse(Fork) := true
- end GetFork
-
- procedure GiveFork(Fork : 1..numPhilosophers)
- pre ForkInUse(Fork)
- ForkInUse(Fork) := false
- signal ForkQueue(Fork)
- end GiveFork
- end Table
-
- const numBites := 25 % number of bites required to finish the meal
- const maxThinkTime := 5 % maximum number of seconds the philosopher will think
- const maxBiteSize := 10 % maximum number of seconds the philosopher will eat
-
- /* This process will be activated for each philosopher. It repeatedly
- * consumes a random number of bites after following this sequence:
- * think, get left fork, think, get right fork, eat, return forks
- * This continues until all the food is consumed (unless deadlock occurs
- * with each philosopher clutching exactly one fork.รจ */
-
- process Philosopher (phil : 1..numPhilosophers)
- var bitesLeft := numBites
- loop % activities that form a single bite
-
- /* think before first Fork */
- var thinkTime : int
- randint(thinkTime, 1, maxThinkTime)
- put "Philosopher ", phil, " will think for ", thinkTime, " seconds."
- pause thinkTime
- put "Philosopher ", phil, " has completed thinking."
-
- /* get left Fork - one philosopher brought to the table */
- put "Philosopher ", phil, " reaching for left Fork."
- GetFork(phil)
- put "Philosopher ", phil, " has obtained left Fork."
-
- /* think a bit more before getting the next Fork */
- randint(thinkTime, 1, maxThinkTime)
- put "Philosopher ", phil, " will pause for ", thinkTime, " seconds."
- pause thinkTime
- put "Philosopher ", phil, " has completed pausing."
-
- /* get right Fork - one the nextdoor philospher brought */
- put "Philosopher ", phil, " reaching for right Fork."
- GetFork(phil mod numPhilosophers + 1)
- put "Philosopher ", phil, " has obtained right Fork."
-
- /* time to eat */
- var biteSize : int
- randint(biteSize, 1, maxBiteSize)
- put "Philosopher ", phil, " will eat for ", biteSize, " cookies."
- biteSize := min(biteSize, bitesLeft) % can only eat what's there
- pause biteSize % one second per bite - chewing 30 times :-)
- put "Philosopher ", phil, " has completed eating."
-
- /* give back the Forks */
- GiveFork(phil)
- GiveFork(phil mod numPhilosophers + 1)
- bitesLeft -= biteSize
- exit when bitesLeft = 0
- put "Philosopher ", phil, " has ", bitesLeft, " cookies left to eat."
- end loop
-
- put "Philosopher ", phil, " has completed his meal."
- end Philosopher
-
- for i : 1..numPhilosophers
- fork Philosopher(i) % start up each philosopher in turn
- end for
-