1 / 62

Compiling Real-Time Functional Reactive Programming (RT-FRP)

Compiling Real-Time Functional Reactive Programming (RT-FRP). Dana N. Xu and Siau-Cheng Khoo National University of Singapore. Compilation. RT-FRP program. Functional Code. Partial evaluation. Automata Code. Tupling. Tupled Automaton Code. Contribution:

Download Presentation

Compiling Real-Time Functional Reactive Programming (RT-FRP)

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. Compiling Real-Time Functional Reactive Programming (RT-FRP) Dana N. Xu and Siau-Cheng Khoo National University of Singapore

  2. Compilation RT-FRP program Functional Code Partial evaluation Automata Code Tupling Tupled Automaton Code Contribution: Systematic compilation via high-level source to source transformation

  3. Contents • Reactive System • Introduction to RT-FRP • Translating RT-FRP to Functional Code • Compiling Functional Code to Automaton Code • Conclusion and Future Work

  4. Reactive System • Reactive systems have to react to an physical environment which cannot wait. • It requires cost (Time & Space) of running a program to be bounded and known before run-time.

  5. Contents • Reactive System • Introduction to RT-FRP • Translating RT-FRP to Functional Code • Compiling Functional Code to Automata Code • Conclusion and Future Work

  6. RT-FRP • Reactive Part • Captures the essential ingredients of FRP programs • Allows recursion and higher order functions • Resource-bounded (both time and space) • Base Language • Choose a terminating and resource-bounded language

  7. RT-FRP Syntax e ::= x | c | () | (e1, e2) | e|  | x.e | e1 e2 v ::= c | () | (v1, v2) | v|  | x.e a. Base language syntax s, ev ::= input | time | ext e | delay v s | let snapshot x s1 in s2 | s1 switch on x ev in s2 | let continue {kj xj = uj } in s | u u ::= s until <evj kj> b. Reactive language syntax Figure 2. RT-FRP language syntax

  8. x1 x2 when s Example 1 - The when operator when s= let snapshot x1  s in let snapshot x2 delay False s in ext (if x2x1 then () else )

  9. Contents • Reactive System • Introduction to RT-FRP • Translating RT-FRP to Functional Code • Compiling Functional Code to Automata Code • Conclusion and Future Work

  10. Event and Behavior in RT-FRP type Behavior a = [Time]  [a] Event a  Behavior (Maybe a) data Maybe a = Nothing | Just a type Event a = [Time]  [Maybe a] time t1 t2 t3 t4 t5 t6 t7 … b v1 v2 v3 v4 v5 v6 v7 … … e j1 j4 j5 j7   

  11. Stream Based Implementation time :: Behavior Time time = \ts -> ts delay :: a -> Behavior a -> Behavior a delay v s = \ts -> v:(s ts) ==> :: Event a -> (a->b) -> Event b .|. :: Event a -> Event a -> Event a untilB :: Behavior a -> Event (Behavior a) -> Behavior a switcher :: Behavior a -> Event (Behavior a) -> Behavior a

  12. Lifting Lifting values/operations at base level to stream of values/operations at reactive level. Example 1 lift0 = constantB constantB 5 = [5, 5, 5, …] Example 2 w1 = let snapshot x <- time in ext (x+1) w1 = lift1 (\x -> x+1) time

  13. Translating RT-FRP to Functional Code []tr :: RExp -> VEnv -> BExp [ext e]tr  = liftk (\v1..vk. e) w1..wk where ([v1..vk], [w1..wk]) =lookup e  [delay v s]tr  = delay v s’ where s’ = [s] 

  14. Compiling RT-FRP to Functional Code [let snapshot x s1 s2]  = … [time]  = time [s1 switch on x ev s2]  = … [s until <evj => kj>j=1..n] = … [let continue {kj xj = uj}j=1..n in s] = …

  15. Equivalent Functional Representation at Abstract Level z = let snapshot a  delay True x in let snapshot b  delay True z in let snapshot c  input in ext (if a then b else ((a and b) or c)) z = lift3 (\a->\b->\c-> if a then b else ((a && b) || c)) (delay True x) (delay True z) input x = let snapshot a  delay True x in let snapshot b  z in ext (if a then False else b) x = lift2 (\a->\b->if a then False else b) (delay True x) z n = let snapshot a  delay True x in let snapshot b  delay 0 n in ext (if a then 0 else b+1) n = lift2 (\a->\b->if a then 0 else b+1) (delay True x) (delay 0 n) Translate to Translate to Translate to

  16. Contents • Reactive System & Synchronous Language • Introduction to RT-FRP • Translating RT-FRP to Functional Code • Compiling Functional Code to Automata Code • Conclusion and Future Work

  17. Our Algorithm • Generalize all constants that may result in infinite variations. • Apply a.Define configuration with state variables b.Instantiate signals c.Unfold & Unify d.Fold or goto 2a to the body of the definition of a signal

  18. From Previous Example z = lift3 (\a->\b->\c-> if a then b else ((a && b) || c)) (delay True x) (delay True z) input x = lift2 (\a->\b->if a then False else b) (delay True x) z n = lift2 (\a->\b->if a then 0 else b+1) (delay True x) (delay 0 n)

  19. Generalize Integer Constants n = lift2 (\a->\b->if a then 0 else b+1) (delay True x) (delay 0 n) nconfig-1[c1,c2,c3]: n = lift2 (\a->\b->if a then c1 else b+c2) (delay True x) (delay c3 n)

  20. Instantiate signals Instantiate: x = delay x# x_ n = delay n# n_ [1] n = lift2 (\a->\b->if a then c1 else b+c2) (delay True x) (delay c3 n) n = lift2 (\a->\b->if a then c1 else b+c2) (delay True (delay x# x_)) (delay c3 (delay n# n_))

  21. Unfold Once and Partial Evaluate The unfolding rule used is : lift2 (\a->\b -> e) (delay v1 v) (delay w1 w) => delay e[v1/a,w1/b] (lift2 (\a->\b -> e) v w) n = lift2 (\a->\b->if a then c1 else b+c2) (delay True (delay x# x_)) (delay c3 (delay n# n_)) n = delay c1 (lift2 (\a->\b->if a then c1 else b+c2) (delay x# x_) (delay n# n_)) [2]

  22. Unification n = delay n# n_ [1] n = delay c1 (lift2 (\a->\b->if a then c1 else b+c2) (delay x# x_) (delay n# n_)) [2] n= delay c1 n_ n_ = (lift2 (\a->\b->if a then c1 else b+c2) (delay x# x_) (delay c1 n_))

  23. Adjust Time Backward (Future  Current) n_ = (lift2 (\a->\b->if a then c1 else b+c2) (delay x# x_) (delay c1 n_)) n = (lift2 (\a->\b->if a then c1 else b+c2) (delay xb x) (delay c1 n)) x# => xb x_ => x n_ => n

  24. Try Folding n = (lift2 (\a->\b->if a then c1 else b+c2) (delay xb x) (delay c1 n)) nconfig-1[c1,c2,c3]: n = lift2 (\a->\b->if a then c1 else b+c2) (delay True x) (delay c3 n) Folding fails

  25. Define a New Configuration n = (lift2 (\a->\b->if a then c1 else b+c2) (delay xb x) (delay c1 n)) n = delay c1nconfig-2[c1,c2,c1] nconfig-2[b1,b2,b3]: n = (lift2 (\a->\b->if a then b1 else b+b2) (delay xb x) (delay b3 n)) from n_ original n

  26. Instantiate Instantiate: x = delay x# x_ n = delay n# n_ n =(lift2 (\a->\b->if a then c1 else b+c2) (delay xb x) (delay c3 n) n =(lift2 (\a->\b->if a then c1 else b+c2) (delay xb(delay x# x_)) (delay c3 (delay n# n_)))

  27. Instantiate Unknown Boolean case xb == False: n =(lift2 (\a->\b->if a then c1 else b+c2) (delay False (delay x# x_)) (delay c3 (delay n# n_))) n = delay (c3+c2) (lift2 (\a->\b->if a then c1 else b+c2) (delay x# x_) (delay n# n_)) {unification with instantiation n#=c3+c2} n = delay (c3+c2) (lift2 (\a->\b->if a then c1 else b+c2) (delay x# x_) (delay (c3+c2) n_)) n = delay (c3+c2) nconfig-2[c1,c2,c3+c2]

  28. (cont.) case xb == True: n =(lift2 (\a->\b->if a then c1 else b+c2) (delay True (delay x# x_)) (delay c3 (delay n# n_))) n = delay c1 (lift2 (\a->\b->if a then c1 else b+c2) (delay x# x_) (delay n# n_)) {unification with instantiation n#=c1} n = delay c1 (lift2 (\a->\b->if a then c1 else b+c2) (delay x# x_) (delay c1 n_)) n = delay c1 nconfig-2[c1,c2,c1]

  29. Automaton for n nconfig-1[c1,c2,c3]: n=delay c1 nconfig-2[c1,c2,c1] nconfig-2[c1,c2,c3]: case xb = False n=delay (c3+c2) nconfig-2[c1,c2,c3+c2] case xb = True n=delay c1 nconfig-2[c1,c2,c1]

  30. Automata for n, x and z

  31. Tupling • To combine multiple automata into a single automaton • Benefits • More efficient • Less control logic • More specialization across automata

  32. Tupling Combine three signals together mconfig-111[c1,c2,c3] (n,x,z)=(nconfig-1[c1,c2,c3],xconfig-1,zconfig-1) = delay (c1,False,True) (nconfig-2[c1,c2,c1],xconfig2,zconfig-2) = delay (c1,False,True) mconfig-222[c1,c2,c1]

  33. Define, Unfold and Fold (twice) mconfig-222[c1,c2,c3] st xb =False, zb =True (n,x,z)=(nconfig-2[c1,c2,c3],xconfig-2,zconfig-2) : = delay (c3+c2,True,True) mconfig-233[c1,c2,c3+c2] mconfig-233[c1,c2,c3] st xb =True, zb =True (n,x,z) = (nconfig-2[c1,c2,c3],xconfig-3,zconfig-3) : = delay (c1,False,True) mconfig-223[c1,c2,c1]

  34. Define, Unfold and Fold mconfig-223[c1,c2,c3] st xb = False, zb = True (n,x,z)= (nconfig-2[c1,c2,c3],xconfig-2,zconfig-3) : = delay (c3+c2,z#,input#) mconfig-233a[c1,c2,c3+c2]

  35. Define, Unfold and Fold mconfig-233a[c1,c2,c3] st x#=z#=input# (n,x,z) = (nconfig-2[c1,c2,c3],xconfig-3,zconfig-3) case x#=z#=False = delay (c3+c2,z#,input#) (nconfig-2[c1,c2,c3+c2],xconfig-3,zconfig-3) =delay (c3+c2,z#,input#) mconfig-233a[c1,c2,c3+c2] case x#=z#=True = delay (c1,False,True) (nconfig-2[c1,c2,c1],xconfig-2,zconfig-3) =delay (c1,False,True) mconfig-223[c1,c2,c1]

  36. Final Tupled Automaton mconfig-111[c1,c2,c3]: (n,x,z)= delay (c1,False,True) mconfig-222[c1,c2,c1] mconfig-222[c1,c2,c3]: (n,x,z)= delay (c3+c2,True,True) mconfig-233[c1,c2,c3+c2] mconfig-233[c1,c2,c3]: (n,x,z)= delay (c1,False,True) mconfig-223[c1,c2,c1] mconfig-223[c1,c2,c3]: (n,x,z)= delay (c3+c2,input#,input#) mconfig-233a[c1,c2,c3+c2] mconfig-233a[c1,c2,c3] st x#=z#=input# (n,x,z) = (nconfig-2[c1,c2,c3],xconfig-3,zconfig-3) case x#=z#=False = delay (c3+c2,input#,input#) mconfig-233a[c1,c2,c3+c2] case x#=z#=True =delay (c1,False,True) mconfig-223[c1,c2,c1]

  37. Final Tupled Automaton

  38. Automata for n, x and z

  39. Final Tupled Automaton

  40. Conclusion • Introduce an approach to building reactive systems based on RT-FRP • A two-stage compiler for RT-FRP • RT-FRP  Functional Code • Functional Code  Automaton • Partial Evaluation • Tupling

  41. Future Work • Re-design RT-FRP • event-driven • deterministic • concurrent • compile to hardware

  42. Unfolding Rules .|. :: Event a -> Event a -> Event a (delay  v) .|. (delay w1 w) => delay w1 (v .|. w) (delay (Just a) v) .|. (delay w1 w) => delay (Just a) (v .|. w) ==> :: Event a -> (a->b) -> Event b (delay  v) ==> f => (delay  (v ==> f)) (delay (Just a) v) ==> f => (delay (Just (f a))) bot)

  43. Unfolding Rules lift2 (\a->\b -> e) (delay v1 v) (delay w1 w) => delay e[v1/a,w1/b] (lift (\a b -> e) v w) switcher :: Behavior a->Event (Behavior a)->Behavior a switcher (delay v1 v) (delay  w) => delay v1 (switcher v w) switcher (delay v1 v) (delay (Just k) w) => delay v1 (switcher k w) untilB :: Behavior a->Event (Behavior a)->Behavior a untilB (delay v1 v) (delay  w) => delay v1 (untilB v w) untilB (delay v1 v) (delay (Just k) w) => delay v1 k

  44. Compiling RT-FRP to Functional Code extr[s]  = let v1..vn = freevar s -  if (n=0) then [s]   elselams v1..vn where lams = \ v1..vn ->[s]  

  45. time value t RT-FRP Example 1 s1 = let snapshot x  time in ext (sin x) 0

  46. FRP vs. RT-FRP FRP type Behavior a = Time  a type Event a = [(Time, a)] RT-FRP Event a  Behavior (Maybe a) data Maybe a = Nothing | Just a type Behavior a = [Time]  [a] type Event a = [Time]  [Maybe a]

  47. Stream Based Implementation ==> :: Event a -> (a->b) -> Event b e1 ==> f = \ts  loop ts (e1 ts) where loop (_:ts) (Nothing:ys) = Nothing:(loop ts ys) loop (_:ts) (Just a:ys) = (Just (f a)):(loop ts ys) fe ==> f = map (map f).fe

  48. <Initialize Memory> foreachinput_event do <Compute Outputs> <Update Memory> end <Initialize Memory> foreachperiod do <Read Inputs> <Compute Outputs> <Update Memory> end a. “Event driven” b. “Sampling” Figure 1. Execution schemes for reactive systems Two Schemes for Reactive System Implementation

  49. Stream Based Implementation time :: Behavior Time time = \ts -> ts delay :: a -> Behavior a -> Behavior a delay v s = \ts -> v:(s ts) ==> :: Event a -> (a->b) -> Event b e ==> f = map (map f) . e

  50. Stream Based Implementation ==> :: Event a -> (a->b) -> Event b e1 ==> f = \ts  loop ts (e1 ts) where loop (_:ts) (Nothing:es) = Nothing:(loop ts es) loop (_:ts) (Just a:es) = (Just (f a)):(loop ts es)

More Related