Raw bits enabled for the multiply-free range coder too.
authorJean-Marc Valin <jean-marc.valin@usherbrooke.ca>
Fri, 24 Oct 2008 00:07:18 +0000 (20:07 -0400)
committerJean-Marc Valin <jean-marc.valin@usherbrooke.ca>
Thu, 23 Jul 2009 11:33:25 +0000 (07:33 -0400)
libcelt/mfrngdec.c
libcelt/mfrngenc.c

index 55dd60c..5239f4e 100644 (file)
@@ -159,6 +159,9 @@ void ec_dec_init(ec_dec *_this,ec_byte_buffer *_buf){
   _this->dif=_this->rem>>EC_SYM_BITS-EC_CODE_EXTRA;
   /*Normalize the interval.*/
   ec_dec_normalize(_this);
+  _this->end_bits_left=0;
+  _this->nb_end_bits=0;
+
 }
 
 unsigned ec_decode(ec_dec *_this,unsigned _ft){
@@ -180,7 +183,24 @@ unsigned ec_decode(ec_dec *_this,unsigned _ft){
 }
 
 unsigned ec_decode_bin(ec_dec *_this,unsigned bits){
+#if 0
   return ec_decode(_this, 1U<<bits);
+#else
+  unsigned value=0;
+  int count=0;
+  _this->nb_end_bits += bits;
+  while (bits>=_this->end_bits_left)
+  {
+    value |= _this->end_byte>>(8-_this->end_bits_left)<<count;
+    count += _this->end_bits_left;
+    bits -= _this->end_bits_left;
+    _this->end_byte=ec_byte_look_at_end(_this->buf);
+    _this->end_bits_left = 8;
+  }
+  value |= ((_this->end_byte>>(8-_this->end_bits_left))&((1<<bits)-1))<<count;
+  _this->end_bits_left -= bits;
+  return value;
+#endif
 }
 
 void ec_dec_update(ec_dec *_this,unsigned _fl,unsigned _fh,unsigned _ft){
@@ -213,7 +233,7 @@ long ec_dec_tell(ec_dec *_this,int _b){
   /*To handle the non-integral number of bits still left in the decoder state,
      we compute the number of bits of low that must be encoded to ensure that
      the value is inside the range for any possible subsequent bits.*/
-  nbits+=EC_CODE_BITS+1;
+  nbits+=EC_CODE_BITS+1+_this->nb_end_bits;
   nbits<<=_b;
   l=EC_ILOG(_this->rng);
   r=_this->rng>>l-16;
index 1266f24..d1f3c31 100644 (file)
@@ -120,6 +120,9 @@ void ec_enc_init(ec_enc *_this,ec_byte_buffer *_buf){
   _this->ext=0;
   _this->low=0;
   _this->rng=EC_CODE_TOP;
+  _this->end_byte=0;
+  _this->end_bits_left=8;
+  _this->nb_end_bits=0;
 }
 
 void ec_encode(ec_enc *_this,unsigned _fl,unsigned _fh,unsigned _ft){
@@ -159,7 +162,22 @@ void ec_encode(ec_enc *_this,unsigned _fl,unsigned _fh,unsigned _ft){
 }
 
 void ec_encode_bin(ec_enc *_this,unsigned _fl,unsigned _fh,unsigned bits){
+#if 0
   ec_encode(_this, _fl, _fh, 1U<<bits);
+#else
+  _this->nb_end_bits += bits;
+  while (bits >= _this->end_bits_left)
+  {
+    _this->end_byte |= (_fl<<(8-_this->end_bits_left)) & 0xff;
+    _fl >>= _this->end_bits_left;
+    ec_byte_write_at_end(_this->buf, _this->end_byte);
+    _this->end_byte = 0;
+    bits -= _this->end_bits_left;
+    _this->end_bits_left = 8;
+  }
+  _this->end_byte |= (_fl<<(8-_this->end_bits_left)) & 0xff;
+  _this->end_bits_left -= bits;
+#endif
 }
 
 long ec_enc_tell(ec_enc *_this,int _b){
@@ -170,7 +188,7 @@ long ec_enc_tell(ec_enc *_this,int _b){
   /*To handle the non-integral number of bits still left in the encoder state,
      we compute the number of bits of low that must be encoded to ensure that
      the value is inside the range for any possible subsequent bits.*/
-  nbits+=EC_CODE_BITS+1;
+  nbits+=EC_CODE_BITS+1+_this->nb_end_bits;
   nbits<<=_b;
   l=EC_ILOG(_this->rng);
   r=_this->rng>>l-16;
@@ -208,4 +226,11 @@ void ec_enc_done(ec_enc *_this){
     ec_enc_carry_out(_this,0);
     _this->rem=-1;
   }
+  {
+    unsigned char *ptr = _this->buf->ptr;
+    while (ptr<= _this->buf->end_ptr)
+      *ptr++ = 0;
+    if (_this->end_bits_left != 8)
+      *_this->buf->end_ptr |= _this->end_byte;
+  }
 }