unagi-chan-0.3.0.2: src/Control/Concurrent/Chan/Unagi/Unboxed.hs
module Control.Concurrent.Chan.Unagi.Unboxed (
-- * Creating channels
newChan
, InChan(), OutChan()
, UnagiPrim(..)
-- * Channel operations
-- ** Reading
, readChan
, readChanOnException
, tryReadChan
, Element(..)
, getChanContents
-- ** Writing
, writeChan
, writeList2Chan
-- ** Broadcasting
, dupChan
) where
-- Forked from src/Control/Concurrent/Chan/Unagi/Internal.hs at 443465
--
-- TODO additonal functions:
-- - write functions optimized for single-writer
-- - faster write/read-many that increments counter by N
-- - this could be used (or forked) to implement an efficient MPSC concurrent
-- ByteString or Text queue (where writes could be variable-sized chunks
-- and we incrCounter accordingly) without too much trouble. Useful?
-- - likewise a SPMC concurrent bytestring consumer?
-- - ...or interop with 'vector' lib
import Control.Concurrent.Chan.Unagi.Unboxed.Internal
import Control.Concurrent.Chan.Unagi.NoBlocking.Types
-- For 'writeList2Chan', as in vanilla Chan
import System.IO.Unsafe ( unsafeInterleaveIO )
-- | Create a new channel, returning its write and read ends.
newChan :: UnagiPrim a=> IO (InChan a, OutChan a)
newChan = newChanStarting (maxBound - 10)
-- lets us test counter overflow in tests and normal course of operation
-- | Return a lazy list representing the contents of the supplied OutChan, much
-- like System.IO.hGetContents.
getChanContents :: UnagiPrim a=> OutChan a -> IO [a]
getChanContents ch = unsafeInterleaveIO (do
x <- unsafeInterleaveIO $ readChan ch
xs <- getChanContents ch
return (x:xs)
)
-- | Write an entire list of items to a chan type. Writes here from multiple
-- threads may be interleaved, and infinite lists are supported.
writeList2Chan :: UnagiPrim a=> InChan a -> [a] -> IO ()
{-# INLINABLE writeList2Chan #-}
writeList2Chan ch = sequence_ . map (writeChan ch)