module Control.SessionTypes.MonadSession (
MonadSession (..),
empty,
empty0,
selN,
selN1,
selN2,
selN3,
selN4,
Select(sel),
(<&),
(<&>),
offer,
recurseFix,
recurse0,
weaken0,
var0,
eps0
) where
import Control.SessionTypes.Indexed as I
import Control.SessionTypes.Types
import Data.Function (fix)
import Data.Typeable (Proxy(..))
class IxMonad m => MonadSession m where
send :: a -> m ('Cap ctx (a :!> r)) ('Cap ctx r) ()
recv :: m ('Cap ctx (a :?> r)) ('Cap ctx r) a
sel1 :: m ('Cap ctx (Sel (s ': xs))) ('Cap ctx s) ()
sel2 :: m ('Cap ctx (Sel (s ': t ': xs))) ('Cap ctx (Sel (t ': xs))) ()
offZ :: m ('Cap ctx s) r a -> m ('Cap ctx (Off '[s])) r a
offS :: m ('Cap ctx s) r a -> m ('Cap ctx (Off (t ': xs))) r a -> m ('Cap ctx (Off (s ': t ': xs))) r a
recurse :: m ('Cap (s ': ctx) s) r a -> m ('Cap ctx (R s)) r a
weaken :: m ('Cap ctx s) r a -> m ('Cap (t ': ctx) (Wk s)) r a
var :: m ('Cap (s ': ctx) s) r a -> m ('Cap (s ': ctx) V) r a
eps :: a -> m ('Cap ctx Eps) ('Cap ctx Eps) a
empty :: MonadSession m => m ('Cap '[] s) r a -> m ('Cap '[] s) r a
empty = id
empty0 :: MonadSession m => m ('Cap '[] r) ('Cap '[] r) ()
empty0 = I.return ()
selN :: MonadSession m => Ref s xs -> m ('Cap ctx (Sel xs)) ('Cap ctx s) ()
selN RefZ = sel1
selN (RefS r) = sel2 I.>> selN r
selN1 :: MonadSession m => m ('Cap ctx (Sel (s ': xs))) ('Cap ctx s) ()
selN1 = sel1
selN2 :: MonadSession m => m ('Cap ctx (Sel (s ': t ': xs))) ('Cap ctx t) ()
selN2 = sel2 I.>> sel1
selN3 :: MonadSession m => m ('Cap ctx (Sel (s ': t ': k ': xs))) ('Cap ctx k) ()
selN3 = sel2 I.>> sel2 I.>> sel1
selN4 :: MonadSession m => m ('Cap ctx (Sel (s ': t ': k ': r ': xs))) ('Cap ctx r) ()
selN4 = sel2 I.>> sel2 I.>> sel2 I.>> sel1
class Select xs s where
sel :: MonadSession m => m ('Cap ctx (Sel xs)) ('Cap ctx s) ()
instance (tl ~ TypeEqList xs s, Select' xs s tl) => Select xs s where
sel = sel' (Proxy :: Proxy tl)
class Select' xs s (tl :: k) | xs tl -> s where
sel' :: MonadSession m => Proxy tl -> m ('Cap ctx (Sel xs)) ('Cap ctx s) ()
instance Select' (s ': xs) s ('True ': tl) where
sel' _ = sel1
instance Select' (r ': xs) t tl => Select' (s ': r ': xs) t ('False ': tl) where
sel' _ = sel2 I.>> sel' (Proxy :: Proxy tl)
offer :: MonadSession m => m ('Cap ctx s) r a -> m ('Cap ctx t) r a -> m ('Cap ctx (Off '[s, t])) r a
offer s r = offS s (offZ r)
infixr 1 <&
(<&) :: MonadSession m => m ('Cap ctx s) r a -> m ('Cap ctx (Off (t ': xs))) r a -> m ('Cap ctx (Off (s ': t ': xs))) r a
(<&) = offS
infix 2 <&>
(<&>) :: MonadSession m => m ('Cap ctx s) r a -> m ('Cap ctx t) r a -> m ('Cap ctx (Off '[s, t])) r a
s <&> r = offS s (offZ r)
recurseFix :: MonadSession m => (m ('Cap (s ': ctx) V) r a -> m ('Cap (s ': ctx) s) r a) -> m ('Cap ctx (R s)) r a
recurseFix s = recurse $ fix (\f -> s $ var f)
recurse0 :: MonadSession m => m ('Cap ctx (R s)) ('Cap (s ': ctx) s) ()
recurse0 = recurse $ I.return ()
weaken0 :: MonadSession m => m ('Cap (t ': ctx) (Wk s)) ('Cap ctx s) ()
weaken0 = weaken $ I.return ()
var0 :: MonadSession m => m ('Cap (s ': ctx) V) ('Cap (s ': ctx) s) ()
var0 = var $ I.return ()
eps0 :: MonadSession m => m ('Cap ctx Eps) ('Cap ctx Eps) ()
eps0 = eps ()