{-# LANGUAGE UndecidableInstances #-}

{- TODO can I replace this with a closed newtype family?? idk if I even want to
    it's just this is clumsy to use sometimes
-}

module Binrep.Type.Int where

import Binrep
import Binrep.Type.Common ( Endianness(..) )
import Strongweak

import Data.Word
import Data.Int
import Data.Aeson
import FlatParse.Basic qualified as FP
import Mason.Builder qualified as Mason

import GHC.Generics ( Generic )
import Data.Data ( Typeable, Data )
import GHC.TypeNats

-- | Wrapper type grouping machine integers (sign, size) along with an explicit
--   endianness.
--
-- The internal representation is selected via a type family to correspond to
-- the relevant Haskell data type, so common overflow behaviour should match.
-- We derive lots of handy instances, so you may perform regular arithmetic on
-- pairs of these types. For example:
--
-- >>> 255 + 1 :: I 'U 'I1 e
-- 0
--
-- >>> 255 + 1 :: I 'U 'I2 e
-- 256
newtype I (sign :: ISign) (size :: ISize) (e :: Endianness)
  = I { forall (sign :: ISign) (size :: ISize) (e :: Endianness).
I sign size e -> IRep sign size
getI :: IRep sign size }
    deriving stock ((forall x. I sign size e -> Rep (I sign size e) x)
-> (forall x. Rep (I sign size e) x -> I sign size e)
-> Generic (I sign size e)
forall x. Rep (I sign size e) x -> I sign size e
forall x. I sign size e -> Rep (I sign size e) x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
forall (sign :: ISign) (size :: ISize) (e :: Endianness) x.
Rep (I sign size e) x -> I sign size e
forall (sign :: ISign) (size :: ISize) (e :: Endianness) x.
I sign size e -> Rep (I sign size e) x
$cto :: forall (sign :: ISign) (size :: ISize) (e :: Endianness) x.
Rep (I sign size e) x -> I sign size e
$cfrom :: forall (sign :: ISign) (size :: ISize) (e :: Endianness) x.
I sign size e -> Rep (I sign size e) x
Generic)

deriving instance (Data (IRep sign size), Typeable sign, Typeable size, Typeable e) => Data (I sign size e)
deriving via (IRep sign size) instance Show     (IRep sign size) => Show     (I sign size e)

-- Steal various numeric instances from the representation types.
deriving via (IRep sign size) instance Eq       (IRep sign size) => Eq       (I sign size e)
deriving via (IRep sign size) instance Ord      (IRep sign size) => Ord      (I sign size e)
deriving via (IRep sign size) instance Bounded  (IRep sign size) => Bounded  (I sign size e)
deriving via (IRep sign size) instance Num      (IRep sign size) => Num      (I sign size e)
deriving via (IRep sign size) instance Real     (IRep sign size) => Real     (I sign size e)
deriving via (IRep sign size) instance Enum     (IRep sign size) => Enum     (I sign size e)
deriving via (IRep sign size) instance Integral (IRep sign size) => Integral (I sign size e)

-- | Unsigned machine integers can be idealized as naturals.
instance (irep ~ IRep 'U size, Integral irep) => Weaken (I 'U size end) where
    type Weak (I 'U size end) = Natural
    weaken :: I 'U size end -> Weak (I 'U size end)
weaken = I 'U size end -> Weak (I 'U size end)
forall a b. (Integral a, Num b) => a -> b
fromIntegral
instance (irep ~ IRep 'U size, Integral irep, Bounded irep, Show irep, Typeable size, Typeable end)
  => Strengthen (I 'U size end) where
      strengthen :: Weak (I 'U size end)
-> Validation (NonEmpty StrengthenFail) (I 'U size end)
strengthen = Weak (I 'U size end)
-> Validation (NonEmpty StrengthenFail) (I 'U size end)
forall b n.
(Integral b, Bounded b, Show b, Typeable b, Integral n, Show n,
 Typeable n) =>
n -> Validation (NonEmpty StrengthenFail) b
strengthenBounded

-- | Signed machine integers can be idealized as integers.
instance (irep ~ IRep 'S size, Integral irep) => Weaken (I 'S size end) where
    type Weak (I 'S size end) = Integer
    weaken :: I 'S size end -> Weak (I 'S size end)
weaken = I 'S size end -> Weak (I 'S size end)
forall a b. (Integral a, Num b) => a -> b
fromIntegral
instance (irep ~ IRep 'S size, Integral irep, Bounded irep, Show irep, Typeable size, Typeable end)
  => Strengthen (I 'S size end) where
      strengthen :: Weak (I 'S size end)
-> Validation (NonEmpty StrengthenFail) (I 'S size end)
strengthen = Weak (I 'S size end)
-> Validation (NonEmpty StrengthenFail) (I 'S size end)
forall b n.
(Integral b, Bounded b, Show b, Typeable b, Integral n, Show n,
 Typeable n) =>
n -> Validation (NonEmpty StrengthenFail) b
strengthenBounded

-- | Machine integer sign.
data ISign
  = S -- ^   signed
  | U -- ^ unsigned
    deriving stock ((forall x. ISign -> Rep ISign x)
-> (forall x. Rep ISign x -> ISign) -> Generic ISign
forall x. Rep ISign x -> ISign
forall x. ISign -> Rep ISign x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cto :: forall x. Rep ISign x -> ISign
$cfrom :: forall x. ISign -> Rep ISign x
Generic, Typeable ISign
Typeable ISign
-> (forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> ISign -> c ISign)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c ISign)
-> (ISign -> Constr)
-> (ISign -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c ISign))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ISign))
-> ((forall b. Data b => b -> b) -> ISign -> ISign)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> ISign -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> ISign -> r)
-> (forall u. (forall d. Data d => d -> u) -> ISign -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> ISign -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> ISign -> m ISign)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ISign -> m ISign)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ISign -> m ISign)
-> Data ISign
ISign -> DataType
ISign -> Constr
(forall b. Data b => b -> b) -> ISign -> ISign
forall a.
Typeable a
-> (forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> a -> c a)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c a)
-> (a -> Constr)
-> (a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c a))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
-> ((forall b. Data b => b -> b) -> a -> a)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall u. (forall d. Data d => d -> u) -> a -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> Data a
forall u. Int -> (forall d. Data d => d -> u) -> ISign -> u
forall u. (forall d. Data d => d -> u) -> ISign -> [u]
forall r r'.
(r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> ISign -> r
forall r r'.
(r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> ISign -> r
forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> ISign -> m ISign
forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISign -> m ISign
forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c ISign
forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ISign -> c ISign
forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c ISign)
forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ISign)
gmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISign -> m ISign
$cgmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISign -> m ISign
gmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISign -> m ISign
$cgmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISign -> m ISign
gmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> ISign -> m ISign
$cgmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> ISign -> m ISign
gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> ISign -> u
$cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> ISign -> u
gmapQ :: forall u. (forall d. Data d => d -> u) -> ISign -> [u]
$cgmapQ :: forall u. (forall d. Data d => d -> u) -> ISign -> [u]
gmapQr :: forall r r'.
(r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> ISign -> r
$cgmapQr :: forall r r'.
(r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> ISign -> r
gmapQl :: forall r r'.
(r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> ISign -> r
$cgmapQl :: forall r r'.
(r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> ISign -> r
gmapT :: (forall b. Data b => b -> b) -> ISign -> ISign
$cgmapT :: (forall b. Data b => b -> b) -> ISign -> ISign
dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ISign)
$cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ISign)
dataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c ISign)
$cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c ISign)
dataTypeOf :: ISign -> DataType
$cdataTypeOf :: ISign -> DataType
toConstr :: ISign -> Constr
$ctoConstr :: ISign -> Constr
gunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c ISign
$cgunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c ISign
gfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ISign -> c ISign
$cgfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ISign -> c ISign
Data, Int -> ISign -> ShowS
[ISign] -> ShowS
ISign -> String
(Int -> ISign -> ShowS)
-> (ISign -> String) -> ([ISign] -> ShowS) -> Show ISign
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ISign] -> ShowS
$cshowList :: [ISign] -> ShowS
show :: ISign -> String
$cshow :: ISign -> String
showsPrec :: Int -> ISign -> ShowS
$cshowsPrec :: Int -> ISign -> ShowS
Show, ISign -> ISign -> Bool
(ISign -> ISign -> Bool) -> (ISign -> ISign -> Bool) -> Eq ISign
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: ISign -> ISign -> Bool
$c/= :: ISign -> ISign -> Bool
== :: ISign -> ISign -> Bool
$c== :: ISign -> ISign -> Bool
Eq)

-- | Machine integer size in number of bytes.
data ISize = I1 | I2 | I4 | I8
    deriving stock ((forall x. ISize -> Rep ISize x)
-> (forall x. Rep ISize x -> ISize) -> Generic ISize
forall x. Rep ISize x -> ISize
forall x. ISize -> Rep ISize x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cto :: forall x. Rep ISize x -> ISize
$cfrom :: forall x. ISize -> Rep ISize x
Generic, Typeable ISize
Typeable ISize
-> (forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> ISize -> c ISize)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c ISize)
-> (ISize -> Constr)
-> (ISize -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c ISize))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ISize))
-> ((forall b. Data b => b -> b) -> ISize -> ISize)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> ISize -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> ISize -> r)
-> (forall u. (forall d. Data d => d -> u) -> ISize -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> ISize -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> ISize -> m ISize)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ISize -> m ISize)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ISize -> m ISize)
-> Data ISize
ISize -> DataType
ISize -> Constr
(forall b. Data b => b -> b) -> ISize -> ISize
forall a.
Typeable a
-> (forall (c :: * -> *).
    (forall d b. Data d => c (d -> b) -> d -> c b)
    -> (forall g. g -> c g) -> a -> c a)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c a)
