bitstream.c
上传用户:zhongxx05
上传日期:2007-06-06
资源大小:33641k
文件大小:7k
源码类别:

Symbian

开发平台:

C/C++

  1. /* ***** BEGIN LICENSE BLOCK ***** 
  2.  * Version: RCSL 1.0/RPSL 1.0 
  3.  *  
  4.  * Portions Copyright (c) 1995-2002 RealNetworks, Inc. All Rights Reserved. 
  5.  *      
  6.  * The contents of this file, and the files included with this file, are 
  7.  * subject to the current version of the RealNetworks Public Source License 
  8.  * Version 1.0 (the "RPSL") available at 
  9.  * http://www.helixcommunity.org/content/rpsl unless you have licensed 
  10.  * the file under the RealNetworks Community Source License Version 1.0 
  11.  * (the "RCSL") available at http://www.helixcommunity.org/content/rcsl, 
  12.  * in which case the RCSL will apply. You may also obtain the license terms 
  13.  * directly from RealNetworks.  You may not use this file except in 
  14.  * compliance with the RPSL or, if you have a valid RCSL with RealNetworks 
  15.  * applicable to this file, the RCSL.  Please see the applicable RPSL or 
  16.  * RCSL for the rights, obligations and limitations governing use of the 
  17.  * contents of the file.  
  18.  *  
  19.  * This file is part of the Helix DNA Technology. RealNetworks is the 
  20.  * developer of the Original Code and owns the copyrights in the portions 
  21.  * it created. 
  22.  *  
  23.  * This file, and the files included with this file, is distributed and made 
  24.  * available on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 
  25.  * EXPRESS OR IMPLIED, AND REALNETWORKS HEREBY DISCLAIMS ALL SUCH WARRANTIES, 
  26.  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, FITNESS 
  27.  * FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 
  28.  * 
  29.  * Technology Compatibility Kit Test Suite(s) Location: 
  30.  *    http://www.helixcommunity.org/content/tck 
  31.  * 
  32.  * Contributor(s): 
  33.  *  
  34.  * ***** END LICENSE BLOCK ***** */ 
  35. /* bitstream reader functions. No checking for end-of-bits included! */
  36. #include "bitstream.h"
  37. #include <stdlib.h>
  38. #define ASSERT(a)
  39. /** The bitstream structure.
  40.  *  The idea of the bitstream reader is to keep a cache word that has the machine's
  41.  *  largest native size. This word keeps the next-to-read bits left-aligned so that
  42.  *  on a read, one shift suffices.
  43.  *  The cache word is only refilled if it does not contain enough bits to satisy a
  44.  *  a read request. Because the refill only happens in multiple of 8 bits, the maximum
  45.  *  read size that is guaranteed to be always fulfilled is the number of bits in a long
  46.  *  minus 8 (or whatever the number of bits in a byte is).
  47.  */
  48. struct BITSTREAM
  49. {
  50.     const unsigned char *buffer ; /**< points to the buffer holding the bits */
  51.     const unsigned char *pkptr ;  /**< read pointer */
  52.     unsigned long cache ;   /**< cache, always holds next bits left-aligned. */
  53.     int cacheBitsLeft ;     /**< number of bits left in cache */
  54.     int nBits ;    /**< the number of bits in the buffer */
  55.     int inc ;      /**< read direction (forward/backward) */
  56. } ;
  57. enum {
  58.     CACHEBITS = 8*sizeof(unsigned long)
  59. } ;
  60. __inline static void fillUp(struct BITSTREAM *pBitstream)
  61. {
  62.     unsigned long k = 0 ;
  63.     while (CACHEBITS - pBitstream->cacheBitsLeft >= 8)
  64.     {
  65.         k = (k<<8) + *(pBitstream->pkptr) ;
  66.         (pBitstream->pkptr)+= pBitstream->inc ;
  67.         pBitstream->cacheBitsLeft += 8 ;
  68.     }
  69.     pBitstream->cache |= (k << (CACHEBITS - pBitstream->cacheBitsLeft)) ;
  70. }
  71. /** read nBits bits from bitstream
  72.   * @param pBitstream the bitstream to read from
  73.   * @param nBits the number of bits to read. nBits must be <= 32, currently.
  74.   * @return the bits read, right-justified
  75.   */
  76. unsigned int readBits(struct BITSTREAM *pBitstream, int nBits)
  77. {
  78.     unsigned int data ;
  79.     if (pBitstream->cacheBitsLeft < nBits)
  80.     {
  81.         fillUp(pBitstream) ;
  82.     }
  83.     data = pBitstream->cache >> (CACHEBITS - nBits) ;
  84.     pBitstream->cache <<= nBits ;
  85.     pBitstream->cacheBitsLeft -= nBits ;
  86.     return data ;
  87. }
  88. /** push bits back into the bitstream.
  89.   * This call is here to make look-ahead possible, where after reading the client
  90.   * may realize it has read too far ahead. It is guaranteed to succeed as long as
  91.   * you don't push more bits back than have been read in the last readBits() call.
  92.   * @param pBitstream the bitstream to push back into
  93.   * @param bits the bits to push back
  94.   * @param nBits the number of bits to push back.
  95.   * @return an error code, signalling success or failure.
  96.   */
  97. int unreadBits(struct BITSTREAM *pBitstream, int bits, int nBits)
  98. {
  99.     pBitstream->cache = (pBitstream->cache>>nBits) | (bits << (CACHEBITS - nBits)) ;
  100.     pBitstream->cacheBitsLeft += nBits ;
  101.     return pBitstream->cacheBitsLeft > (signed)CACHEBITS ? -1 : 0 ;
  102. }
  103. /** byte-align the bitstream read pointer. */
  104. void byteAlign(struct BITSTREAM *pBitstream)
  105. {
  106.     int adjust = (pBitstream->cacheBitsLeft & 7) ;
  107.     pBitstream->cache <<= adjust ;
  108.     pBitstream->cacheBitsLeft -= adjust ;
  109. }
  110. /** allocate memory for a new bitstream structure.
  111.   * @param ppBitstream a pointer to a bitstream handle, to be initialized on
  112.   *        successfull return
  113.   * @param nBits the maximum number of bits this bitstream must be able to hold.
  114.   *        nBits must be divisible by 32.
  115.   * @return an error code, signalling success or failure.
  116.   * @see reverseBitstream
  117.   */
  118. int newBitstream(struct BITSTREAM **ppBitstream, int nBits)
  119. {
  120.     struct BITSTREAM *pBitstream ;
  121.     pBitstream = (struct BITSTREAM *)malloc(sizeof(struct BITSTREAM)) ;
  122.     if (!pBitstream || !ppBitstream)
  123.         return -1 ;
  124.     pBitstream->cacheBitsLeft = 0 ;
  125.     *ppBitstream = pBitstream ;
  126.     return 0 ;
  127. }
  128. /** free memory associated with a bitstream structure.
  129.   * @param pBitstream a bitstream handle
  130.   */
  131. void deleteBitstream(struct BITSTREAM *pBitstream)
  132. {
  133. if (pBitstream) free (pBitstream) ;
  134. }
  135. /** feed nbits bits to the bitstream, byte-wise.
  136.   * @param pBitstream the bitstream into which to feed the bytes
  137.   * @param input the input from which to read the bytes
  138.   * @param nbits the number of bits in the input. nbits must be divisible by 32
  139.   *  for reverseBitstream() to work.
  140.   * @return an error code, signalling success or failure.
  141.   * @see reverseBitstream
  142.   */
  143. int feedBitstream(struct BITSTREAM *pBitstream, const unsigned char *input, int nbits)
  144. {
  145.     pBitstream->buffer = input ;
  146.     pBitstream->nBits  = nbits ;
  147.     return 0 ;
  148. }
  149. /** return the number of bits left until end-of-stream.
  150.   * @param pBitstream the bitstream
  151.   * @return the number of bits left
  152.   */
  153. int bitsLeftInBitstream(struct BITSTREAM *pBitstream)
  154. {
  155.     return pBitstream->nBits - (pBitstream->pkptr - pBitstream->buffer) * 8 + pBitstream->cacheBitsLeft ;
  156. }
  157. /** set bitstream position, relative to origin defined through feedBitstream().
  158.   * @param pBitstream the bitstream
  159.   * @param position the position in bits (must be multiple of 8, currently).
  160.   * Always measured from beginning, regardless of direction.
  161.   * @param direction the direction of reading (+1/-1)
  162.   */
  163. int setAtBitstream(struct BITSTREAM *pBitstream, int position, int direction)
  164. {
  165.     ASSERT( position % 8 == 0 ) ;
  166.     pBitstream->pkptr = pBitstream->buffer + (position>>3) ;
  167.     pBitstream->cacheBitsLeft = 0 ;
  168.     pBitstream->cache = 0 ;
  169.     pBitstream->inc = direction ;
  170.     return 0 ;
  171. }