cae.cpp
上传用户:sun1608
上传日期:2007-02-02
资源大小:6116k
文件大小:9k
源码类别:

流媒体/Mpeg4/MP4

开发平台:

Visual C++

  1. /*************************************************************************
  2. This software module was adopted from MPEG4 VM7.0 text, modified by 
  3. Wei-ge Chen (wchen@microsoft.com), Microsoft Corporation
  4. (date: April, 1997)
  5. and also edited by
  6. Yoshihiro Kikuchi (TOSHIBA CORPORATION)
  7. Takeshi Nagai (TOSHIBA CORPORATION)
  8. Toshiaki Watanabe (TOSHIBA CORPORATION)
  9. Noboru Yamaguchi (TOSHIBA CORPORATION)
  10. in the course of development of the MPEG-4 Video (ISO/IEC 14496-2). 
  11. This software module is an implementation of a part of one or more MPEG-4 Video tools 
  12. as specified by the MPEG-4 Video. 
  13. ISO/IEC gives users of the MPEG-4 Video free license to this software module or modifications 
  14. thereof for use in hardware or software products claiming conformance to the MPEG-4 Video. 
  15. Those intending to use this software module in hardware or software products are advised that its use may infringe existing patents. 
  16. The original developer of this software module and his/her company, 
  17. the subsequent editors and their companies, 
  18. and ISO/IEC have no liability for use of this software module or modifications thereof in an implementation. 
  19. Copyright is not released for non MPEG-4 Video conforming products. 
  20. Microsoft retains full right to use the code for his/her own purpose, 
  21. assign or donate the code to a third party and to inhibit third parties from using the code for non <MPEG standard> conforming products. 
  22. This copyright notice must be included in all copies or derivative works. 
  23. Copyright (c) 1996, 1997.
  24. Module Name:
  25. cae.c
  26. Abstract:
  27. Context-based arithmatic coding
  28. Revision History:
  29. *************************************************************************/
  30. #include "typeapi.h"
  31. #include "basic.hpp"
  32. #include "global.hpp" // Added for error resilient mode by Toshiba(1997-11-14)
  33. #include "entropy/bitstrm.hpp"
  34. #include "cae.h"
  35. #ifdef __MFC_
  36. #ifdef _DEBUG
  37. #undef THIS_FILE
  38. static char BASED_CODE THIS_FILE[] = __FILE__;
  39. #endif
  40. #define new DEBUG_NEW    
  41. #endif // __MFC_
  42. /* START ENCODING A STREAM OF SYMBOLS */
  43. Void StartArCoder(ArCoder *coder) 
  44. {
  45.   coder->L = 0;
  46.   coder->R = HALF-1;
  47.   coder->bits_to_follow = 0;
  48.   coder->first_bit = 1;
  49.   coder->nzeros = g_iMaxHeading; // Modified for error resilient mode by Toshiba(1997-11-14)
  50.   coder->nonzero = 0;
  51.   coder->nBits = 0; //added by wchen
  52. }
  53. /* FINISH ENCODING THE STREAM */
  54. Int StopArCoder(ArCoder *coder, COutBitStream* bitstream) 
  55. {
  56.   Int a = (coder->L) >> (CODE_BITS-3);
  57.   Int b = (coder->R + coder->L) >> (CODE_BITS-3);
  58.   Int nbits, bits, i;
  59.   if (b == 0)
  60.     b = 8;
  61.   if (b - a >= 4 || (b - a == 3 && (a & 1))) {
  62.     nbits = 2;
  63.     bits = (a>>1) + 1;
  64.   }
  65.   else {
  66.     nbits = 3;
  67.     bits = a + 1;
  68.   }
  69.   
  70.   for (i = 1; i <= nbits; i++)
  71.     BitPlusFollow (((bits >> (nbits - i)) & 1), coder, bitstream);
  72.   
  73.   if (coder->nzeros < g_iMaxMiddle-g_iMaxTrailing || coder->nonzero == 0) { // Modified for error resilient mode by Toshiba(1997-11-14)
  74.     BitPlusFollow (1, coder, bitstream);
  75.   }
  76. //  return;
  77.   return 0;
  78. }
  79. Void BitByItself(Int bit, ArCoder *coder, COutBitStream* bitstream) {
  80. //BitstreamPutBit(bitstream,bit); /* Output the bit */
  81.   if (bitstream != NULL)
  82. bitstream->putBits (bit, 1, "MB_CAE_Bit");
  83.   coder->nBits++;
  84.   if (bit == 0) {
  85.     coder->nzeros--;
  86.     if (coder->nzeros == 0) {
  87. //    BitstreamPutBit(bitstream,1);
  88.   if (bitstream != NULL)
  89. bitstream->putBits (1, (UInt) 1, "MB_CAE_Bit");
  90.   coder->nBits++;
  91.       coder->nonzero = 1;
  92.       coder->nzeros = g_iMaxMiddle; // Modified for error resilient mode by Toshiba(1997-11-14)
  93.     }
  94.   }
  95.   else {
  96.     coder->nonzero = 1;
  97.     coder->nzeros = g_iMaxMiddle; // Modified for error resilient mode by Toshiba(1997-11-14)
  98.   }
  99. }
  100. /* OUTPUT BITS PLUS FOLLOWING OPPOSITE BITS */
  101. Void BitPlusFollow(Int bit, ArCoder *coder, COutBitStream *bitstream)
  102. {
  103. if (!coder->first_bit)
  104. BitByItself(bit, coder, bitstream);
  105. else
  106. coder->first_bit = 0;
  107. while ((coder->bits_to_follow) > 0) {
  108. BitByItself(!bit, coder, bitstream);
  109. coder->bits_to_follow -= 1;
  110. }
  111. }
  112. /* ENCODE A BINARY SYMBOL */
  113. Void ArCodeSymbol(Int bit, USInt c0, ArCoder *coder, COutBitStream *bitstream) 
  114. {
  115.   //  Int bits = 0;
  116.   USInt c1 = (1<<16) - c0;
  117.   
  118.   Int LPS = (c0 > c1);
  119.   USInt cLPS = (LPS) ? c1 : c0;
  120.   assert (cLPS != 0);
  121.   
  122.   unsigned long rLPS;
  123.   
  124.   rLPS = ((coder->R) >> 16) * cLPS;
  125.   
  126.   if (bit == LPS) {
  127.     coder->L += coder->R - rLPS;
  128.     coder->R = rLPS;
  129.   }
  130.   else
  131.     coder->R -= rLPS;
  132.   
  133.   ENCODE_RENORMALISE(coder,bitstream);
  134. }
  135. Void ENCODE_RENORMALISE(ArCoder *coder, COutBitStream* bitstream) 
  136. {
  137. while (coder->R < QUARTER) {  
  138. if (coder->L >= HALF) {  
  139. BitPlusFollow(1,coder,bitstream);  
  140. coder->L -= HALF;  
  141. }  
  142. else 
  143. if (coder->L + coder->R <= HALF) 
  144. BitPlusFollow(0,coder,bitstream);
  145. else {  
  146. coder->bits_to_follow++;  
  147. coder->L -= QUARTER;  
  148. }  
  149. coder->L += coder->L;  
  150. coder->R += coder->R;  
  151. }
  152. }
  153. //Decoder part
  154. Void StartArDecoder(ArDecoder *decoder, CInBitStream *bitstream) 
  155. {
  156.   Int i,j;
  157.   
  158.   decoder->V = 0;  
  159.   decoder->nzerosf = g_iMaxHeading; // Modified for error resilient mode by Toshiba(1997-11-14)
  160.   decoder->extrabits = 0;
  161.   for (i = 1; i<CODE_BITS; i++) {
  162. //    j = BitstreamLookBit(bitstream,i+decoder->extrabits);
  163.   j = bitstream->peekOneBit ((uint32_t)i + decoder->extrabits);
  164.     decoder->V += decoder->V + j;
  165.     if (j == 0) {
  166.       decoder->nzerosf--;
  167.       if (decoder->nzerosf == 0) {
  168. decoder->extrabits++;
  169. decoder->nzerosf = g_iMaxMiddle; // Modified for error resilient mode by Toshiba(1997-11-14)
  170.       }
  171.     }
  172.     else
  173.       decoder->nzerosf = g_iMaxMiddle; // Modified for error resilient mode by Toshiba(1997-11-14)
  174.   }
  175.   decoder->L = 0;
  176.   decoder->R = HALF - 1;
  177.   decoder->bits_to_follow = 0;
  178.   decoder->arpipe = decoder->V;
  179.   decoder->nzeros = g_iMaxHeading; // Modified for error resilient mode by Toshiba(1997-11-14)
  180.   decoder->nonzero = 0;
  181. }
  182.   
  183. Void StopArDecoder(ArDecoder *decoder, CInBitStream *bitstream) 
  184. {
  185.   Int a = decoder->L >> (CODE_BITS - 3);
  186.   Int b = (decoder->R + decoder->L) >> (CODE_BITS - 3);
  187.   Int nbits,i;
  188.   if (b == 0) {
  189.     b = 8;
  190.   }
  191.   if (b - a >= 4 || (b - a == 3 && a&1))
  192.     nbits = 2;
  193.   else
  194.     nbits = 3;
  195.   for (i = 1; i <= nbits - 1; i++)
  196.     AddNextInputBit (bitstream, decoder);
  197.   
  198.   if (decoder->nzeros < g_iMaxMiddle-g_iMaxTrailing || decoder->nonzero == 0) { // Modified for error resilient mode by Toshiba(1997-11-14)
  199.     BitstreamFlushBits(bitstream,1);
  200.   }
  201. }
  202. Void AddNextInputBit(CInBitStream *bitstream, ArDecoder *decoder) 
  203. {
  204. Int i;
  205. if (((decoder->arpipe >> (CODE_BITS-2)) & 1) == 0) {
  206. decoder->nzeros--;
  207. if (decoder->nzeros == 0) {
  208. BitstreamFlushBits(bitstream,1);
  209. decoder->extrabits--;
  210. decoder->nzeros = g_iMaxMiddle; // Modified for error resilient mode by Toshiba(1997-11-14)
  211. decoder->nonzero = 1;
  212. }
  213. }
  214. else {
  215. decoder->nzeros = g_iMaxMiddle; // Modified for error resilient mode by Toshiba(1997-11-14)
  216. decoder->nonzero = 1;
  217. }
  218. BitstreamFlushBits(bitstream, 1);
  219. // i = (Int)BitstreamLookBit(bitstream, CODE_BITS-1+decoder->extrabits);
  220. i = bitstream->peekOneBit ((uint32_t)CODE_BITS-1+decoder->extrabits);
  221. decoder->V += decoder->V + i;
  222. decoder->arpipe += decoder->arpipe + i;
  223. if (i == 0) {
  224. decoder->nzerosf--;
  225. if (decoder->nzerosf == 0) {
  226. decoder->nzerosf = g_iMaxMiddle; // Modified for error resilient mode by Toshiba(1997-11-14)
  227. decoder->extrabits++;
  228. }
  229. }
  230. else
  231. decoder->nzerosf = g_iMaxMiddle; // Modified for error resilient mode by Toshiba(1997-11-14)
  232. }
  233. Int ArDecodeSymbol(USInt c0, ArDecoder *decoder, CInBitStream *bitstream) 
  234. {
  235. Int bit;
  236. Int c1 = (1<<16) - c0;
  237. Int LPS = c0 > c1;
  238. Int cLPS = LPS ? c1 : c0;
  239. unsigned long rLPS;
  240. rLPS = ((decoder->R) >> 16) * cLPS;
  241. if ((decoder->V - decoder->L) >= (decoder->R - rLPS))  {
  242. bit = LPS;
  243. decoder->L += decoder->R - rLPS;
  244. decoder->R = rLPS;
  245. }
  246. else  {
  247. bit = (1-LPS);
  248. decoder->R -= rLPS;
  249. }
  250. DECODE_RENORMALISE(decoder,bitstream);
  251. return(bit);
  252. }
  253. Void DECODE_RENORMALISE(ArDecoder *decoder,  CInBitStream *bitstream) 
  254. {
  255. while (decoder->R < QUARTER)  {
  256. if (decoder->L >= HALF)  {
  257. decoder->V -= HALF;
  258. decoder->L -= HALF;
  259. decoder->bits_to_follow = 0;
  260. }
  261. else
  262. if (decoder->L + decoder->R <= HALF) 
  263. decoder->bits_to_follow = 0;
  264. else {
  265. decoder->V -= QUARTER;
  266. decoder->L -= QUARTER;
  267. (decoder->bits_to_follow)++;
  268. }
  269. decoder->L += decoder->L;
  270. decoder->R += decoder->R;
  271. AddNextInputBit(bitstream, decoder);
  272. }
  273. }
  274. Void  BitstreamFlushBits(CInBitStream *bitstream, Int nBits)
  275. {
  276. assert (nBits >= 0);
  277. bitstream->getBits ((uint32_t)nBits);
  278. }
  279. /*
  280. //decoding
  281. pf = fopen (TEST_FILENAME, "r");
  282. ac = (ArDecoder*) malloc (sizeof (ArDecoder));
  283. StartArDecoder (ac, pf);
  284. for (i = 0; i < NUM_SYMBOL; i++) {
  285. j = ArDecodeSymbol (intra_prob [i], ac, pf); //context is simply "i"
  286. assert (j == i % 2); //symbol should be 0, 1 alternatively
  287. }
  288. StopArDecoder(ac, pf);
  289. free (ac);
  290. fclose (pf);
  291. */