on master help sign in
Merge branch 'master' of ssh://github.com/kolmodin/binary-bits
2cc392fLennart Kolmodin
BitsQC.hs+43
@@ -38,6 +38,20 @@ tests =
38 , testGroup "getByteString"
38 , testGroup "getByteString"
39 [ testProperty "prop_getByteString_negative" prop_getByteString_negative ]
39 [ testProperty "prop_getByteString_negative" prop_getByteString_negative ]
40
40
41+ , testGroup "getLazyByteString"
42+ [ testProperty "getLazyByteString == getByteString"
43+ prop_getLazyByteString_equal_to_ByteString
44+ , testProperty "getLazyByteString == getByteString (with shift)"
45+ prop_getLazyByteString_equal_to_ByteString2
46+ ]
47+
48+ , testGroup "isEmpty"
49+ [ testProperty "prop_isEmptyOfEmptyEmpty" prop_isEmptyOfEmptyEmpty
50+ , testProperty "prop_isEmptyOfNonEmptyEmpty" prop_isEmptyOfNonEmptyEmpty
51+ , testProperty "prop_isEmptyOfConsumedEmpty" prop_isEmptyOfConsumedEmpty
52+ , testProperty "prop_isEmptyOfNotConsumedNotEmpty" prop_isEmptyOfNotConsumedNotEmpty
53+ ]
54+
41 , testGroup "Fail"
55 , testGroup "Fail"
42 [ testProperty "monadic fail" prop_fail ]
56 [ testProperty "monadic fail" prop_fail ]
43
57
@@ -105,6 +119,35 @@ tests =
105 ]
119 ]
106 ]
120 ]
107
121
122+prop_isEmptyOfEmptyEmpty :: Bool
123+prop_isEmptyOfEmptyEmpty = runGet (runBitGet isEmpty) L.empty
124+
125+prop_isEmptyOfNonEmptyEmpty :: L.ByteString -> Property
126+prop_isEmptyOfNonEmptyEmpty bs =
127+ not (L.null bs) ==> not (runGet (runBitGet isEmpty) bs)
128+
129+prop_isEmptyOfConsumedEmpty :: L.ByteString -> Property
130+prop_isEmptyOfConsumedEmpty bs =
131+ not (L.null bs) ==>
132+ runGet (runBitGet (getByteString n >> isEmpty)) bs
133+ where n = fromIntegral $ L.length bs
134+
135+prop_isEmptyOfNotConsumedNotEmpty :: L.ByteString -> Int -> Property
136+prop_isEmptyOfNotConsumedNotEmpty bs n =
137+ (fromIntegral n) < L.length bs && not (L.null bs) ==>
138+ not (runGet (runBitGet (getByteString n >> isEmpty)) bs)
139+
140+prop_getLazyByteString_equal_to_ByteString :: L.ByteString -> Int -> Property
141+prop_getLazyByteString_equal_to_ByteString bs n =
142+ (fromIntegral n) <= L.length bs ==>
143+ runGet (runBitGet (getLazyByteString (fromIntegral n))) bs ==
144+ (L.fromChunks . (:[]) $ runGet (runBitGet (getByteString n)) bs)
145+
146+prop_getLazyByteString_equal_to_ByteString2 :: L.ByteString -> Int -> Property
147+prop_getLazyByteString_equal_to_ByteString2 bs n =
148+ (L.length bs > 1) && (fromIntegral n) < L.length bs ==>
149+ runGet (runBitGet (getWord8 2 >> getLazyByteString (fromIntegral n))) bs ==
150+ (L.fromChunks . (:[]) $ runGet (runBitGet (getWord8 2 >> getByteString n)) bs)
108
151
109prop_getByteString_negative :: Int -> Property
152prop_getByteString_negative :: Int -> Property
110prop_getByteString_negative n =
153prop_getByteString_negative n =
Data/Binary/Bits/Get.hs+18−6
@@ -79,10 +79,11 @@ module Data.Binary.Bits.Get
79 , byteString
79 , byteString
80 , Data.Binary.Bits.Get.getByteString
80 , Data.Binary.Bits.Get.getByteString
81 , Data.Binary.Bits.Get.getLazyByteString
81 , Data.Binary.Bits.Get.getLazyByteString
82+ , Data.Binary.Bits.Get.isEmpty
82
83
83 ) where
84 ) where
84
85
85−import Data.Binary.Get as B ( runGet, Get, getByteString, getLazyByteString )
86+import Data.Binary.Get as B ( runGet, Get, getByteString, getLazyByteString, isEmpty )
86import Data.Binary.Get.Internal as B ( get, put, ensureN )
87import Data.Binary.Get.Internal as B ( get, put, ensureN )
87
88
88import Data.ByteString as B
89import Data.ByteString as B
@@ -91,7 +92,6 @@ import Data.ByteString.Unsafe
91
92
92import Data.Bits
93import Data.Bits
93import Data.Word
94import Data.Word
94−
95import Control.Applicative
95import Control.Applicative
96
96
97import Prelude as P
97import Prelude as P
@@ -416,11 +416,23 @@ getWord64be n = block (word64be n)
416getByteString :: Int -> BitGet ByteString
416getByteString :: Int -> BitGet ByteString
417getByteString n = block (byteString n)
417getByteString n = block (byteString n)
418
418
419+-- | Get @n@ bytes as a lazy ByteString.
419getLazyByteString :: Int -> BitGet L.ByteString
420getLazyByteString :: Int -> BitGet L.ByteString
420−getLazyByteString m = B $ \ (S n bs) -> do
421+getLazyByteString n = do
422+ (S _ o) <- getState
423+ case o of
424+ 0 -> B $ \ (S bs o') -> do
421− putBackState n bs
425+ putBackState bs o'
422− lbs <- B.getLazyByteString (fromIntegral m)
426+ lbs <- B.getLazyByteString (fromIntegral n)
423− return (S B.empty 0, lbs)
427+ return (S B.empty 0, lbs)
428+ _ -> L.fromChunks . (:[]) <$> Data.Binary.Bits.Get.getByteString n
429+
430+-- | Test whether all input has been consumed, i.e. there are no remaining
431+-- undecoded bytes.
432+isEmpty :: BitGet Bool
433+isEmpty = B $ \ (S bs o) -> if B.null bs
434+ then B.isEmpty >>= \e -> return (S bs o, e)
435+ else return (S bs o, False)
424
436
425-- | Read a 1 bit 'Bool'.
437-- | Read a 1 bit 'Bool'.
426bool :: Block Bool
438bool :: Block Bool