diff options
author | Paul Gilbert | 2016-09-10 20:35:02 -0400 |
---|---|---|
committer | Paul Gilbert | 2016-09-10 20:35:02 -0400 |
commit | 23b1dbbb0e9c10035a1df98bffa9d6eaa5a6d338 (patch) | |
tree | fb2b3194e646bce8e7f6f966424fc217b586c502 /image/codecs/indeo/get_bits.cpp | |
parent | 9c6a55a2a660d2c59e9c0e22402e4d16e08ef987 (diff) | |
download | scummvm-rg350-23b1dbbb0e9c10035a1df98bffa9d6eaa5a6d338.tar.gz scummvm-rg350-23b1dbbb0e9c10035a1df98bffa9d6eaa5a6d338.tar.bz2 scummvm-rg350-23b1dbbb0e9c10035a1df98bffa9d6eaa5a6d338.zip |
IMAGE: Refactored Indeo GetBits class to derive from Common::BitStream
Diffstat (limited to 'image/codecs/indeo/get_bits.cpp')
-rw-r--r-- | image/codecs/indeo/get_bits.cpp | 440 |
1 files changed, 20 insertions, 420 deletions
diff --git a/image/codecs/indeo/get_bits.cpp b/image/codecs/indeo/get_bits.cpp index ade4baaa81..ede5fa2a8f 100644 --- a/image/codecs/indeo/get_bits.cpp +++ b/image/codecs/indeo/get_bits.cpp @@ -21,439 +21,39 @@ */ #include "image/codecs/indeo/get_bits.h" -#include "image/codecs/indeo/mem.h" -#include "common/algorithm.h" -#include "common/endian.h" -#include "common/textconsole.h" - -/* Intel Indeo 4 bitstream reader - * - * Original copyright note: - * Copyright (c) 2004 Michael Niedermayer - */ namespace Image { namespace Indeo { -/* Macro documentation - * name - * arbitrary name which is used as prefix for local variables - * - * OPEN_READER(name) - * load index into local variable - * - * CLOSE_READER(name) - * store local index back into class state - * - * UPDATE_CACHE(name) - * Refill the internal cache from the bitstream. - * After this call at least MIN_CACHE_BITS will be available. - * - * GET_CACHE(name) - * Will output the contents of the internal cache, - * next bit is MSB of 32 or 64 bits (FIXME 64 bits). - * - * SHOW_UBITS(name, num) - * Will return the next num bits. - * - * SHOW_SBITS(name, num) - * Will return the next num bits and do sign extension. - * - * SKIP_BITS(name, num) - * Will skip over the next num bits. - * Note, this is equivalent to SKIP_CACHE; SKIP_COUNTER. - * - * SKIP_CACHE(name, num) - * Will remove the next num bits from the cache (note SKIP_COUNTER - * MUST be called before UPDATE_CACHE / CLOSE_READER). - * - * SKIP_COUNTER(name, num) - * Will increment the internal bit counter (see SKIP_CACHE & SKIP_BITS). - * - * LAST_SKIP_BITS(name, num) - * Like SKIP_BITS, to be used if next call is UPDATE_CACHE or CLOSE_READER. - * - * BITS_LEFT(name) - * Return the number of bits left - * - * For examples see getBits, show_bits, skip_bits, get_vlc. - */ -#define BITSTREAM_READER_LE - -#ifdef LONG_BITSTREAM_READER -# define MIN_CACHE_BITS 32 -#else -# define MIN_CACHE_BITS 25 -#endif - -#define NEG_USR32(a,s) (((uint32)(a)) >> (32 -(s))) - -#define OPEN_READER_NOSIZE(name) \ - unsigned int name ## _index = _index; \ - unsigned int name ## _cache - -#define OPEN_READER(name) OPEN_READER_NOSIZE(name) -#define BITS_AVAILABLE(name) 1 - -#define CLOSE_READER(name) _index = name ## _index - -# ifdef LONG_BITSTREAM_READER -# define UPDATE_CACHE_LE(name) name ## _cache = \ - AV_RL64(_buffer + (name ## _index >> 3)) >> (name ## _index & 7) - -# define UPDATE_CACHE_BE(name) name ## _cache = \ - AV_RB64(_buffer + (name ## _index >> 3)) >> (32 - (name ## _index & 7)) -#else -# define UPDATE_CACHE_LE(name) name ## _cache = \ - READ_LE_UINT32(_buffer + (name ## _index >> 3)) >> (name ## _index & 7) - -# define UPDATE_CACHE_BE(name) name ## _cache = \ - AV_RB32(_buffer + (name ## _index >> 3)) << (name ## _index & 7) -#endif - -#ifdef BITSTREAM_READER_LE -# define UPDATE_CACHE(name) UPDATE_CACHE_LE(name) -# define SKIP_CACHE(name, num) name ## _cache >>= (num) -#else -# define UPDATE_CACHE(name) UPDATE_CACHE_BE(name) -# define SKIP_CACHE(name, num) name ## _cache <<= (num) -#endif - -#define SKIP_COUNTER(name, num) name ## _index += (num) - -#define BITS_LEFT(name) ((int)(_size_in_bits - name ## _index)) - -#define SKIP_BITS(name, num) \ - do { \ - SKIP_CACHE(name, num); \ - SKIP_COUNTER(name, num); \ - } while (0) - -#define LAST_SKIP_BITS(name, num) SKIP_COUNTER(name, num) - -#define SHOW_UBITS_LE(name, num) zeroExtend(name ## _cache, num) -#define SHOW_SBITS_LE(name, num) signExtend(name ## _cache, num) - -#define SHOW_UBITS_BE(name, num) NEG_USR32(name ## _cache, num) -#define SHOW_SBITS_BE(name, num) NEG_SSR32(name ## _cache, num) - -#ifdef BITSTREAM_READER_LE -# define SHOW_UBITS(name, num) SHOW_UBITS_LE(name, num) -# define SHOW_SBITS(name, num) SHOW_SBITS_LE(name, num) -#else -# define SHOW_UBITS(name, num) SHOW_UBITS_BE(name, num) -# define SHOW_SBITS(name, num) SHOW_SBITS_BE(name, num) -#endif - -#define GET_CACHE(name) ((uint32) name ## _cache) - - -static int signExtend(int val, uint bits) { - uint shift = 8 * sizeof(int) - bits; - union { uint u; int s; } v = { (unsigned)val << shift }; - return v.s >> shift; -} - -static uint zeroExtend(uint val, uint bits) { - return (val << ((8 * sizeof(int)) - bits)) >> ((8 * sizeof(int)) - bits); -} - -GetBits::GetBits(const byte *buffer, size_t totalBits) { - assert(buffer && totalBits < (MAX_INTEGER - 7)); - - _buffer = buffer; - _sizeInBits = totalBits; - _sizeInBitsPlus8 = totalBits + 8; - _index = 0; -} - -GetBits::GetBits(const GetBits &src) : _index(src._index), _buffer(src._buffer), - _sizeInBits(src._sizeInBits), _sizeInBitsPlus8(src._sizeInBitsPlus8){ -} - -int GetBits::getXbits(int n) { - int sign; - int cache; - OPEN_READER(re); - assert(n > 0 && n <= 25); - UPDATE_CACHE(re); - cache = GET_CACHE(re); - sign = ~cache >> 31; - LAST_SKIP_BITS(re, n); - CLOSE_READER(re); - return (NEG_USR32(sign ^ cache, n) ^ sign) - sign; -} - -int GetBits::getSbits(int n) { - int tmp; - OPEN_READER(re); - assert(n > 0 && n <= 25); - UPDATE_CACHE(re); - tmp = SHOW_SBITS(re, n); - LAST_SKIP_BITS(re, n); - CLOSE_READER(re); - return tmp; -} - -/** -* Read 1-25 bits. -*/ -uint GetBits::getBits(int n) { - int tmp; - OPEN_READER(re); - assert(n > 0 && n <= 25); - UPDATE_CACHE(re); - tmp = SHOW_UBITS(re, n); - LAST_SKIP_BITS(re, n); - CLOSE_READER(re); - return tmp; -} - -int GetBits::getBitsZ(int n) { - return n ? getBits(n) : 0; -} - -uint GetBits::getBitsLE(int n) { - int tmp; - OPEN_READER(re); - assert(n > 0 && n <= 25); - UPDATE_CACHE_LE(re); - tmp = SHOW_UBITS_LE(re, n); - LAST_SKIP_BITS(re, n); - CLOSE_READER(re); - return tmp; -} - -uint GetBits::showBits(int n) { - int tmp; - OPEN_READER_NOSIZE(re); - assert(n > 0 && n <= 25); - UPDATE_CACHE(re); - tmp = SHOW_UBITS(re, n); - return tmp; -} - -void GetBits::skipBits(int n) { - OPEN_READER(re); - LAST_SKIP_BITS(re, n); - CLOSE_READER(re); -} - -uint GetBits::getBits1() { - uint index = _index; - uint8 result = _buffer[index >> 3]; -#ifdef BITSTREAM_READER_LE - result >>= index & 7; - result &= 1; -#else - result <<= index & 7; - result >>= 8 - 1; -#endif - index++; - _index = index; - - return result; -} - -uint GetBits::showBits1() { - return showBits(1); -} - -void GetBits::skipBits1() { - skipBits(1); -} - -/** -* Read 0-32 bits. -*/ -uint GetBits::getBitsLong(int n) { - if (!n) { - return 0; - } else if (n <= MIN_CACHE_BITS) { - return getBits(n); - } else { -#ifdef BITSTREAM_READER_LE - unsigned ret = getBits(16); - return ret | (getBits(n - 16) << 16); -#else - unsigned ret = getBits(16) << (n - 16); - return ret | getBits(n - 16); -#endif - } -} - -/** - * Read 0-64 bits. - */ -uint64 GetBits::getBits64(int n) { - if (n <= 32) { - return getBitsLong(n); - } else { -#ifdef BITSTREAM_READER_LE - uint64 ret = getBitsLong(32); - return ret | (uint64)getBitsLong(n - 32) << 32; -#else - uint64 ret = (uint64)getBitsLong(n - 32) << 32; - return ret | getBitsLong(32); -#endif - } -} - -int GetBits::getSbitsLong(int n) { - return signExtend(getBitsLong(n), n); -} - -/** -* Show 0-32 bits. -*/ -uint GetBits::showBitsLong(int n) { - if (n <= MIN_CACHE_BITS) { - return showBits(n); - } else { - GetBits gb(*this); - return gb.getBitsLong(n); - } -} - -int GetBits::checkMarker(void *logctx, const char *msg) { - int bit = getBits1(); - if (!bit) - warning("Marker bit missing at %d of %d %s\n", - getBitsCount() - 1, _sizeInBits, msg); - - return bit; -} - -const byte *GetBits::alignGetBits() { - int n = -(int)getBitsCount() & 7; - if (n) - skipBits(n); - - return _buffer + (_index >> 3); -} - -/** - * If the vlc code is invalid and max_depth=1, then no bits will be removed. - * If the vlc code is invalid and max_depth>1, then the number of bits removed - * is undefined. - */ -#define GET_VLC(code, name, table, bits, max_depth) \ - do { \ - int n, nb_bits; \ - unsigned int index; \ - \ - index = SHOW_UBITS(name, bits); \ - code = table[index][0]; \ - n = table[index][1]; \ - \ - if (max_depth > 1 && n < 0) { \ - LAST_SKIP_BITS(name, bits); \ - UPDATE_CACHE(name); \ - \ - nb_bits = -n; \ - \ - index = SHOW_UBITS(name, nb_bits) + code; \ - code = table[index][0]; \ - n = table[index][1]; \ - if (max_depth > 2 && n < 0) { \ - LAST_SKIP_BITS(name, nb_bits); \ - UPDATE_CACHE(name); \ - \ - nb_bits = -n; \ - \ - index = SHOW_UBITS(name, nb_bits) + code; \ - code = table[index][0]; \ - n = table[index][1]; \ - } \ - } \ - SKIP_BITS(name, n); \ - } while (0) - -#define GET_RL_VLC(level, run, name, table, bits, \ - max_depth, need_update) \ - do { \ - int n, nb_bits; \ - unsigned int index; \ - \ - index = SHOW_UBITS(name, bits); \ - level = table[index].level; \ - n = table[index].len; \ - \ - if (max_depth > 1 && n < 0) { \ - SKIP_BITS(name, bits); \ - if (need_update) { \ - UPDATE_CACHE(name); \ - } \ - \ - nb_bits = -n; \ - \ - index = SHOW_UBITS(name, nb_bits) + level; \ - level = table[index].level; \ - n = table[index].len; \ - if (max_depth > 2 && n < 0) { \ - LAST_SKIP_BITS(name, nb_bits); \ - if (need_update) { \ - UPDATE_CACHE(name); \ - } \ - nb_bits = -n; \ - \ - index = SHOW_UBITS(name, nb_bits) + level; \ - level = table[index].level; \ - n = table[index].len; \ - } \ - } \ - run = table[index].run; \ - SKIP_BITS(name, n); \ - } while (0) - -/** -* Parse a vlc code. -* @param bits is the number of bits which will be read at once, must be -* identical to nb_bits in init_vlc() -* @param max_depth is the number of times bits bits must be read to completely -* read the longest vlc code -* = (max_vlc_length + bits - 1) / bits -*/ int GetBits::getVLC2(int16 (*table)[2], int bits, int maxDepth) { int code; + int n, nbBits; + unsigned int index; - OPEN_READER(re); - UPDATE_CACHE(re); + index = peekBits(bits); + code = table[index][0]; + n = table[index][1]; - GET_VLC(code, re, table, bits, maxDepth); + if (maxDepth > 1 && n < 0) { + skip(bits); + nbBits = -n; - CLOSE_READER(re); + index = peekBits(nbBits) + code; + code = table[index][0]; + n = table[index][1]; - return code; -} + if (maxDepth > 2 && n < 0) { + skip(nbBits); + nbBits = -n; -int GetBits::decode012() { - int n; - n = getBits1(); - if (n == 0) - return 0; - else - return getBits1() + 1; -} - -int GetBits::decode210() { - if (getBits1()) - return 0; - else - return 2 - getBits1(); -} - -int GetBits::skip1stop8dataBits() { - if (getBitsLeft() <= 0) - return -1; - - while (getBits1()) { - skipBits(8); - if (getBitsLeft() <= 0) - return -1; + index = peekBits(nbBits) + code; + code = table[index][0]; + n = table[index][1]; + } } - return 0; + skip(n); + return code; } } // End of namespace Indeo |