1 // Copyright 2011 Google Inc. All Rights Reserved. 2 // 3 // This code is licensed under the same terms as WebM: 4 // Software License Agreement: http://www.webmproject.org/license/software/ 5 // Additional IP Rights Grant: http://www.webmproject.org/license/additional/ 6 // ----------------------------------------------------------------------------- 7 // 8 // Bit writing and boolean coder 9 // 10 // Author: Skal (pascal.massimino (at) gmail.com) 11 12 #ifndef WEBP_UTILS_BIT_WRITER_H_ 13 #define WEBP_UTILS_BIT_WRITER_H_ 14 15 #include "webp/types.h" 16 17 #if defined(__cplusplus) || defined(c_plusplus) 18 extern "C" { 19 #endif 20 21 //------------------------------------------------------------------------------ 22 // Bit-writing 23 24 typedef struct VP8BitWriter VP8BitWriter; 25 struct VP8BitWriter { 26 int32_t range_; // range-1 27 int32_t value_; 28 int run_; // number of outstanding bits 29 int nb_bits_; // number of pending bits 30 uint8_t* buf_; // internal buffer. Re-allocated regularly. Not owned. 31 size_t pos_; 32 size_t max_pos_; 33 int error_; // true in case of error 34 }; 35 36 // Initialize the object. Allocates some initial memory based on expected_size. 37 int VP8BitWriterInit(VP8BitWriter* const bw, size_t expected_size); 38 // Finalize the bitstream coding. Returns a pointer to the internal buffer. 39 uint8_t* VP8BitWriterFinish(VP8BitWriter* const bw); 40 // Release any pending memory and zeroes the object. Not a mandatory call. 41 // Only useful in case of error, when the internal buffer hasn't been grabbed! 42 void VP8BitWriterWipeOut(VP8BitWriter* const bw); 43 44 int VP8PutBit(VP8BitWriter* const bw, int bit, int prob); 45 int VP8PutBitUniform(VP8BitWriter* const bw, int bit); 46 void VP8PutValue(VP8BitWriter* const bw, int value, int nb_bits); 47 void VP8PutSignedValue(VP8BitWriter* const bw, int value, int nb_bits); 48 49 // Appends some bytes to the internal buffer. Data is copied. 50 int VP8BitWriterAppend(VP8BitWriter* const bw, 51 const uint8_t* data, size_t size); 52 53 // return approximate write position (in bits) 54 static WEBP_INLINE uint64_t VP8BitWriterPos(const VP8BitWriter* const bw) { 55 return (uint64_t)(bw->pos_ + bw->run_) * 8 + 8 + bw->nb_bits_; 56 } 57 58 // Returns a pointer to the internal buffer. 59 static WEBP_INLINE uint8_t* VP8BitWriterBuf(const VP8BitWriter* const bw) { 60 return bw->buf_; 61 } 62 // Returns the size of the internal buffer. 63 static WEBP_INLINE size_t VP8BitWriterSize(const VP8BitWriter* const bw) { 64 return bw->pos_; 65 } 66 67 //------------------------------------------------------------------------------ 68 // VP8LBitWriter 69 // TODO(vikasa): VP8LBitWriter is copied as-is from lossless code. There's scope 70 // of re-using VP8BitWriter. Will evaluate once basic lossless encoder is 71 // implemented. 72 73 typedef struct { 74 uint8_t* buf_; 75 size_t bit_pos_; 76 size_t max_bytes_; 77 78 // After all bits are written, the caller must observe the state of 79 // error_. A value of 1 indicates that a memory allocation failure 80 // has happened during bit writing. A value of 0 indicates successful 81 // writing of bits. 82 int error_; 83 } VP8LBitWriter; 84 85 static WEBP_INLINE size_t VP8LBitWriterNumBytes(VP8LBitWriter* const bw) { 86 return (bw->bit_pos_ + 7) >> 3; 87 } 88 89 static WEBP_INLINE uint8_t* VP8LBitWriterFinish(VP8LBitWriter* const bw) { 90 return bw->buf_; 91 } 92 93 // Returns 0 in case of memory allocation error. 94 int VP8LBitWriterInit(VP8LBitWriter* const bw, size_t expected_size); 95 96 void VP8LBitWriterDestroy(VP8LBitWriter* const bw); 97 98 // This function writes bits into bytes in increasing addresses, and within 99 // a byte least-significant-bit first. 100 // 101 // The function can write up to 16 bits in one go with WriteBits 102 // Example: let's assume that 3 bits (Rs below) have been written already: 103 // 104 // BYTE-0 BYTE+1 BYTE+2 105 // 106 // 0000 0RRR 0000 0000 0000 0000 107 // 108 // Now, we could write 5 or less bits in MSB by just sifting by 3 109 // and OR'ing to BYTE-0. 110 // 111 // For n bits, we take the last 5 bytes, OR that with high bits in BYTE-0, 112 // and locate the rest in BYTE+1 and BYTE+2. 113 // 114 // VP8LBitWriter's error_ flag is set in case of memory allocation error. 115 void VP8LWriteBits(VP8LBitWriter* const bw, int n_bits, uint32_t bits); 116 117 //------------------------------------------------------------------------------ 118 119 #if defined(__cplusplus) || defined(c_plusplus) 120 } // extern "C" 121 #endif 122 123 #endif /* WEBP_UTILS_BIT_WRITER_H_ */ 124