Permalink
Browse files

Make the new concurrency examples a bit more likely to work.

  • Loading branch information...
sellout committed Apr 27, 2012
1 parent 6076a9f commit 467ba599f457812daea41a7c56f74a1ec1cdc9b2
Showing with 105 additions and 74 deletions.
  1. +32 −27 examples/dining-philosophers.kiln
  2. +30 −16 examples/producer-consumer.kiln
  3. +23 −17 examples/readers-writers.kiln
  4. +20 −14 examples/sleeping-barber.kiln
@@ -1,29 +1,34 @@
-{chopstick 1}
-{chopstick 2}
-{chopstick 3}
-{chopstick 4}
-{chopstick 5}
+(load "library/replication")
+(load "library/utilities")
-(trigger* {philosopher (list ?index1 ?index2)}
- {format (list "Philosopher ~D is thinking" index1)}
- {sleep {seconds 1}
- ;; NOTE: Because the trigger either matches or doesn’t, we
- ;; either get both chopsticks or none. It’s not possible
- ;; to deadlock. Is it possible to starve? (Depends on the
- ;; implementation’s fairness, I think.)
- {then (trigger (par {chopstick index1} {chopstick index2})
- {format (list "Philosopher ~D is eating"
- index1)}
- {sleep {seconds 1}
- {then {format (list "Philosopher ~D finished eating"
- index1)}
- {chopstick index1}
- {chopstick index2}
- {philosopher (list index1
- index2)}}})}})
+(trigger* {run-dining-philosophers {table-size ?size}}
+ (new (chopstick philosopher)
+ {chopstick 1}
+ {chopstick 2}
+ {chopstick 3}
+ {chopstick 4}
+ {chopstick 5}
-{philosopher (list 1 2)}
-{philosopher (list 2 3)}
-{philosopher (list 3 4)}
-{philosopher (list 4 5)}
-{philosopher (list 5 1)}
+ (trigger* {philosopher (list ?index1 ?index2)}
+ {format (list "Philosopher ~D is thinking" index1)}
+ {sleep {seconds 1}
+ ;; NOTE: Because the trigger either matches or doesn’t, we
+ ;; either get both chopsticks or none. It’s not possible
+ ;; to deadlock. Is it possible to starve? (Depends on the
+ ;; implementation’s fairness, I think.)
+ {then (trigger (par {chopstick index1} {chopstick index2})
+ {format (list "Philosopher ~D is eating"
+ index1)}
+ {sleep {seconds 1}
+ {then {format (list "Philosopher ~D finished eating"
+ index1)}
+ {chopstick index1}
+ {chopstick index2}
+ {philosopher (list index1
+ index2)}}})}})
+
+ {philosopher (list 1 2)}
+ {philosopher (list 2 3)}
+ {philosopher (list 3 4)}
+ {philosopher (list 4 5)}
+ {philosopher (list 5 1)}))
@@ -1,18 +1,32 @@
-{buffer {nil}}
-{item-count 0}
+(load "library/replication")
+(load "library/constants")
+(load "library/simple-components")
+{include-component "library/math"}
-; producer
-(trigger* (par {buffer {nil}} {item-count 0})
- (trigger {new-item ?item}
- {buffer {cons {car ?item} {cdr {nil}}}}
- {item-count 1}))
-(trigger* (par {buffer {cons ?items}} {item-count ?count})
- ;; FIXME: need to give up if it's full
- (trigger {new-item ?item}
- {buffer {cons {car ?item} {cdr {cons ?items}}}}
- {+ (list ?count 1 {item-count})}))
+(trigger* {run-producer-consumer {buffer-size ?size}}
+ (new (buffer buffer-size item-count)
+ {buffer {nil}}
+ {constant {buffer-size size}}
+ {item-count 0}
-; consumer
-(trigger* (par {buffer {cons {car ?item} {cdr ?items}}} {item-count ?count})
- {buffer ?items}
- {- (list ?count 1 {item-count})})
+ ;; producer
+ (trigger* (par {buffer {nil}} {item-count 0})
+ (trigger {new-item ?item}
+ {buffer {cons {car item} {cdr {nil}}}}
+ {item-count 1}))
+ (trigger* (par {buffer {cons ?items}}
+ {item-count ?count}
+ {buffer-size ?size})
+ {< (list count size
+ (trigger {new-item ?item}
+ {buffer {cons {car item}
+ {cdr {cons items}}}}
+ {+ (list count 1 {item-count})})
+ (par {buffer {cons items}}
+ {item-count count}))})
+
+ ;; consumer
+ (trigger* (par {buffer {cons {car ?item} {cdr ?items}}}
+ {item-count ?count})
+ {buffer ?items}
+ {- (list ?count 1 {item-count})})))
@@ -1,19 +1,25 @@
-{no-writers}
-{readers 0}
+(load "library/replication")
+(load "library/simple-components")
+{include-component "library/math"}
-;;; writer
-(trigger* (par {no-writers} {readers 0})
- {readers 0}
- ;; FIXME: This continuation isn't quite good enough, it fires when the
- ;; write message is matched, not when the operation is
- ;; complete.
- (cont {write ...} {no-writers}))
+(trigger {run-readers-writers}
+ (new (no-writers readers)
+ {no-writers}
+ {readers 0}
-;;; reader
-(trigger* (par {no-writers} {readers ?count})
- {+ (list count 1 {readers})}
- {no-writers}
- {read {message}}
- (trigger (par {message} {readers ?count})
- {echo message}
- {- (list count 1 {readers})}))
+ ;; writer
+ (trigger* (par {no-writers} {readers 0})
+ {readers 0}
+ ;; FIXME: This continuation isn't quite good enough, it
+ ;; fires when the write message is matched, not
+ ;; when the operation is complete.
+ (cont {write "message"} {no-writers}))
+
+ ;; reader
+ (trigger* (par {no-writers} {readers ?count})
+ {+ (list count 1 {readers})}
+ {no-writers}
+ {read {message}}
+ (trigger (par {message ?message} {readers ?count})
+ {echo message}
+ {- (list count 1 {readers})}))))
@@ -1,16 +1,22 @@
-{free-seats 5}
+(load "library/replication")
+(load "library/simple-components")
+{include-component "library/math"}
-;;; barber
-(trigger* (par {customer-ready} {free-seats ?count})
- {barber-ready}
- {+ (list count 1 {free-seats})})
+(trigger* {run-sleeping-barber {seats ?seats}}
+ (new (free-seats customer-ready barber-ready)
+ {free-seats seats}
+
+ ;; barber
+ (trigger* (par {customer-ready} {free-seats ?count})
+ {barber-ready}
+ {+ (list count 1 {free-seats})})
-;;; customer
-(trigger* {free-seats ?count}
- {< (list 0 count
- (par {customer-ready}
- {- (list count 1 {free-seats})}
- (trigger {barber-ready}
- {echo "Getting hair cut"}))
- (par {free-seats count}
- {echo "Left without haircut"}))})
+ ;; customer
+ (trigger* {free-seats ?count}
+ {< (list 0 count
+ (par {customer-ready}
+ {- (list count 1 {free-seats})}
+ (trigger {barber-ready}
+ {echo "Getting hair cut"}))
+ (par {free-seats count}
+ {echo "Left without haircut"}))})))

0 comments on commit 467ba59

Please sign in to comment.