Cog/Frameworks/OpenMPT/OpenMPT/soundlib/BitReader.h
Christopher Snowhill da1973bcd9 Build libOpenMPT from source once again
Bundle libOpenMPT as a dynamic framework, which should be safe once
again, now that there is only one version to bundle. Also, now it is
using the versions of libvorbisfile and libmpg123 that are bundled with
the player, instead of compiling minimp3 and stbvorbis.

Signed-off-by: Christopher Snowhill <kode54@gmail.com>
2022-06-30 22:56:52 -07:00

82 lines
1.8 KiB
C++

/*
* BitReader.h
* -----------
* Purpose: An extended FileReader to read bit-oriented rather than byte-oriented streams.
* Notes : The current implementation can only read bit widths up to 32 bits, and it always
* reads bits starting from the least significant bit, as this is all that is
* required by the class users at the moment.
* Authors: OpenMPT Devs
* The OpenMPT source code is released under the BSD license. Read LICENSE for more details.
*/
#pragma once
#include "openmpt/all/BuildSettings.hpp"
#include "../common/FileReader.h"
#include <stdexcept>
#include "mpt/io/base.hpp"
OPENMPT_NAMESPACE_BEGIN
class BitReader : private FileReader
{
protected:
off_t m_bufPos = 0, m_bufSize = 0;
uint32 bitBuf = 0; // Current bit buffer
int m_bitNum = 0; // Currently available number of bits
std::byte buffer[mpt::IO::BUFFERSIZE_TINY]{};
public:
class eof : public std::range_error
{
public:
eof() : std::range_error("Truncated bit buffer") { }
};
BitReader() : FileReader() { }
BitReader(mpt::span<const std::byte> bytedata) : FileReader(bytedata) { }
BitReader(const FileCursor &other) : FileReader(other) { }
BitReader(FileCursor &&other) : FileReader(std::move(other)) { }
off_t GetLength() const
{
return FileReader::GetLength();
}
off_t GetPosition() const
{
return FileReader::GetPosition() - m_bufSize + m_bufPos;
}
uint32 ReadBits(int numBits)
{
while(m_bitNum < numBits)
{
// Fetch more bits
if(m_bufPos >= m_bufSize)
{
m_bufSize = ReadRaw(mpt::as_span(buffer)).size();
m_bufPos = 0;
if(!m_bufSize)
{
throw eof();
}
}
bitBuf |= (static_cast<uint32>(buffer[m_bufPos++]) << m_bitNum);
m_bitNum += 8;
}
uint32 v = bitBuf & ((1 << numBits) - 1);
bitBuf >>= numBits;
m_bitNum -= numBits;
return v;
}
};
OPENMPT_NAMESPACE_END