Add little-endian encoding functions for Word{16,32,64}. Add machine encoding functions for 64-bit signed int. These just convert it to an unsigned int and call the corresponding encoding function.
This commit is contained in:
parent
e0b9d744cf
commit
3ad5261ff4
3 changed files with 92 additions and 3 deletions
|
@ -4,6 +4,8 @@
|
||||||
|
|
||||||
* Introduce `consLensBE32` for efficient serialization of wire protocols
|
* Introduce `consLensBE32` for efficient serialization of wire protocols
|
||||||
that require prefixing a payload with its length.
|
that require prefixing a payload with its length.
|
||||||
|
* Add `int64BE` as a convenience.
|
||||||
|
* Add little-endian encoding functions for `Word16`, `Word32`, and `Word64`.
|
||||||
|
|
||||||
## 0.2.1.0 -- 2019-09-05
|
## 0.2.1.0 -- 2019-09-05
|
||||||
|
|
||||||
|
|
|
@ -54,10 +54,20 @@ module Data.ByteArray.Builder
|
||||||
, ascii
|
, ascii
|
||||||
, char
|
, char
|
||||||
-- ** Machine-Readable
|
-- ** Machine-Readable
|
||||||
|
-- *** One
|
||||||
|
, word8
|
||||||
|
-- **** Big Endian
|
||||||
, word64BE
|
, word64BE
|
||||||
, word32BE
|
, word32BE
|
||||||
, word16BE
|
, word16BE
|
||||||
, word8
|
, int64BE
|
||||||
|
-- **** Little Endian
|
||||||
|
, word64LE
|
||||||
|
, word32LE
|
||||||
|
, word16LE
|
||||||
|
, int64LE
|
||||||
|
-- *** Many
|
||||||
|
, word8Array
|
||||||
-- ** Prefixing with Length
|
-- ** Prefixing with Length
|
||||||
, consLength32BE
|
, consLength32BE
|
||||||
, consLength64BE
|
, consLength64BE
|
||||||
|
@ -75,7 +85,7 @@ import Data.ByteString.Short.Internal (ShortByteString(SBS))
|
||||||
import Data.Bytes.Types (Bytes(Bytes),MutableBytes(MutableBytes))
|
import Data.Bytes.Types (Bytes(Bytes),MutableBytes(MutableBytes))
|
||||||
import Data.Char (ord)
|
import Data.Char (ord)
|
||||||
import Data.Int (Int64,Int32,Int16,Int8)
|
import Data.Int (Int64,Int32,Int16,Int8)
|
||||||
import Data.Primitive (ByteArray(..),MutableByteArray(..))
|
import Data.Primitive (ByteArray(..),MutableByteArray(..),PrimArray(..))
|
||||||
import Data.Primitive.ByteArray.Offset (MutableByteArrayOffset(..))
|
import Data.Primitive.ByteArray.Offset (MutableByteArrayOffset(..))
|
||||||
import Data.Text.Short (ShortText)
|
import Data.Text.Short (ShortText)
|
||||||
import Data.Word (Word64,Word32,Word16,Word8)
|
import Data.Word (Word64,Word32,Word16,Word8)
|
||||||
|
@ -218,6 +228,12 @@ bytes (Bytes src soff slen) = construct $ \(MutableBytes arr off len) -> if len
|
||||||
pure (Just (off + slen))
|
pure (Just (off + slen))
|
||||||
else pure Nothing
|
else pure Nothing
|
||||||
|
|
||||||
|
-- | Create a builder from a slice of an array of 'Word8'. There is the same
|
||||||
|
-- as 'bytes' but is provided as a convenience for users working with different
|
||||||
|
-- types.
|
||||||
|
word8Array :: PrimArray Word8 -> Int -> Int -> Builder
|
||||||
|
word8Array (PrimArray arr) off len = bytes (Bytes (ByteArray arr) off len)
|
||||||
|
|
||||||
-- Internal function. Precondition, the referenced slice of the
|
-- Internal function. Precondition, the referenced slice of the
|
||||||
-- byte sequence is UTF-8 encoded text.
|
-- byte sequence is UTF-8 encoded text.
|
||||||
slicedUtf8TextJson :: ByteArray# -> Int# -> Int# -> Builder
|
slicedUtf8TextJson :: ByteArray# -> Int# -> Int# -> Builder
|
||||||
|
@ -417,6 +433,31 @@ shrinkMutableByteArray :: MutableByteArray s -> Int -> ST s ()
|
||||||
shrinkMutableByteArray (MutableByteArray arr) (I# sz) =
|
shrinkMutableByteArray (MutableByteArray arr) (I# sz) =
|
||||||
primitive_ (Exts.shrinkMutableByteArray# arr sz)
|
primitive_ (Exts.shrinkMutableByteArray# arr sz)
|
||||||
|
|
||||||
|
-- | Requires exactly 8 bytes. Dump the octets of a 64-bit
|
||||||
|
-- signed integer in a little-endian fashion.
|
||||||
|
int64LE :: Int64 -> Builder
|
||||||
|
int64LE w = fromBounded Nat.constant (Bounded.int64LE w)
|
||||||
|
|
||||||
|
-- | Requires exactly 8 bytes. Dump the octets of a 64-bit
|
||||||
|
-- signed integer in a big-endian fashion.
|
||||||
|
int64BE :: Int64 -> Builder
|
||||||
|
int64BE w = fromBounded Nat.constant (Bounded.int64BE w)
|
||||||
|
|
||||||
|
-- | Requires exactly 8 bytes. Dump the octets of a 64-bit
|
||||||
|
-- word in a little-endian fashion.
|
||||||
|
word64LE :: Word64 -> Builder
|
||||||
|
word64LE w = fromBounded Nat.constant (Bounded.word64LE w)
|
||||||
|
|
||||||
|
-- | Requires exactly 4 bytes. Dump the octets of a 32-bit
|
||||||
|
-- word in a little-endian fashion.
|
||||||
|
word32LE :: Word32 -> Builder
|
||||||
|
word32LE w = fromBounded Nat.constant (Bounded.word32LE w)
|
||||||
|
|
||||||
|
-- | Requires exactly 2 bytes. Dump the octets of a 16-bit
|
||||||
|
-- word in a little-endian fashion.
|
||||||
|
word16LE :: Word16 -> Builder
|
||||||
|
word16LE w = fromBounded Nat.constant (Bounded.word16LE w)
|
||||||
|
|
||||||
-- | Requires exactly 8 bytes. Dump the octets of a 64-bit
|
-- | Requires exactly 8 bytes. Dump the octets of a 64-bit
|
||||||
-- word in a big-endian fashion.
|
-- word in a big-endian fashion.
|
||||||
word64BE :: Word64 -> Builder
|
word64BE :: Word64 -> Builder
|
||||||
|
|
|
@ -52,10 +52,18 @@ module Data.ByteArray.Builder.Bounded
|
||||||
, ascii
|
, ascii
|
||||||
, char
|
, char
|
||||||
-- ** Machine-Readable
|
-- ** Machine-Readable
|
||||||
|
-- *** One
|
||||||
|
, word8
|
||||||
|
-- **** Big Endian
|
||||||
, word64BE
|
, word64BE
|
||||||
, word32BE
|
, word32BE
|
||||||
, word16BE
|
, word16BE
|
||||||
, word8
|
, int64BE
|
||||||
|
-- **** Little Endian
|
||||||
|
, word64LE
|
||||||
|
, word32LE
|
||||||
|
, word16LE
|
||||||
|
, int64LE
|
||||||
-- * Encode Floating-Point Types
|
-- * Encode Floating-Point Types
|
||||||
, doubleDec
|
, doubleDec
|
||||||
) where
|
) where
|
||||||
|
@ -579,6 +587,26 @@ char c
|
||||||
byteFourFour :: Word -> Word
|
byteFourFour :: Word -> Word
|
||||||
byteFourFour w = (0b00111111 .&. w) .|. 0b10000000
|
byteFourFour w = (0b00111111 .&. w) .|. 0b10000000
|
||||||
|
|
||||||
|
int64BE :: Int64 -> Builder 8
|
||||||
|
int64BE (I64# i) = word64BE (W64# (int2Word# i))
|
||||||
|
|
||||||
|
int64LE :: Int64 -> Builder 8
|
||||||
|
int64LE (I64# i) = word64LE (W64# (int2Word# i))
|
||||||
|
|
||||||
|
-- | Requires exactly 8 bytes. Dump the octets of a 64-bit
|
||||||
|
-- word in a little-endian fashion.
|
||||||
|
word64LE :: Word64 -> Builder 8
|
||||||
|
word64LE w = Unsafe.construct $ \arr off -> do
|
||||||
|
writeByteArray arr (off + 7) (fromIntegral @Word64 @Word8 (unsafeShiftR w 56))
|
||||||
|
writeByteArray arr (off + 6) (fromIntegral @Word64 @Word8 (unsafeShiftR w 48))
|
||||||
|
writeByteArray arr (off + 5) (fromIntegral @Word64 @Word8 (unsafeShiftR w 40))
|
||||||
|
writeByteArray arr (off + 4) (fromIntegral @Word64 @Word8 (unsafeShiftR w 32))
|
||||||
|
writeByteArray arr (off + 3) (fromIntegral @Word64 @Word8 (unsafeShiftR w 24))
|
||||||
|
writeByteArray arr (off + 2) (fromIntegral @Word64 @Word8 (unsafeShiftR w 16))
|
||||||
|
writeByteArray arr (off + 1) (fromIntegral @Word64 @Word8 (unsafeShiftR w 8))
|
||||||
|
writeByteArray arr (off ) (fromIntegral @Word64 @Word8 w)
|
||||||
|
pure (off + 8)
|
||||||
|
|
||||||
-- | Requires exactly 8 bytes. Dump the octets of a 64-bit
|
-- | Requires exactly 8 bytes. Dump the octets of a 64-bit
|
||||||
-- word in a big-endian fashion.
|
-- word in a big-endian fashion.
|
||||||
word64BE :: Word64 -> Builder 8
|
word64BE :: Word64 -> Builder 8
|
||||||
|
@ -593,6 +621,16 @@ word64BE w = Unsafe.construct $ \arr off -> do
|
||||||
writeByteArray arr (off + 7) (fromIntegral @Word64 @Word8 w)
|
writeByteArray arr (off + 7) (fromIntegral @Word64 @Word8 w)
|
||||||
pure (off + 8)
|
pure (off + 8)
|
||||||
|
|
||||||
|
-- | Requires exactly 4 bytes. Dump the octets of a 32-bit
|
||||||
|
-- word in a little-endian fashion.
|
||||||
|
word32LE :: Word32 -> Builder 4
|
||||||
|
word32LE w = Unsafe.construct $ \arr off -> do
|
||||||
|
writeByteArray arr (off + 3) (fromIntegral @Word32 @Word8 (unsafeShiftR w 24))
|
||||||
|
writeByteArray arr (off + 2) (fromIntegral @Word32 @Word8 (unsafeShiftR w 16))
|
||||||
|
writeByteArray arr (off + 1) (fromIntegral @Word32 @Word8 (unsafeShiftR w 8))
|
||||||
|
writeByteArray arr (off ) (fromIntegral @Word32 @Word8 w)
|
||||||
|
pure (off + 4)
|
||||||
|
|
||||||
-- | Requires exactly 4 bytes. Dump the octets of a 32-bit
|
-- | Requires exactly 4 bytes. Dump the octets of a 32-bit
|
||||||
-- word in a big-endian fashion.
|
-- word in a big-endian fashion.
|
||||||
word32BE :: Word32 -> Builder 4
|
word32BE :: Word32 -> Builder 4
|
||||||
|
@ -603,6 +641,14 @@ word32BE w = Unsafe.construct $ \arr off -> do
|
||||||
writeByteArray arr (off + 3) (fromIntegral @Word32 @Word8 w)
|
writeByteArray arr (off + 3) (fromIntegral @Word32 @Word8 w)
|
||||||
pure (off + 4)
|
pure (off + 4)
|
||||||
|
|
||||||
|
-- | Requires exactly 2 bytes. Dump the octets of a 16-bit
|
||||||
|
-- word in a little-endian fashion.
|
||||||
|
word16LE :: Word16 -> Builder 2
|
||||||
|
word16LE w = Unsafe.construct $ \arr off -> do
|
||||||
|
writeByteArray arr (off + 1) (fromIntegral @Word16 @Word8 (unsafeShiftR w 8))
|
||||||
|
writeByteArray arr (off ) (fromIntegral @Word16 @Word8 w)
|
||||||
|
pure (off + 2)
|
||||||
|
|
||||||
-- | Requires exactly 2 bytes. Dump the octets of a 16-bit
|
-- | Requires exactly 2 bytes. Dump the octets of a 16-bit
|
||||||
-- word in a big-endian fashion.
|
-- word in a big-endian fashion.
|
||||||
word16BE :: Word16 -> Builder 2
|
word16BE :: Word16 -> Builder 2
|
||||||
|
|
Loading…
Reference in a new issue