Skip to content

Conversation

@konsumlamm
Copy link
Contributor

@konsumlamm konsumlamm commented Jan 13, 2026

Add Control.Monad.ST.Lazy, Control.Monad.ST.Lazy.Unsafe, Control.Monad.ST.Strict, Data.STRef.Lazy, Data.STRef.Strict.

I used primPerformIO to achieve the laziness required for lazy ST.

Add `Control.Monad.ST.Lazy`, `Control.Monad.ST.Lazy.Unsafe`, `Data.STRef.Lazy`, `Data.STRef.Strict`
@konsumlamm konsumlamm marked this pull request as draft January 13, 2026 18:46
@konsumlamm
Copy link
Contributor Author

I marked this as a draft because I noticed that GHC has a test case for lazy ST, which currently fails: https://gitlab.haskell.org/ghc/ghc/-/blob/master/libraries/base/tests/lazySTexamples.hs.

@augustss
Copy link
Owner

I won't merge until you've tested more.

Add test from GHC's test suite
@konsumlamm konsumlamm marked this pull request as ready for review January 13, 2026 23:54
@konsumlamm
Copy link
Contributor Author

I rewrote the lazy ST implementation to use State s -> (a, State s), like in the GHC version. The test from GHC's test suite now passes.

@konsumlamm
Copy link
Contributor Author

konsumlamm commented Jan 14, 2026

It turns out now lazyToStrictST is incorrect, for example

import Control.Monad.ST as S
import Control.Monad.ST.Lazy (lazyToStrict)
import Data.STRef.Lazy as L

main :: IO ()
main = print $ S.runST $ do
  ref <- lazyToStrictST $ L.newSTRef 0
  let action = lazyToStrictST $ L.modifySTRef ref (+ 1)
  action
  action
  lazyToStrictST $ L.readSTRef ref

prints 1, even though it should print 2.

@konsumlamm konsumlamm marked this pull request as draft January 14, 2026 00:07
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants