layer3.c
上传用户:tuheem
上传日期:2007-05-01
资源大小:21889k
文件大小:4k
源码类别:

多媒体编程

开发平台:

Visual C++

  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include "common.h"
  4. #include "decode.h"
  5. void main(int argc, char**argv)
  6. {
  7. FILE *musicout;
  8. Bit_stream_struc  bs;
  9. frame_params fr_ps;
  10. III_side_info_t III_side_info;
  11. III_scalefac_t III_scalefac;
  12. unsigned int old_crc;
  13. layer info;
  14. int sync, clip;
  15. int done = FALSE;
  16. unsigned long frameNum=0;
  17. unsigned long bitsPerSlot;
  18. unsigned long sample_frames;
  19. typedef short PCM[2][SSLIMIT][SBLIMIT];
  20. PCM *pcm_sample;
  21. pcm_sample = (PCM *) mem_alloc((long) sizeof(PCM), "PCM Samp");
  22. if (argc==1) {
  23. printf("Useage:decode file.mp3 output.pcmn");
  24. return;
  25. }
  26. fr_ps.header = &info;
  27. if ((musicout = fopen(argv[2], "w+b")) == NULL) {
  28. printf ("Could not create "%s".n", argv[2]);
  29. exit(1);
  30. }
  31.     open_bit_stream_r(&bs, argv[1], BUFFER_SIZE);
  32. sample_frames = 0;
  33. while(!end_bs(&bs)) {
  34. //尝试帧同步
  35. sync = seek_sync(&bs, SYNC_WORD, SYNC_WORD_LENGTH);
  36. if (!sync) {
  37. done = TRUE;
  38. printf("nFrame cannot be locatedn");
  39. out_fifo(*pcm_sample, 3, &fr_ps, done, musicout, &sample_frames);
  40. break;
  41. }
  42. //解码帧头
  43. decode_info(&bs, &fr_ps);
  44. //将fr_ps.header中的信息解读到fr_ps的相关域中
  45. hdr_to_frps(&fr_ps);
  46. //输出相关信息
  47. if(frameNum == 0)
  48.    WriteHdr(&fr_ps);
  49. printf("r%05lu", frameNum++);
  50. if (info.error_protection)
  51. buffer_CRC(&bs, &old_crc);
  52. switch (info.lay) {
  53. case 3:
  54. {
  55. int nSlots, main_data_end, flush_main;
  56. int bytes_to_discard, gr, ch, ss, sb;
  57. static int frame_start = 0;
  58. bitsPerSlot = 8;
  59. //取Side信息
  60. III_get_side_info(&bs, &III_side_info, &fr_ps);
  61. nSlots = main_data_slots(fr_ps);
  62.  //读主数据(Audio Data)
  63. for (; nSlots > 0; nSlots--)  /* read main data. */
  64. hputbuf((unsigned int) getbits(&bs,8), 8);
  65. main_data_end = hsstell() / 8; /*of privious frame*/
  66. if ( flush_main=(hsstell() % bitsPerSlot) ) {
  67. hgetbits((int)(bitsPerSlot - flush_main));
  68. main_data_end ++;
  69. }
  70. bytes_to_discard = frame_start - main_data_end - III_side_info.main_data_begin ;
  71. if( main_data_end > 4096 ) {   frame_start -= 4096;
  72. rewindNbytes( 4096 );
  73. }
  74. frame_start += main_data_slots(fr_ps);
  75. if (bytes_to_discard < 0) {
  76. printf("Not enough main data to decode frame %d.  Frame discarded.n",
  77. frameNum - 1); break;
  78. }
  79. for (; bytes_to_discard > 0; bytes_to_discard--) hgetbits(8);
  80. clip = 0;
  81. for (gr=0;gr<2;gr++) {
  82. double lr[2][SBLIMIT][SSLIMIT],ro[2][SBLIMIT][SSLIMIT];
  83. //主解码
  84. for (ch=0; ch<fr_ps.stereo; ch++) {
  85. long int is[SBLIMIT][SSLIMIT];   /*保存量化数据*/
  86. int part2_start;
  87. part2_start = hsstell();
  88. //获取比例因子
  89. III_get_scale_factors(&III_scalefac,&III_side_info, gr, ch, &fr_ps);
  90. //Huffman解码
  91. III_hufman_decode(is, &III_side_info, ch, gr, part2_start, &fr_ps);
  92. //反量化采样
  93. III_dequantize_sample(is, ro[ch], &III_scalefac, &(III_side_info.ch[ch].gr[gr]), ch, &fr_ps);
  94. }
  95. //立体声处理
  96. III_stereo(ro, lr, &III_scalefac, &(III_side_info.ch[0].gr[gr]), &fr_ps);
  97. for (ch=0; ch<fr_ps.stereo; ch++) {
  98. double re[SBLIMIT][SSLIMIT];
  99. double hybridIn[SBLIMIT][SSLIMIT];/* Hybrid filter input */
  100. double hybridOut[SBLIMIT][SSLIMIT];/* Hybrid filter out */
  101. double polyPhaseIn[SBLIMIT];     /* PolyPhase Input. */
  102. III_reorder(lr[ch], re, &(III_side_info.ch[ch].gr[gr]), &fr_ps);
  103. //抗锯齿处理
  104. III_antialias(re, hybridIn, /* Antialias butterflies. */
  105. &(III_side_info.ch[ch].gr[gr]), &fr_ps);
  106. //IMDCT
  107. for (sb=0; sb<SBLIMIT; sb++) { /* Hybrid synthesis. */
  108. III_hybrid(hybridIn[sb], hybridOut[sb], sb, ch, &(III_side_info.ch[ch].gr[gr]), &fr_ps);
  109. }
  110. for (ss=0;ss<18;ss++) //多相频率倒置
  111. for (sb=0; sb<SBLIMIT; sb++)
  112. if ((ss%2) && (sb%2))
  113. hybridOut[sb][ss] = -hybridOut[sb][ss];
  114. for (ss=0;ss<18;ss++) { //多相合成
  115. for (sb=0; sb<SBLIMIT; sb++)
  116. polyPhaseIn[sb] = hybridOut[sb][ss];
  117. //子带合成
  118. clip += SubBandSynthesis(polyPhaseIn, ch, &((*pcm_sample)[ch][ss][0]));
  119. }
  120. }
  121. //PCM输出
  122. /* Output PCM sample points for one granule(颗粒). */
  123. out_fifo(*pcm_sample, 18, &fr_ps, done, musicout, &sample_frames);
  124. }
  125. if(clip > 0)
  126. printf("n%d samples clipped.n", clip);
  127. }
  128. break;
  129. default:
  130. printf("nOnly layer III supported!n");
  131. exit(1);
  132. break;
  133. }
  134. }
  135. close_bit_stream_r(&bs);
  136. fclose(musicout);
  137. printf("nDecoding done.n");
  138. return;
  139. }