module System.Process.ByteString.Lazy where
import Control.Exception
import qualified Control.Exception as C (evaluate)
import Control.Monad
import Data.ByteString.Lazy (ByteString)
import qualified Data.ByteString.Lazy as B
import System.Process
import System.Exit (ExitCode)
import System.IO
import Utils (forkWait)
readProcessWithExitCode
:: FilePath
-> [String]
-> ByteString
-> IO (ExitCode, ByteString, ByteString)
readProcessWithExitCode cmd args input = mask $ \restore -> do
(Just inh, Just outh, Just errh, pid) <-
createProcess (proc cmd args){ std_in = CreatePipe,
std_out = CreatePipe,
std_err = CreatePipe }
flip onException
(do hClose inh; hClose outh; hClose errh;
terminateProcess pid; waitForProcess pid) $ restore $ do
out <- B.hGetContents outh
waitOut <- forkWait $ void $ C.evaluate $ B.length out
err <- B.hGetContents errh
waitErr <- forkWait $ void $ C.evaluate $ B.length err
unless (B.null input) $ do B.hPutStr inh input; hFlush inh
hClose inh
waitOut
waitErr
hClose outh
hClose errh
ex <- waitForProcess pid
return (ex, out, err)