Why does theStdGen require unsafePerformIO? I recompiled the Random module with theStdGen :: IO (IORef StdGen) theStdGen = do rng <- mkStdRNG 0 newIORef rng The implementations of a few functions needed to change slightly (to extract the IORef from IO), but no other type signatures needed changing, and nothing blew up.