-> (a -> Constr)
-> (a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c a))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
-> ((forall b. Data b => b -> b) -> a -> a)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall u. (forall d. Data d => d -> u) -> a -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> Data a
forall u. Int -> (forall d. Data d => d -> u) -> ISize -> u
forall u. (forall d. Data d => d -> u) -> ISize -> [u]
forall r r'.
(r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> ISize -> r
forall r r'.
(r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> ISize -> r
forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> ISize -> m ISize
forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISize -> m ISize
forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c ISize
forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ISize -> c ISize
forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c ISize)
forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ISize)
gmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISize -> m ISize
$cgmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISize -> m ISize
gmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISize -> m ISize
$cgmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ISize -> m ISize
gmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> ISize -> m ISize
$cgmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> ISize -> m ISize
gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> ISize -> u
$cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> ISize -> u
gmapQ :: forall u. (forall d. Data d => d -> u) -> ISize -> [u]
$cgmapQ :: forall u. (forall d. Data d => d -> u) -> ISize -> [u]
gmapQr :: forall r r'.
(r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> ISize -> r
$cgmapQr :: forall r r'.
(r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> ISize -> r
gmapQl :: forall r r'.
(r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> ISize -> r
$cgmapQl :: forall r r'.
(r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> ISize -> r
gmapT :: (forall b. Data b => b -> b) -> ISize -> ISize
$cgmapT :: (forall b. Data b => b -> b) -> ISize -> ISize
dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ISize)
$cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c ISize)
dataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c ISize)
$cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c ISize)
dataTypeOf :: ISize -> DataType
$cdataTypeOf :: ISize -> DataType
toConstr :: ISize -> Constr
$ctoConstr :: ISize -> Constr
gunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c ISize
$cgunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c ISize
gfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ISize -> c ISize
$cgfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ISize -> c ISize
Data, Int -> ISize -> ShowS
[ISize] -> ShowS
ISize -> String
(Int -> ISize -> ShowS)
-> (ISize -> String) -> ([ISize] -> ShowS) -> Show ISize
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ISize] -> ShowS
$cshowList :: [ISize] -> ShowS
show :: ISize -> String
$cshow :: ISize -> String
showsPrec :: Int -> ISize -> ShowS
$cshowsPrec :: Int -> ISize -> ShowS
Show, ISize -> ISize -> Bool
(ISize -> ISize -> Bool) -> (ISize -> ISize -> Bool) -> Eq ISize
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: ISize -> ISize -> Bool
$c/= :: ISize -> ISize -> Bool
== :: ISize -> ISize -> Bool
$c== :: ISize -> ISize -> Bool
Eq)

