4 module Control.Exception,
9 import Prelude hiding (catch)
11 #if __GLASGOW_HASKELL__ < 609
12 import Control.Exception.Extensible as Control.Exception
14 import Control.Exception
17 catchIO :: IO a -> (IOException -> IO a) -> IO a
20 handleIO :: (IOException -> IO a) -> IO a -> IO a
21 handleIO = flip catchIO
23 tryIO :: IO a -> IO (Either IOException a)
26 -- | A monad that can catch exceptions. A minimal definition
27 -- requires a definition of 'gcatch'.
29 -- Implementations on top of 'IO' should implement 'gblock' and 'gunblock' to
30 -- eventually call the primitives 'Control.Exception.block' and
31 -- 'Control.Exception.unblock' respectively. These are used for
32 -- implementations that support asynchronous exceptions. The default
33 -- implementations of 'gbracket' and 'gfinally' use 'gblock' and 'gunblock'
34 -- thus rarely require overriding.
36 class Monad m => ExceptionMonad m where
38 -- | Generalised version of 'Control.Exception.catch', allowing an arbitrary
39 -- exception handling monad instead of just 'IO'.
40 gcatch :: Exception e => m a -> (e -> m a) -> m a
42 -- | Generalised version of 'Control.Exception.block', allowing an arbitrary
43 -- exception handling monad instead of just 'IO'.
46 -- | Generalised version of 'Control.Exception.unblock', allowing an
47 -- arbitrary exception handling monad instead of just 'IO'.
48 gunblock :: m a -> m a
50 -- | Generalised version of 'Control.Exception.bracket', allowing an arbitrary
51 -- exception handling monad instead of just 'IO'.
52 gbracket :: m a -> (a -> m b) -> (a -> m c) -> m c
54 -- | Generalised version of 'Control.Exception.finally', allowing an arbitrary
55 -- exception handling monad instead of just 'IO'.
56 gfinally :: m a -> m b -> m a
61 gbracket before after thing =
64 r <- gunblock (thing a) `gonException` after a
70 r <- gunblock a `gonException` sequel
74 instance ExceptionMonad IO where
79 gtry :: (ExceptionMonad m, Exception e) => m a -> m (Either e a)
80 gtry act = gcatch (act >>= \a -> return (Right a))
81 (\e -> return (Left e))
83 -- | Generalised version of 'Control.Exception.handle', allowing an arbitrary
84 -- exception handling monad instead of just 'IO'.
85 ghandle :: (ExceptionMonad m, Exception e) => (e -> m a) -> m a -> m a
88 -- | Always executes the first argument. If this throws an exception the
89 -- second argument is executed and the exception is raised again.
90 gonException :: (ExceptionMonad m) => m a -> m b -> m a
91 gonException ioA cleanup = ioA `gcatch` \e ->
93 throw (e :: SomeException)