-- | Unlifted "Data.IORef".
--
-- @since 0.1.0.0
module UnliftIO.IORef
  ( IORef
  , newIORef
  , readIORef
  , writeIORef
  , modifyIORef
  , modifyIORef'
  , atomicModifyIORef
  , atomicModifyIORef'
  , atomicWriteIORef
  , mkWeakIORef
  ) where

import Data.IORef (IORef)
import qualified Data.IORef as I
import Control.Monad.IO.Unlift
import System.Mem.Weak (Weak)

-- | Lifted 'I.newIORef'.
--
-- @since 0.1.0.0
newIORef :: MonadIO m => a -> m (IORef a)
newIORef :: forall (m :: * -> *) a. MonadIO m => a -> m (IORef a)
newIORef = IO (IORef a) -> m (IORef a)
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO (IORef a) -> m (IORef a))
-> (a -> IO (IORef a)) -> a -> m (IORef a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> IO (IORef a)
forall a. a -> IO (IORef a)
I.newIORef

-- | Lifted 'I.readIORef'.
--
-- @since 0.1.0.0
readIORef :: MonadIO m => IORef a -> m a
readIORef :: forall (m :: * -> *) a. MonadIO m => IORef a -> m a
readIORef = IO a -> m a
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO a -> m a) -> (IORef a -> IO a) -> IORef a -> m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. IORef a -> IO a
forall a. IORef a -> IO a
I.readIORef

-- | Lifted 'I.writeIORef'.
--
-- @since 0.1.0.0
writeIORef :: MonadIO m => IORef a -> a -> m ()
writeIORef :: forall (m :: * -> *) a. MonadIO m => IORef a -> a -> m ()
writeIORef IORef a
ref = IO () -> m ()
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> m ()) -> (a -> IO ()) -> a -> m ()
forall b c a. (b -> c) -> (a -> b) -> a -> c
. IORef a -> a -> IO ()
forall a. IORef a -> a -> IO ()
I.writeIORef IORef a
ref

-- | Lifted 'I.modifyIORef'.
--
-- @since 0.1.0.0
modifyIORef :: MonadIO m => IORef a -> (a -> a) -> m ()
modifyIORef :: forall (m :: * -> *) a. MonadIO m => IORef a -> (a -> a) -> m ()
modifyIORef IORef a
ref = IO () -> m ()
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> m ()) -> ((a -> a) -> IO ()) -> (a -> a) -> m ()
forall b c a. (b -> c) -> (a -> b) -> a -> c
. IORef a -> (a -> a) -> IO ()
forall a. IORef a -> (a -> a) -> IO ()
I.modifyIORef IORef a
ref

-- | Lifted 'I.modifyIORef''.
--
-- @since 0.1.0.0
modifyIORef' :: MonadIO m => IORef a -> (a -> a) -> m ()
modifyIORef' :: forall (m :: * -> *) a. MonadIO m => IORef a -> (a -> a) -> m ()
modifyIORef' IORef a
ref = IO () -> m ()
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> m ()) -> ((a -> a) -> IO ()) -> (a -> a) -> m ()
forall b c a. (b -> c) -> (a -> b) -> a -> c
. IORef a -> (a -> a) -> IO ()
forall a. IORef a -> (a -> a) -> IO ()
I.modifyIORef' IORef a
ref

-- | Lifted 'I.atomicModifyIORef'.
--
-- @since 0.1.0.0
atomicModifyIORef :: MonadIO m => IORef a -> (a -> (a, b)) -> m b
atomicModifyIORef :: forall (m :: * -> *) a b.
MonadIO m =>
IORef a -> (a -> (a, b)) -> m b
atomicModifyIORef IORef a
ref = IO b -> m b
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO b -> m b) -> ((a -> (a, b)) -> IO b) -> (a -> (a, b)) -> m b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. IORef a -> (a -> (a, b)) -> IO b
forall a b. IORef a -> (a -> (a, b)) -> IO b
I.atomicModifyIORef IORef a
ref

-- | Lifted 'I.atomicModifyIORef''.
--
-- @since 0.1.0.0
atomicModifyIORef' :: MonadIO m => IORef a -> (a -> (a, b)) -> m b
atomicModifyIORef' :: forall (m :: * -> *) a b.
MonadIO m =>
IORef a -> (a -> (a, b)) -> m b
atomicModifyIORef' IORef a
ref = IO b -> m b
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO b -> m b) -> ((a -> (a, b)) -> IO b) -> (a -> (a, b)) -> m b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. IORef a -> (a -> (a, b)) -> IO b
forall a b. IORef a -> (a -> (a, b)) -> IO b
I.atomicModifyIORef' IORef a
ref

-- | Lifted 'I.atomicWriteIORef'.
--
-- @since 0.1.0.0
atomicWriteIORef :: MonadIO m => IORef a -> a -> m ()
atomicWriteIORef :: forall (m :: * -> *) a. MonadIO m => IORef a -> a -> m ()
atomicWriteIORef IORef a
ref = IO () -> m ()
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> m ()) -> (a -> IO ()) -> a -> m ()
forall b c a. (b -> c) -> (a -> b) -> a -> c
. IORef a -> a -> IO ()
forall a. IORef a -> a -> IO ()
I.atomicWriteIORef IORef a
ref

-- | Unlifted 'I.mkWeakIORef'.
--
-- @since 0.1.0.0
mkWeakIORef :: MonadUnliftIO m => IORef a -> m () -> m (Weak (IORef a))
mkWeakIORef :: forall (m :: * -> *) a.
MonadUnliftIO m =>
IORef a -> m () -> m (Weak (IORef a))
mkWeakIORef IORef a
ref m ()
final = ((forall a. m a -> IO a) -> IO (Weak (IORef a)))
-> m (Weak (IORef a))
forall b. ((forall a. m a -> IO a) -> IO b) -> m b
forall (m :: * -> *) b.
MonadUnliftIO m =>
((forall a. m a -> IO a) -> IO b) -> m b
withRunInIO (((forall a. m a -> IO a) -> IO (Weak (IORef a)))
 -> m (Weak (IORef a)))
-> ((forall a. m a -> IO a) -> IO (Weak (IORef a)))
-> m (Weak (IORef a))
forall a b. (a -> b) -> a -> b
$ \forall a. m a -> IO a
run -> IORef a -> IO () -> IO (Weak (IORef a))
forall a. IORef a -> IO () -> IO (Weak (IORef a))
I.mkWeakIORef IORef a
ref (m () -> IO ()
forall a. m a -> IO a
run m ()
final)