Pistache: A π-Calculus Internal Domain Specific Language for Scala

E54f4140dc133a17200fe7a104c33a8e?s=47 Pedro Matiello
September 26, 2011

Pistache: A π-Calculus Internal Domain Specific Language for Scala

Presented at: XIV Simpósio Brasileiro de Métodos Formais (SBMF 2011), September/2011.

E54f4140dc133a17200fe7a104c33a8e?s=128

Pedro Matiello

September 26, 2011
Tweet

Transcript

  1. PISTACHE A π-Calculus Internal Domain Specific Language for Scala

  2. •Pedro Matiello pmatiello@gmail.com •Ana Cristina de Melo acvm@ime.usp.br •http://code.google.com/p/pistache/

  3. • Pistache is an implementation of the π-Calculus as a

    domain specific language hosted in Scala INTRODUCTION
  4. • It provides π-Calculus’ abstractions for concurrent computation within the

    Scala programming language INTRODUCTION
  5. π-CALCULUS

  6. •π-Calculus is a formal language for describing concurrent computation with

    dynamic reconfiguration
  7. •Agents communicate by exchanging names through channels (which are also

    names) •Connections between agents may change in the course of the computation
  8. AGENTS 0 Nil α.P Prefix P + Q Sum PʛQ

    Parallel (νx)P Restriction [x=y].P Match [x≠y].P Mismatch
  9. PREFIXES yx Output y(x) Input τ Silent _

  10. • The Agents: C = (νz) y(p).pz S = yx.S

    P = x(w).α.P • The composition: C | S | P & 6 3 \ [ _ _ EXAMPLE Example adapted from: An Introduction to the pi-Calculus, by Joachim Parrow
  11. SCALA

  12. •Scala is a general-purpose programming language providing features both of

    object-oriented and functional programming
  13. •Flexible syntax •Statically-typed •Runs on the Java Virtual Machine

  14. •Actively-developed •Growing community

  15. PISTACHE

  16. •Pistache is an implementation of π-Calculus as an internal Domain

    Specific Language for Scala
  17. val P = Agent(...) lazy val recP:Agent = Agent(...) val

    restrP = Agent { val restrictedName = Name(...) ... } AGENT DEFINITION
  18. val name = Name(some_object) val name = Name[Type] name :=

    other_object value = name.value NAMES
  19. val y = Link[Type] y~x yx y(x) y(x) CHANNELS _

  20. val silent = Action{ doSomething() } τ SILENT TRANSITIONS

  21. val P = Agent { p1 * p2 * Q

    } P = α.β.Q CONCATENATION
  22. val P = Agent { Q | R | S

    } P = Q | R | S COMPOSITION
  23. val P = Agent { (p1 :: Q) + (p2

    :: R) + (p3 :: S) P = αQ + βR + γS } SUMMATION
  24. val P = Agent(If (x==y) {Q}) P = [x=y] Q

    MATCHING
  25. • The Agents: C = (νz) y(p).pz S = yx.S

    P = x(w).α.P • The composition: C | S | P & 6 3 \ [ _ _ EXAMPLE
  26. val y = Link[Link[String]] val x = Link[String] EXAMPLE

  27. val y = Link[Link[String]] val x = Link[String] val C

    = Agent { val p = Name[Link[String]] val z = "message" y(p) * p~z } EXAMPLE C = (νz) y(p).pz _
  28. val y = Link[Link[String]] val x = Link[String] val C

    = Agent { val p = Name[Link[String]] y(p) * p~"message" } lazy val S:Agent = Agent { y~x*S } EXAMPLE S = yx.S _
  29. val y = Link[Link[String]] val x = Link[String] val C

    = Agent { val p = Name[Link[String]] y(p) * p~"message" } lazy val S:Agent = Agent { y~x*S } lazy val P:Agent = Agent { val w = Name[String] val act = Action { println(msg.value) } x(w) * act * P } EXAMPLE P = x(w).α.P
  30. val y = Link[Link[String]] val x = Link[String] val C

    = Agent { val p = Name[Link[String]] y(p) * p~"message" } lazy val S:Agent = Agent { y~x*S } lazy val P:Agent = Agent { val msg = Name[String] val act = Action { println(msg.value) } x(msg) * act * P } new ThreadedRunner(C | S | P) start EXAMPLE C | S | P
  31. MESSAGE PASSING • Channels are implemented as shared buffers •

    Communication between agents is synchronous
  32. MESSAGE PASSING Output yx Input y(x) Wait until y is

    empty Wait until y is not empty Put x on y Put the contents of y in x Signal y not empty Signal y empty Wait until y is empty _
  33. val P = Agent ( p1 * p2 * p3

    * Q ) DATA STRUCTURE
  34. val P = Agent ( p1 * p2 * p3

    * Q ) DATA STRUCTURE 3 S &RQFDWHQDWLRQ$JHQW &RQFDWHQDWLRQ3UHIL[ &RQFDWHQDWLRQ3UHIL[ 4 S S
  35. def execute(agent:PiObject) { agent match { case ConcatenationAgent(left, right) =>

    ... case CompositionAgent(left, right) => ... ... } } EXECUTION
  36. case ConcatenationAgent(left, right) => execute(left apply) execute(right apply) EXECUTION

  37. case CompositionAgent(left, right) => executeInNewThread(left apply) executeInNewThread(right apply) EXECUTION

  38. def executeInNewThread(agent:PiObject) { val runnable = new Runnable() { override

    def run() { execute(agent) } } executor.execute(runnable) } THREAD SPAWNING
  39. THREAD SPAWNING • CachedThreadPool • Caches finished threads • Reuses

    cached threads • Creates new threads if none are available • Deletes from the pool threads that have not been used reused for 60 seconds
  40. THREAD SPAWNING Strategy Time consumed for 100k agents new Thread

    23 743 ms CachedThreadPool 2 089 ms
  41. • We knew that: • Concurrent programming is hard CONCLUSION

  42. • We learned that: • Proper abstractions can improve our

    understanding of concurrency and concurrent programs CONCLUSION
  43. • We also learned that: • The abstractions present in

    π-Calculus provide a feasible model for concurrency in actual software programming CONCLUSION
  44. PISTACHE Pedro Matiello Ana Cristina de Melo