Is this generalization of runST safe?
haskell, state-monad
Solution
I don't think so:
crash = runSTCont crasher where
crasher :: forall s. (forall b . ST s b -> b) -> Integer
crasher go =
let r :: forall a. STRef s (a -> a)
r = go $ newSTRef id
in go $ do writeSTRef r (tail . tail)
f <- readSTRef r
return $ f (17 :: Integer)
The problem is that Haskell lacks the value restriction.
Problem
`Control.Monad.ST` in the `base` package contains `runST` to run the strict state-transformer monad: ``` runST :: (forall s. ST s a) -> a ``` However, I need a generalized version of `runST`: ``` runSTCont :: (forall s . (forall b . ST s b -> b) -> a) -> a runSTCont f = f $ \m -> runST $ unsafeCoerce m ``` My question is: Is this use of `unsafeCoerse` safe? (I guess so, because as I understand, the only purpose of the index `s` is to prevent to leak `s`-indexed values in the result `a`. The type of `runSTCont` cannot leak `s`-indexed values so it should be OK.) Note that `runST` can be expressed in terms of `runSTCont` so `runSTCont` is at least as general as `runST`: ``` runST' :: (forall s. ST s a) -> a runST' m = runSTCont $ \runST -> runST m ```