-- | Grouping for matching a signedness and size to a Haskell integer data type.
type family IRep (sign :: ISign) (size :: ISize) where
    IRep 'U 'I1 = Word8
    IRep 'S 'I1 =  Int8
    IRep 'U 'I2 = Word16
    IRep 'S 'I2 =  Int16
    IRep 'U 'I4 = Word32
    IRep 'S 'I4 =  Int32
    IRep 'U 'I8 = Word64
    IRep 'S 'I8 =  Int64

-- Also steal Aeson instances. The parser applies bounding checks appropriately.
deriving via (IRep sign size) instance ToJSON   (IRep sign size) => ToJSON   (I sign size e)
deriving via (IRep sign size) instance FromJSON (IRep sign size) => FromJSON (I sign size e)

type instance CBLen (I sign size end) = CBLen (IRep sign size)

deriving anyclass instance KnownNat (CBLen (I sign size end)) => BLen (I sign size end)

instance Put (I 'U 'I1 e) where put :: I 'U 'I1 e -> Builder
put = Word8 -> Builder
forall a. Put a => a -> Builder
put (Word8 -> Builder)
-> (I 'U 'I1 e -> Word8) -> I 'U 'I1 e -> Builder
forall b c a. (b -> c) -> (a -> b) -> a -> c
. I 'U 'I1 e -> Word8
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
I sign size e -> IRep sign size
getI
instance Get (I 'U 'I1 e) where get :: Getter (I 'U 'I1 e)
get = Word8 -> I 'U 'I1 e
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Word8 -> I 'U 'I1 e) -> Parser String Word8 -> Getter (I 'U 'I1 e)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Word8
forall a. Get a => Getter a
get
instance Put (I 'S 'I1 e) where put :: I 'S 'I1 e -> Builder
put = Int8 -> Builder
forall a. Put a => a -> Builder
put (Int8 -> Builder) -> (I 'S 'I1 e -> Int8) -> I 'S 'I1 e -> Builder
forall b c a. (b -> c) -> (a -> b) -> a -> c
. I 'S 'I1 e -> Int8
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
I sign size e -> IRep sign size
getI
instance Get (I 'S 'I1 e) where get :: Getter (I 'S 'I1 e)
get = Int8 -> I 'S 'I1 e
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Int8 -> I 'S 'I1 e) -> Parser String Int8 -> Getter (I 'S 'I1 e)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Int8
forall a. Get a => Getter a
get

