-- Hoogle documentation, generated by Haddock
-- See Hoogle, http://www.haskell.org/hoogle/

-- | Run IO operations asynchronously and wait for their results
--   
--   This package provides a higher-level interface over threads, in which
--   an Async a is a concurrent thread that will eventually
--   deliver a value of type a. The package provides ways to
--   create Async computations, wait for their results, and cancel
--   them.
--   
--   Using Async is safer than using threads in two ways:
--   
--   
--   
- When waiting for a thread to return a result, if the thread dies
--   with an exception then the caller must either re-throw the exception
--   (wait) or handle it (waitCatch); the exception cannot be
--   ignored.
--   
- The API makes it possible to build a tree of threads that are
--   automatically killed when their parent dies (see
--   withAsync).
--   
@package async
@version 2.2.5

-- | This module is an internal module. The public API is provided in
--   Control.Concurrent.Async. Breaking changes to this module will
--   not be reflected in a major bump, and using this module may break your
--   code unless you are extremely careful.
module Control.Concurrent.Async.Internal

-- | An asynchronous action spawned by async or withAsync.
--   Asynchronous actions are executed in a separate thread, and operations
--   are provided for waiting for asynchronous actions to complete and
--   obtaining their results (see e.g. wait).
data Async a
Async :: {-# UNPACK #-} !ThreadId -> STM (Either SomeException a) -> Async a

-- | Returns the ThreadId of the thread running the given
--   Async.
[asyncThreadId] :: Async a -> {-# UNPACK #-} !ThreadId
[_asyncWait] :: Async a -> STM (Either SomeException a)

-- | Compare two Asyncs that may have different types by their
--   ThreadId.
compareAsyncs :: Async a -> Async b -> Ordering

-- | Spawn an asynchronous action in a separate thread.
--   
--   Like for forkIO, the action may be left running unintentionally
--   (see module-level documentation for details).
--   
--   Use withAsync style functions wherever you can instead!
async :: IO a -> IO (Async a)

-- | Like async but using forkOS internally.
asyncBound :: IO a -> IO (Async a)

-- | Like async but using forkOn internally.
asyncOn :: Int -> IO a -> IO (Async a)

-- | Like async but using forkIOWithUnmask internally. The
--   child thread is passed a function that can be used to unmask
--   asynchronous exceptions.
asyncWithUnmask :: ((forall b. () => IO b -> IO b) -> IO a) -> IO (Async a)

-- | Like asyncOn but using forkOnWithUnmask internally. The
--   child thread is passed a function that can be used to unmask
--   asynchronous exceptions.
asyncOnWithUnmask :: Int -> ((forall b. () => IO b -> IO b) -> IO a) -> IO (Async a)
asyncUsing :: (IO () -> IO ThreadId) -> IO a -> IO (Async a)

-- | Spawn an asynchronous action in a separate thread, and pass its
--   Async handle to the supplied function. When the function
--   returns or throws an exception, uninterruptibleCancel is called
--   on the Async.
--   
--   
--   withAsync action inner = mask $ \restore -> do
--     a <- async (restore action)
--     restore (inner a) `finally` uninterruptibleCancel a
--   
--   
--   This is a useful variant of async that ensures an
--   Async is never left running unintentionally.
--   
--   Note: a reference to the child thread is kept alive until the call to
--   withAsync returns, so nesting many withAsync calls
--   requires linear memory.
withAsync :: IO a -> (Async a -> IO b) -> IO b

-- | Like withAsync but uses forkOS internally.
withAsyncBound :: IO a -> (Async a -> IO b) -> IO b

-- | Like withAsync but uses forkOn internally.
withAsyncOn :: Int -> IO a -> (Async a -> IO b) -> IO b

-- | Like withAsync but uses forkIOWithUnmask internally. The
--   child thread is passed a function that can be used to unmask
--   asynchronous exceptions.
withAsyncWithUnmask :: ((forall c. () => IO c -> IO c) -> IO a) -> (Async a -> IO b) -> IO b

-- | Like withAsyncOn but uses forkOnWithUnmask internally.
--   The child thread is passed a function that can be used to unmask
--   asynchronous exceptions
withAsyncOnWithUnmask :: Int -> ((forall c. () => IO c -> IO c) -> IO a) -> (Async a -> IO b) -> IO b
withAsyncUsing :: (IO () -> IO ThreadId) -> IO a -> (Async a -> IO b) -> IO b

-- | Wait for an asynchronous action to complete, and return its value. If
--   the asynchronous action threw an exception, then the exception is
--   re-thrown by wait.
--   
--   
--   wait = atomically . waitSTM
--   
wait :: Async a -> IO a

-- | Wait for an asynchronous action to complete, and return either
--   Left e if the action raised an exception e, or
--   Right a if it returned a value a.
--   
--   
--   waitCatch = atomically . waitCatchSTM
--   
waitCatch :: Async a -> IO (Either SomeException a)

-- | Check whether an Async has completed yet. If it has not
--   completed yet, then the result is Nothing, otherwise the
--   result is Just e where e is Left x if the
--   Async raised an exception x, or Right a if
--   it returned a value a.
--   
--   
--   poll = atomically . pollSTM
--   
poll :: Async a -> IO (Maybe (Either SomeException a))

-- | A version of wait that can be used inside an STM transaction.
waitSTM :: Async a -> STM a

-- | A version of waitCatch that can be used inside an STM
--   transaction.
waitCatchSTM :: Async a -> STM (Either SomeException a)

-- | A version of poll that can be used inside an STM transaction.
pollSTM :: Async a -> STM (Maybe (Either SomeException a))

-- | Cancel an asynchronous action by throwing the AsyncCancelled
--   exception to it, and waiting for the Async thread to quit. Has
--   no effect if the Async has already completed.
--   
--   
--   cancel a = throwTo (asyncThreadId a) AsyncCancelled <* waitCatch a
--   
--   
--   Note that cancel will not terminate until the thread the
--   Async refers to has terminated. This means that cancel
--   will block for as long said thread blocks when receiving an
--   asynchronous exception.
--   
--   For example, it could block if:
--   
--   
--   
- It's executing a foreign call, and thus cannot receive the
--   asynchronous exception;
--   
- It's executing some cleanup handler after having received the
--   exception, and the handler is blocking.
--   
cancel :: Async a -> IO ()

-- | Cancel multiple asynchronous actions by throwing the
--   AsyncCancelled exception to each of them in turn, then
--   waiting for all the Async threads to complete.
cancelMany :: [Async a] -> IO ()

-- | The exception thrown by cancel to terminate a thread.
data AsyncCancelled
AsyncCancelled :: AsyncCancelled

-- | Cancel an asynchronous action
--   
--   This is a variant of cancel, but it is not interruptible.
uninterruptibleCancel :: Async a -> IO ()

-- | Cancel an asynchronous action by throwing the supplied exception to
--   it.
--   
--   
--   cancelWith a x = throwTo (asyncThreadId a) x
--   
--   
--   The notes about the synchronous nature of cancel also apply to
--   cancelWith.
cancelWith :: Exception e => Async a -> e -> IO ()

-- | Wait for any of the supplied asynchronous operations to complete. The
--   value returned is a pair of the Async that completed, and the
--   result that would be returned by wait on that Async. The
--   input list must be non-empty.
--   
--   If multiple Asyncs complete or have completed, then the value
--   returned corresponds to the first completed Async in the list.
waitAnyCatch :: [Async a] -> IO (Async a, Either SomeException a)

-- | A version of waitAnyCatch that can be used inside an STM
--   transaction.
waitAnyCatchSTM :: [Async a] -> STM (Async a, Either SomeException a)

-- | Like waitAnyCatch, but also cancels the other asynchronous
--   operations as soon as one has completed.
waitAnyCatchCancel :: [Async a] -> IO (Async a, Either SomeException a)

-- | Wait for any of the supplied Asyncs to complete. If the first
--   to complete throws an exception, then that exception is re-thrown by
--   waitAny. The input list must be non-empty.
--   
--   If multiple Asyncs complete or have completed, then the value
--   returned corresponds to the first completed Async in the list.
waitAny :: [Async a] -> IO (Async a, a)

-- | A version of waitAny that can be used inside an STM
--   transaction.
waitAnySTM :: [Async a] -> STM (Async a, a)

-- | Like waitAny, but also cancels the other asynchronous
--   operations as soon as one has completed.
waitAnyCancel :: [Async a] -> IO (Async a, a)

-- | Wait for the first of two Asyncs to finish.
waitEitherCatch :: Async a -> Async b -> IO (Either (Either SomeException a) (Either SomeException b))

-- | A version of waitEitherCatch that can be used inside an STM
--   transaction.
waitEitherCatchSTM :: Async a -> Async b -> STM (Either (Either SomeException a) (Either SomeException b))

-- | Like waitEitherCatch, but also cancels both
--   Asyncs before returning.
waitEitherCatchCancel :: Async a -> Async b -> IO (Either (Either SomeException a) (Either SomeException b))

-- | Wait for the first of two Asyncs to finish. If the
--   Async that finished first raised an exception, then the
--   exception is re-thrown by waitEither.
waitEither :: Async a -> Async b -> IO (Either a b)

-- | A version of waitEither that can be used inside an STM
--   transaction.
waitEitherSTM :: Async a -> Async b -> STM (Either a b)

-- | Like waitEither, but the result is ignored.
waitEither_ :: Async a -> Async b -> IO ()

-- | A version of waitEither_ that can be used inside an STM
--   transaction.
waitEitherSTM_ :: Async a -> Async b -> STM ()

-- | Like waitEither, but also cancels both Asyncs
--   before returning.
waitEitherCancel :: Async a -> Async b -> IO (Either a b)

-- | Waits for both Asyncs to finish, but if either of them throws
--   an exception before they have both finished, then the exception is
--   re-thrown by waitBoth.
waitBoth :: Async a -> Async b -> IO (a, b)

-- | A version of waitBoth that can be used inside an STM
--   transaction.
waitBothSTM :: Async a -> Async b -> STM (a, b)
data ExceptionInLinkedThread
ExceptionInLinkedThread :: Async a -> SomeException -> ExceptionInLinkedThread

-- | Link the given Async to the current thread, such that if the
--   Async raises an exception, that exception will be re-thrown
--   in the current thread, wrapped in ExceptionInLinkedThread.
--   
--   link ignores AsyncCancelled exceptions thrown in the
--   other thread, so that it's safe to cancel a thread you're
--   linked to. If you want different behaviour, use linkOnly.
link :: Async a -> IO ()

-- | Link the given Async to the current thread, such that if the
--   Async raises an exception, that exception will be re-thrown
--   in the current thread, wrapped in ExceptionInLinkedThread.
--   
--   The supplied predicate determines which exceptions in the target
--   thread should be propagated to the source thread.
linkOnly :: (SomeException -> Bool) -> Async a -> IO ()

-- | Link two Asyncs together, such that if either raises an
--   exception, the same exception is re-thrown in the other
--   Async, wrapped in ExceptionInLinkedThread.
--   
--   link2 ignores AsyncCancelled exceptions, so that it's
--   possible to cancel either thread without cancelling the other.
--   If you want different behaviour, use link2Only.
link2 :: Async a -> Async b -> IO ()

-- | Link two Asyncs together, such that if either raises an
--   exception, the same exception is re-thrown in the other
--   Async, wrapped in ExceptionInLinkedThread.
--   
--   The supplied predicate determines which exceptions in the target
--   thread should be propagated to the source thread.
link2Only :: (SomeException -> Bool) -> Async a -> Async b -> IO ()
isCancel :: SomeException -> Bool

-- | Run two IO actions concurrently, and return the first to
--   finish. The loser of the race is cancelled.
--   
--   
--   race left right =
--     withAsync left $ \a ->
--     withAsync right $ \b ->
--     waitEither a b
--   
race :: IO a -> IO b -> IO (Either a b)

-- | Like race, but the result is ignored.
race_ :: IO a -> IO b -> IO ()

-- | Run two IO actions concurrently, and return both results. If
--   either action throws an exception at any time, then the other action
--   is cancelled, and the exception is re-thrown by
--   concurrently.
--   
--   
--   concurrently left right =
--     withAsync left $ \a ->
--     withAsync right $ \b ->
--     waitBoth a b
--   
concurrently :: IO a -> IO b -> IO (a, b)

-- | Run two IO actions concurrently. If both of them end with
--   Right, return both results. If one of then ends with
--   Left, interrupt the other action and return the
--   Left.
concurrentlyE :: IO (Either e a) -> IO (Either e b) -> IO (Either e (a, b))
concurrently' :: IO a -> IO b -> (IO (Either SomeException (Either a b)) -> IO r) -> IO r

-- | concurrently, but ignore the result values
concurrently_ :: IO a -> IO b -> IO ()

-- | Maps an IO-performing function over any Traversable data
--   type, performing all the IO actions concurrently, and
--   returning the original data structure with the arguments replaced by
--   the results.
--   
--   If any of the actions throw an exception, then all other actions are
--   cancelled and the exception is re-thrown.
--   
--   For example, mapConcurrently works with lists:
--   
--   
--   pages <- mapConcurrently getURL ["url1", "url2", "url3"]
--   
--   
--   Take into account that async will try to immediately spawn a
--   thread for each element of the Traversable, so running this
--   on large inputs without care may lead to resource exhaustion (of
--   memory, file descriptors, or other limited resources).
mapConcurrently :: Traversable t => (a -> IO b) -> t a -> IO (t b)

-- | forConcurrently is mapConcurrently with its arguments
--   flipped
--   
--   
--   pages <- forConcurrently ["url1", "url2", "url3"] $ \url -> getURL url
--   
forConcurrently :: Traversable t => t a -> (a -> IO b) -> IO (t b)

-- | mapConcurrently_ is mapConcurrently with the return
--   value discarded; a concurrent equivalent of mapM_.
mapConcurrently_ :: Foldable f => (a -> IO b) -> f a -> IO ()

-- | forConcurrently_ is forConcurrently with the return
--   value discarded; a concurrent equivalent of forM_.
forConcurrently_ :: Foldable f => f a -> (a -> IO b) -> IO ()

-- | Perform the action in the given number of threads.
replicateConcurrently :: Int -> IO a -> IO [a]

-- | Same as replicateConcurrently, but ignore the results.
replicateConcurrently_ :: Int -> IO a -> IO ()

-- | A value of type Concurrently a is an IO operation
--   that can be composed with other Concurrently values, using
--   the Applicative and Alternative instances.
--   
--   Calling runConcurrently on a value of type Concurrently
--   a will execute the IO operations it contains
--   concurrently, before delivering the result of type a.
--   
--   For example
--   
--   
--   (page1, page2, page3)
--       <- runConcurrently $ (,,)
--       <$> Concurrently (getURL "url1")
--       <*> Concurrently (getURL "url2")
--       <*> Concurrently (getURL "url3")
--   
newtype Concurrently a
Concurrently :: IO a -> Concurrently a
[runConcurrently] :: Concurrently a -> IO a

-- | A value of type ConcurrentlyE e a is an IO operation
--   that can be composed with other ConcurrentlyE values, using
--   the Applicative instance.
--   
--   Calling runConcurrentlyE on a value of type ConcurrentlyE
--   e a will execute the IO operations it contains
--   concurrently, before delivering either the result of type a,
--   or an error of type e if one of the actions returns
--   Left.
--   
--   | @since 2.2.5
newtype ConcurrentlyE e a
ConcurrentlyE :: IO (Either e a) -> ConcurrentlyE e a
[runConcurrentlyE] :: ConcurrentlyE e a -> IO (Either e a)

-- | Fork a thread that runs the supplied action, and if it raises an
--   exception, re-runs the action. The thread terminates only when the
--   action runs to completion without raising an exception.
forkRepeat :: IO a -> IO ThreadId
catchAll :: IO a -> (SomeException -> IO a) -> IO a
tryAll :: IO a -> IO (Either SomeException a)
rawForkIO :: IO () -> IO ThreadId
rawForkOn :: Int -> IO () -> IO ThreadId
instance GHC.Internal.Base.Alternative Control.Concurrent.Async.Internal.Concurrently
instance GHC.Internal.Base.Applicative Control.Concurrent.Async.Internal.Concurrently
instance GHC.Internal.Base.Applicative (Control.Concurrent.Async.Internal.ConcurrentlyE e)
instance Data.Bifunctor.Bifunctor Control.Concurrent.Async.Internal.ConcurrentlyE
instance GHC.Classes.Eq (Control.Concurrent.Async.Internal.Async a)
instance GHC.Classes.Eq Control.Concurrent.Async.Internal.AsyncCancelled
instance GHC.Internal.Exception.Type.Exception Control.Concurrent.Async.Internal.AsyncCancelled
instance GHC.Internal.Exception.Type.Exception Control.Concurrent.Async.Internal.ExceptionInLinkedThread
instance GHC.Internal.Base.Functor Control.Concurrent.Async.Internal.Async
instance GHC.Internal.Base.Functor Control.Concurrent.Async.Internal.Concurrently
instance GHC.Internal.Base.Functor (Control.Concurrent.Async.Internal.ConcurrentlyE e)
instance Data.Hashable.Class.Hashable (Control.Concurrent.Async.Internal.Async a)
instance (GHC.Internal.Base.Semigroup a, GHC.Internal.Base.Monoid a) => GHC.Internal.Base.Monoid (Control.Concurrent.Async.Internal.Concurrently a)
instance (GHC.Internal.Base.Semigroup a, GHC.Internal.Base.Monoid a) => GHC.Internal.Base.Monoid (Control.Concurrent.Async.Internal.ConcurrentlyE e a)
instance GHC.Classes.Ord (Control.Concurrent.Async.Internal.Async a)
instance GHC.Internal.Base.Semigroup a => GHC.Internal.Base.Semigroup (Control.Concurrent.Async.Internal.Concurrently a)
instance GHC.Internal.Base.Semigroup a => GHC.Internal.Base.Semigroup (Control.Concurrent.Async.Internal.ConcurrentlyE e a)
instance GHC.Internal.Show.Show Control.Concurrent.Async.Internal.AsyncCancelled
instance GHC.Internal.Show.Show Control.Concurrent.Async.Internal.ExceptionInLinkedThread

-- | This module provides a set of operations for running IO operations
--   asynchronously and waiting for their results. It is a thin layer over
--   the basic concurrency operations provided by
--   Control.Concurrent. The main additional functionality it
--   provides is the ability to wait for the return value of a thread, but
--   the interface also provides some additional safety and robustness over
--   using forkIO threads and MVar directly.
--   
--   
High-level API
--   
--   async's high-level API spawns lexically scoped
--   threads, ensuring the following key poperties that make it safer to
--   use than using plain forkIO:
--   
--   
--   
- No exception is swallowed (waiting for results propagates
--   exceptions).
--   
- No thread is leaked (left running unintentionally).
--   
--   
--   (This is done using the bracket pattern to work in presence of
--   synchronous and asynchronous exceptions.)
--   
--   Most practical/production code should only use the high-level
--   API.
--   
--   The basic type is Async a, which represents an
--   asynchronous IO action that will return a value of type
--   a, or die with an exception. An Async is a wrapper
--   around a low-level forkIO thread.
--   
--   The fundamental function to spawn threads with the high-level API is
--   withAsync.
--   
--   For example, to fetch two web pages at the same time, we could do this
--   (assuming a suitable getURL function):
--   
--   
--   withAsync (getURL url1) $ \a1 -> do
--     withAsync (getURL url2) $ \a2 -> do
--       page1 <- wait a1
--       page2 <- wait a2
--       ...
--   
--   
--   where withAsync starts the operation in a separate thread, and
--   wait waits for and returns the result.
--   
--   
--   
- If the operation throws an exception, then that exception is
--   re-thrown by wait. This ensures property (1): No exception is
--   swallowed.
--   
- If an exception bubbles up through a withAsync, then the
--   Async it spawned is canceled. This ensures property (2):
--   No thread is leaked.
--   
--   
--   Often we do not care to work manually with Async handles like
--   a1 and a2. Instead, we want to express high-level
--   objectives like performing two or more tasks concurrently, and waiting
--   for one or all of them to finish.
--   
--   For example, the pattern of performing two IO actions concurrently and
--   waiting for both their results is packaged up in a combinator
--   concurrently, so we can further shorten the above example to:
--   
--   
--   (page1, page2) <- concurrently (getURL url1) (getURL url2)
--   ...
--   
--   
--   The section High-level utilities covers the most common
--   high-level objectives, including:
--   
--   
--   
- Waiting for 2 results (concurrently).
--   
- Waiting for many results (mapConcurrently /
--   forConcurrently).
--   
- Waiting for the first of 2 results (race).
--   
- Waiting for arbitrary nestings of "all of N" and "the first
--   of N" results with the Concurrently newtype and its
--   Applicative and Alternative instances.
--   
--   
--   Click here to scroll to that section:
--   Control.Concurrent.Async#high-level-utilities.
--   
--   
Low-level API
--   
--   Some use cases require parallelism that is not lexically scoped.
--   
--   For those, the low-level function async can be used as a direct
--   equivalent of forkIO:
--   
--   
--   -- Do NOT use this code in production, it has a flaw (explained below).
--   do
--     a1 <- async (getURL url1)
--     a2 <- async (getURL url2)
--     page1 <- wait a1
--     page2 <- wait a2
--     ...
--   
--   
--   In contrast to withAsync, this code has a problem.
--   
--   It still fulfills property (1) in that an exception arising from
--   getUrl will be re-thrown by wait, but it does not
--   fulfill property (2). Consider the case when the first wait
--   throws an exception; then the second wait will not happen, and
--   the second async may be left running in the background,
--   possibly indefinitely.
--   
--   withAsync is like async, except that the Async is
--   automatically killed (using uninterruptibleCancel) if the
--   enclosing IO operation returns before it has completed. Furthermore,
--   withAsync allows a tree of threads to be built, such that
--   children are automatically killed if their parents die for any reason.
--   
--   If you need to use the low-level API, ensure that you guarantee
--   property (2) by other means, such as linking asyncs that need
--   to die together, and protecting against asynchronous exceptions using
--   bracket, mask, or other functions from
--   Control.Exception.
--   
--   
Miscellaneous
--   
--   The Functor instance can be used to change the result of an
--   Async. For example:
--   
--   
--   ghci> withAsync (return 3) (\a -> wait (fmap (+1) a))
--   4
--   
--   
--   
Resource exhaustion
--   
--   As with all concurrent programming, keep in mind that while Haskell's
--   cooperative ("green") multithreading carries low overhead, spawning
--   too many of them at the same time may lead to resource exhaustion (of
--   memory, file descriptors, or other limited resources), given that the
--   actions running in the threads consume these resources.
module Control.Concurrent.Async

-- | An asynchronous action spawned by async or withAsync.
--   Asynchronous actions are executed in a separate thread, and operations
--   are provided for waiting for asynchronous actions to complete and
--   obtaining their results (see e.g. wait).
data Async a

-- | Spawn an asynchronous action in a separate thread, and pass its
--   Async handle to the supplied function. When the function
--   returns or throws an exception, uninterruptibleCancel is called
--   on the Async.
--   
--   
--   withAsync action inner = mask $ \restore -> do
--     a <- async (restore action)
--     restore (inner a) `finally` uninterruptibleCancel a
--   
--   
--   This is a useful variant of async that ensures an
--   Async is never left running unintentionally.
--   
--   Note: a reference to the child thread is kept alive until the call to
--   withAsync returns, so nesting many withAsync calls
--   requires linear memory.
withAsync :: IO a -> (Async a -> IO b) -> IO b

-- | Like withAsync but uses forkOS internally.
withAsyncBound :: IO a -> (Async a -> IO b) -> IO b

-- | Like withAsync but uses forkOn internally.
withAsyncOn :: Int -> IO a -> (Async a -> IO b) -> IO b

-- | Like withAsync but uses forkIOWithUnmask internally. The
--   child thread is passed a function that can be used to unmask
--   asynchronous exceptions.
withAsyncWithUnmask :: ((forall c. () => IO c -> IO c) -> IO a) -> (Async a -> IO b) -> IO b

-- | Like withAsyncOn but uses forkOnWithUnmask internally.
--   The child thread is passed a function that can be used to unmask
--   asynchronous exceptions
withAsyncOnWithUnmask :: Int -> ((forall c. () => IO c -> IO c) -> IO a) -> (Async a -> IO b) -> IO b

-- | Wait for an asynchronous action to complete, and return its value. If
--   the asynchronous action threw an exception, then the exception is
--   re-thrown by wait.
--   
--   
--   wait = atomically . waitSTM
--   
wait :: Async a -> IO a

-- | Check whether an Async has completed yet. If it has not
--   completed yet, then the result is Nothing, otherwise the
--   result is Just e where e is Left x if the
--   Async raised an exception x, or Right a if
--   it returned a value a.
--   
--   
--   poll = atomically . pollSTM
--   
poll :: Async a -> IO (Maybe (Either SomeException a))

-- | Wait for an asynchronous action to complete, and return either
--   Left e if the action raised an exception e, or
--   Right a if it returned a value a.
--   
--   
--   waitCatch = atomically . waitCatchSTM
--   
waitCatch :: Async a -> IO (Either SomeException a)

-- | Returns the ThreadId of the thread running the given
--   Async.
asyncThreadId :: Async a -> ThreadId

-- | Cancel an asynchronous action by throwing the AsyncCancelled
--   exception to it, and waiting for the Async thread to quit. Has
--   no effect if the Async has already completed.
--   
--   
--   cancel a = throwTo (asyncThreadId a) AsyncCancelled <* waitCatch a
--   
--   
--   Note that cancel will not terminate until the thread the
--   Async refers to has terminated. This means that cancel
--   will block for as long said thread blocks when receiving an
--   asynchronous exception.
--   
--   For example, it could block if:
--   
--   
--   
- It's executing a foreign call, and thus cannot receive the
--   asynchronous exception;
--   
- It's executing some cleanup handler after having received the
--   exception, and the handler is blocking.
--   
cancel :: Async a -> IO ()

-- | Cancel multiple asynchronous actions by throwing the
--   AsyncCancelled exception to each of them in turn, then
--   waiting for all the Async threads to complete.
cancelMany :: [Async a] -> IO ()

-- | Cancel an asynchronous action
--   
--   This is a variant of cancel, but it is not interruptible.
uninterruptibleCancel :: Async a -> IO ()

-- | Cancel an asynchronous action by throwing the supplied exception to
--   it.
--   
--   
--   cancelWith a x = throwTo (asyncThreadId a) x
--   
--   
--   The notes about the synchronous nature of cancel also apply to
--   cancelWith.
cancelWith :: Exception e => Async a -> e -> IO ()

-- | The exception thrown by cancel to terminate a thread.
data AsyncCancelled
AsyncCancelled :: AsyncCancelled

-- | Run two IO actions concurrently, and return the first to
--   finish. The loser of the race is cancelled.
--   
--   
--   race left right =
--     withAsync left $ \a ->
--     withAsync right $ \b ->
--     waitEither a b
--   
race :: IO a -> IO b -> IO (Either a b)

-- | Like race, but the result is ignored.
race_ :: IO a -> IO b -> IO ()

-- | Run two IO actions concurrently, and return both results. If
--   either action throws an exception at any time, then the other action
--   is cancelled, and the exception is re-thrown by
--   concurrently.
--   
--   
--   concurrently left right =
--     withAsync left $ \a ->
--     withAsync right $ \b ->
--     waitBoth a b
--   
concurrently :: IO a -> IO b -> IO (a, b)

-- | concurrently, but ignore the result values
concurrently_ :: IO a -> IO b -> IO ()

-- | Maps an IO-performing function over any Traversable data
--   type, performing all the IO actions concurrently, and
--   returning the original data structure with the arguments replaced by
--   the results.
--   
--   If any of the actions throw an exception, then all other actions are
--   cancelled and the exception is re-thrown.
--   
--   For example, mapConcurrently works with lists:
--   
--   
--   pages <- mapConcurrently getURL ["url1", "url2", "url3"]
--   
--   
--   Take into account that async will try to immediately spawn a
--   thread for each element of the Traversable, so running this
--   on large inputs without care may lead to resource exhaustion (of
--   memory, file descriptors, or other limited resources).
mapConcurrently :: Traversable t => (a -> IO b) -> t a -> IO (t b)

-- | forConcurrently is mapConcurrently with its arguments
--   flipped
--   
--   
--   pages <- forConcurrently ["url1", "url2", "url3"] $ \url -> getURL url
--   
forConcurrently :: Traversable t => t a -> (a -> IO b) -> IO (t b)

-- | mapConcurrently_ is mapConcurrently with the return
--   value discarded; a concurrent equivalent of mapM_.
mapConcurrently_ :: Foldable f => (a -> IO b) -> f a -> IO ()

-- | forConcurrently_ is forConcurrently with the return
--   value discarded; a concurrent equivalent of forM_.
forConcurrently_ :: Foldable f => f a -> (a -> IO b) -> IO ()

-- | Perform the action in the given number of threads.
replicateConcurrently :: Int -> IO a -> IO [a]

-- | Same as replicateConcurrently, but ignore the results.
replicateConcurrently_ :: Int -> IO a -> IO ()

-- | A value of type Concurrently a is an IO operation
--   that can be composed with other Concurrently values, using
--   the Applicative and Alternative instances.
--   
--   Calling runConcurrently on a value of type Concurrently
--   a will execute the IO operations it contains
--   concurrently, before delivering the result of type a.
--   
--   For example
--   
--   
--   (page1, page2, page3)
--       <- runConcurrently $ (,,)
--       <$> Concurrently (getURL "url1")
--       <*> Concurrently (getURL "url2")
--       <*> Concurrently (getURL "url3")
--   
newtype Concurrently a
Concurrently :: IO a -> Concurrently a
[runConcurrently] :: Concurrently a -> IO a

-- | Run two IO actions concurrently. If both of them end with
--   Right, return both results. If one of then ends with
--   Left, interrupt the other action and return the
--   Left.
concurrentlyE :: IO (Either e a) -> IO (Either e b) -> IO (Either e (a, b))

-- | A value of type ConcurrentlyE e a is an IO operation
--   that can be composed with other ConcurrentlyE values, using
--   the Applicative instance.
--   
--   Calling runConcurrentlyE on a value of type ConcurrentlyE
--   e a will execute the IO operations it contains
--   concurrently, before delivering either the result of type a,
--   or an error of type e if one of the actions returns
--   Left.
--   
--   | @since 2.2.5
newtype ConcurrentlyE e a
ConcurrentlyE :: IO (Either e a) -> ConcurrentlyE e a
[runConcurrentlyE] :: ConcurrentlyE e a -> IO (Either e a)

-- | Compare two Asyncs that may have different types by their
--   ThreadId.
compareAsyncs :: Async a -> Async b -> Ordering

-- | A version of wait that can be used inside an STM transaction.
waitSTM :: Async a -> STM a

-- | A version of poll that can be used inside an STM transaction.
pollSTM :: Async a -> STM (Maybe (Either SomeException a))

-- | A version of waitCatch that can be used inside an STM
--   transaction.
waitCatchSTM :: Async a -> STM (Either SomeException a)

-- | Wait for any of the supplied Asyncs to complete. If the first
--   to complete throws an exception, then that exception is re-thrown by
--   waitAny. The input list must be non-empty.
--   
--   If multiple Asyncs complete or have completed, then the value
--   returned corresponds to the first completed Async in the list.
waitAny :: [Async a] -> IO (Async a, a)

-- | Wait for any of the supplied asynchronous operations to complete. The
--   value returned is a pair of the Async that completed, and the
--   result that would be returned by wait on that Async. The
--   input list must be non-empty.
--   
--   If multiple Asyncs complete or have completed, then the value
--   returned corresponds to the first completed Async in the list.
waitAnyCatch :: [Async a] -> IO (Async a, Either SomeException a)

-- | Like waitAny, but also cancels the other asynchronous
--   operations as soon as one has completed.
waitAnyCancel :: [Async a] -> IO (Async a, a)

-- | Like waitAnyCatch, but also cancels the other asynchronous
--   operations as soon as one has completed.
waitAnyCatchCancel :: [Async a] -> IO (Async a, Either SomeException a)

-- | Wait for the first of two Asyncs to finish. If the
--   Async that finished first raised an exception, then the
--   exception is re-thrown by waitEither.
waitEither :: Async a -> Async b -> IO (Either a b)

-- | Wait for the first of two Asyncs to finish.
waitEitherCatch :: Async a -> Async b -> IO (Either (Either SomeException a) (Either SomeException b))

-- | Like waitEither, but also cancels both Asyncs
--   before returning.
waitEitherCancel :: Async a -> Async b -> IO (Either a b)

-- | Like waitEitherCatch, but also cancels both
--   Asyncs before returning.
waitEitherCatchCancel :: Async a -> Async b -> IO (Either (Either SomeException a) (Either SomeException b))

-- | Like waitEither, but the result is ignored.
waitEither_ :: Async a -> Async b -> IO ()

-- | Waits for both Asyncs to finish, but if either of them throws
--   an exception before they have both finished, then the exception is
--   re-thrown by waitBoth.
waitBoth :: Async a -> Async b -> IO (a, b)

-- | A version of waitAny that can be used inside an STM
--   transaction.
waitAnySTM :: [Async a] -> STM (Async a, a)

-- | A version of waitAnyCatch that can be used inside an STM
--   transaction.
waitAnyCatchSTM :: [Async a] -> STM (Async a, Either SomeException a)

-- | A version of waitEither that can be used inside an STM
--   transaction.
waitEitherSTM :: Async a -> Async b -> STM (Either a b)

-- | A version of waitEitherCatch that can be used inside an STM
--   transaction.
waitEitherCatchSTM :: Async a -> Async b -> STM (Either (Either SomeException a) (Either SomeException b))

-- | A version of waitEither_ that can be used inside an STM
--   transaction.
waitEitherSTM_ :: Async a -> Async b -> STM ()

-- | A version of waitBoth that can be used inside an STM
--   transaction.
waitBothSTM :: Async a -> Async b -> STM (a, b)

-- | Spawn an asynchronous action in a separate thread.
--   
--   Like for forkIO, the action may be left running unintentionally
--   (see module-level documentation for details).
--   
--   Use withAsync style functions wherever you can instead!
async :: IO a -> IO (Async a)

-- | Like async but using forkOS internally.
asyncBound :: IO a -> IO (Async a)

-- | Like async but using forkOn internally.
asyncOn :: Int -> IO a -> IO (Async a)

-- | Like async but using forkIOWithUnmask internally. The
--   child thread is passed a function that can be used to unmask
--   asynchronous exceptions.
asyncWithUnmask :: ((forall b. () => IO b -> IO b) -> IO a) -> IO (Async a)

-- | Like asyncOn but using forkOnWithUnmask internally. The
--   child thread is passed a function that can be used to unmask
--   asynchronous exceptions.
asyncOnWithUnmask :: Int -> ((forall b. () => IO b -> IO b) -> IO a) -> IO (Async a)

-- | Link the given Async to the current thread, such that if the
--   Async raises an exception, that exception will be re-thrown
--   in the current thread, wrapped in ExceptionInLinkedThread.
--   
--   link ignores AsyncCancelled exceptions thrown in the
--   other thread, so that it's safe to cancel a thread you're
--   linked to. If you want different behaviour, use linkOnly.
link :: Async a -> IO ()

-- | Link the given Async to the current thread, such that if the
--   Async raises an exception, that exception will be re-thrown
--   in the current thread, wrapped in ExceptionInLinkedThread.
--   
--   The supplied predicate determines which exceptions in the target
--   thread should be propagated to the source thread.
linkOnly :: (SomeException -> Bool) -> Async a -> IO ()

-- | Link two Asyncs together, such that if either raises an
--   exception, the same exception is re-thrown in the other
--   Async, wrapped in ExceptionInLinkedThread.
--   
--   link2 ignores AsyncCancelled exceptions, so that it's
--   possible to cancel either thread without cancelling the other.
--   If you want different behaviour, use link2Only.
link2 :: Async a -> Async b -> IO ()

-- | Link two Asyncs together, such that if either raises an
--   exception, the same exception is re-thrown in the other
--   Async, wrapped in ExceptionInLinkedThread.
--   
--   The supplied predicate determines which exceptions in the target
--   thread should be propagated to the source thread.
link2Only :: (SomeException -> Bool) -> Async a -> Async b -> IO ()
data ExceptionInLinkedThread
ExceptionInLinkedThread :: Async a -> SomeException -> ExceptionInLinkedThread
