Proposal: end lazy IO results with errors/exceptions

David Feuer david.feuer at gmail.com
Mon Jul 21 20:16:02 UTC 2014


Currently,

withFile "foo" hGetContents >>= putStrLn

prints out an empty line, the better to confuse newbies.

I propose modifying the lazyRead function in GHC.IO.Handle.Text that
currently reads

lazyRead :: Handle -> IO String
lazyRead handle =
   unsafeInterleaveIO $
        withHandle "hGetContents" handle $ \ handle_ -> do
        case haType handle_ of
          ClosedHandle     -> return (handle_, "")
          SemiClosedHandle -> lazyReadBuffered handle handle_
          _ -> ioException
                  (IOError (Just handle) IllegalOperation "hGetContents"
                        "illegal handle type" Nothing Nothing)

to something like

lazyRead :: Handle -> IO String
lazyRead handle =
   unsafeInterleaveIO $
        withHandle "hGetContents" handle $ \ handle_ -> do
        case haType handle_ of
          ClosedHandle     -> return (handle_, error "Forcing the
result of a lazy read led to an attempt to read from a closed
handle.")
          SemiClosedHandle -> lazyReadBuffered handle handle_
          _ -> ioException
                  (IOError (Just handle) IllegalOperation "hGetContents"
                        "illegal handle type" Nothing Nothing)

Ideally that error should instead be something to throw an imprecise
exception, but I don't know how to use those yet. I can't personally
see a way for this to break sane, working code, but the folks on #ghc
thought it should be discussed and debated on list.

David Feuer


More information about the Libraries mailing list