1 {-# LANGUAGE CPP, NoImplicitPrelude, ForeignFunctionInterface #-}
2 {-# OPTIONS_GHC -#include "HsBase.h" #-}
4 -----------------------------------------------------------------------------
6 -- Module : Foreign.C.Error
7 -- Copyright : (c) The FFI task force 2001
8 -- License : BSD-style (see the file libraries/base/LICENSE)
10 -- Maintainer : ffi@haskell.org
11 -- Stability : provisional
12 -- Portability : portable
14 -- C-specific Marshalling support: Handling of C \"errno\" error codes.
16 -----------------------------------------------------------------------------
18 module Foreign.C.Error (
20 -- * Haskell representations of @errno@ values
22 Errno(..), -- instance: Eq
24 -- ** Common @errno@ symbols
25 -- | Different operating systems and\/or C libraries often support
26 -- different values of @errno@. This module defines the common values,
27 -- but due to the open definition of 'Errno' users may add definitions
28 -- which are not predefined.
29 eOK, e2BIG, eACCES, eADDRINUSE, eADDRNOTAVAIL, eADV, eAFNOSUPPORT, eAGAIN,
30 eALREADY, eBADF, eBADMSG, eBADRPC, eBUSY, eCHILD, eCOMM, eCONNABORTED,
31 eCONNREFUSED, eCONNRESET, eDEADLK, eDESTADDRREQ, eDIRTY, eDOM, eDQUOT,
32 eEXIST, eFAULT, eFBIG, eFTYPE, eHOSTDOWN, eHOSTUNREACH, eIDRM, eILSEQ,
33 eINPROGRESS, eINTR, eINVAL, eIO, eISCONN, eISDIR, eLOOP, eMFILE, eMLINK,
34 eMSGSIZE, eMULTIHOP, eNAMETOOLONG, eNETDOWN, eNETRESET, eNETUNREACH,
35 eNFILE, eNOBUFS, eNODATA, eNODEV, eNOENT, eNOEXEC, eNOLCK, eNOLINK,
36 eNOMEM, eNOMSG, eNONET, eNOPROTOOPT, eNOSPC, eNOSR, eNOSTR, eNOSYS,
37 eNOTBLK, eNOTCONN, eNOTDIR, eNOTEMPTY, eNOTSOCK, eNOTTY, eNXIO,
38 eOPNOTSUPP, ePERM, ePFNOSUPPORT, ePIPE, ePROCLIM, ePROCUNAVAIL,
39 ePROGMISMATCH, ePROGUNAVAIL, ePROTO, ePROTONOSUPPORT, ePROTOTYPE,
40 eRANGE, eREMCHG, eREMOTE, eROFS, eRPCMISMATCH, eRREMOTE, eSHUTDOWN,
41 eSOCKTNOSUPPORT, eSPIPE, eSRCH, eSRMNT, eSTALE, eTIME, eTIMEDOUT,
42 eTOOMANYREFS, eTXTBSY, eUSERS, eWOULDBLOCK, eXDEV,
44 -- ** 'Errno' functions
46 isValidErrno, -- :: Errno -> Bool
48 -- access to the current thread's "errno" value
50 getErrno, -- :: IO Errno
51 resetErrno, -- :: IO ()
53 -- conversion of an "errno" value into IO error
55 errnoToIOError, -- :: String -- location
57 -- -> Maybe Handle -- handle
58 -- -> Maybe String -- filename
61 -- throw current "errno" value
63 throwErrno, -- :: String -> IO a
65 -- ** Guards for IO operations that may fail
67 throwErrnoIf, -- :: (a -> Bool) -> String -> IO a -> IO a
68 throwErrnoIf_, -- :: (a -> Bool) -> String -> IO a -> IO ()
69 throwErrnoIfRetry, -- :: (a -> Bool) -> String -> IO a -> IO a
70 throwErrnoIfRetry_, -- :: (a -> Bool) -> String -> IO a -> IO ()
71 throwErrnoIfMinus1, -- :: Num a
72 -- => String -> IO a -> IO a
73 throwErrnoIfMinus1_, -- :: Num a
74 -- => String -> IO a -> IO ()
75 throwErrnoIfMinus1Retry,
77 -- => String -> IO a -> IO a
78 throwErrnoIfMinus1Retry_,
80 -- => String -> IO a -> IO ()
81 throwErrnoIfNull, -- :: String -> IO (Ptr a) -> IO (Ptr a)
82 throwErrnoIfNullRetry,-- :: String -> IO (Ptr a) -> IO (Ptr a)
84 throwErrnoIfRetryMayBlock,
85 throwErrnoIfRetryMayBlock_,
86 throwErrnoIfMinus1RetryMayBlock,
87 throwErrnoIfMinus1RetryMayBlock_,
88 throwErrnoIfNullRetryMayBlock,
94 throwErrnoPathIfMinus1,
95 throwErrnoPathIfMinus1_,
99 -- this is were we get the CONST_XXX definitions from that configure
103 #include "HsBaseConfig.h"
107 import Foreign.C.Types
108 import Foreign.C.String
109 import Foreign.Marshal.Error ( void )
112 #if __GLASGOW_HASKELL__
114 import GHC.IO.Exception
115 import GHC.IO.Handle.Types
119 import Hugs.Prelude ( Handle, IOError, ioError )
120 import System.IO.Unsafe ( unsafePerformIO )
122 import System.IO ( Handle )
123 import System.IO.Error ( IOError, ioError )
124 import System.IO.Unsafe ( unsafePerformIO )
125 import Foreign.Storable ( Storable(poke,peek) )
129 {-# CFILES cbits/PrelIOUtils.c #-}
136 -- | Haskell representation for @errno@ values.
137 -- The implementation is deliberately exposed, to allow users to add
138 -- their own definitions of 'Errno' values.
140 newtype Errno = Errno CInt
142 instance Eq Errno where
143 errno1@(Errno no1) == errno2@(Errno no2)
144 | isValidErrno errno1 && isValidErrno errno2 = no1 == no2
147 -- common "errno" symbols
149 eOK, e2BIG, eACCES, eADDRINUSE, eADDRNOTAVAIL, eADV, eAFNOSUPPORT, eAGAIN,
150 eALREADY, eBADF, eBADMSG, eBADRPC, eBUSY, eCHILD, eCOMM, eCONNABORTED,
151 eCONNREFUSED, eCONNRESET, eDEADLK, eDESTADDRREQ, eDIRTY, eDOM, eDQUOT,
152 eEXIST, eFAULT, eFBIG, eFTYPE, eHOSTDOWN, eHOSTUNREACH, eIDRM, eILSEQ,
153 eINPROGRESS, eINTR, eINVAL, eIO, eISCONN, eISDIR, eLOOP, eMFILE, eMLINK,
154 eMSGSIZE, eMULTIHOP, eNAMETOOLONG, eNETDOWN, eNETRESET, eNETUNREACH,
155 eNFILE, eNOBUFS, eNODATA, eNODEV, eNOENT, eNOEXEC, eNOLCK, eNOLINK,
156 eNOMEM, eNOMSG, eNONET, eNOPROTOOPT, eNOSPC, eNOSR, eNOSTR, eNOSYS,
157 eNOTBLK, eNOTCONN, eNOTDIR, eNOTEMPTY, eNOTSOCK, eNOTTY, eNXIO,
158 eOPNOTSUPP, ePERM, ePFNOSUPPORT, ePIPE, ePROCLIM, ePROCUNAVAIL,
159 ePROGMISMATCH, ePROGUNAVAIL, ePROTO, ePROTONOSUPPORT, ePROTOTYPE,
160 eRANGE, eREMCHG, eREMOTE, eROFS, eRPCMISMATCH, eRREMOTE, eSHUTDOWN,
161 eSOCKTNOSUPPORT, eSPIPE, eSRCH, eSRMNT, eSTALE, eTIME, eTIMEDOUT,
162 eTOOMANYREFS, eTXTBSY, eUSERS, eWOULDBLOCK, eXDEV :: Errno
164 -- the cCONST_XXX identifiers are cpp symbols whose value is computed by
171 e2BIG = Errno (CONST_E2BIG)
172 eACCES = Errno (CONST_EACCES)
173 eADDRINUSE = Errno (CONST_EADDRINUSE)
174 eADDRNOTAVAIL = Errno (CONST_EADDRNOTAVAIL)
175 eADV = Errno (CONST_EADV)
176 eAFNOSUPPORT = Errno (CONST_EAFNOSUPPORT)
177 eAGAIN = Errno (CONST_EAGAIN)
178 eALREADY = Errno (CONST_EALREADY)
179 eBADF = Errno (CONST_EBADF)
180 eBADMSG = Errno (CONST_EBADMSG)
181 eBADRPC = Errno (CONST_EBADRPC)
182 eBUSY = Errno (CONST_EBUSY)
183 eCHILD = Errno (CONST_ECHILD)
184 eCOMM = Errno (CONST_ECOMM)
185 eCONNABORTED = Errno (CONST_ECONNABORTED)
186 eCONNREFUSED = Errno (CONST_ECONNREFUSED)
187 eCONNRESET = Errno (CONST_ECONNRESET)
188 eDEADLK = Errno (CONST_EDEADLK)
189 eDESTADDRREQ = Errno (CONST_EDESTADDRREQ)
190 eDIRTY = Errno (CONST_EDIRTY)
191 eDOM = Errno (CONST_EDOM)
192 eDQUOT = Errno (CONST_EDQUOT)
193 eEXIST = Errno (CONST_EEXIST)
194 eFAULT = Errno (CONST_EFAULT)
195 eFBIG = Errno (CONST_EFBIG)
196 eFTYPE = Errno (CONST_EFTYPE)
197 eHOSTDOWN = Errno (CONST_EHOSTDOWN)
198 eHOSTUNREACH = Errno (CONST_EHOSTUNREACH)
199 eIDRM = Errno (CONST_EIDRM)
200 eILSEQ = Errno (CONST_EILSEQ)
201 eINPROGRESS = Errno (CONST_EINPROGRESS)
202 eINTR = Errno (CONST_EINTR)
203 eINVAL = Errno (CONST_EINVAL)
204 eIO = Errno (CONST_EIO)
205 eISCONN = Errno (CONST_EISCONN)
206 eISDIR = Errno (CONST_EISDIR)
207 eLOOP = Errno (CONST_ELOOP)
208 eMFILE = Errno (CONST_EMFILE)
209 eMLINK = Errno (CONST_EMLINK)
210 eMSGSIZE = Errno (CONST_EMSGSIZE)
211 eMULTIHOP = Errno (CONST_EMULTIHOP)
212 eNAMETOOLONG = Errno (CONST_ENAMETOOLONG)
213 eNETDOWN = Errno (CONST_ENETDOWN)
214 eNETRESET = Errno (CONST_ENETRESET)
215 eNETUNREACH = Errno (CONST_ENETUNREACH)
216 eNFILE = Errno (CONST_ENFILE)
217 eNOBUFS = Errno (CONST_ENOBUFS)
218 eNODATA = Errno (CONST_ENODATA)
219 eNODEV = Errno (CONST_ENODEV)
220 eNOENT = Errno (CONST_ENOENT)
221 eNOEXEC = Errno (CONST_ENOEXEC)
222 eNOLCK = Errno (CONST_ENOLCK)
223 eNOLINK = Errno (CONST_ENOLINK)
224 eNOMEM = Errno (CONST_ENOMEM)
225 eNOMSG = Errno (CONST_ENOMSG)
226 eNONET = Errno (CONST_ENONET)
227 eNOPROTOOPT = Errno (CONST_ENOPROTOOPT)
228 eNOSPC = Errno (CONST_ENOSPC)
229 eNOSR = Errno (CONST_ENOSR)
230 eNOSTR = Errno (CONST_ENOSTR)
231 eNOSYS = Errno (CONST_ENOSYS)
232 eNOTBLK = Errno (CONST_ENOTBLK)
233 eNOTCONN = Errno (CONST_ENOTCONN)
234 eNOTDIR = Errno (CONST_ENOTDIR)
235 eNOTEMPTY = Errno (CONST_ENOTEMPTY)
236 eNOTSOCK = Errno (CONST_ENOTSOCK)
237 eNOTTY = Errno (CONST_ENOTTY)
238 eNXIO = Errno (CONST_ENXIO)
239 eOPNOTSUPP = Errno (CONST_EOPNOTSUPP)
240 ePERM = Errno (CONST_EPERM)
241 ePFNOSUPPORT = Errno (CONST_EPFNOSUPPORT)
242 ePIPE = Errno (CONST_EPIPE)
243 ePROCLIM = Errno (CONST_EPROCLIM)
244 ePROCUNAVAIL = Errno (CONST_EPROCUNAVAIL)
245 ePROGMISMATCH = Errno (CONST_EPROGMISMATCH)
246 ePROGUNAVAIL = Errno (CONST_EPROGUNAVAIL)
247 ePROTO = Errno (CONST_EPROTO)
248 ePROTONOSUPPORT = Errno (CONST_EPROTONOSUPPORT)
249 ePROTOTYPE = Errno (CONST_EPROTOTYPE)
250 eRANGE = Errno (CONST_ERANGE)
251 eREMCHG = Errno (CONST_EREMCHG)
252 eREMOTE = Errno (CONST_EREMOTE)
253 eROFS = Errno (CONST_EROFS)
254 eRPCMISMATCH = Errno (CONST_ERPCMISMATCH)
255 eRREMOTE = Errno (CONST_ERREMOTE)
256 eSHUTDOWN = Errno (CONST_ESHUTDOWN)
257 eSOCKTNOSUPPORT = Errno (CONST_ESOCKTNOSUPPORT)
258 eSPIPE = Errno (CONST_ESPIPE)
259 eSRCH = Errno (CONST_ESRCH)
260 eSRMNT = Errno (CONST_ESRMNT)
261 eSTALE = Errno (CONST_ESTALE)
262 eTIME = Errno (CONST_ETIME)
263 eTIMEDOUT = Errno (CONST_ETIMEDOUT)
264 eTOOMANYREFS = Errno (CONST_ETOOMANYREFS)
265 eTXTBSY = Errno (CONST_ETXTBSY)
266 eUSERS = Errno (CONST_EUSERS)
267 eWOULDBLOCK = Errno (CONST_EWOULDBLOCK)
268 eXDEV = Errno (CONST_EXDEV)
271 -- | Yield 'True' if the given 'Errno' value is valid on the system.
272 -- This implies that the 'Eq' instance of 'Errno' is also system dependent
273 -- as it is only defined for valid values of 'Errno'.
275 isValidErrno :: Errno -> Bool
277 -- the configure script sets all invalid "errno"s to -1
279 isValidErrno (Errno errno) = errno /= -1
282 -- access to the current thread's "errno" value
283 -- --------------------------------------------
285 -- | Get the current value of @errno@ in the current thread.
289 -- We must call a C function to get the value of errno in general. On
290 -- threaded systems, errno is hidden behind a C macro so that each OS
291 -- thread gets its own copy.
293 getErrno = do e <- peek _errno; return (Errno e)
294 foreign import ccall unsafe "errno.h &errno" _errno :: Ptr CInt
296 getErrno = do e <- get_errno; return (Errno e)
297 foreign import ccall unsafe "HsBase.h __hscore_get_errno" get_errno :: IO CInt
300 -- | Reset the current thread\'s @errno@ value to 'eOK'.
304 -- Again, setting errno has to be done via a C function.
306 resetErrno = poke _errno 0
308 resetErrno = set_errno 0
309 foreign import ccall unsafe "HsBase.h __hscore_set_errno" set_errno :: CInt -> IO ()
312 -- throw current "errno" value
313 -- ---------------------------
315 -- | Throw an 'IOError' corresponding to the current value of 'getErrno'.
317 throwErrno :: String -- ^ textual description of the error location
322 ioError (errnoToIOError loc errno Nothing Nothing)
325 -- guards for IO operations that may fail
326 -- --------------------------------------
328 -- | Throw an 'IOError' corresponding to the current value of 'getErrno'
329 -- if the result value of the 'IO' action meets the given predicate.
331 throwErrnoIf :: (a -> Bool) -- ^ predicate to apply to the result value
332 -- of the 'IO' operation
333 -> String -- ^ textual description of the location
334 -> IO a -- ^ the 'IO' operation to be executed
336 throwErrnoIf pred loc f =
339 if pred res then throwErrno loc else return res
341 -- | as 'throwErrnoIf', but discards the result of the 'IO' action after
344 throwErrnoIf_ :: (a -> Bool) -> String -> IO a -> IO ()
345 throwErrnoIf_ pred loc f = void $ throwErrnoIf pred loc f
347 -- | as 'throwErrnoIf', but retry the 'IO' action when it yields the
348 -- error code 'eINTR' - this amounts to the standard retry loop for
349 -- interrupted POSIX system calls.
351 throwErrnoIfRetry :: (a -> Bool) -> String -> IO a -> IO a
352 throwErrnoIfRetry pred loc f =
359 then throwErrnoIfRetry pred loc f
363 -- | as 'throwErrnoIfRetry', but additionally if the operation
364 -- yields the error code 'eAGAIN' or 'eWOULDBLOCK', an alternative
365 -- action is executed before retrying.
367 throwErrnoIfRetryMayBlock
368 :: (a -> Bool) -- ^ predicate to apply to the result value
369 -- of the 'IO' operation
370 -> String -- ^ textual description of the location
371 -> IO a -- ^ the 'IO' operation to be executed
372 -> IO b -- ^ action to execute before retrying if
373 -- an immediate retry would block
375 throwErrnoIfRetryMayBlock pred loc f on_block =
382 then throwErrnoIfRetryMayBlock pred loc f on_block
383 else if err == eWOULDBLOCK || err == eAGAIN
384 then do _ <- on_block
385 throwErrnoIfRetryMayBlock pred loc f on_block
389 -- | as 'throwErrnoIfRetry', but discards the result.
391 throwErrnoIfRetry_ :: (a -> Bool) -> String -> IO a -> IO ()
392 throwErrnoIfRetry_ pred loc f = void $ throwErrnoIfRetry pred loc f
394 -- | as 'throwErrnoIfRetryMayBlock', but discards the result.
396 throwErrnoIfRetryMayBlock_ :: (a -> Bool) -> String -> IO a -> IO b -> IO ()
397 throwErrnoIfRetryMayBlock_ pred loc f on_block
398 = void $ throwErrnoIfRetryMayBlock pred loc f on_block
400 -- | Throw an 'IOError' corresponding to the current value of 'getErrno'
401 -- if the 'IO' action returns a result of @-1@.
403 throwErrnoIfMinus1 :: Num a => String -> IO a -> IO a
404 throwErrnoIfMinus1 = throwErrnoIf (== -1)
406 -- | as 'throwErrnoIfMinus1', but discards the result.
408 throwErrnoIfMinus1_ :: Num a => String -> IO a -> IO ()
409 throwErrnoIfMinus1_ = throwErrnoIf_ (== -1)
411 -- | Throw an 'IOError' corresponding to the current value of 'getErrno'
412 -- if the 'IO' action returns a result of @-1@, but retries in case of
413 -- an interrupted operation.
415 throwErrnoIfMinus1Retry :: Num a => String -> IO a -> IO a
416 throwErrnoIfMinus1Retry = throwErrnoIfRetry (== -1)
418 -- | as 'throwErrnoIfMinus1', but discards the result.
420 throwErrnoIfMinus1Retry_ :: Num a => String -> IO a -> IO ()
421 throwErrnoIfMinus1Retry_ = throwErrnoIfRetry_ (== -1)
423 -- | as 'throwErrnoIfMinus1Retry', but checks for operations that would block.
425 throwErrnoIfMinus1RetryMayBlock :: Num a => String -> IO a -> IO b -> IO a
426 throwErrnoIfMinus1RetryMayBlock = throwErrnoIfRetryMayBlock (== -1)
428 -- | as 'throwErrnoIfMinus1RetryMayBlock', but discards the result.
430 throwErrnoIfMinus1RetryMayBlock_ :: Num a => String -> IO a -> IO b -> IO ()
431 throwErrnoIfMinus1RetryMayBlock_ = throwErrnoIfRetryMayBlock_ (== -1)
433 -- | Throw an 'IOError' corresponding to the current value of 'getErrno'
434 -- if the 'IO' action returns 'nullPtr'.
436 throwErrnoIfNull :: String -> IO (Ptr a) -> IO (Ptr a)
437 throwErrnoIfNull = throwErrnoIf (== nullPtr)
439 -- | Throw an 'IOError' corresponding to the current value of 'getErrno'
440 -- if the 'IO' action returns 'nullPtr',
441 -- but retry in case of an interrupted operation.
443 throwErrnoIfNullRetry :: String -> IO (Ptr a) -> IO (Ptr a)
444 throwErrnoIfNullRetry = throwErrnoIfRetry (== nullPtr)
446 -- | as 'throwErrnoIfNullRetry', but checks for operations that would block.
448 throwErrnoIfNullRetryMayBlock :: String -> IO (Ptr a) -> IO b -> IO (Ptr a)
449 throwErrnoIfNullRetryMayBlock = throwErrnoIfRetryMayBlock (== nullPtr)
451 -- | as 'throwErrno', but exceptions include the given path when appropriate.
453 throwErrnoPath :: String -> FilePath -> IO a
454 throwErrnoPath loc path =
457 ioError (errnoToIOError loc errno Nothing (Just path))
459 -- | as 'throwErrnoIf', but exceptions include the given path when
462 throwErrnoPathIf :: (a -> Bool) -> String -> FilePath -> IO a -> IO a
463 throwErrnoPathIf pred loc path f =
466 if pred res then throwErrnoPath loc path else return res
468 -- | as 'throwErrnoIf_', but exceptions include the given path when
471 throwErrnoPathIf_ :: (a -> Bool) -> String -> FilePath -> IO a -> IO ()
472 throwErrnoPathIf_ pred loc path f = void $ throwErrnoPathIf pred loc path f
474 -- | as 'throwErrnoIfNull', but exceptions include the given path when
477 throwErrnoPathIfNull :: String -> FilePath -> IO (Ptr a) -> IO (Ptr a)
478 throwErrnoPathIfNull = throwErrnoPathIf (== nullPtr)
480 -- | as 'throwErrnoIfMinus1', but exceptions include the given path when
483 throwErrnoPathIfMinus1 :: Num a => String -> FilePath -> IO a -> IO a
484 throwErrnoPathIfMinus1 = throwErrnoPathIf (== -1)
486 -- | as 'throwErrnoIfMinus1_', but exceptions include the given path when
489 throwErrnoPathIfMinus1_ :: Num a => String -> FilePath -> IO a -> IO ()
490 throwErrnoPathIfMinus1_ = throwErrnoPathIf_ (== -1)
492 -- conversion of an "errno" value into IO error
493 -- --------------------------------------------
495 -- | Construct an 'IOError' based on the given 'Errno' value.
496 -- The optional information can be used to improve the accuracy of
499 errnoToIOError :: String -- ^ the location where the error occurred
500 -> Errno -- ^ the error number
501 -> Maybe Handle -- ^ optional handle associated with the error
502 -> Maybe String -- ^ optional filename associated with the error
504 errnoToIOError loc errno maybeHdl maybeName = unsafePerformIO $ do
505 str <- strerror errno >>= peekCString
506 #if __GLASGOW_HASKELL__
507 return (IOError maybeHdl errType loc str (Just errno') maybeName)
511 | errno == eOK = OtherError
512 | errno == e2BIG = ResourceExhausted
513 | errno == eACCES = PermissionDenied
514 | errno == eADDRINUSE = ResourceBusy
515 | errno == eADDRNOTAVAIL = UnsupportedOperation
516 | errno == eADV = OtherError
517 | errno == eAFNOSUPPORT = UnsupportedOperation
518 | errno == eAGAIN = ResourceExhausted
519 | errno == eALREADY = AlreadyExists
520 | errno == eBADF = InvalidArgument
521 | errno == eBADMSG = InappropriateType
522 | errno == eBADRPC = OtherError
523 | errno == eBUSY = ResourceBusy
524 | errno == eCHILD = NoSuchThing
525 | errno == eCOMM = ResourceVanished
526 | errno == eCONNABORTED = OtherError
527 | errno == eCONNREFUSED = NoSuchThing
528 | errno == eCONNRESET = ResourceVanished
529 | errno == eDEADLK = ResourceBusy
530 | errno == eDESTADDRREQ = InvalidArgument
531 | errno == eDIRTY = UnsatisfiedConstraints
532 | errno == eDOM = InvalidArgument
533 | errno == eDQUOT = PermissionDenied
534 | errno == eEXIST = AlreadyExists
535 | errno == eFAULT = OtherError
536 | errno == eFBIG = PermissionDenied
537 | errno == eFTYPE = InappropriateType
538 | errno == eHOSTDOWN = NoSuchThing
539 | errno == eHOSTUNREACH = NoSuchThing
540 | errno == eIDRM = ResourceVanished
541 | errno == eILSEQ = InvalidArgument
542 | errno == eINPROGRESS = AlreadyExists
543 | errno == eINTR = Interrupted
544 | errno == eINVAL = InvalidArgument
545 | errno == eIO = HardwareFault
546 | errno == eISCONN = AlreadyExists
547 | errno == eISDIR = InappropriateType
548 | errno == eLOOP = InvalidArgument
549 | errno == eMFILE = ResourceExhausted
550 | errno == eMLINK = ResourceExhausted
551 | errno == eMSGSIZE = ResourceExhausted
552 | errno == eMULTIHOP = UnsupportedOperation
553 | errno == eNAMETOOLONG = InvalidArgument
554 | errno == eNETDOWN = ResourceVanished
555 | errno == eNETRESET = ResourceVanished
556 | errno == eNETUNREACH = NoSuchThing
557 | errno == eNFILE = ResourceExhausted
558 | errno == eNOBUFS = ResourceExhausted
559 | errno == eNODATA = NoSuchThing
560 | errno == eNODEV = UnsupportedOperation
561 | errno == eNOENT = NoSuchThing
562 | errno == eNOEXEC = InvalidArgument
563 | errno == eNOLCK = ResourceExhausted
564 | errno == eNOLINK = ResourceVanished
565 | errno == eNOMEM = ResourceExhausted
566 | errno == eNOMSG = NoSuchThing
567 | errno == eNONET = NoSuchThing
568 | errno == eNOPROTOOPT = UnsupportedOperation
569 | errno == eNOSPC = ResourceExhausted
570 | errno == eNOSR = ResourceExhausted
571 | errno == eNOSTR = InvalidArgument
572 | errno == eNOSYS = UnsupportedOperation
573 | errno == eNOTBLK = InvalidArgument
574 | errno == eNOTCONN = InvalidArgument
575 | errno == eNOTDIR = InappropriateType
576 | errno == eNOTEMPTY = UnsatisfiedConstraints
577 | errno == eNOTSOCK = InvalidArgument
578 | errno == eNOTTY = IllegalOperation
579 | errno == eNXIO = NoSuchThing
580 | errno == eOPNOTSUPP = UnsupportedOperation
581 | errno == ePERM = PermissionDenied
582 | errno == ePFNOSUPPORT = UnsupportedOperation
583 | errno == ePIPE = ResourceVanished
584 | errno == ePROCLIM = PermissionDenied
585 | errno == ePROCUNAVAIL = UnsupportedOperation
586 | errno == ePROGMISMATCH = ProtocolError
587 | errno == ePROGUNAVAIL = UnsupportedOperation
588 | errno == ePROTO = ProtocolError
589 | errno == ePROTONOSUPPORT = ProtocolError
590 | errno == ePROTOTYPE = ProtocolError
591 | errno == eRANGE = UnsupportedOperation
592 | errno == eREMCHG = ResourceVanished
593 | errno == eREMOTE = IllegalOperation
594 | errno == eROFS = PermissionDenied
595 | errno == eRPCMISMATCH = ProtocolError
596 | errno == eRREMOTE = IllegalOperation
597 | errno == eSHUTDOWN = IllegalOperation
598 | errno == eSOCKTNOSUPPORT = UnsupportedOperation
599 | errno == eSPIPE = UnsupportedOperation
600 | errno == eSRCH = NoSuchThing
601 | errno == eSRMNT = UnsatisfiedConstraints
602 | errno == eSTALE = ResourceVanished
603 | errno == eTIME = TimeExpired
604 | errno == eTIMEDOUT = TimeExpired
605 | errno == eTOOMANYREFS = ResourceExhausted
606 | errno == eTXTBSY = ResourceBusy
607 | errno == eUSERS = ResourceExhausted
608 | errno == eWOULDBLOCK = OtherError
609 | errno == eXDEV = UnsupportedOperation
610 | otherwise = OtherError
612 return (userError (loc ++ ": " ++ str ++ maybe "" (": "++) maybeName))
615 foreign import ccall unsafe "string.h" strerror :: Errno -> IO (Ptr CChar)