instance Put (I 'U 'I2 'BE) where put :: I 'U 'I2 'BE -> Builder
put (I IRep 'U 'I2
i) = Word16 -> Builder
Mason.word16BE Word16
IRep 'U 'I2
i
instance Get (I 'U 'I2 'BE) where get :: Getter (I 'U 'I2 'BE)
get = Word16 -> I 'U 'I2 'BE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Word16 -> I 'U 'I2 'BE)
-> Parser String Word16 -> Getter (I 'U 'I2 'BE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Word16
forall e. Parser e Word16
FP.anyWord16be
instance Put (I 'U 'I2 'LE) where put :: I 'U 'I2 'LE -> Builder
put (I IRep 'U 'I2
i) = Word16 -> Builder
Mason.word16LE Word16
IRep 'U 'I2
i
instance Get (I 'U 'I2 'LE) where get :: Getter (I 'U 'I2 'LE)
get = Word16 -> I 'U 'I2 'LE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Word16 -> I 'U 'I2 'LE)
-> Parser String Word16 -> Getter (I 'U 'I2 'LE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Word16
forall e. Parser e Word16
FP.anyWord16le
instance Put (I 'S 'I2 'BE) where put :: I 'S 'I2 'BE -> Builder
put (I IRep 'S 'I2
i) = Int16 -> Builder
Mason.int16BE Int16
IRep 'S 'I2
i
instance Get (I 'S 'I2 'BE) where get :: Getter (I 'S 'I2 'BE)
get = Int16 -> I 'S 'I2 'BE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Int16 -> I 'S 'I2 'BE)
-> Parser String Int16 -> Getter (I 'S 'I2 'BE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Int16
forall e. Parser e Int16
FP.anyInt16be
instance Put (I 'S 'I2 'LE) where put :: I 'S 'I2 'LE -> Builder
put (I IRep 'S 'I2
i) = Int16 -> Builder
Mason.int16LE Int16
IRep 'S 'I2
i
instance Get (I 'S 'I2 'LE) where get :: Getter (I 'S 'I2 'LE)
get = Int16 -> I 'S 'I2 'LE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Int16 -> I 'S 'I2 'LE)
-> Parser String Int16 -> Getter (I 'S 'I2 'LE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Int16
forall e. Parser e Int16
FP.anyInt16le

instance Put (I 'U 'I4 'BE) where put :: I 'U 'I4 'BE -> Builder
put (I IRep 'U 'I4
i) = Word32 -> Builder
Mason.word32BE Word32
IRep 'U 'I4
i
instance Get (I 'U 'I4 'BE) where get :: Getter (I 'U 'I4 'BE)
get = Word32 -> I 'U 'I4 'BE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Word32 -> I 'U 'I4 'BE)
-> Parser String Word32 -> Getter (I 'U 'I4 'BE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Word32
forall e. Parser e Word32
FP.anyWord32be
instance Put (I 'U 'I4 'LE) where put :: I 'U 'I4 'LE -> Builder
put (I IRep 'U 'I4
i) = Word32 -> Builder
Mason.word32LE Word32
IRep 'U 'I4
i
instance Get (I 'U 'I4 'LE) where get :: Getter (I 'U 'I4 'LE)
get = Word32 -> I 'U 'I4 'LE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Word32 -> I 'U 'I4 'LE)
-> Parser String Word32 -> Getter (I 'U 'I4 'LE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Word32
forall e. Parser e Word32
FP.anyWord32le
instance Put (I 'S 'I4 'BE) where put :: I 'S 'I4 'BE -> Builder
put (I IRep 'S 'I4
i) = Int32 -> Builder
Mason.int32BE Int32
IRep 'S 'I4
i
instance Get (I 'S 'I4 'BE) where get :: Getter (I 'S 'I4 'BE)
get = Int32 -> I 'S 'I4 'BE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Int32 -> I 'S 'I4 'BE)
-> Parser String Int32 -> Getter (I 'S 'I4 'BE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Int32
forall e. Parser e Int32
FP.anyInt32be
instance Put (I 'S 'I4 'LE) where put :: I 'S 'I4 'LE -> Builder
put (I IRep 'S 'I4
i) = Int32 -> Builder
Mason.int32LE Int32
IRep 'S 'I4
i
instance Get (I 'S 'I4 'LE) where get :: Getter (I 'S 'I4 'LE)
get = Int32 -> I 'S 'I4 'LE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Int32 -> I 'S 'I4 'LE)
-> Parser String Int32 -> Getter (I 'S 'I4 'LE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Int32
forall e. Parser e Int32
FP.anyInt32le

instance Put (I 'U 'I8 'BE) where put :: I 'U 'I8 'BE -> Builder
put (I IRep 'U 'I8
i) = Word64 -> Builder
Mason.word64BE Word64
IRep 'U 'I8
i
instance Get (I 'U 'I8 'BE) where get :: Getter (I 'U 'I8 'BE)
get = Word64 -> I 'U 'I8 'BE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Word64 -> I 'U 'I8 'BE)
-> Parser String Word64 -> Getter (I 'U 'I8 'BE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Word64
forall e. Parser e Word64
FP.anyWord64be
instance Put (I 'U 'I8 'LE) where put :: I 'U 'I8 'LE -> Builder
put (I IRep 'U 'I8
i) = Word64 -> Builder
Mason.word64LE Word64
IRep 'U 'I8
i
instance Get (I 'U 'I8 'LE) where get :: Getter (I 'U 'I8 'LE)
get = Word64 -> I 'U 'I8 'LE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Word64 -> I 'U 'I8 'LE)
-> Parser String Word64 -> Getter (I 'U 'I8 'LE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Word64
forall e. Parser e Word64
FP.anyWord64le
instance Put (I 'S 'I8 'BE) where put :: I 'S 'I8 'BE -> Builder
put (I IRep 'S 'I8
i) = Int64 -> Builder
Mason.int64BE Int64
IRep 'S 'I8
i
instance Get (I 'S 'I8 'BE) where get :: Getter (I 'S 'I8 'BE)
get = Int64 -> I 'S 'I8 'BE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Int64 -> I 'S 'I8 'BE)
-> Parser String Int64 -> Getter (I 'S 'I8 'BE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Int64
forall e. Parser e Int64
FP.anyInt64be
instance Put (I 'S 'I8 'LE) where put :: I 'S 'I8 'LE -> Builder
put (I IRep 'S 'I8
i) = Int64 -> Builder
Mason.int64LE Int64
IRep 'S 'I8
i
instance Get (I 'S 'I8 'LE) where get :: Getter (I 'S 'I8 'LE)
get = Int64 -> I 'S 'I8 'LE
forall (sign :: ISign) (size :: ISize) (e :: Endianness).
IRep sign size -> I sign size e
I (Int64 -> I 'S 'I8 'LE)
-> Parser String Int64 -> Getter (I 'S 'I8 'LE)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser String Int64
forall e. Parser e Int64
FP.anyInt64le

-- | Shortcut.
type family IMax (sign :: ISign) (size :: ISize) :: Natural where
    IMax sign size = MaxBound (IRep sign size)

-- | Restricted reflected version of @maxBound@.
type family MaxBound w :: Natural where
    MaxBound Word8  = 255
    MaxBound  Int8  = 127
    MaxBound Word16 = 65535
    MaxBound  Int16 = 32767
    MaxBound Word32 = 4294967295
    MaxBound  Int32 = 2147483647
    MaxBound Word64 = 18446744073709551615
    MaxBound  Int64 = 9223372036854775807