{-# LANGUAGE LambdaCase #-} {-# LANGUAGE Trustworthy #-} module Network.Tox.Encoding where import Data.Binary (Binary, get, put) import Data.Binary.Bits.Get (BitGet) import Data.Binary.Bits.Put (BitPut) import Data.Binary.Get (Decoder (..), pushChunk, runGetIncremental) import Data.Binary.Put (runPut) import Data.ByteString (ByteString) import qualified Data.ByteString as ByteString import qualified Data.ByteString.Lazy as LazyByteString import Network.Tox.Crypto.Box (PlainText (..)) class BitEncoding a where bitGet :: BitGet a bitPut :: a -> BitPut () encode :: Binary a => a -> ByteString encode = LazyByteString.toStrict . runPut . put decode :: (Monad m, Binary a) => ByteString -> m a decode bytes = finish $ pushChunk (runGetIncremental get) bytes where finish = \case Done unconsumed _ output -> if ByteString.null unconsumed then return output else fail $ "unconsumed input: " ++ show (PlainText unconsumed) Fail _ _ msg -> fail msg Partial f -> finish $ f Nothing