• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2017 The Chromium OS Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef SRC_BIT_READER_H_
6 #define SRC_BIT_READER_H_
7 
8 #include <cstddef>
9 #include <cstdint>
10 
11 #include "puffin/src/include/puffin/common.h"
12 
13 namespace puffin {
14 
15 // An abstract class for reading bits from a deflate stream. It can be used
16 // either for the beginning of the deflate stream or for any place inside the
17 // deflate stream. For more information on the pattern of reading, refer to
18 // RFC1951 in https://www.ietf.org/rfc/rfc1951.txt
19 class BitReaderInterface {
20  public:
21   virtual ~BitReaderInterface() = default;
22 
23   // Caches at least |nbits| starting from the next available bit (next bit that
24   // will be read in |ReadBits|) in the cache. The maximum of number of bits
25   // that can be cached is implementation dependent.
26   //
27   // |nbits| IN  The number of bits to see if available in the input.
28   virtual bool CacheBits(size_t nbits) = 0;
29 
30   // Reads |nbits| from the cached input. Users should call |CacheBits| with
31   // greater than or equal to |nbits| bits before calling this function.
32   //
33   // |nbits| IN  The number of bits to read from the cache.
34   // Returns the read bits as an unsigned integer.
35   virtual uint32_t ReadBits(size_t nbits) = 0;
36 
37   // Drops |nbits| from the input cache. Users should be careful that |nbits|
38   // does not exceed the number of bits in the cache.
39   //
40   // |nbits| IN  The number of bits to drop from the cache.
41   virtual void DropBits(size_t nbits) = 0;
42 
43   // TODO(*): Add ReadAndDropBits(uint32_t nbits); Because it is a common
44   // pattern.
45 
46   // Returns an unsigned byte equal to the unread bits in the first cached
47   // byte. This function should not advance the bit pointer in any way. A call
48   // to |SkipBoundaryBits| should do the advancement.
49   virtual uint8_t ReadBoundaryBits() = 0;
50 
51   // Moves the current bit pointer to the beginning of the next byte and returns
52   // the number of bits skipped.
53   virtual size_t SkipBoundaryBits() = 0;
54 
55   // Populates a function that allows reading from the byte that has the next
56   // avilable bit for reading. This function clears all the bits that have been
57   // cached previously. As a consequence the next |CacheBits| starts reading
58   // from a byte boundary. The returned functin can only read |length| bytes. It
59   // might be necessary to call |ReadBoundaryBits| and |SkipBoundaryBits| before
60   // this function.
61   virtual bool GetByteReaderFn(
62       size_t length,
63       std::function<bool(uint8_t* buffer, size_t count)>* read_fn) = 0;
64 
65   // Returns the number of bytes read till now. This size includes the last
66   // partially read byte.
67   virtual size_t Offset() const = 0;
68 
69   // Returns the number of bits read (dropped) till now.
70   virtual uint64_t OffsetInBits() const = 0;
71 
72   // Returns the number of bits remaining to be cached.
73   virtual uint64_t BitsRemaining() const = 0;
74 };
75 
76 // A raw buffer implementation of |BitReaderInterface|.
77 class BufferBitReader : public BitReaderInterface {
78  public:
79   // Sets the beginning of the buffer that the users wants to read.
80   //
81   // |in_buf|  IN  The input buffer
82   // |in_size| IN  The size of the input buffer
BufferBitReader(const uint8_t * in_buf,size_t in_size)83   BufferBitReader(const uint8_t* in_buf, size_t in_size)
84       : in_buf_(in_buf),
85         in_size_(in_size),
86         index_(0),
87         in_cache_(0),
88         in_cache_bits_(0) {}
89 
90   ~BufferBitReader() override = default;
91 
92   // Can only cache up to 32 bits.
93   bool CacheBits(size_t nbits) override;
94   uint32_t ReadBits(size_t nbits) override;
95   void DropBits(size_t nbits) override;
96   uint8_t ReadBoundaryBits() override;
97   size_t SkipBoundaryBits() override;
98   bool GetByteReaderFn(
99       size_t length,
100       std::function<bool(uint8_t* buffer, size_t count)>* read_fn) override;
101   size_t Offset() const override;
102   uint64_t OffsetInBits() const override;
103   uint64_t BitsRemaining() const override;
104 
105  private:
106   const uint8_t* in_buf_;  // The input buffer.
107   uint64_t in_size_;       // The number of bytes in |in_buf_|.
108   uint64_t index_;         // The index to the next byte to be read.
109   uint32_t in_cache_;      // The temporary buffer to put input data into.
110   size_t in_cache_bits_;   // The number of bits available in |in_cache_|.
111 
112   DISALLOW_COPY_AND_ASSIGN(BufferBitReader);
113 };
114 
115 }  // namespace puffin
116 
117 #endif  // SRC_BIT_READER_H_
118