{-# LANGUAGE Trustworthy #-}
{-# LANGUAGE CPP
, NoImplicitPrelude
, ExistentialQuantification
#-}
{-# OPTIONS_GHC -funbox-strict-fields #-}
{-# OPTIONS_HADDOCK not-home #-}
module GHC.Internal.IO.Handle.Types (
Handle(..), Handle__(..), showHandle,
checkHandleInvariants,
BufferList(..),
HandleType(..),
isReadableHandleType, isWritableHandleType, isReadWriteHandleType,
isAppendHandleType,
BufferMode(..),
BufferCodec(..),
NewlineMode(..), Newline(..), nativeNewline,
universalNewlineMode, noNewlineTranslation, nativeNewlineMode
) where
#undef DEBUG
import GHC.Internal.Base (String, return, (.))
import GHC.Internal.Classes (Eq(..), Ord(..))
import GHC.Internal.Maybe (Maybe)
import GHC.Internal.MVar
import GHC.Internal.IO
import GHC.Internal.IO.Buffer
import GHC.Internal.IO.BufferedIO
import GHC.Internal.IO.Encoding.Types
import GHC.Internal.IORef
import GHC.Internal.Show
import GHC.Internal.Read
import GHC.Internal.Types (Bool(..), Int)
import GHC.Internal.Word
import GHC.Internal.IO.Device
import GHC.Internal.Data.Typeable
#if defined(DEBUG)
import GHC.Internal.Control.Monad
#endif
data Handle
= FileHandle
FilePath
!(MVar Handle__)
| DuplexHandle
FilePath
!(MVar Handle__)
!(MVar Handle__)
instance Eq Handle where
(FileHandle FilePath
_ MVar Handle__
h1) == :: Handle -> Handle -> Bool
== (FileHandle FilePath
_ MVar Handle__
h2) = MVar Handle__
h1 MVar Handle__ -> MVar Handle__ -> Bool
forall a. Eq a => a -> a -> Bool
== MVar Handle__
h2
(DuplexHandle FilePath
_ MVar Handle__
h1 MVar Handle__
_) == (DuplexHandle FilePath
_ MVar Handle__
h2 MVar Handle__
_) = MVar Handle__
h1 MVar Handle__ -> MVar Handle__ -> Bool
forall a. Eq a => a -> a -> Bool
== MVar Handle__
h2
Handle
_ == Handle
_ = Bool
False
data Handle__
= forall dev enc_state dec_state . (RawIO dev, IODevice dev, BufferedIO dev, Typeable dev) =>
Handle__ {
()
haDevice :: !dev,
Handle__ -> HandleType
haType :: HandleType,
Handle__ -> IORef (Buffer Word8)
haByteBuffer :: !(IORef (Buffer Word8)),
Handle__ -> BufferMode
haBufferMode :: BufferMode,
()
haLastDecode :: !(IORef (dec_state, Buffer Word8)),
Handle__ -> IORef (Buffer CharBufElem)
haCharBuffer :: !(IORef (Buffer CharBufElem)),
Handle__ -> IORef (BufferList CharBufElem)
haBuffers :: !(IORef (BufferList CharBufElem)),
()
haEncoder :: Maybe (TextEncoder enc_state),
()
haDecoder :: Maybe (TextDecoder dec_state),
Handle__ -> Maybe TextEncoding
haCodec :: Maybe TextEncoding,
Handle__ -> Newline
haInputNL :: Newline,
Handle__ -> Newline
haOutputNL :: Newline,
Handle__ -> Maybe (MVar Handle__)
haOtherSide :: Maybe (MVar Handle__)
}
data BufferList e
= BufferListNil
| BufferListCons (RawBuffer e) (BufferList e)
data HandleType
= ClosedHandle
| SemiClosedHandle
| ReadHandle
| WriteHandle
| AppendHandle
| ReadWriteHandle
isReadableHandleType :: HandleType -> Bool
isReadableHandleType :: HandleType -> Bool
isReadableHandleType HandleType
ReadHandle = Bool
True
isReadableHandleType HandleType
ReadWriteHandle = Bool
True
isReadableHandleType HandleType
_ = Bool
False
isWritableHandleType :: HandleType -> Bool
isWritableHandleType :: HandleType -> Bool
isWritableHandleType HandleType
AppendHandle = Bool
True
isWritableHandleType HandleType
WriteHandle = Bool
True
isWritableHandleType HandleType
ReadWriteHandle = Bool
True
isWritableHandleType HandleType
_ = Bool
False
isReadWriteHandleType :: HandleType -> Bool
isReadWriteHandleType :: HandleType -> Bool
isReadWriteHandleType ReadWriteHandle{} = Bool
True
isReadWriteHandleType HandleType
_ = Bool
False
isAppendHandleType :: HandleType -> Bool
isAppendHandleType :: HandleType -> Bool
isAppendHandleType HandleType
AppendHandle = Bool
True
isAppendHandleType HandleType
_ = Bool
False
checkHandleInvariants :: Handle__ -> IO ()
#if defined(DEBUG)
checkHandleInvariants h_ = do
bbuf <- readIORef (haByteBuffer h_)
checkBuffer bbuf
cbuf <- readIORef (haCharBuffer h_)
checkBuffer cbuf
when (isWriteBuffer cbuf && not (isEmptyBuffer cbuf)) $
errorWithoutStackTrace ("checkHandleInvariants: char write buffer non-empty: " ++
summaryBuffer bbuf ++ ", " ++ summaryBuffer cbuf)
when (isWriteBuffer bbuf /= isWriteBuffer cbuf) $
errorWithoutStackTrace ("checkHandleInvariants: buffer modes differ: " ++
summaryBuffer bbuf ++ ", " ++ summaryBuffer cbuf)
#else
checkHandleInvariants :: Handle__ -> IO ()
checkHandleInvariants Handle__
_ = () -> IO ()
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return ()
#endif
data BufferMode
= NoBuffering
| LineBuffering
| BlockBuffering (Maybe Int)
deriving ( BufferMode -> BufferMode -> Bool
(BufferMode -> BufferMode -> Bool)
-> (BufferMode -> BufferMode -> Bool) -> Eq BufferMode
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: BufferMode -> BufferMode -> Bool
== :: BufferMode -> BufferMode -> Bool
$c/= :: BufferMode -> BufferMode -> Bool
/= :: BufferMode -> BufferMode -> Bool
Eq
, Eq BufferMode
Eq BufferMode =>
(BufferMode -> BufferMode -> Ordering)
-> (BufferMode -> BufferMode -> Bool)
-> (BufferMode -> BufferMode -> Bool)
-> (BufferMode -> BufferMode -> Bool)
-> (BufferMode -> BufferMode -> Bool)
-> (BufferMode -> BufferMode -> BufferMode)
-> (BufferMode -> BufferMode -> BufferMode)
-> Ord BufferMode
BufferMode -> BufferMode -> Bool
BufferMode -> BufferMode -> Ordering
BufferMode -> BufferMode -> BufferMode
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: BufferMode -> BufferMode -> Ordering
compare :: BufferMode -> BufferMode -> Ordering
$c< :: BufferMode -> BufferMode -> Bool
< :: BufferMode -> BufferMode -> Bool
$c<= :: BufferMode -> BufferMode -> Bool
<= :: BufferMode -> BufferMode -> Bool
$c> :: BufferMode -> BufferMode -> Bool
> :: BufferMode -> BufferMode -> Bool
$c>= :: BufferMode -> BufferMode -> Bool
>= :: BufferMode -> BufferMode -> Bool
$cmax :: BufferMode -> BufferMode -> BufferMode
max :: BufferMode -> BufferMode -> BufferMode
$cmin :: BufferMode -> BufferMode -> BufferMode
min :: BufferMode -> BufferMode -> BufferMode
Ord
, ReadPrec [BufferMode]
ReadPrec BufferMode
Int -> ReadS BufferMode
ReadS [BufferMode]
(Int -> ReadS BufferMode)
-> ReadS [BufferMode]
-> ReadPrec BufferMode
-> ReadPrec [BufferMode]
-> Read BufferMode
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS BufferMode
readsPrec :: Int -> ReadS BufferMode
$creadList :: ReadS [BufferMode]
readList :: ReadS [BufferMode]
$creadPrec :: ReadPrec BufferMode
readPrec :: ReadPrec BufferMode
$creadListPrec :: ReadPrec [BufferMode]
readListPrec :: ReadPrec [BufferMode]
Read
, Int -> BufferMode -> ShowS
[BufferMode] -> ShowS
BufferMode -> FilePath
(Int -> BufferMode -> ShowS)
-> (BufferMode -> FilePath)
-> ([BufferMode] -> ShowS)
-> Show BufferMode
forall a.
(Int -> a -> ShowS) -> (a -> FilePath) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> BufferMode -> ShowS
showsPrec :: Int -> BufferMode -> ShowS
$cshow :: BufferMode -> FilePath
show :: BufferMode -> FilePath
$cshowList :: [BufferMode] -> ShowS
showList :: [BufferMode] -> ShowS
Show
)
data Newline = LF
| CRLF
deriving ( Newline -> Newline -> Bool
(Newline -> Newline -> Bool)
-> (Newline -> Newline -> Bool) -> Eq Newline
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: Newline -> Newline -> Bool
== :: Newline -> Newline -> Bool
$c/= :: Newline -> Newline -> Bool
/= :: Newline -> Newline -> Bool
Eq
, Eq Newline
Eq Newline =>
(Newline -> Newline -> Ordering)
-> (Newline -> Newline -> Bool)
-> (Newline -> Newline -> Bool)
-> (Newline -> Newline -> Bool)
-> (Newline -> Newline -> Bool)
-> (Newline -> Newline -> Newline)
-> (Newline -> Newline -> Newline)
-> Ord Newline
Newline -> Newline -> Bool
Newline -> Newline -> Ordering
Newline -> Newline -> Newline
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: Newline -> Newline -> Ordering
compare :: Newline -> Newline -> Ordering
$c< :: Newline -> Newline -> Bool
< :: Newline -> Newline -> Bool
$c<= :: Newline -> Newline -> Bool
<= :: Newline -> Newline -> Bool
$c> :: Newline -> Newline -> Bool
> :: Newline -> Newline -> Bool
$c>= :: Newline -> Newline -> Bool
>= :: Newline -> Newline -> Bool
$cmax :: Newline -> Newline -> Newline
max :: Newline -> Newline -> Newline
$cmin :: Newline -> Newline -> Newline
min :: Newline -> Newline -> Newline
Ord
, ReadPrec [Newline]
ReadPrec Newline
Int -> ReadS Newline
ReadS [Newline]
(Int -> ReadS Newline)
-> ReadS [Newline]
-> ReadPrec Newline
-> ReadPrec [Newline]
-> Read Newline
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS Newline
readsPrec :: Int -> ReadS Newline
$creadList :: ReadS [Newline]
readList :: ReadS [Newline]
$creadPrec :: ReadPrec Newline
readPrec :: ReadPrec Newline
$creadListPrec :: ReadPrec [Newline]
readListPrec :: ReadPrec [Newline]
Read
, Int -> Newline -> ShowS
[Newline] -> ShowS
Newline -> FilePath
(Int -> Newline -> ShowS)
-> (Newline -> FilePath) -> ([Newline] -> ShowS) -> Show Newline
forall a.
(Int -> a -> ShowS) -> (a -> FilePath) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> Newline -> ShowS
showsPrec :: Int -> Newline -> ShowS
$cshow :: Newline -> FilePath
show :: Newline -> FilePath
$cshowList :: [Newline] -> ShowS
showList :: [Newline] -> ShowS
Show
)
data NewlineMode
= NewlineMode { NewlineMode -> Newline
inputNL :: Newline,
NewlineMode -> Newline
outputNL :: Newline
}
deriving ( NewlineMode -> NewlineMode -> Bool
(NewlineMode -> NewlineMode -> Bool)
-> (NewlineMode -> NewlineMode -> Bool) -> Eq NewlineMode
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: NewlineMode -> NewlineMode -> Bool
== :: NewlineMode -> NewlineMode -> Bool
$c/= :: NewlineMode -> NewlineMode -> Bool
/= :: NewlineMode -> NewlineMode -> Bool
Eq
, Eq NewlineMode
Eq NewlineMode =>
(NewlineMode -> NewlineMode -> Ordering)
-> (NewlineMode -> NewlineMode -> Bool)
-> (NewlineMode -> NewlineMode -> Bool)
-> (NewlineMode -> NewlineMode -> Bool)
-> (NewlineMode -> NewlineMode -> Bool)
-> (NewlineMode -> NewlineMode -> NewlineMode)
-> (NewlineMode -> NewlineMode -> NewlineMode)
-> Ord NewlineMode
NewlineMode -> NewlineMode -> Bool
NewlineMode -> NewlineMode -> Ordering
NewlineMode -> NewlineMode -> NewlineMode
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: NewlineMode -> NewlineMode -> Ordering
compare :: NewlineMode -> NewlineMode -> Ordering
$c< :: NewlineMode -> NewlineMode -> Bool
< :: NewlineMode -> NewlineMode -> Bool
$c<= :: NewlineMode -> NewlineMode -> Bool
<= :: NewlineMode -> NewlineMode -> Bool
$c> :: NewlineMode -> NewlineMode -> Bool
> :: NewlineMode -> NewlineMode -> Bool
$c>= :: NewlineMode -> NewlineMode -> Bool
>= :: NewlineMode -> NewlineMode -> Bool
$cmax :: NewlineMode -> NewlineMode -> NewlineMode
max :: NewlineMode -> NewlineMode -> NewlineMode
$cmin :: NewlineMode -> NewlineMode -> NewlineMode
min :: NewlineMode -> NewlineMode -> NewlineMode
Ord
, ReadPrec [NewlineMode]
ReadPrec NewlineMode
Int -> ReadS NewlineMode
ReadS [NewlineMode]
(Int -> ReadS NewlineMode)
-> ReadS [NewlineMode]
-> ReadPrec NewlineMode
-> ReadPrec [NewlineMode]
-> Read NewlineMode
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS NewlineMode
readsPrec :: Int -> ReadS NewlineMode
$creadList :: ReadS [NewlineMode]
readList :: ReadS [NewlineMode]
$creadPrec :: ReadPrec NewlineMode
readPrec :: ReadPrec NewlineMode
$creadListPrec :: ReadPrec [NewlineMode]
readListPrec :: ReadPrec [NewlineMode]
Read
, Int -> NewlineMode -> ShowS
[NewlineMode] -> ShowS
NewlineMode -> FilePath
(Int -> NewlineMode -> ShowS)
-> (NewlineMode -> FilePath)
-> ([NewlineMode] -> ShowS)
-> Show NewlineMode
forall a.
(Int -> a -> ShowS) -> (a -> FilePath) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> NewlineMode -> ShowS
showsPrec :: Int -> NewlineMode -> ShowS
$cshow :: NewlineMode -> FilePath
show :: NewlineMode -> FilePath
$cshowList :: [NewlineMode] -> ShowS
showList :: [NewlineMode] -> ShowS
Show
)
nativeNewline :: Newline
#if defined(mingw32_HOST_OS)
nativeNewline = CRLF
#else
nativeNewline :: Newline
nativeNewline = Newline
LF
#endif
universalNewlineMode :: NewlineMode
universalNewlineMode :: NewlineMode
universalNewlineMode = NewlineMode { inputNL :: Newline
inputNL = Newline
CRLF,
outputNL :: Newline
outputNL = Newline
nativeNewline }
nativeNewlineMode :: NewlineMode
nativeNewlineMode :: NewlineMode
nativeNewlineMode = NewlineMode { inputNL :: Newline
inputNL = Newline
nativeNewline,
outputNL :: Newline
outputNL = Newline
nativeNewline }
noNewlineTranslation :: NewlineMode
noNewlineTranslation :: NewlineMode
noNewlineTranslation = NewlineMode { inputNL :: Newline
inputNL = Newline
LF, outputNL :: Newline
outputNL = Newline
LF }
instance Show HandleType where
showsPrec :: Int -> HandleType -> ShowS
showsPrec Int
_ HandleType
t =
case HandleType
t of
HandleType
ClosedHandle -> FilePath -> ShowS
showString FilePath
"closed"
HandleType
SemiClosedHandle -> FilePath -> ShowS
showString FilePath
"semi-closed"
HandleType
ReadHandle -> FilePath -> ShowS
showString FilePath
"readable"
HandleType
WriteHandle -> FilePath -> ShowS
showString FilePath
"writable"
HandleType
AppendHandle -> FilePath -> ShowS
showString FilePath
"writable (append)"
HandleType
ReadWriteHandle -> FilePath -> ShowS
showString FilePath
"read-writable"
instance Show Handle where
showsPrec :: Int -> Handle -> ShowS
showsPrec Int
_ (FileHandle FilePath
file MVar Handle__
_) = FilePath -> ShowS
showHandle FilePath
file
showsPrec Int
_ (DuplexHandle FilePath
file MVar Handle__
_ MVar Handle__
_) = FilePath -> ShowS
showHandle FilePath
file
showHandle :: FilePath -> String -> String
showHandle :: FilePath -> ShowS
showHandle FilePath
file = FilePath -> ShowS
showString FilePath
"{handle: " ShowS -> ShowS -> ShowS
forall b c a. (b -> c) -> (a -> b) -> a -> c
. FilePath -> ShowS
showString FilePath
file ShowS -> ShowS -> ShowS
forall b c a. (b -> c) -> (a -> b) -> a -> c
. FilePath -> ShowS
showString FilePath
"}"