{-# LANGUAGE
    Strict
  , MagicHash
  , UnboxedTuples
  , AllowAmbiguousTypes
  , TypeApplications
  , CPP
  , PatternSynonyms
  #-}

{-# OPTIONS_GHC -Wno-redundant-bang-patterns #-}

module Agda.Utils.Serialize (
    Serialize(..)
  , serialize
  , deserialize
  , serializePure
  , deserializePure
  , ensure
  , Get(..)
  , Put(..)
  , putByteArray#
  , getByteArray#
  ) where

import GHC.Exts
import GHC.ForeignPtr
import GHC.Types
import GHC.Word
import GHC.Num.Integer
import System.IO.Unsafe

import qualified Data.ByteString as B
import qualified Data.ByteString.Internal as B
import qualified Data.Text as T
import qualified Data.Text.Array as T
import qualified Data.Text.Internal as T
import qualified Data.Text.Internal.Lazy as TL
import qualified Data.Text.Lazy as TL
import qualified Data.Text.Unsafe as T

import Data.Bits

#include "MachDeps.h"

#if MIN_VERSION_text(2,0,0)

pattern TArray :: ByteArray# -> T.Array
pattern $mTArray :: forall {r}. Array -> (ByteArray# -> r) -> ((# #) -> r) -> r
$bTArray :: ByteArray# -> Array
TArray arr = T.ByteArray arr
{-# INLINE TArray #-}
{-# COMPLETE TArray #-}

#else

pattern TArray :: ByteArray# -> T.Array
pattern TArray arr = T.Array arr
{-# INLINE TArray #-}
{-# COMPLETE TArray #-}

#endif

{-# INLINE tLengthWord8 #-}
tLengthWord8 :: T.Text -> Int
tLengthWord8 :: Text -> Int
tLengthWord8 (T.Text (TArray ByteArray#
arr) Int
_ Int
_) = Int# -> Int
I# (ByteArray# -> Int#
sizeofByteArray# ByteArray#
arr)

type RW = State# RealWorld
newtype Put = Put {Put -> Addr# -> RW -> (# Addr#, RW #)
unPut :: Addr# -> RW -> (# Addr#, RW #)}
newtype Get a = Get {forall a. Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
unGet :: Addr# -> Addr# -> RW -> (# Addr#, RW, a #)}

class Serialize a where
  size :: a -> Int
  put  :: a -> Put
  get  :: Get a

instance Semigroup Put where
  {-# INLINE (<>) #-}
  Put Addr# -> RW -> (# Addr#, RW #)
f <> :: Put -> Put -> Put
<> Put Addr# -> RW -> (# Addr#, RW #)
g = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Addr# -> RW -> (# Addr#, RW #)
f Addr#
p RW
s of (# Addr#
p, RW
s #) -> Addr# -> RW -> (# Addr#, RW #)
g Addr#
p RW
s

instance Monoid Put where
  {-# INLINE mempty #-}
  mempty :: Put
mempty = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> (# Addr#
p, RW
s #)
  {-# INLINE mappend #-}
  mappend :: Put -> Put -> Put
mappend = Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
(<>)
  mconcat :: [Put] -> Put
mconcat = [Char] -> [Put] -> Put
forall a. HasCallStack => [Char] -> a
error [Char]
"Put: mconcat not implemented"

instance Functor Get where
  {-# INLINE fmap #-}
  fmap :: forall a b. (a -> b) -> Get a -> Get b
fmap a -> b
f (Get Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
g) = (Addr# -> Addr# -> RW -> (# Addr#, RW, b #)) -> Get b
forall a. (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
Get \Addr#
e Addr#
p RW
s -> case Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
g Addr#
e Addr#
p RW
s of
    (# Addr#
p, RW
s, a
a #) -> let b :: b
b = a -> b
f a
a in (# Addr#
p, RW
s, b
b #)

instance Applicative Get where
  {-# INLINE pure #-}
  pure :: forall a. a -> Get a
pure a
a = (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
forall a. (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
Get \Addr#
e Addr#
p RW
s -> (# Addr#
p, RW
s, a
a #)
  {-# INLINE (<*>) #-}
  Get Addr# -> Addr# -> RW -> (# Addr#, RW, a -> b #)
ff <*> :: forall a b. Get (a -> b) -> Get a -> Get b
<*> Get Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
fa = (Addr# -> Addr# -> RW -> (# Addr#, RW, b #)) -> Get b
forall a. (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
Get \Addr#
e Addr#
p RW
s -> case Addr# -> Addr# -> RW -> (# Addr#, RW, a -> b #)
ff Addr#
e Addr#
p RW
s of
    (# Addr#
p, RW
s, a -> b
f #) -> case Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
fa Addr#
e Addr#
p RW
s of
      (# Addr#
p, RW
s, a
a #) -> let b :: b
b = a -> b
f a
a in (# Addr#
p, RW
s, b
b #)

instance Monad Get where
  {-# INLINE return #-}
  return :: forall a. a -> Get a
return = a -> Get a
forall a. a -> Get a
forall (f :: * -> *) a. Applicative f => a -> f a
pure
  {-# INLINE (>>=) #-}
  Get Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
ma >>= :: forall a b. Get a -> (a -> Get b) -> Get b
>>= a -> Get b
f = (Addr# -> Addr# -> RW -> (# Addr#, RW, b #)) -> Get b
forall a. (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
Get \Addr#
e Addr#
p RW
s -> case Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
ma Addr#
e Addr#
p RW
s of
    (# Addr#
p, RW
s, a
a #) -> Get b -> Addr# -> Addr# -> RW -> (# Addr#, RW, b #)
forall a. Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
unGet (a -> Get b
f a
a) Addr#
e Addr#
p RW
s

-- ensure that we have N bytes to read.
ensure :: Int -> (Addr# -> Get a) -> Get a
ensure :: forall a. Int -> (Addr# -> Get a) -> Get a
ensure (I# Int#
n) Addr# -> Get a
k = (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
forall a. (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
Get \Addr#
e Addr#
p RW
s ->
  let p' :: Addr#
p' = Addr# -> Int# -> Addr#
plusAddr# Addr#
p Int#
n in
  case Addr# -> Addr# -> Int#
leAddr# Addr#
p' Addr#
e of
    Int#
1# -> Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
forall a. Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
unGet (Addr# -> Get a
k Addr#
p') Addr#
e Addr#
p RW
s
    Int#
_  -> [Char] -> (# Addr#, RW, a #)
forall a. HasCallStack => [Char] -> a
error [Char]
"deserialize: not enough input"
{-# INLINE ensure #-}

serialize :: Serialize a => a -> IO B.ByteString
serialize :: forall a. Serialize a => a -> IO ByteString
serialize a
a = do
  let sz :: Int
sz = a -> Int
forall a. Serialize a => a -> Int
size a
a
  fptr@(ForeignPtr addr fp) <- Int -> IO (ForeignPtr Word8)
forall a. Int -> IO (ForeignPtr a)
B.mallocByteString Int
sz
  str <- IO \RW
s -> ForeignPtrContents
-> RW -> (RW -> (# RW, ByteString #)) -> (# RW, ByteString #)
forall a d b. a -> State# d -> (State# d -> b) -> b
keepAlive# ForeignPtrContents
fp RW
s \RW
s -> case Put -> Addr# -> RW -> (# Addr#, RW #)
unPut (a -> Put
forall a. Serialize a => a -> Put
put a
a) Addr#
addr RW
s of
    (# Addr#
p, RW
s #) -> (# RW
s, ForeignPtr Word8 -> Int -> ByteString
B.BS ForeignPtr Word8
fptr (Int# -> Int
I# (Addr# -> Addr# -> Int#
minusAddr# Addr#
p Addr#
addr)) #)
  if B.length str == sz
    then pure str
    else error "serialize: impossible mismatch of computed and written size"

deserialize :: forall a. Serialize a => B.ByteString -> IO a
deserialize :: forall a. Serialize a => ByteString -> IO a
deserialize (B.BS (ForeignPtr Addr#
p ForeignPtrContents
fp) (I# Int#
l)) =
  (RW -> (# RW, a #)) -> IO a
forall a. (RW -> (# RW, a #)) -> IO a
IO \RW
s -> ForeignPtrContents -> RW -> (RW -> (# RW, a #)) -> (# RW, a #)
forall a d b. a -> State# d -> (State# d -> b) -> b
keepAlive# ForeignPtrContents
fp RW
s \RW
s ->
    let e :: Addr#
e = Addr# -> Int# -> Addr#
plusAddr# Addr#
p Int#
l in
    case Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
forall a. Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
unGet (forall a. Serialize a => Get a
get @a) (Addr# -> Int# -> Addr#
plusAddr# Addr#
p Int#
l) Addr#
p RW
s of
      (# Addr#
p, RW
s, a
a #) -> case Addr# -> Addr# -> Int#
ltAddr# Addr#
p Addr#
e of
        Int#
1# -> [Char] -> (# RW, a #)
forall a. HasCallStack => [Char] -> a
error [Char]
"deserialize: not all input was consumed"
        Int#
_  -> case Addr# -> Addr# -> Int#
eqAddr# Addr#
p Addr#
e of
          Int#
1# -> (# RW
s, a
a #)
          Int#
_  -> [Char] -> (# RW, a #)
forall a. HasCallStack => [Char] -> a
error [Char]
"deserialize: impossible out of bounds access"

serializePure :: Serialize a => a -> B.ByteString
serializePure :: forall a. Serialize a => a -> ByteString
serializePure a
a = IO ByteString -> ByteString
forall a. IO a -> a
unsafeDupablePerformIO (IO ByteString -> ByteString) -> IO ByteString -> ByteString
forall a b. (a -> b) -> a -> b
$ a -> IO ByteString
forall a. Serialize a => a -> IO ByteString
serialize a
a

deserializePure :: Serialize a => B.ByteString -> a
deserializePure :: forall a. Serialize a => ByteString -> a
deserializePure ByteString
str = IO a -> a
forall a. IO a -> a
unsafeDupablePerformIO (IO a -> a) -> IO a -> a
forall a b. (a -> b) -> a -> b
$ ByteString -> IO a
forall a. Serialize a => ByteString -> IO a
deserialize ByteString
str

testTrip :: forall a. Show a => Eq a => Serialize a => a -> IO ()
testTrip :: forall a. (Show a, Eq a, Serialize a) => a -> IO ()
testTrip a
a = do
  a' <- ByteString -> IO a
forall a. Serialize a => ByteString -> IO a
deserialize (ByteString -> IO a) -> IO ByteString -> IO a
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< a -> IO ByteString
forall a. Serialize a => a -> IO ByteString
serialize a
a
  print a'
  if a == a' then putStrLn "OK"
             else putStrLn "mismatch"

--------------------------------------------------------------------------------

instance Serialize () where
  size :: () -> Int
size ()
_ = Int
0
  put :: () -> Put
put ()
_ = Put
forall a. Monoid a => a
mempty
  get :: Get ()
get = () -> Get ()
forall a. a -> Get a
forall (f :: * -> *) a. Applicative f => a -> f a
pure ()

instance Serialize Int where
  {-# INLINE size #-}
  size :: Int -> Int
size Int
_ = SIZEOF_HSINT
  {-# INLINE put #-}
  put :: Int -> Put
put (I# Int#
n) = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Addr# -> Int# -> Int# -> RW -> RW
forall d. Addr# -> Int# -> Int# -> State# d -> State# d
writeIntOffAddr# Addr#
p Int#
0# Int#
n RW
s of
    RW
s -> (# Addr# -> Int# -> Addr#
plusAddr# Addr#
p SIZEOF_HSINT#, s #)
  {-# INLINE get #-}
  get :: Get Int
get = Int -> (Addr# -> Get Int) -> Get Int
forall a. Int -> (Addr# -> Get a) -> Get a
ensure SIZEOF_HSINT \p' -> Get \e p s ->
    case readIntOffAddr# p 0# s of
      (# s, n #) -> (# p', s, I# n #)

instance Serialize Double where
  {-# INLINE size #-}
  size :: Double -> Int
size Double
_ = SIZEOF_HSDOUBLE
  {-# INLINE put #-}
  put :: Double -> Put
put (D# Double#
n) = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Addr# -> Int# -> Double# -> RW -> RW
forall d. Addr# -> Int# -> Double# -> State# d -> State# d
writeDoubleOffAddr# Addr#
p Int#
0# Double#
n RW
s of
    RW
s -> (# Addr# -> Int# -> Addr#
plusAddr# Addr#
p SIZEOF_HSDOUBLE#, s #)
  {-# INLINE get #-}
  get :: Get Double
get = Int -> (Addr# -> Get Double) -> Get Double
forall a. Int -> (Addr# -> Get a) -> Get a
ensure SIZEOF_HSDOUBLE \p' -> Get \e p s -> case readDoubleOffAddr# p 0# s of
    (# s, n #) -> (# p', s, D# n #)

instance Serialize Word where
  {-# INLINE size #-}
  size :: Word -> Int
size Word
_ = SIZEOF_HSWORD
  {-# INLINE put #-}
  put :: Word -> Put
put (W# Word#
n) = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Addr# -> Int# -> Word# -> RW -> RW
forall d. Addr# -> Int# -> Word# -> State# d -> State# d
writeWordOffAddr# Addr#
p Int#
0# Word#
n RW
s of
    RW
s -> (# Addr# -> Int# -> Addr#
plusAddr# Addr#
p SIZEOF_HSWORD#, s #)
  {-# INLINE get #-}
  get :: Get Word
get = Int -> (Addr# -> Get Word) -> Get Word
forall a. Int -> (Addr# -> Get a) -> Get a
ensure SIZEOF_HSWORD \p' -> Get \e p s -> case readWordOffAddr# p 0# s of
    (# s, n #) -> (# p', s, W# n #)

instance Serialize Word8 where
  {-# INLINE size #-}
  size :: Word8 -> Int
size Word8
_ = SIZEOF_WORD8
  {-# INLINE put #-}
  put :: Word8 -> Put
put (W8# Word8#
n) = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Addr# -> Int# -> Word8# -> RW -> RW
forall d. Addr# -> Int# -> Word8# -> State# d -> State# d
writeWord8OffAddr# Addr#
p Int#
0# Word8#
n RW
s of
    RW
s -> (# Addr# -> Int# -> Addr#
plusAddr# Addr#
p SIZEOF_WORD8#, s #)
  {-# INLINE get #-}
  get :: Get Word8
get = Int -> (Addr# -> Get Word8) -> Get Word8
forall a. Int -> (Addr# -> Get a) -> Get a
ensure SIZEOF_WORD8 \p' -> Get \e p s -> case readWord8OffAddr# p 0# s of
    (# s, n #) -> (# p', s, W8# n #)

instance Serialize Word16 where
  {-# INLINE size #-}
  size :: Word16 -> Int
size Word16
_ = SIZEOF_WORD16
  {-# INLINE put #-}
  put :: Word16 -> Put
put (W16# Word16#
n) = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Addr# -> Int# -> Word16# -> RW -> RW
forall d. Addr# -> Int# -> Word16# -> State# d -> State# d
writeWord16OffAddr# Addr#
p Int#
0# Word16#
n RW
s of
    RW
s -> (# Addr# -> Int# -> Addr#
plusAddr# Addr#
p SIZEOF_WORD16#, s #)
  {-# INLINE get #-}
  get :: Get Word16
get = Int -> (Addr# -> Get Word16) -> Get Word16
forall a. Int -> (Addr# -> Get a) -> Get a
ensure SIZEOF_WORD16 \p' -> Get \e p s -> case readWord16OffAddr# p 0# s of
    (# s, n #) -> (# p', s, W16# n #)

instance Serialize Word32 where
  {-# INLINE size #-}
  size :: Word32 -> Int
size Word32
_ = SIZEOF_WORD32
  {-# INLINE put #-}
  put :: Word32 -> Put
put (W32# Word32#
n) = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Addr# -> Int# -> Word32# -> RW -> RW
forall d. Addr# -> Int# -> Word32# -> State# d -> State# d
writeWord32OffAddr# Addr#
p Int#
0# Word32#
n RW
s of
    RW
s -> (# Addr# -> Int# -> Addr#
plusAddr# Addr#
p SIZEOF_WORD32#, s #)
  {-# INLINE get #-}
  get :: Get Word32
get = Int -> (Addr# -> Get Word32) -> Get Word32
forall a. Int -> (Addr# -> Get a) -> Get a
ensure SIZEOF_WORD32 \p' -> Get \e p s -> case readWord32OffAddr# p 0# s of
    (# s, n #) -> (# p', s, W32# n #)

instance Serialize Word64 where
  {-# INLINE size #-}
  size :: Word64 -> Int
size Word64
_ = SIZEOF_WORD64
  {-# INLINE put #-}
  put :: Word64 -> Put
put (W64# Word64#
n) = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Addr# -> Int# -> Word64# -> RW -> RW
forall d. Addr# -> Int# -> Word64# -> State# d -> State# d
writeWord64OffAddr# Addr#
p Int#
0# Word64#
n RW
s of
    RW
s -> (# Addr# -> Int# -> Addr#
plusAddr# Addr#
p SIZEOF_WORD64#, s #)
  {-# INLINE get #-}
  get :: Get Word64
get = Int -> (Addr# -> Get Word64) -> Get Word64
forall a. Int -> (Addr# -> Get a) -> Get a
ensure SIZEOF_WORD64 \p' -> Get \e p s -> case readWord64OffAddr# p 0# s of
    (# s, n #) -> (# p', s, W64# n #)

instance Serialize Char where
  {-# INLINE size #-}
  size :: Char -> Int
size Char
_ = SIZEOF_HSCHAR
  {-# INLINE put #-}
  put :: Char -> Put
put (C# Char#
n) = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Addr# -> Int# -> Char# -> RW -> RW
forall d. Addr# -> Int# -> Char# -> State# d -> State# d
writeWideCharOffAddr# Addr#
p Int#
0# Char#
n RW
s of
    RW
s -> (# Addr# -> Int# -> Addr#
plusAddr# Addr#
p SIZEOF_HSCHAR#, s #)
  {-# INLINE get #-}
  get :: Get Char
get = Int -> (Addr# -> Get Char) -> Get Char
forall a. Int -> (Addr# -> Get a) -> Get a
ensure SIZEOF_HSCHAR \p' -> Get \e p s -> case readWideCharOffAddr# p 0# s of
    (# s, n #) -> (# p', s, C# n #)

instance Serialize a => Serialize [a] where
  size :: [a] -> Int
size = Int -> [a] -> Int
go (Int -> Int
forall a. Serialize a => a -> Int
size (Int
0::Int)) where
    go :: Int -> [a] -> Int
    go :: Int -> [a] -> Int
go Int
acc []     = Int
acc
    go Int
acc (a
a:[a]
as) = Int -> [a] -> Int
go (Int
acc Int -> Int -> Int
forall a. Num a => a -> a -> a
+ a -> Int
forall a. Serialize a => a -> Int
size a
a) [a]
as
  {-# INLINE put #-}

  -- this is a bit fancy: we remember the address of the length header,
  -- do a single traversal over the list, then write the length back to
  -- the header.
  put :: [a] -> Put
put [a]
as = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
pHeader RW
s ->

    let go :: [a] -> Addr# -> RW -> Int# -> (# Addr#, RW, Int# #)
        go :: [a] -> Addr# -> RW -> Int# -> (# Addr#, RW, Int# #)
go ~[a]
as Addr#
p RW
s Int#
len = case [a]
as of
          []   -> (# Addr#
p, RW
s, Int#
len #)
          a
a:[a]
as -> case Put -> Addr# -> RW -> (# Addr#, RW #)
unPut (a -> Put
forall a. Serialize a => a -> Put
put a
a) Addr#
p RW
s of (# Addr#
p, RW
s #) -> [a] -> Addr# -> RW -> Int# -> (# Addr#, RW, Int# #)
go [a]
as Addr#
p RW
s (Int#
len Int# -> Int# -> Int#
+# Int#
1#)

    in case [a] -> Addr# -> RW -> Int# -> (# Addr#, RW, Int# #)
go [a]
as (Addr# -> Int# -> Addr#
plusAddr# Addr#
pHeader SIZEOF_HSINT#) s 0# of
      (# Addr#
p, RW
s, Int#
len #) -> case Addr# -> Int# -> Int# -> RW -> RW
forall d. Addr# -> Int# -> Int# -> State# d -> State# d
writeIntOffAddr# Addr#
pHeader Int#
0# Int#
len RW
s of
        RW
s -> (# Addr#
p, RW
s #)

  {-# INLINE get #-}
  get :: Get [a]
get = do {l <- forall a. Serialize a => Get a
get @Int; go l} where
    go :: t -> Get [a]
go t
n = (Addr# -> Addr# -> RW -> (# Addr#, RW, [a] #)) -> Get [a]
forall a. (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
Get \Addr#
p Addr#
s -> case t
n of
      t
0 -> Get [a] -> Addr# -> Addr# -> RW -> (# Addr#, RW, [a] #)
forall a. Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
unGet ([a] -> Get [a]
forall a. a -> Get a
forall (f :: * -> *) a. Applicative f => a -> f a
pure []) Addr#
p Addr#
s
      t
n -> Get [a] -> Addr# -> Addr# -> RW -> (# Addr#, RW, [a] #)
forall a. Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
unGet ((:) (a -> [a] -> [a]) -> Get a -> Get ([a] -> [a])
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Get a
forall a. Serialize a => Get a
get Get ([a] -> [a]) -> Get [a] -> Get [a]
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> t -> Get [a]
go (t
n t -> t -> t
forall a. Num a => a -> a -> a
- t
1)) Addr#
p Addr#
s

instance (Serialize a, Serialize b) => Serialize (a, b) where
  {-# INLINE size #-}
  size :: (a, b) -> Int
size (a
a, b
b) = a -> Int
forall a. Serialize a => a -> Int
size a
a Int -> Int -> Int
forall a. Num a => a -> a -> a
+ b -> Int
forall a. Serialize a => a -> Int
size b
b
  {-# INLINE put #-}
  put :: (a, b) -> Put
put (a
a, b
b) = a -> Put
forall a. Serialize a => a -> Put
put a
a Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> b -> Put
forall a. Serialize a => a -> Put
put b
b
  {-# INLINE get #-}
  get :: Get (a, b)
get = (,) (a -> b -> (a, b)) -> Get a -> Get (b -> (a, b))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Get a
forall a. Serialize a => Get a
get Get (b -> (a, b)) -> Get b -> Get (a, b)
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get b
forall a. Serialize a => Get a
get

instance (Serialize a, Serialize b, Serialize c) => Serialize (a, b, c) where
  {-# INLINE size #-}
  size :: (a, b, c) -> Int
size (a
a, b
b, c
c) = a -> Int
forall a. Serialize a => a -> Int
size a
a Int -> Int -> Int
forall a. Num a => a -> a -> a
+ b -> Int
forall a. Serialize a => a -> Int
size b
b Int -> Int -> Int
forall a. Num a => a -> a -> a
+ c -> Int
forall a. Serialize a => a -> Int
size c
c
  {-# INLINE put #-}
  put :: (a, b, c) -> Put
put (a
a, b
b, c
c) = a -> Put
forall a. Serialize a => a -> Put
put a
a Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> b -> Put
forall a. Serialize a => a -> Put
put b
b Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> c -> Put
forall a. Serialize a => a -> Put
put c
c
  {-# INLINE get #-}
  get :: Get (a, b, c)
get = (,,) (a -> b -> c -> (a, b, c)) -> Get a -> Get (b -> c -> (a, b, c))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Get a
forall a. Serialize a => Get a
get Get (b -> c -> (a, b, c)) -> Get b -> Get (c -> (a, b, c))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get b
forall a. Serialize a => Get a
get Get (c -> (a, b, c)) -> Get c -> Get (a, b, c)
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get c
forall a. Serialize a => Get a
get

instance (Serialize a, Serialize b, Serialize c, Serialize d) => Serialize (a, b, c, d) where
  {-# INLINE size #-}
  size :: (a, b, c, d) -> Int
size (a
a, b
b, c
c, d
d) = a -> Int
forall a. Serialize a => a -> Int
size a
a Int -> Int -> Int
forall a. Num a => a -> a -> a
+ b -> Int
forall a. Serialize a => a -> Int
size b
b Int -> Int -> Int
forall a. Num a => a -> a -> a
+ c -> Int
forall a. Serialize a => a -> Int
size c
c Int -> Int -> Int
forall a. Num a => a -> a -> a
+ d -> Int
forall a. Serialize a => a -> Int
size d
d
  {-# INLINE put #-}
  put :: (a, b, c, d) -> Put
put (a
a, b
b, c
c, d
d) = a -> Put
forall a. Serialize a => a -> Put
put a
a Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> b -> Put
forall a. Serialize a => a -> Put
put b
b Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> c -> Put
forall a. Serialize a => a -> Put
put c
c Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> d -> Put
forall a. Serialize a => a -> Put
put d
d
  {-# INLINE get #-}
  get :: Get (a, b, c, d)
get = (,,,) (a -> b -> c -> d -> (a, b, c, d))
-> Get a -> Get (b -> c -> d -> (a, b, c, d))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Get a
forall a. Serialize a => Get a
get Get (b -> c -> d -> (a, b, c, d))
-> Get b -> Get (c -> d -> (a, b, c, d))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get b
forall a. Serialize a => Get a
get Get (c -> d -> (a, b, c, d)) -> Get c -> Get (d -> (a, b, c, d))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get c
forall a. Serialize a => Get a
get Get (d -> (a, b, c, d)) -> Get d -> Get (a, b, c, d)
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get d
forall a. Serialize a => Get a
get

instance (Serialize a, Serialize b, Serialize c, Serialize d, Serialize e)
      => Serialize (a, b, c, d, e) where
  {-# INLINE size #-}
  size :: (a, b, c, d, e) -> Int
size (a
a, b
b, c
c, d
d, e
e) = a -> Int
forall a. Serialize a => a -> Int
size a
a Int -> Int -> Int
forall a. Num a => a -> a -> a
+ b -> Int
forall a. Serialize a => a -> Int
size b
b Int -> Int -> Int
forall a. Num a => a -> a -> a
+ c -> Int
forall a. Serialize a => a -> Int
size c
c Int -> Int -> Int
forall a. Num a => a -> a -> a
+ d -> Int
forall a. Serialize a => a -> Int
size d
d Int -> Int -> Int
forall a. Num a => a -> a -> a
+ e -> Int
forall a. Serialize a => a -> Int
size e
e
  {-# INLINE put #-}
  put :: (a, b, c, d, e) -> Put
put (a
a, b
b, c
c, d
d, e
e) = a -> Put
forall a. Serialize a => a -> Put
put a
a Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> b -> Put
forall a. Serialize a => a -> Put
put b
b Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> c -> Put
forall a. Serialize a => a -> Put
put c
c Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> d -> Put
forall a. Serialize a => a -> Put
put d
d Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> e -> Put
forall a. Serialize a => a -> Put
put e
e
  {-# INLINE get #-}
  get :: Get (a, b, c, d, e)
get = (,,,,) (a -> b -> c -> d -> e -> (a, b, c, d, e))
-> Get a -> Get (b -> c -> d -> e -> (a, b, c, d, e))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Get a
forall a. Serialize a => Get a
get Get (b -> c -> d -> e -> (a, b, c, d, e))
-> Get b -> Get (c -> d -> e -> (a, b, c, d, e))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get b
forall a. Serialize a => Get a
get Get (c -> d -> e -> (a, b, c, d, e))
-> Get c -> Get (d -> e -> (a, b, c, d, e))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get c
forall a. Serialize a => Get a
get Get (d -> e -> (a, b, c, d, e))
-> Get d -> Get (e -> (a, b, c, d, e))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get d
forall a. Serialize a => Get a
get Get (e -> (a, b, c, d, e)) -> Get e -> Get (a, b, c, d, e)
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get e
forall a. Serialize a => Get a
get

instance (Serialize a, Serialize b, Serialize c, Serialize d, Serialize e, Serialize f)
      => Serialize (a, b, c, d, e, f) where
  {-# INLINE size #-}
  size :: (a, b, c, d, e, f) -> Int
size (a
a, b
b, c
c, d
d, e
e, f
f) = a -> Int
forall a. Serialize a => a -> Int
size a
a Int -> Int -> Int
forall a. Num a => a -> a -> a
+ b -> Int
forall a. Serialize a => a -> Int
size b
b Int -> Int -> Int
forall a. Num a => a -> a -> a
+ c -> Int
forall a. Serialize a => a -> Int
size c
c Int -> Int -> Int
forall a. Num a => a -> a -> a
+ d -> Int
forall a. Serialize a => a -> Int
size d
d Int -> Int -> Int
forall a. Num a => a -> a -> a
+ e -> Int
forall a. Serialize a => a -> Int
size e
e Int -> Int -> Int
forall a. Num a => a -> a -> a
+ f -> Int
forall a. Serialize a => a -> Int
size f
f
  {-# INLINE put #-}
  put :: (a, b, c, d, e, f) -> Put
put (a
a, b
b, c
c, d
d, e
e, f
f) = a -> Put
forall a. Serialize a => a -> Put
put a
a Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> b -> Put
forall a. Serialize a => a -> Put
put b
b Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> c -> Put
forall a. Serialize a => a -> Put
put c
c Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> d -> Put
forall a. Serialize a => a -> Put
put d
d Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> e -> Put
forall a. Serialize a => a -> Put
put e
e Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> f -> Put
forall a. Serialize a => a -> Put
put f
f
  {-# INLINE get #-}
  get :: Get (a, b, c, d, e, f)
get = (,,,,,) (a -> b -> c -> d -> e -> f -> (a, b, c, d, e, f))
-> Get a -> Get (b -> c -> d -> e -> f -> (a, b, c, d, e, f))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Get a
forall a. Serialize a => Get a
get Get (b -> c -> d -> e -> f -> (a, b, c, d, e, f))
-> Get b -> Get (c -> d -> e -> f -> (a, b, c, d, e, f))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get b
forall a. Serialize a => Get a
get Get (c -> d -> e -> f -> (a, b, c, d, e, f))
-> Get c -> Get (d -> e -> f -> (a, b, c, d, e, f))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get c
forall a. Serialize a => Get a
get Get (d -> e -> f -> (a, b, c, d, e, f))
-> Get d -> Get (e -> f -> (a, b, c, d, e, f))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get d
forall a. Serialize a => Get a
get Get (e -> f -> (a, b, c, d, e, f))
-> Get e -> Get (f -> (a, b, c, d, e, f))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get e
forall a. Serialize a => Get a
get Get (f -> (a, b, c, d, e, f)) -> Get f -> Get (a, b, c, d, e, f)
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get f
forall a. Serialize a => Get a
get

instance ( Serialize a, Serialize b, Serialize c
         , Serialize d, Serialize e, Serialize f, Serialize g)
      => Serialize (a, b, c, d, e, f, g) where
  {-# INLINE size #-}
  size :: (a, b, c, d, e, f, g) -> Int
size (a
a, b
b, c
c, d
d, e
e, f
f, g
g) = a -> Int
forall a. Serialize a => a -> Int
size a
a Int -> Int -> Int
forall a. Num a => a -> a -> a
+ b -> Int
forall a. Serialize a => a -> Int
size b
b Int -> Int -> Int
forall a. Num a => a -> a -> a
+ c -> Int
forall a. Serialize a => a -> Int
size c
c Int -> Int -> Int
forall a. Num a => a -> a -> a
+ d -> Int
forall a. Serialize a => a -> Int
size d
d Int -> Int -> Int
forall a. Num a => a -> a -> a
+ e -> Int
forall a. Serialize a => a -> Int
size e
e Int -> Int -> Int
forall a. Num a => a -> a -> a
+ f -> Int
forall a. Serialize a => a -> Int
size f
f Int -> Int -> Int
forall a. Num a => a -> a -> a
+ g -> Int
forall a. Serialize a => a -> Int
size g
g
  {-# INLINE put #-}
  put :: (a, b, c, d, e, f, g) -> Put
put (a
a, b
b, c
c, d
d, e
e, f
f, g
g) = a -> Put
forall a. Serialize a => a -> Put
put a
a Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> b -> Put
forall a. Serialize a => a -> Put
put b
b Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> c -> Put
forall a. Serialize a => a -> Put
put c
c Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> d -> Put
forall a. Serialize a => a -> Put
put d
d Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> e -> Put
forall a. Serialize a => a -> Put
put e
e Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> f -> Put
forall a. Serialize a => a -> Put
put f
f Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> g -> Put
forall a. Serialize a => a -> Put
put g
g
  {-# INLINE get #-}
  get :: Get (a, b, c, d, e, f, g)
get = (,,,,,,) (a -> b -> c -> d -> e -> f -> g -> (a, b, c, d, e, f, g))
-> Get a
-> Get (b -> c -> d -> e -> f -> g -> (a, b, c, d, e, f, g))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Get a
forall a. Serialize a => Get a
get Get (b -> c -> d -> e -> f -> g -> (a, b, c, d, e, f, g))
-> Get b -> Get (c -> d -> e -> f -> g -> (a, b, c, d, e, f, g))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get b
forall a. Serialize a => Get a
get Get (c -> d -> e -> f -> g -> (a, b, c, d, e, f, g))
-> Get c -> Get (d -> e -> f -> g -> (a, b, c, d, e, f, g))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get c
forall a. Serialize a => Get a
get Get (d -> e -> f -> g -> (a, b, c, d, e, f, g))
-> Get d -> Get (e -> f -> g -> (a, b, c, d, e, f, g))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get d
forall a. Serialize a => Get a
get Get (e -> f -> g -> (a, b, c, d, e, f, g))
-> Get e -> Get (f -> g -> (a, b, c, d, e, f, g))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get e
forall a. Serialize a => Get a
get Get (f -> g -> (a, b, c, d, e, f, g))
-> Get f -> Get (g -> (a, b, c, d, e, f, g))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get f
forall a. Serialize a => Get a
get Get (g -> (a, b, c, d, e, f, g))
-> Get g -> Get (a, b, c, d, e, f, g)
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get g
forall a. Serialize a => Get a
get

instance ( Serialize a, Serialize b, Serialize c
         , Serialize d, Serialize e, Serialize f, Serialize g, Serialize h)
      => Serialize (a, b, c, d, e, f, g, h) where
  {-# INLINE size #-}
  size :: (a, b, c, d, e, f, g, h) -> Int
size (a
a, b
b, c
c, d
d, e
e, f
f, g
g, h
h) =
    a -> Int
forall a. Serialize a => a -> Int
size a
a Int -> Int -> Int
forall a. Num a => a -> a -> a
+ b -> Int
forall a. Serialize a => a -> Int
size b
b Int -> Int -> Int
forall a. Num a => a -> a -> a
+ c -> Int
forall a. Serialize a => a -> Int
size c
c Int -> Int -> Int
forall a. Num a => a -> a -> a
+ d -> Int
forall a. Serialize a => a -> Int
size d
d Int -> Int -> Int
forall a. Num a => a -> a -> a
+ e -> Int
forall a. Serialize a => a -> Int
size e
e Int -> Int -> Int
forall a. Num a => a -> a -> a
+ f -> Int
forall a. Serialize a => a -> Int
size f
f Int -> Int -> Int
forall a. Num a => a -> a -> a
+ g -> Int
forall a. Serialize a => a -> Int
size g
g Int -> Int -> Int
forall a. Num a => a -> a -> a
+ h -> Int
forall a. Serialize a => a -> Int
size h
h
  {-# INLINE put #-}
  put :: (a, b, c, d, e, f, g, h) -> Put
put (a
a, b
b, c
c, d
d, e
e, f
f, g
g, h
h) =
    a -> Put
forall a. Serialize a => a -> Put
put a
a Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> b -> Put
forall a. Serialize a => a -> Put
put b
b Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> c -> Put
forall a. Serialize a => a -> Put
put c
c Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> d -> Put
forall a. Serialize a => a -> Put
put d
d Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> e -> Put
forall a. Serialize a => a -> Put
put e
e Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> f -> Put
forall a. Serialize a => a -> Put
put f
f Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> g -> Put
forall a. Serialize a => a -> Put
put g
g Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> h -> Put
forall a. Serialize a => a -> Put
put h
h
  {-# INLINE get #-}
  get :: Get (a, b, c, d, e, f, g, h)
get = (,,,,,,,) (a -> b -> c -> d -> e -> f -> g -> h -> (a, b, c, d, e, f, g, h))
-> Get a
-> Get
     (b -> c -> d -> e -> f -> g -> h -> (a, b, c, d, e, f, g, h))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Get a
forall a. Serialize a => Get a
get Get (b -> c -> d -> e -> f -> g -> h -> (a, b, c, d, e, f, g, h))
-> Get b
-> Get (c -> d -> e -> f -> g -> h -> (a, b, c, d, e, f, g, h))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get b
forall a. Serialize a => Get a
get Get (c -> d -> e -> f -> g -> h -> (a, b, c, d, e, f, g, h))
-> Get c -> Get (d -> e -> f -> g -> h -> (a, b, c, d, e, f, g, h))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get c
forall a. Serialize a => Get a
get Get (d -> e -> f -> g -> h -> (a, b, c, d, e, f, g, h))
-> Get d -> Get (e -> f -> g -> h -> (a, b, c, d, e, f, g, h))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get d
forall a. Serialize a => Get a
get Get (e -> f -> g -> h -> (a, b, c, d, e, f, g, h))
-> Get e -> Get (f -> g -> h -> (a, b, c, d, e, f, g, h))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get e
forall a. Serialize a => Get a
get Get (f -> g -> h -> (a, b, c, d, e, f, g, h))
-> Get f -> Get (g -> h -> (a, b, c, d, e, f, g, h))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get f
forall a. Serialize a => Get a
get Get (g -> h -> (a, b, c, d, e, f, g, h))
-> Get g -> Get (h -> (a, b, c, d, e, f, g, h))
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get g
forall a. Serialize a => Get a
get Get (h -> (a, b, c, d, e, f, g, h))
-> Get h -> Get (a, b, c, d, e, f, g, h)
forall a b. Get (a -> b) -> Get a -> Get b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Get h
forall a. Serialize a => Get a
get

-- low-level ByteArray# helpers
-- Write a ByteArray# to buffer, with offset + length.
{-# INLINE putByteArray# #-}
putByteArray# :: ByteArray# -> Int# -> Int# -> Put
putByteArray# :: ByteArray# -> Int# -> Int# -> Put
putByteArray# ByteArray#
arr Int#
start Int#
len = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s ->
  case ByteArray# -> Int# -> Addr# -> Int# -> RW -> RW
forall d.
ByteArray# -> Int# -> Addr# -> Int# -> State# d -> State# d
copyByteArrayToAddr# ByteArray#
arr Int#
start Addr#
p Int#
len RW
s of
    RW
s -> (# Addr# -> Int# -> Addr#
plusAddr# Addr#
p Int#
len, RW
s #)

-- Read a ByteArray# of length "len" from buffer
{-# INLINE getByteArray# #-}
getByteArray# :: Int# -> (ByteArray# -> Get a) -> Get a
getByteArray# :: forall a. Int# -> (ByteArray# -> Get a) -> Get a
getByteArray# Int#
len ByteArray# -> Get a
k = Int -> (Addr# -> Get a) -> Get a
forall a. Int -> (Addr# -> Get a) -> Get a
ensure (Int# -> Int
I# Int#
len) \Addr#
p' -> (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
forall a. (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
Get \Addr#
e Addr#
p RW
s ->
  case Int# -> RW -> (# RW, MutableByteArray# RealWorld #)
forall d. Int# -> State# d -> (# State# d, MutableByteArray# d #)
newByteArray# Int#
len RW
s of
    (# RW
s, MutableByteArray# RealWorld
arr #) -> case Addr# -> MutableByteArray# RealWorld -> Int# -> Int# -> RW -> RW
forall d.
Addr#
-> MutableByteArray# d -> Int# -> Int# -> State# d -> State# d
copyAddrToByteArray# Addr#
p MutableByteArray# RealWorld
arr Int#
0# Int#
len RW
s of
      RW
s -> case MutableByteArray# RealWorld -> RW -> (# RW, ByteArray# #)
forall d.
MutableByteArray# d -> State# d -> (# State# d, ByteArray# #)
unsafeFreezeByteArray# MutableByteArray# RealWorld
arr RW
s of
        (# RW
s, ByteArray#
arr #) -> Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
forall a. Get a -> Addr# -> Addr# -> RW -> (# Addr#, RW, a #)
unGet (ByteArray# -> Get a
k ByteArray#
arr) Addr#
e Addr#
p' RW
s

instance Serialize T.Text where
  {-# INLINE size #-}
  size :: Text -> Int
size Text
t = Int -> Int
forall a. Serialize a => a -> Int
size (Int
0::Int) Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Text -> Int
tLengthWord8 Text
t

  put :: Text -> Put
put (T.Text (TArray ByteArray#
arr) (I# Int#
start) (I# Int#
len)) =
    Int -> Put
forall a. Serialize a => a -> Put
put (Int# -> Int
I# Int#
len) Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> ByteArray# -> Int# -> Int# -> Put
putByteArray# ByteArray#
arr Int#
start Int#
len

  get :: Get Text
get = do
    I# l <- Get Int
forall a. Serialize a => Get a
get
    getByteArray# l \ByteArray#
arr -> (Addr# -> Addr# -> RW -> (# Addr#, RW, Text #)) -> Get Text
forall a. (Addr# -> Addr# -> RW -> (# Addr#, RW, a #)) -> Get a
Get \Addr#
e Addr#
p RW
s ->
      (# Addr#
p, RW
s, Array -> Int -> Int -> Text
T.Text (ByteArray# -> Array
TArray ByteArray#
arr) Int
0 (Int# -> Int
I# Int#
l) #)

lTextBytes :: TL.Text -> Int
lTextBytes :: Text -> Int
lTextBytes Text
t = Text -> Int -> Int
go Text
t Int
0 where
  go :: Text -> Int -> Int
go Text
TL.Empty        Int
acc = Int
acc
  go (TL.Chunk Text
t Text
ts) Int
acc = Text -> Int -> Int
go Text
ts (Text -> Int
tLengthWord8 Text
t Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Int
acc)

instance Serialize TL.Text where
  size :: Text -> Int
size Text
t = Int -> Int
forall a. Serialize a => a -> Int
size (Int
0::Int) Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Text -> Int
lTextBytes Text
t
  put :: Text -> Put
put Text
t = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
pHeader RW
s -> let

    go :: TL.Text -> Addr# -> RW -> Int# -> (# Addr#, RW, Int# #)
    go :: Text -> Addr# -> RW -> Int# -> (# Addr#, RW, Int# #)
go Text
TL.Empty        Addr#
p RW
s Int#
len = (# Addr#
p, RW
s, Int#
len #)
    go (TL.Chunk Text
t Text
ts) Addr#
p RW
s Int#
len = case Text
t of
      T.Text (TArray ByteArray#
arr) (I# Int#
start) (I# Int#
l) ->
        case Put -> Addr# -> RW -> (# Addr#, RW #)
unPut (ByteArray# -> Int# -> Int# -> Put
putByteArray# ByteArray#
arr Int#
start Int#
l) Addr#
p RW
s of
          (# Addr#
p , RW
s #) -> Text -> Addr# -> RW -> Int# -> (# Addr#, RW, Int# #)
go Text
ts Addr#
p RW
s (Int#
len Int# -> Int# -> Int#
+# Int#
l)

    in case Text -> Addr# -> RW -> Int# -> (# Addr#, RW, Int# #)
go Text
t (Addr# -> Int# -> Addr#
plusAddr# Addr#
pHeader SIZEOF_HSINT#) s 0# of
      (# Addr#
p, RW
s, Int#
len #) -> case Addr# -> Int# -> Int# -> RW -> RW
forall d. Addr# -> Int# -> Int# -> State# d -> State# d
writeIntOffAddr# Addr#
pHeader Int#
0# Int#
len RW
s of
        RW
s -> (# Addr#
p, RW
s #)

  get :: Get Text
get = Text -> Text
TL.fromStrict (Text -> Text) -> Get Text -> Get Text
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Get Text
forall a. Serialize a => Get a
get

instance Serialize Integer where
  size :: Integer -> Int
size Integer
i = SIZEOF_WORD8 + case i of
    IS i   -> size (I# i)
    IP arr -> SIZEOF_HSINT + I# (sizeofByteArray# arr)
    IN arr -> SIZEOF_HSINT + I# (sizeofByteArray# arr)
  put :: Integer -> Put
put Integer
x = (Addr# -> RW -> (# Addr#, RW #)) -> Put
Put \Addr#
p RW
s -> case Integer
x of
    IS Int#
i   -> Put -> Addr# -> RW -> (# Addr#, RW #)
unPut (Word8 -> Put
forall a. Serialize a => a -> Put
put (Word8
0::Word8) Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> Int -> Put
forall a. Serialize a => a -> Put
put (Int# -> Int
I# Int#
i)) Addr#
p RW
s
    IP ByteArray#
arr -> let sz :: Int#
sz = ByteArray# -> Int#
sizeofByteArray# ByteArray#
arr
              in Put -> Addr# -> RW -> (# Addr#, RW #)
unPut (Word8 -> Put
forall a. Serialize a => a -> Put
put (Word8
1::Word8) Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> Int -> Put
forall a. Serialize a => a -> Put
put (Int# -> Int
I# Int#
sz) Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> ByteArray# -> Int# -> Int# -> Put
putByteArray# ByteArray#
arr Int#
0# Int#
sz) Addr#
p RW
s
    IN ByteArray#
arr -> let sz :: Int#
sz = ByteArray# -> Int#
sizeofByteArray# ByteArray#
arr
              in Put -> Addr# -> RW -> (# Addr#, RW #)
unPut (Word8 -> Put
forall a. Serialize a => a -> Put
put (Word8
2::Word8) Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> Int -> Put
forall a. Serialize a => a -> Put
put (Int# -> Int
I# Int#
sz) Put -> Put -> Put
forall a. Semigroup a => a -> a -> a
<> ByteArray# -> Int# -> Int# -> Put
putByteArray# ByteArray#
arr Int#
0# Int#
sz) Addr#
p RW
s
  get :: Get Integer
get = forall a. Serialize a => Get a
get @Word8 Get Word8 -> (Word8 -> Get Integer) -> Get Integer
forall a b. Get a -> (a -> Get b) -> Get b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= \case
    Word8
0 -> do {I# n  <- Get Int
forall a. Serialize a => Get a
get; pure $ IS n}
    Word8
1 -> do {I# sz <- Get Int
forall a. Serialize a => Get a
get; getByteArray# sz \ByteArray#
arr -> Integer -> Get Integer
forall a. a -> Get a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Integer -> Get Integer) -> Integer -> Get Integer
forall a b. (a -> b) -> a -> b
$ ByteArray# -> Integer
IP ByteArray#
arr}
    Word8
2 -> do {I# sz <- Get Int
forall a. Serialize a => Get a
get; getByteArray# sz \ByteArray#
arr -> Integer -> Get Integer
forall a. a -> Get a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Integer -> Get Integer) -> Integer -> Get Integer
forall a b. (a -> b) -> a -> b
$ ByteArray# -> Integer
IN ByteArray#
arr}
    Word8
_ -> [Char] -> Get Integer
forall a. HasCallStack => [Char] -> a
error [Char]
"deserialize: malformed input"