{-# LANGUAGE DataKinds #-}
{-# LANGUAGE TypeOperators #-}
{-# LANGUAGE RebindableSyntax #-}
{-# LANGUAGE TemplateHaskell #-}
module Test.Program.Closure where
import Control.SessionTypes.Indexed
import Control.Distributed.Session
import Control.Distributed.Process as P (Process, ProcessId, NodeId, ReceivePort)
import Control.Distributed.Process.Serializable (SerializableDict(..))
import Control.Distributed.Process.Closure (remotable, mkStatic, mkStaticClosure, mkClosure)
import qualified Prelude as PL
sess1 :: Session ('Cap '[] (R (Int :?> Sel '[V, Wk Eps]))) ('Cap '[] Eps) Int
sess1 = recurseFix $ \f -> do
n <- recv
liftIO (putStrLn $ show n)
if n > 0
then sel1 >> f
else selN2 >> weaken0 >> eps n
sess1' :: ProcessId -> Session ('Cap '[] (R (Int :?> Sel '[V, Wk Eps]))) ('Cap '[] Eps) ()
sess1' pid = recurseFix $ \f -> do
n <- recv
liftIO (putStrLn $ show n)
if n > 0
then sel1 >> f
else selN2 >> weaken0 >> utsend pid n >> eps ()
sess2 :: Session ('Cap '[] (R (Int :!> Off '[V, Wk Eps]))) ('Cap '[] Eps) ()
sess2 = recurse $ go 3
where
go n = do
send n
offer (var $ go (n - 1)) (weaken0 >> eps0)
sessReturn :: Session s s Int
sessReturn = return 5
sessSpawnCh :: ProcessId -> ReceivePort Int -> Session s s ()
sessSpawnCh pid rp = do
a <- receiveChan rp
utsend pid a
sessSpawn :: ProcessId -> Session s s ()
sessSpawn pid = utsend pid (5 :: Int)
spawnSess :: SpawnSession Int ()
spawnSess = SpawnSession sess1 sess2
spawnSess0 :: ProcessId -> SpawnSession () ()
spawnSess0 pid = SpawnSession (sess1' pid) sess2
sessWrap :: SessionWrap Int
sessWrap = SessionWrap sessReturn
spawnChWrap :: ProcessId -> ReceivePort Int -> SessionWrap ()
spawnChWrap pid rp = SessionWrap $ sessSpawnCh pid rp
sessSpawnWrap :: ProcessId -> SessionWrap ()
sessSpawnWrap pid = SessionWrap $ sessSpawn pid
sdictInt :: SerializableDict Int
sdictInt = SerializableDict
remotable ['spawnSess, 'spawnSess0, 'sdictInt, 'sessWrap, 'spawnChWrap, 'sessSpawnWrap]