{-# LANGUAGE RecordWildCards #-}
module System.Process.Extra
where
import Control.Concurrent
import Control.Exception
import Foreign.C ( Errno(..), ePIPE )
import GHC.IO.Exception ( IOErrorType(..), IOException(..) )
withForkWait :: IO () -> (IO () -> IO a) -> IO a
withForkWait async body = do
waitVar <- newEmptyMVar :: IO (MVar (Either SomeException ()))
mask $ \restore -> do
tid <- forkIO $ try (restore async) >>= putMVar waitVar
let wait = takeMVar waitVar >>= either throwIO return
restore (body wait) `onException` killThread tid
ignoreSIGPIPE :: IO () -> IO ()
ignoreSIGPIPE =
handle $ \e ->
case e of
IOError{..} | ResourceVanished <- ioe_type
, Just ioe <- ioe_errno
, Errno ioe == ePIPE
-> return ()
_ -> throwIO e