{-# LANGUAGE CPP #-}
#if __GLASGOW_HASKELL__ >= 701
{-# LANGUAGE Trustworthy #-}
#endif
module Data.Binary (
Binary(..)
#ifdef GENERICS
, GBinary(..)
#endif
, Get
, Put
, putWord8
, getWord8
, encode
, decode
, decodeOrFail
, encodeFile
, decodeFile
, decodeFileOrFail
, module Data.Word
) where
import Data.Word
import Data.Binary.Class
import Data.Binary.Put
import Data.Binary.Get
#ifdef GENERICS
import Data.Binary.Generic ()
#endif
import qualified Data.ByteString as B ( hGet, length )
import Data.ByteString.Lazy (ByteString)
import qualified Data.ByteString.Lazy as L
import qualified Data.ByteString.Lazy.Internal as L ( defaultChunkSize )
import System.IO ( withBinaryFile, IOMode(ReadMode) )
encode :: Binary a => a -> ByteString
encode = runPut . put
{-# INLINE encode #-}
decode :: Binary a => ByteString -> a
decode = runGet get
decodeOrFail :: Binary a => L.ByteString
-> Either (L.ByteString, ByteOffset, String)
(L.ByteString, ByteOffset, a)
decodeOrFail = runGetOrFail get
encodeFile :: Binary a => FilePath -> a -> IO ()
encodeFile f v = L.writeFile f (encode v)
decodeFile :: Binary a => FilePath -> IO a
decodeFile f = do
result <- decodeFileOrFail f
case result of
Right x -> return x
Left (_,str) -> error str
decodeFileOrFail :: Binary a => FilePath -> IO (Either (ByteOffset, String) a)
decodeFileOrFail f =
withBinaryFile f ReadMode $ \h -> do
feed (runGetIncremental get) h
where
feed (Done _ _ x) _ = return (Right x)
feed (Fail _ pos str) _ = return (Left (pos, str))
feed (Partial k) h = do
chunk <- B.hGet h L.defaultChunkSize
case B.length chunk of
0 -> feed (k Nothing) h
_ -> feed (k (Just chunk)) h