{-# LANGUAGE GeneralizedNewtypeDeriving #-} module Futhark.Optimise.Fusion.TryFusion ( TryFusion , tryFusion , liftMaybe ) where import Control.Applicative import Control.Monad.State import Control.Monad.Reader import Futhark.Representation.SOACS import Futhark.MonadFreshNames newtype TryFusion a = TryFusion (ReaderT (Scope SOACS) (StateT VNameSource Maybe) a) deriving (a -> TryFusion b -> TryFusion a (a -> b) -> TryFusion a -> TryFusion b (forall a b. (a -> b) -> TryFusion a -> TryFusion b) -> (forall a b. a -> TryFusion b -> TryFusion a) -> Functor TryFusion forall a b. a -> TryFusion b -> TryFusion a forall a b. (a -> b) -> TryFusion a -> TryFusion b forall (f :: * -> *). (forall a b. (a -> b) -> f a -> f b) -> (forall a b. a -> f b -> f a) -> Functor f <$ :: a -> TryFusion b -> TryFusion a $c<$ :: forall a b. a -> TryFusion b -> TryFusion a fmap :: (a -> b) -> TryFusion a -> TryFusion b $cfmap :: forall a b. (a -> b) -> TryFusion a -> TryFusion b Functor, Functor TryFusion a -> TryFusion a Functor TryFusion -> (forall a. a -> TryFusion a) -> (forall a b. TryFusion (a -> b) -> TryFusion a -> TryFusion b) -> (forall a b c. (a -> b -> c) -> TryFusion a -> TryFusion b -> TryFusion c) -> (forall a b. TryFusion a -> TryFusion b -> TryFusion b) -> (forall a b. TryFusion a -> TryFusion b -> TryFusion a) -> Applicative TryFusion TryFusion a -> TryFusion b -> TryFusion b TryFusion a -> TryFusion b -> TryFusion a TryFusion (a -> b) -> TryFusion a -> TryFusion b (a -> b -> c) -> TryFusion a -> TryFusion b -> TryFusion c forall a. a -> TryFusion a forall a b. TryFusion a -> TryFusion b -> TryFusion a forall a b. TryFusion a -> TryFusion b -> TryFusion b forall a b. TryFusion (a -> b) -> TryFusion a -> TryFusion b forall a b c. (a -> b -> c) -> TryFusion a -> TryFusion b -> TryFusion c forall (f :: * -> *). Functor f -> (forall a. a -> f a) -> (forall a b. f (a -> b) -> f a -> f b) -> (forall a b c. (a -> b -> c) -> f a -> f b -> f c) -> (forall a b. f a -> f b -> f b) -> (forall a b. f a -> f b -> f a) -> Applicative f <* :: TryFusion a -> TryFusion b -> TryFusion a $c<* :: forall a b. TryFusion a -> TryFusion b -> TryFusion a *> :: TryFusion a -> TryFusion b -> TryFusion b $c*> :: forall a b. TryFusion a -> TryFusion b -> TryFusion b liftA2 :: (a -> b -> c) -> TryFusion a -> TryFusion b -> TryFusion c $cliftA2 :: forall a b c. (a -> b -> c) -> TryFusion a -> TryFusion b -> TryFusion c <*> :: TryFusion (a -> b) -> TryFusion a -> TryFusion b $c<*> :: forall a b. TryFusion (a -> b) -> TryFusion a -> TryFusion b pure :: a -> TryFusion a $cpure :: forall a. a -> TryFusion a $cp1Applicative :: Functor TryFusion Applicative, Applicative TryFusion TryFusion a Applicative TryFusion -> (forall a. TryFusion a) -> (forall a. TryFusion a -> TryFusion a -> TryFusion a) -> (forall a. TryFusion a -> TryFusion [a]) -> (forall a. TryFusion a -> TryFusion [a]) -> Alternative TryFusion TryFusion a -> TryFusion a -> TryFusion a TryFusion a -> TryFusion [a] TryFusion a -> TryFusion [a] forall a. TryFusion a forall a. TryFusion a -> TryFusion [a] forall a. TryFusion a -> TryFusion a -> TryFusion a forall (f :: * -> *). Applicative f -> (forall a. f a) -> (forall a. f a -> f a -> f a) -> (forall a. f a -> f [a]) -> (forall a. f a -> f [a]) -> Alternative f many :: TryFusion a -> TryFusion [a] $cmany :: forall a. TryFusion a -> TryFusion [a] some :: TryFusion a -> TryFusion [a] $csome :: forall a. TryFusion a -> TryFusion [a] <|> :: TryFusion a -> TryFusion a -> TryFusion a $c<|> :: forall a. TryFusion a -> TryFusion a -> TryFusion a empty :: TryFusion a $cempty :: forall a. TryFusion a $cp1Alternative :: Applicative TryFusion Alternative, Applicative TryFusion a -> TryFusion a Applicative TryFusion -> (forall a b. TryFusion a -> (a -> TryFusion b) -> TryFusion b) -> (forall a b. TryFusion a -> TryFusion b -> TryFusion b) -> (forall a. a -> TryFusion a) -> Monad TryFusion TryFusion a -> (a -> TryFusion b) -> TryFusion b TryFusion a -> TryFusion b -> TryFusion b forall a. a -> TryFusion a forall a b. TryFusion a -> TryFusion b -> TryFusion b forall a b. TryFusion a -> (a -> TryFusion b) -> TryFusion b forall (m :: * -> *). Applicative m -> (forall a b. m a -> (a -> m b) -> m b) -> (forall a b. m a -> m b -> m b) -> (forall a. a -> m a) -> Monad m return :: a -> TryFusion a $creturn :: forall a. a -> TryFusion a >> :: TryFusion a -> TryFusion b -> TryFusion b $c>> :: forall a b. TryFusion a -> TryFusion b -> TryFusion b >>= :: TryFusion a -> (a -> TryFusion b) -> TryFusion b $c>>= :: forall a b. TryFusion a -> (a -> TryFusion b) -> TryFusion b $cp1Monad :: Applicative TryFusion Monad, Monad TryFusion Monad TryFusion -> (forall a. String -> TryFusion a) -> MonadFail TryFusion String -> TryFusion a forall a. String -> TryFusion a forall (m :: * -> *). Monad m -> (forall a. String -> m a) -> MonadFail m fail :: String -> TryFusion a $cfail :: forall a. String -> TryFusion a $cp1MonadFail :: Monad TryFusion MonadFail, Monad TryFusion Applicative TryFusion TryFusion VNameSource Applicative TryFusion -> Monad TryFusion -> TryFusion VNameSource -> (VNameSource -> TryFusion ()) -> MonadFreshNames TryFusion VNameSource -> TryFusion () forall (m :: * -> *). Applicative m -> Monad m -> m VNameSource -> (VNameSource -> m ()) -> MonadFreshNames m putNameSource :: VNameSource -> TryFusion () $cputNameSource :: VNameSource -> TryFusion () getNameSource :: TryFusion VNameSource $cgetNameSource :: TryFusion VNameSource $cp2MonadFreshNames :: Monad TryFusion $cp1MonadFreshNames :: Applicative TryFusion MonadFreshNames, HasScope SOACS, LocalScope SOACS) tryFusion :: MonadFreshNames m => TryFusion a -> Scope SOACS -> m (Maybe a) tryFusion :: TryFusion a -> Scope SOACS -> m (Maybe a) tryFusion (TryFusion ReaderT (Scope SOACS) (StateT VNameSource Maybe) a m) Scope SOACS types = (VNameSource -> (Maybe a, VNameSource)) -> m (Maybe a) forall (m :: * -> *) a. MonadFreshNames m => (VNameSource -> (a, VNameSource)) -> m a modifyNameSource ((VNameSource -> (Maybe a, VNameSource)) -> m (Maybe a)) -> (VNameSource -> (Maybe a, VNameSource)) -> m (Maybe a) forall a b. (a -> b) -> a -> b $ \VNameSource src -> case StateT VNameSource Maybe a -> VNameSource -> Maybe (a, VNameSource) forall s (m :: * -> *) a. StateT s m a -> s -> m (a, s) runStateT (ReaderT (Scope SOACS) (StateT VNameSource Maybe) a -> Scope SOACS -> StateT VNameSource Maybe a forall r (m :: * -> *) a. ReaderT r m a -> r -> m a runReaderT ReaderT (Scope SOACS) (StateT VNameSource Maybe) a m Scope SOACS types) VNameSource src of Just (a x, VNameSource src') -> (a -> Maybe a forall a. a -> Maybe a Just a x, VNameSource src') Maybe (a, VNameSource) Nothing -> (Maybe a forall a. Maybe a Nothing, VNameSource src) liftMaybe :: Maybe a -> TryFusion a liftMaybe :: Maybe a -> TryFusion a liftMaybe Maybe a Nothing = String -> TryFusion a forall (m :: * -> *) a. MonadFail m => String -> m a fail String "Nothing" liftMaybe (Just a x) = a -> TryFusion a forall (m :: * -> *) a. Monad m => a -> m a return a x