2 {-# OPTIONS -fno-implicit-prelude #-}
3 -----------------------------------------------------------------------------
6 -- Copyright : (c) The University of Glasgow 1994-2002
7 -- License : see libraries/base/LICENSE
9 -- Maintainer : cvs-ghc@haskell.org
10 -- Stability : internal
11 -- Portability : non-portable (GHC Extensions)
13 -- Definitions for the 'IO' monad and its friends.
15 -----------------------------------------------------------------------------
17 module GHC.IOBase where
20 import GHC.Arr -- to derive Ix class
21 import GHC.Enum -- to derive Enum class
24 import GHC.Num -- To get fromInteger etc, needed because of -fno-implicit-prelude
25 import Data.Maybe ( Maybe(..) )
31 import {-# SOURCE #-} Data.Dynamic
34 -- ---------------------------------------------------------------------------
38 The IO Monad is just an instance of the ST monad, where the state is
39 the real world. We use the exception mechanism (in GHC.Exception) to
40 implement IO exceptions.
42 NOTE: The IO representation is deeply wired in to various parts of the
43 system. The following list may or may not be exhaustive:
45 Compiler - types of various primitives in PrimOp.lhs
47 RTS - forceIO (StgMiscClosures.hc)
48 - catchzh_fast, (un)?blockAsyncExceptionszh_fast, raisezh_fast
50 - raiseAsync (Schedule.c)
52 Prelude - GHC.IOBase.lhs, and several other places including
55 Libraries - parts of hslibs/lang.
61 A value of type @'IO' a@ is a computation which, when performed,
62 does some I\/O before returning a value of type @a@.
64 There is really only one way to \"perform\" an I\/O action: bind it to
65 @Main.main@ in your program. When your program is run, the I\/O will
66 be performed. It isn't possible to perform I\/O from an arbitrary
67 function, unless that function is itself in the 'IO' monad and called
68 at some point, directly or indirectly, from @Main.main@.
70 'IO' is a monad, so 'IO' actions can be combined using either the do-notation
71 or the '>>' and '>>=' operations from the 'Monad' class.
73 newtype IO a = IO (State# RealWorld -> (# State# RealWorld, a #))
75 unIO :: IO a -> (State# RealWorld -> (# State# RealWorld, a #))
78 instance Functor IO where
79 fmap f x = x >>= (return . f)
81 instance Monad IO where
85 m >> k = m >>= \ _ -> k
91 failIO :: String -> IO a
92 failIO s = ioError (userError s)
94 liftIO :: IO a -> State# RealWorld -> STret RealWorld a
95 liftIO (IO m) = \s -> case m s of (# s', r #) -> STret s' r
97 bindIO :: IO a -> (a -> IO b) -> IO b
98 bindIO (IO m) k = IO ( \ s ->
100 (# new_s, a #) -> unIO (k a) new_s
103 thenIO :: IO a -> IO b -> IO b
104 thenIO (IO m) k = IO ( \ s ->
106 (# new_s, a #) -> unIO k new_s
109 returnIO :: a -> IO a
110 returnIO x = IO (\ s -> (# s, x #))
112 -- ---------------------------------------------------------------------------
113 -- Coercions between IO and ST
115 --stToIO :: (forall s. ST s a) -> IO a
116 stToIO :: ST RealWorld a -> IO a
119 ioToST :: IO a -> ST RealWorld a
120 ioToST (IO m) = (ST m)
122 -- ---------------------------------------------------------------------------
123 -- Unsafe IO operations
126 This is the "back door" into the 'IO' monad, allowing
127 'IO' computation to be performed at any time. For
128 this to be safe, the 'IO' computation should be
129 free of side effects and independent of its environment.
131 If the I\/O computation wrapped in 'unsafePerformIO'
132 performs side effects, then the relative order in which those side
133 effects take place (relative to the main I\/O trunk, or other calls to
134 'unsafePerformIO') is indeterminate.
136 However, it is less well known that
137 'unsafePerformIO' is not type safe. For example:
140 > test = unsafePerformIO $ newIORef []
143 > writeIORef test [42]
144 > bang \<- readIORef test
145 > print (bang :: [Char])
147 This program will core dump. This problem with polymorphic references
148 is well known in the ML community, and does not arise with normal
149 monadic use of references. There is no easy way to make it impossible
150 once you use 'unsafePerformIO'. Indeed, it is
151 possible to write @coerce :: a -> b@ with the
152 help of 'unsafePerformIO'. So be careful!
154 {-# NOINLINE unsafePerformIO #-}
155 unsafePerformIO :: IO a -> a
156 unsafePerformIO (IO m) = case m realWorld# of (# _, r #) -> r
159 'unsafeInterleaveIO' allows 'IO' computation to be deferred lazily.
160 When passed a value of type @IO a@, the 'IO' will only be performed
161 when the value of the @a@ is demanded. This is used to implement lazy
162 file reading, see 'IO.hGetContents'.
164 {-# NOINLINE unsafeInterleaveIO #-}
165 unsafeInterleaveIO :: IO a -> IO a
166 unsafeInterleaveIO (IO m)
168 r = case m s of (# _, res #) -> res
172 -- ---------------------------------------------------------------------------
175 data MVar a = MVar (MVar# RealWorld a)
177 An 'MVar' (pronounced \"em-var\") is a synchronising variable, used
178 for communication between concurrent threads. It can be thought of
179 as a a box, which may be empty or full.
182 -- pull in Eq (Mvar a) too, to avoid GHC.Conc being an orphan-instance module
183 instance Eq (MVar a) where
184 (MVar mvar1#) == (MVar mvar2#) = sameMVar# mvar1# mvar2#
186 -- A Handle is represented by (a reference to) a record
187 -- containing the state of the I/O port/device. We record
188 -- the following pieces of info:
190 -- * type (read,write,closed etc.)
191 -- * the underlying file descriptor
193 -- * buffer, and spare buffers
194 -- * user-friendly name (usually the
195 -- FilePath used when IO.openFile was called)
197 -- Note: when a Handle is garbage collected, we want to flush its buffer
198 -- and close the OS file handle, so as to free up a (precious) resource.
201 = FileHandle -- A normal handle to a file
204 | DuplexHandle -- A handle to a read/write stream
205 !(MVar Handle__) -- The read side
206 !(MVar Handle__) -- The write side
209 -- * A 'FileHandle' is seekable. A 'DuplexHandle' may or may not be
212 instance Eq Handle where
213 (FileHandle h1) == (FileHandle h2) = h1 == h2
214 (DuplexHandle h1 _) == (DuplexHandle h2 _) = h1 == h2
217 type FD = Int -- XXX ToDo: should be CInt
221 haFD :: !FD, -- file descriptor
222 haType :: HandleType, -- type (read/write/append etc.)
223 haIsBin :: Bool, -- binary mode?
224 haIsStream :: Bool, -- is this a stream handle?
225 haBufferMode :: BufferMode, -- buffer contains read/write data?
226 haFilePath :: FilePath, -- file name, possibly
227 haBuffer :: !(IORef Buffer), -- the current buffer
228 haBuffers :: !(IORef BufferList), -- spare buffers
229 haOtherSide :: Maybe (MVar Handle__) -- ptr to the write side of a
233 -- ---------------------------------------------------------------------------
236 -- The buffer is represented by a mutable variable containing a
237 -- record, where the record contains the raw buffer and the start/end
238 -- points of the filled portion. We use a mutable variable so that
239 -- the common operation of writing (or reading) some data from (to)
240 -- the buffer doesn't need to modify, and hence copy, the handle
241 -- itself, it just updates the buffer.
243 -- There will be some allocation involved in a simple hPutChar in
244 -- order to create the new Buffer structure (below), but this is
245 -- relatively small, and this only has to be done once per write
248 -- The buffer contains its size - we could also get the size by
249 -- calling sizeOfMutableByteArray# on the raw buffer, but that tends
250 -- to be rounded up to the nearest Word.
252 type RawBuffer = MutableByteArray# RealWorld
254 -- INVARIANTS on a Buffer:
256 -- * A handle *always* has a buffer, even if it is only 1 character long
257 -- (an unbuffered handle needs a 1 character buffer in order to support
258 -- hLookAhead and hIsEOF).
260 -- * if r == w, then r == 0 && w == 0
261 -- * if state == WriteBuffer, then r == 0
262 -- * a write buffer is never full. If an operation
263 -- fills up the buffer, it will always flush it before
265 -- * a read buffer may be full as a result of hLookAhead. In normal
266 -- operation, a read buffer always has at least one character of space.
274 bufState :: BufferState
277 data BufferState = ReadBuffer | WriteBuffer deriving (Eq)
279 -- we keep a few spare buffers around in a handle to avoid allocating
280 -- a new one for each hPutStr. These buffers are *guaranteed* to be the
281 -- same size as the main buffer.
284 | BufferListCons RawBuffer BufferList
287 bufferIsWritable :: Buffer -> Bool
288 bufferIsWritable Buffer{ bufState=WriteBuffer } = True
289 bufferIsWritable _other = False
291 bufferEmpty :: Buffer -> Bool
292 bufferEmpty Buffer{ bufRPtr=r, bufWPtr=w } = r == w
294 -- only makes sense for a write buffer
295 bufferFull :: Buffer -> Bool
296 bufferFull b@Buffer{ bufWPtr=w } = w >= bufSize b
298 -- Internally, we classify handles as being one
309 isReadableHandleType ReadHandle = True
310 isReadableHandleType ReadWriteHandle = True
311 isReadableHandleType _ = False
313 isWritableHandleType AppendHandle = True
314 isWritableHandleType WriteHandle = True
315 isWritableHandleType ReadWriteHandle = True
316 isWritableHandleType _ = False
318 -- File names are specified using @FilePath@, a OS-dependent
319 -- string that (hopefully, I guess) maps to an accessible file/object.
321 type FilePath = String
323 -- ---------------------------------------------------------------------------
326 -- Three kinds of buffering are supported: line-buffering,
327 -- block-buffering or no-buffering. These modes have the following
328 -- effects. For output, items are written out from the internal
329 -- buffer according to the buffer mode:
331 -- o line-buffering the entire output buffer is written
332 -- out whenever a newline is output, the output buffer overflows,
333 -- a flush is issued, or the handle is closed.
335 -- o block-buffering the entire output buffer is written out whenever
336 -- it overflows, a flush is issued, or the handle
339 -- o no-buffering output is written immediately, and never stored
340 -- in the output buffer.
342 -- The output buffer is emptied as soon as it has been written out.
344 -- Similarly, input occurs according to the buffer mode for handle {\em hdl}.
346 -- o line-buffering when the input buffer for the handle is not empty,
347 -- the next item is obtained from the buffer;
348 -- otherwise, when the input buffer is empty,
349 -- characters up to and including the next newline
350 -- character are read into the buffer. No characters
351 -- are available until the newline character is
354 -- o block-buffering when the input buffer for the handle becomes empty,
355 -- the next block of data is read into this buffer.
357 -- o no-buffering the next input item is read and returned.
359 -- For most implementations, physical files will normally be block-buffered
360 -- and terminals will normally be line-buffered. (the IO interface provides
361 -- operations for changing the default buffering of a handle tho.)
364 = NoBuffering | LineBuffering | BlockBuffering (Maybe Int)
365 deriving (Eq, Ord, Read, Show)
367 -- ---------------------------------------------------------------------------
370 -- |A mutable variable in the 'IO' monad
371 newtype IORef a = IORef (STRef RealWorld a) deriving Eq
373 -- |Build a new 'IORef'
374 newIORef :: a -> IO (IORef a)
375 newIORef v = stToIO (newSTRef v) >>= \ var -> return (IORef var)
377 -- |Read the value of an 'IORef'
378 readIORef :: IORef a -> IO a
379 readIORef (IORef var) = stToIO (readSTRef var)
381 -- |Write a new value into an 'IORef'
382 writeIORef :: IORef a -> a -> IO ()
383 writeIORef (IORef var) v = stToIO (writeSTRef var v)
385 -- ---------------------------------------------------------------------------
386 -- Show instance for Handles
388 -- handle types are 'show'n when printing error msgs, so
389 -- we provide a more user-friendly Show instance for it
390 -- than the derived one.
392 instance Show HandleType where
395 ClosedHandle -> showString "closed"
396 SemiClosedHandle -> showString "semi-closed"
397 ReadHandle -> showString "readable"
398 WriteHandle -> showString "writable"
399 AppendHandle -> showString "writable (append)"
400 ReadWriteHandle -> showString "read-writable"
402 instance Show Handle where
403 showsPrec p (FileHandle h) = showHandle p h False
404 showsPrec p (DuplexHandle _ h) = showHandle p h True
406 showHandle p h duplex =
408 -- (Big) SIGH: unfolded defn of takeMVar to avoid
409 -- an (oh-so) unfortunate module loop with GHC.Conc.
410 hdl_ = unsafePerformIO (IO $ \ s# ->
411 case h of { MVar h# ->
412 case takeMVar# h# s# of { (# s2# , r #) ->
413 case putMVar# h# r s2# of { s3# ->
416 showType | duplex = showString "duplex (read-write)"
417 | otherwise = showsPrec p (haType hdl_)
420 showHdl (haType hdl_)
421 (showString "loc=" . showString (haFilePath hdl_) . showChar ',' .
422 showString "type=" . showType . showChar ',' .
423 showString "binary=" . showsPrec p (haIsBin hdl_) . showChar ',' .
424 showString "buffering=" . showBufMode (unsafePerformIO (readIORef (haBuffer hdl_))) (haBufferMode hdl_) . showString "}" )
427 showHdl :: HandleType -> ShowS -> ShowS
430 ClosedHandle -> showsPrec p ht . showString "}"
433 showBufMode :: Buffer -> BufferMode -> ShowS
434 showBufMode buf bmo =
436 NoBuffering -> showString "none"
437 LineBuffering -> showString "line"
438 BlockBuffering (Just n) -> showString "block " . showParen True (showsPrec p n)
439 BlockBuffering Nothing -> showString "block " . showParen True (showsPrec p def)
444 -- ------------------------------------------------------------------------
445 -- Exception datatype and operations
447 -- |The type of exceptions. Every kind of system-generated exception
448 -- has a constructor in the 'Exception' type, and values of other
449 -- types may be injected into 'Exception' by coercing them to
450 -- 'Dynamic' (see the section on Dynamic Exceptions: "Control.Exception\#DynamicExceptions").
452 -- For backwards compatibility with Haskell 98, 'IOError' is a type synonym
455 = ArithException ArithException
456 -- ^Exceptions raised by arithmetic
457 -- operations. (NOTE: GHC currently does not throw
458 -- 'ArithException's).
459 | ArrayException ArrayException
460 -- ^Exceptions raised by array-related
461 -- operations. (NOTE: GHC currently does not throw
462 -- 'ArrayException's).
463 | AssertionFailed String
464 -- ^This exception is thrown by the
465 -- 'assert' operation when the condition
466 -- fails. The 'String' argument contains the
467 -- location of the assertion in the source program.
468 | AsyncException AsyncException
469 -- ^Asynchronous exceptions (see section on Asynchronous Exceptions: "Control.Exception\#AsynchronousExceptions").
471 -- ^The current thread was executing a call to
472 -- 'takeMVar' that could never return, because there are no other
473 -- references to this 'MVar'.
475 -- ^There are no runnable threads, so the program is
476 -- deadlocked. The 'Deadlock' exception is
477 -- raised in the main thread only (see also: "Control.Concurrent").
478 | DynException Dynamic
479 -- ^Dynamically typed exceptions (see section on Dynamic Exceptions: "Control.Exception\#DynamicExceptions").
481 -- ^The 'ErrorCall' exception is thrown by 'error'. The 'String'
482 -- argument of 'ErrorCall' is the string passed to 'error' when it was
484 | ExitException ExitCode
485 -- ^The 'ExitException' exception is thrown by 'System.exitWith' (and
486 -- 'System.exitFailure'). The 'ExitCode' argument is the value passed
487 -- to 'System.exitWith'. An unhandled 'ExitException' exception in the
488 -- main thread will cause the program to be terminated with the given
490 | IOException IOException
491 -- ^These are the standard IO exceptions generated by
492 -- Haskell\'s @IO@ operations. See also "System.IO.Error".
493 | NoMethodError String
494 -- ^An attempt was made to invoke a class method which has
495 -- no definition in this instance, and there was no default
496 -- definition given in the class declaration. GHC issues a
497 -- warning when you compile an instance which has missing
500 -- ^The current thread is stuck in an infinite loop. This
501 -- exception may or may not be thrown when the program is
503 | PatternMatchFail String
504 -- ^A pattern matching failure. The 'String' argument should contain a
505 -- descriptive message including the function name, source file
508 -- ^An attempt was made to evaluate a field of a record
509 -- for which no value was given at construction time. The
510 -- 'String' argument gives the location of the
511 -- record construction in the source program.
513 -- ^A field selection was attempted on a constructor that
514 -- doesn\'t have the requested field. This can happen with
515 -- multi-constructor records when one or more fields are
516 -- missing from some of the constructors. The
517 -- 'String' argument gives the location of the
518 -- record selection in the source program.
520 -- ^An attempt was made to update a field in a record,
521 -- where the record doesn\'t have the requested field. This can
522 -- only occur with multi-constructor records, when one or more
523 -- fields are missing from some of the constructors. The
524 -- 'String' argument gives the location of the
525 -- record update in the source program.
527 -- |The type of arithmetic exceptions
537 -- |Asynchronous exceptions
540 -- ^The current thread\'s stack exceeded its limit.
541 -- Since an exception has been raised, the thread\'s stack
542 -- will certainly be below its limit again, but the
543 -- programmer should take remedial action
546 -- ^The program\'s heap is reaching its limit, and
547 -- the program should take action to reduce the amount of
548 -- live data it has. Notes:
550 -- * It is undefined which thread receives this exception.
552 -- * GHC currently does not throw 'HeapOverflow' exceptions.
554 -- ^This exception is raised by another thread
555 -- calling 'killThread', or by the system
556 -- if it needs to terminate the thread for some
560 -- | Exceptions generated by array operations
562 = IndexOutOfBounds String
563 -- ^An attempt was made to index an array outside
564 -- its declared bounds.
565 | UndefinedElement String
566 -- ^An attempt was made to evaluate an element of an
567 -- array that had not been initialized.
570 stackOverflow, heapOverflow :: Exception -- for the RTS
571 stackOverflow = AsyncException StackOverflow
572 heapOverflow = AsyncException HeapOverflow
574 instance Show ArithException where
575 showsPrec _ Overflow = showString "arithmetic overflow"
576 showsPrec _ Underflow = showString "arithmetic underflow"
577 showsPrec _ LossOfPrecision = showString "loss of precision"
578 showsPrec _ DivideByZero = showString "divide by zero"
579 showsPrec _ Denormal = showString "denormal"
581 instance Show AsyncException where
582 showsPrec _ StackOverflow = showString "stack overflow"
583 showsPrec _ HeapOverflow = showString "heap overflow"
584 showsPrec _ ThreadKilled = showString "thread killed"
586 instance Show ArrayException where
587 showsPrec _ (IndexOutOfBounds s)
588 = showString "array index out of range"
589 . (if not (null s) then showString ": " . showString s
591 showsPrec _ (UndefinedElement s)
592 = showString "undefined array element"
593 . (if not (null s) then showString ": " . showString s
596 instance Show Exception where
597 showsPrec _ (IOException err) = shows err
598 showsPrec _ (ArithException err) = shows err
599 showsPrec _ (ArrayException err) = shows err
600 showsPrec _ (ErrorCall err) = showString err
601 showsPrec _ (ExitException err) = showString "exit: " . shows err
602 showsPrec _ (NoMethodError err) = showString err
603 showsPrec _ (PatternMatchFail err) = showString err
604 showsPrec _ (RecSelError err) = showString err
605 showsPrec _ (RecConError err) = showString err
606 showsPrec _ (RecUpdError err) = showString err
607 showsPrec _ (AssertionFailed err) = showString err
608 showsPrec _ (DynException _err) = showString "unknown exception"
609 showsPrec _ (AsyncException e) = shows e
610 showsPrec _ (BlockedOnDeadMVar) = showString "thread blocked indefinitely"
611 showsPrec _ (NonTermination) = showString "<<loop>>"
612 showsPrec _ (Deadlock) = showString "<<deadlock>>"
614 instance Eq Exception where
615 IOException e1 == IOException e2 = e1 == e2
616 ArithException e1 == ArithException e2 = e1 == e2
617 ArrayException e1 == ArrayException e2 = e1 == e2
618 ErrorCall e1 == ErrorCall e2 = e1 == e2
619 ExitException e1 == ExitException e2 = e1 == e2
620 NoMethodError e1 == NoMethodError e2 = e1 == e2
621 PatternMatchFail e1 == PatternMatchFail e2 = e1 == e2
622 RecSelError e1 == RecSelError e2 = e1 == e2
623 RecConError e1 == RecConError e2 = e1 == e2
624 RecUpdError e1 == RecUpdError e2 = e1 == e2
625 AssertionFailed e1 == AssertionFailed e2 = e1 == e2
626 DynException _ == DynException _ = False -- incomparable
627 AsyncException e1 == AsyncException e2 = e1 == e2
628 BlockedOnDeadMVar == BlockedOnDeadMVar = True
629 NonTermination == NonTermination = True
630 Deadlock == Deadlock = True
632 -- -----------------------------------------------------------------------------
635 -- The `ExitCode' type defines the exit codes that a program
636 -- can return. `ExitSuccess' indicates successful termination;
637 -- and `ExitFailure code' indicates program failure
638 -- with value `code'. The exact interpretation of `code'
639 -- is operating-system dependent. In particular, some values of
640 -- `code' may be prohibited (e.g. 0 on a POSIX-compliant system).
642 -- We need it here because it is used in ExitException in the
643 -- Exception datatype (above).
645 data ExitCode = ExitSuccess | ExitFailure Int
646 deriving (Eq, Ord, Read, Show)
648 -- --------------------------------------------------------------------------
651 -- | Throw an exception. Exceptions may be thrown from purely
652 -- functional code, but may only be caught within the 'IO' monad.
653 throw :: Exception -> a
654 throw exception = raise# exception
656 -- | A variant of 'throw' that can be used within the 'IO' monad.
658 -- Although 'ioError' has a type that is an instance of the type of 'throw', the
659 -- two functions are subtly different:
661 -- > throw e `seq` return () ===> throw e
662 -- > ioError e `seq` return () ===> return ()
664 -- The first example will cause the exception @e@ to be raised,
665 -- whereas the second one won\'t. In fact, 'ioError' will only cause
666 -- an exception to be raised when it is used within the 'IO' monad.
667 -- The 'ioError' variant should be used in preference to 'throw' to
668 -- raise an exception within the 'IO' monad because it guarantees
669 -- ordering with respect to other 'IO' operations, whereas 'throw'
671 ioError :: Exception -> IO a
672 ioError err = IO $ \s -> throw err s
674 ioException :: IOException -> IO a
675 ioException err = IO $ \s -> throw (IOException err) s
677 -- ---------------------------------------------------------------------------
680 -- A value @IOError@ encode errors occurred in the @IO@ monad.
681 -- An @IOError@ records a more specific error type, a descriptive
682 -- string and maybe the handle that was used when the error was
685 type IOError = Exception
689 ioe_handle :: Maybe Handle, -- the handle used by the action flagging
691 ioe_type :: IOErrorType, -- what it was.
692 ioe_location :: String, -- location.
693 ioe_descr :: String, -- error type specific information.
694 ioe_filename :: Maybe FilePath -- filename the error is related to.
697 instance Eq IOException where
698 (IOError h1 e1 loc1 str1 fn1) == (IOError h2 e2 loc2 str2 fn2) =
699 e1==e2 && str1==str2 && h1==h2 && loc1==loc2 && fn1==fn2
712 | UnsatisfiedConstraints
719 | UnsupportedOperation
723 | DynIOError Dynamic -- cheap&cheerful extensible IO error type.
725 instance Eq IOErrorType where
728 DynIOError{} -> False -- from a strictness POV, compatible with a derived Eq inst?
729 _ -> getTag# x ==# getTag# y
731 instance Show IOErrorType where
735 AlreadyExists -> "already exists"
736 NoSuchThing -> "does not exist"
737 ResourceBusy -> "resource busy"
738 ResourceExhausted -> "resource exhausted"
740 IllegalOperation -> "illegal operation"
741 PermissionDenied -> "permission denied"
742 UserError -> "user error"
743 HardwareFault -> "hardware fault"
744 InappropriateType -> "inappropriate type"
745 Interrupted -> "interrupted"
746 InvalidArgument -> "invalid argument"
747 OtherError -> "failed"
748 ProtocolError -> "protocol error"
749 ResourceVanished -> "resource vanished"
750 SystemError -> "system error"
751 TimeExpired -> "timeout"
752 UnsatisfiedConstraints -> "unsatisified constraints" -- ultra-precise!
753 UnsupportedOperation -> "unsupported operation"
754 DynIOError{} -> "unknown IO error"
756 userError :: String -> IOError
757 userError str = IOException (IOError Nothing UserError "" str Nothing)
759 -- ---------------------------------------------------------------------------
762 instance Show IOException where
763 showsPrec p (IOError hdl iot loc s fn) =
767 _ -> showString "\nAction: " . showString loc) .
770 Just h -> showString "\nHandle: " . showsPrec p h) .
773 _ -> showString "\nReason: " . showString s) .
776 Just name -> showString "\nFile: " . showString name)
778 -- -----------------------------------------------------------------------------
781 data IOMode = ReadMode | WriteMode | AppendMode | ReadWriteMode
782 deriving (Eq, Ord, Ix, Enum, Read, Show)