Skip to content

Instantly share code, notes, and snippets.

@brendanhay
Last active October 13, 2016 00:50
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save brendanhay/e6f2501c15ac5160ca7dbb6ada6777f0 to your computer and use it in GitHub Desktop.
Save brendanhay/e6f2501c15ac5160ca7dbb6ada6777f0 to your computer and use it in GitHub Desktop.
GHC8 ImpredictiveTypes + monad-control instances
name: monad-control-ghc8
version: 0.0.0
cabal-version: >= 1.10
library
default-language: Haskell2010
exposed-modules:
MonadControlGHC8
build-depends:
base == 4.9.*
, monad-control >= 1.0.1.0
, mtl >= 2.2.1
, transformers-base >= 0.4.4
{-# LANGUAGE GeneralizedNewtypeDeriving #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE UndecidableInstances #-}
module MonadControlGHC8 where
import Control.Applicative (Alternative, Applicative)
import Control.Monad.Base (MonadBase)
import Control.Monad.Reader (MonadReader, ReaderT)
import Control.Monad.Trans.Control (MonadBaseControl (..))
data Env = Env
newtype Foo a = Foo { unFoo :: ReaderT Env IO a }
deriving
( Functor
, Applicative
, Alternative
, Monad
, MonadBase IO
, MonadReader Env
)
-- The following instance compiles on GHC 7.10.3 and GHC 8.0.1.
-- Note the use of apply rather than compose:
--
instance MonadBaseControl IO Foo where
type StM Foo a = StM (ReaderT Env IO) a
liftBaseWith f = Foo $ liftBaseWith $ \g -> f (g . unFoo)
restoreM = Foo . restoreM
newtype Bar a = Bar { unBar :: ReaderT Env IO a }
deriving
( Functor
, Applicative
, Alternative
, Monad
, MonadBase IO
, MonadReader Env
)
-- The following instance fails to compile on GHC 8.0.1, with the error:
--
-- /MonadControlGHC8.hs:44:28: error:
-- • Cannot instantiate unification variable ‘t0’
-- with a type involving foralls:
-- forall a1. ReaderT Env IO a1 -> IO (StM (ReaderT Env IO) a1)
-- GHC doesn't yet support impredicative polymorphism
-- • In the second argument of ‘(.)’, namely ‘liftBaseWith’
-- In the expression: Bar . liftBaseWith
-- In the expression: Bar . liftBaseWith $ \ g -> f (g . unBar)
-- MonadControlGHC8.hs:44:52: error:
-- • Couldn't match expected type ‘ReaderT Env IO a1 -> IO a1’
-- with actual type ‘t0’
-- because type variable ‘a1’ would escape its scope
-- This (rigid, skolem) type variable is bound by
-- a type expected by the context:
-- Bar a1 -> IO (StM Bar a1)
-- at src/MonadControlGHC8.hs:44:49-61
-- • In the first argument of ‘(.)’, namely ‘g’
-- In the first argument of ‘f’, namely ‘(g . unBar)’
-- In the expression: f (g . unBar)
-- • Relevant bindings include
-- g :: t0 (bound at MonadControlGHC8.hs:44:44)
--
instance MonadBaseControl IO Bar where
type StM Bar a = StM (ReaderT Env IO) a
liftBaseWith f = Bar . liftBaseWith $ \g -> f (g . unBar)
restoreM = Bar . restoreM
compiler: ghc-8.0.1
resolver: nightly-2016-06-07
flags: {}
extra-deps: []
packages:
- '.'
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment