15d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// Copyright 2014 The Chromium Authors. All rights reserved. 25d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// found in the LICENSE file. 45d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 55d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#ifndef MEDIA_BASE_BIT_READER_CORE_H_ 65d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#define MEDIA_BASE_BIT_READER_CORE_H_ 75d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 85d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "base/basictypes.h" 95d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "base/logging.h" 105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "media/base/media_export.h" 115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)namespace media { 135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)class MEDIA_EXPORT BitReaderCore { 155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) public: 165d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) class ByteStreamProvider { 175d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) public: 185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) ByteStreamProvider(); 195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual ~ByteStreamProvider(); 205d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 215d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Consume at most the following |max_n| bytes of the stream 225d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // and return the number n of bytes actually consumed. 235d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Set |*array| to point to a memory buffer containing those n bytes. 245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Note: |*array| must be valid until the next call to GetBytes 255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // but there is no guarantee it is valid after. 265d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual int GetBytes(int max_n, const uint8** array) = 0; 275d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) }; 285d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 295d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Lifetime of |byte_stream_provider| must be longer than BitReaderCore. 305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) explicit BitReaderCore(ByteStreamProvider* byte_stream_provider); 315d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) ~BitReaderCore(); 325d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 335d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Read one bit from the stream and return it as a boolean in |*out|. 345d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Remark: we do not use the template version for reading a bool 355d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // since it generates some optimization warnings during compilation 365d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // on Windows platforms. 375d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool ReadBits(int num_bits, bool* out) { 385d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DCHECK_EQ(num_bits, 1); 395d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) return ReadFlag(out); 405d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) } 415d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 425d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Read |num_bits| next bits from stream and return in |*out|, first bit 435d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // from the stream starting at |num_bits| position in |*out|, 445d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // bits of |*out| whose position is strictly greater than |num_bits| 455d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // are all set to zero. 465d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Notes: 475d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // - |num_bits| cannot be larger than the bits the type can hold. 485d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // - From the above description, passing a signed type in |T| does not 495d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // mean the first bit read from the stream gives the sign of the value. 505d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Return false if the given number of bits cannot be read (not enough 515d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // bits in the stream), true otherwise. When return false, the stream will 525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // enter a state where further ReadBits/SkipBits operations will always 535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // return false unless |num_bits| is 0. The type |T| has to be a primitive 545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // integer type. 555d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) template<typename T> bool ReadBits(int num_bits, T* out) { 565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DCHECK_LE(num_bits, static_cast<int>(sizeof(T) * 8)); 575d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) uint64 temp; 585d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool ret = ReadBitsInternal(num_bits, &temp); 595d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) *out = static_cast<T>(temp); 605d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) return ret; 615d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) } 625d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Read one bit from the stream and return it as a boolean in |*flag|. 645d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool ReadFlag(bool* flag); 655d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 665d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Retrieve some bits without actually consuming them. 675d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Bits returned in |*out| are shifted so the most significant bit contains 685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // the next bit that can be read from the stream. 695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Return the number of bits actually written in |out|. 705d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Note: |num_bits| is just a suggestion of how many bits the caller 715d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // wish to get in |*out| and must be less than 64: 725d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // - The number of bits returned can be more than |num_bits|. 735d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // - However, it will be strictly less than |num_bits| 745d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // if and only if there are not enough bits left in the stream. 755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) int PeekBitsMsbAligned(int num_bits, uint64* out); 765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Skip |num_bits| next bits from stream. Return false if the given number of 785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // bits cannot be skipped (not enough bits in the stream), true otherwise. 795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // When return false, the stream will enter a state where further 805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // ReadBits/ReadFlag/SkipBits operations 815d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // will always return false unless |num_bits| is 0. 825d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool SkipBits(int num_bits); 835d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 845d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Returns the number of bits read so far. 855d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) int bits_read() const; 865d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 875d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) private: 881320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // This function can skip any number of bits but is more efficient 891320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // for small numbers. Return false if the given number of bits cannot be 901320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // skipped (not enough bits in the stream), true otherwise. 911320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci bool SkipBitsSmall(int num_bits); 921320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 935d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Help function used by ReadBits to avoid inlining the bit reading logic. 945d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool ReadBitsInternal(int num_bits, uint64* out); 955d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 965d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Refill bit registers to have at least |min_nbits| bits available. 975d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Return true if the mininimum bit count condition is met after the refill. 985d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool Refill(int min_nbits); 995d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1005d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Refill the current bit register from the next bit register. 1015d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void RefillCurrentRegister(); 1025d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1035d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) ByteStreamProvider* const byte_stream_provider_; 1045d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1055d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Number of bits read so far. 1065d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) int bits_read_; 1075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Number of bits in |reg_| that have not been consumed yet. 1095d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Note: bits are consumed from MSB to LSB. 1105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) int nbits_; 1115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) uint64 reg_; 1125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Number of bits in |reg_next_| that have not been consumed yet. 1145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Note: bits are consumed from MSB to LSB. 1155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) int nbits_next_; 1165d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) uint64 reg_next_; 1175d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(BitReaderCore); 1195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)}; 1205d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1215d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} // namespace media 1225d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1235d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#endif // MEDIA_BASE_BIT_READER_CORE_H_ 124