📄 mp3enc_bitstream.cpp
字号:
/*////////////////////////////////////////////////////////////////////////////////// INTEL CORPORATION PROPRIETARY INFORMATION// This software is supplied under the terms of a license agreement or// nondisclosure agreement with Intel Corporation and may not be copied// or disclosed except in accordance with the terms of that agreement.// Copyright(c) 2002-2005 Intel Corporation. All Rights Reserved.//*/#include "umc_mp3_enc_int.h"namespace UMC {/*******************************************************************/#define PutBitsSI(val, len) PUT_BITS(&sideStream, val, len)#define PutBits(val, len) PUT_BITS(&mainStream, val, len)/*******************************************************************/ void MP3EncoderInt::encodeBigValues(short *pInput, int gr, int ch) { int i, j, bigvalues, len; int shift, offset; int bitoffset; short tmp_src[288], *q; Ipp8u *pDst; IppsVLCEncodeSpec_32s* pVLCEncSpec; pDst = (Ipp8u*)mainStream.pCurrent_dword + ((32 - mainStream.nBit_offset) >> 3); bitoffset = (32 - mainStream.nBit_offset) & 0x7; SAVE_BITSTREAM(&mainStream) bigvalues = si_bigVals[gr][ch] << 1; if (si_address[gr][ch][0] > 0) { i = si_pTableSelect[gr][ch][0]; shift = mp3enc_VLCShifts[i]; offset = mp3enc_VLCOffsets[i]; pVLCEncSpec = (IppsVLCEncodeSpec_32s*)htables[i].phuftable; len = si_address[gr][ch][0] >> 1; q = pInput; if (htables[i].linbits == 0) { for (j = 0; j < len; j++) { tmp_src[j] = (short)((q[0] << shift) + (q[1] + offset)); q += 2; } ippsVLCEncodeBlock_16s1u(tmp_src, len, &pDst, &bitoffset, pVLCEncSpec); } else ippsVLCEncodeEscBlock_MP3_16s1u(q, len * 2, htables[i].linbits, &pDst, &bitoffset, pVLCEncSpec); } if (si_address[gr][ch][1] > si_address[gr][ch][0]) { i = si_pTableSelect[gr][ch][1]; shift = mp3enc_VLCShifts[i]; offset = mp3enc_VLCOffsets[i]; pVLCEncSpec = (IppsVLCEncodeSpec_32s*)htables[i].phuftable; len = (si_address[gr][ch][1] - si_address[gr][ch][0]) >> 1; q = pInput + si_address[gr][ch][0]; if (htables[i].linbits == 0) { for (j = 0; j < len; j++) { tmp_src[j] = (short)((q[0] << shift) + (q[1] + offset)); q += 2; } ippsVLCEncodeBlock_16s1u(tmp_src, len, &pDst, &bitoffset, pVLCEncSpec); } else ippsVLCEncodeEscBlock_MP3_16s1u(q, len * 2, htables[i].linbits, &pDst, &bitoffset, pVLCEncSpec); } if ((unsigned int)bigvalues > si_address[gr][ch][1]) { i = si_pTableSelect[gr][ch][2]; shift = mp3enc_VLCShifts[i]; offset = mp3enc_VLCOffsets[i]; pVLCEncSpec = (IppsVLCEncodeSpec_32s*)htables[i].phuftable; len = (bigvalues - si_address[gr][ch][1]) >> 1; q = pInput + si_address[gr][ch][1]; if (htables[i].linbits == 0) { for (j = 0; j < len; j++) { tmp_src[j] = (short)((q[0] << shift) + (q[1] + offset)); q += 2; } ippsVLCEncodeBlock_16s1u(tmp_src, len, &pDst, &bitoffset, pVLCEncSpec); } else ippsVLCEncodeEscBlock_MP3_16s1u(q, len * 2, htables[i].linbits, &pDst, &bitoffset, pVLCEncSpec); } mainStream.pCurrent_dword = (Ipp32u*)(pDst - ((Ipp32s)(pDst) & 3)); mainStream.nBit_offset = 32 - ((pDst - (Ipp8u*)mainStream.pCurrent_dword) << 3) - bitoffset; LOAD_DWORD(&mainStream) return; }/*******************************************************************/ void MP3EncoderInt::huffmanCodeBits(int gr, int ch) { int count1End; int bits, bits_before; int i, bigvalues; VM_ALIGN16_DECL(short) pInput[576]; short x, y, w, v, p, val, len; short *h; bigvalues = si_bigVals[gr][ch] << 1; if (bigvalues) { if (!(si_mixedBlock[gr][ch]) && si_winSwitch[gr][ch] && (si_blockType[gr][ch] == 2)) { int sfb, window, line, start, end; unsigned int *sfb_short = mp3enc_sfBandIndex[header.samplingFreq].s; IXS *ix_s = (IXS *) quant_ix[gr][ch]; i = 0; for (sfb = 0; sfb < 13; sfb++) { start = sfb_short[sfb]; end = sfb_short[sfb + 1]; for (window = 0; window < 3; window++) { for (line = start; line < end; line += 2) { pInput[i++] = x = (*ix_s)[line][window]; pInput[i++] = y = (*ix_s)[line + 1][window]; } } } GET_BITS_COUNT(&mainStream, bits_before) encodeBigValues(pInput, gr, ch); GET_BITS_COUNT(&mainStream, bits) bits -= bits_before; } else if (si_mixedBlock[gr][ch] && si_blockType[gr][ch] == 2) { vm_debug_msg(-1, VM_STRING("mixed block is not implemented")); } else { encodeBigValues(quant_ix[gr][ch], gr, ch); } } if (si_cnt1TabSel[gr][ch]) h = mp3enc_table33; else h = mp3enc_table32; count1End = bigvalues + (si_count1[gr][ch] * 4); for (i = bigvalues; i < count1End; i += 4) { v = (short)abs(quant_ix[gr][ch][i]); w = (short)abs(quant_ix[gr][ch][i + 1]); x = (short)abs(quant_ix[gr][ch][i + 2]); y = (short)abs(quant_ix[gr][ch][i + 3]); p = (v << 3) | (w << 2) | (x << 1) | y; val = h[3 * p + 2]; len = h[3 * p + 1]; val = (val << v) | ((quant_ix[gr][ch][i] < 0) ? 1 : 0); val = (val << w) | ((quant_ix[gr][ch][i + 1] < 0) ? 1 : 0); val = (val << x) | ((quant_ix[gr][ch][i + 2] < 0) ? 1 : 0); val = (val << y) | ((quant_ix[gr][ch][i + 3] < 0) ? 1 : 0); PutBits(val, len); } }/*******************************************************************/ int MP3EncoderInt::encodeSideInfo() { int i, gr, ch; header.mode = (stereo == 1) ? 0x3 : 0x0;// header PutBitsSI(0xfff, 12); PutBitsSI(1, 1); PutBitsSI(header.layer, 2); PutBitsSI(!header.protectionBit, 1); PutBitsSI(header.bitRate, 4); PutBitsSI(header.samplingFreq, 2); PutBitsSI(header.paddingBit, 1); PutBitsSI(header.privateBit, 1); PutBitsSI(header.mode, 2); PutBitsSI(header.modeExt, 2); PutBitsSI(header.copyright, 1); PutBitsSI(header.originalCopy, 1); PutBitsSI(header.emphasis, 2);// side info PutBitsSI(si_main_data_begin, 9); if (stereo == 2) PutBitsSI(si_private_bits, 3) else PutBitsSI(si_private_bits, 5); for (ch = 0; ch < stereo; ch++) for (i = 0; i < 4; i++) PutBitsSI(si_scfsi[ch][i], 1); for (gr = 0; gr < 2; gr++) for (ch = 0; ch < stereo; ch++) { PutBitsSI(si_part23Len[gr][ch], 12); PutBitsSI(si_bigVals[gr][ch], 9); PutBitsSI(si_globGain[gr][ch], 8); PutBitsSI(si_sfCompress[gr][ch], 4); PutBitsSI(si_winSwitch[gr][ch], 1); if (si_winSwitch[gr][ch]) { PutBitsSI(si_blockType[gr][ch], 2); PutBitsSI(si_mixedBlock[gr][ch], 1); for (i = 0; i < 2; i++) PutBitsSI(si_pTableSelect[gr][ch][i], 5); for (i = 0; i < 3; i++) PutBitsSI(si_pSubBlkGain[gr][ch][i], 3); } else { for (i = 0; i < 3; i++) PutBitsSI(si_pTableSelect[gr][ch][i], 5); PutBitsSI(si_reg0Cnt[gr][ch], 4); PutBitsSI(si_reg1Cnt[gr][ch], 3); } PutBitsSI(si_preFlag[gr][ch], 1); PutBitsSI(si_sfScale[gr][ch], 1); PutBitsSI(si_cnt1TabSel[gr][ch], 1); } return 0; }/*******************************************************************/ void MP3EncoderInt::encodeMainData() { int gr, ch, sfb, window; for (gr = 0; gr < 2; gr++) { for (ch = 0; ch < stereo; ch++) { short slen1 = (short)mp3enc_slen1_tab[si_sfCompress[gr][ch]]; short slen2 = (short)mp3enc_slen2_tab[si_sfCompress[gr][ch]]; if ((si_winSwitch[gr][ch] == 1) && (si_blockType[gr][ch] == 2)) { if (si_mixedBlock[gr][ch]) { for (sfb = 0; sfb < 8; sfb++) PutBits(scalefac_l[gr][ch][sfb], slen1); for (sfb = 3; sfb < 6; sfb++) for (window = 0; window < 3; window++) PutBits(scalefac_s[gr][ch][sfb][window], slen1); for (sfb = 6; sfb < 12; sfb++) for (window = 0; window < 3; window++) PutBits(scalefac_s[gr][ch][sfb][window], slen2); } else { for (sfb = 0; sfb < 6; sfb++) for (window = 0; window < 3; window++) PutBits(scalefac_s[gr][ch][sfb][window], slen1); for (sfb = 6; sfb < 12; sfb++) for (window = 0; window < 3; window++) PutBits(scalefac_s[gr][ch][sfb][window], slen2); } } else { if ((gr == 0) || (si_scfsi[ch][0] == 0)) for (sfb = 0; sfb < 6; sfb++) PutBits(scalefac_l[gr][ch][sfb], slen1); if ((gr == 0) || (si_scfsi[ch][1] == 0)) for (sfb = 6; sfb < 11; sfb++) PutBits(scalefac_l[gr][ch][sfb], slen1); if ((gr == 0) || (si_scfsi[ch][2] == 0)) for (sfb = 11; sfb < 16; sfb++) PutBits(scalefac_l[gr][ch][sfb], slen2); if ((gr == 0) || (si_scfsi[ch][3] == 0)) for (sfb = 16; sfb < 21; sfb++) PutBits(scalefac_l[gr][ch][sfb], slen2); } huffmanCodeBits(gr, ch); } } }/*******************************************************************/ int MP3EncoderInt::WriteFrame(int si_bits, int bits, unsigned char *pOutputData) { int i, slot, res, len; unsigned char *ptr_main = (unsigned char *)buffer_main_data; unsigned char *ptr_side = (unsigned char *)buffer_side_info; unsigned char *ptr_out = pOutputData; int si_bytes, bytes; slot = slot_size; bits = (bits + 7) & ~7; resr_bytes += slot; res = 0; si_bytes = si_bits >> 3; bytes = bits >> 3; for (i = 0; i < si_bytes; i++) si_buf[si_new][i] = *ptr_side++; si_num++; si_new++; if (si_new >= SI_MAX) si_new = 0; do { int left = resr_mod_slot; len = left < bytes ? left : bytes; for (i = 0; i < len; i++) *ptr_out++ = *ptr_main++; res += len; bytes -= len; resr_bytes -= len; resr_mod_slot -= len; if (resr_mod_slot < 0) resr_mod_slot += slot; if (len == left && si_num > 0) { for (i = 0; i < si_bytes; i++) *ptr_out++ = si_buf[si_beg][i]; res += si_bytes; resr_bytes -= si_bytes; resr_mod_slot -= si_bytes; if (resr_mod_slot < 0) resr_mod_slot += slot; si_num--; si_beg++; if (si_beg >= SI_MAX) si_beg = 0; } } while(bytes); while ((si_main_data_begin = resr_bytes - si_num * si_bytes) > 511) { int left = resr_mod_slot; len = left < ((int)si_main_data_begin - 511) ? left : ((int)si_main_data_begin - 511); for (i = 0; i < len; i++) *ptr_out++ = 0; res += len; resr_bytes -= len; resr_mod_slot -= len; if (resr_mod_slot < 0) resr_mod_slot += slot; if (len == left && si_num > 0) { for (i = 0; i < si_bytes; i++) *ptr_out++ = si_buf[si_beg][i]; res += si_bytes; resr_bytes -= si_bytes; resr_mod_slot -= si_bytes; if (resr_mod_slot < 0) resr_mod_slot += slot; si_num--; si_beg++; if (si_beg >= SI_MAX) si_beg = 0; } }/* if (bitrate[header.bitRate] == 320) { if (si_main_data_begin > 0) { for (i = 0; i < si_main_data_begin; i++) *ptr_out++ = 0; res += si_main_data_begin; resr_bytes -= si_main_data_begin; } si_main_data_begin = 0; }*/ return res; }/*******************************************************************/ int MP3EncoderInt::formatBitstream(unsigned char *pOutputData) { int gr, ch, i, bits, si_bits; int bytes; VM_ALIGN16_DECL(int) sign[576]; for (gr = 0; gr < 2; gr++) { for (ch = 0; ch < stereo; ch++) { ippsRShiftC_32s((int *)mdct_out_int[gr][ch], 31, sign, 576); for (i = 0; i < 576; i++) { quant_ix[gr][ch][i] -= (quant_ix[gr][ch][i] << 1) & (short)sign[i] ; } } }// si_bits - count of bits for header and sideinfo// bits - count of bits for main data INIT_BITSTREAM(&mainStream, buffer_main_data) INIT_BITSTREAM(&sideStream, buffer_side_info) encodeSideInfo(); GET_BITS_COUNT(&sideStream, si_bits) encodeMainData(); GET_BITS_COUNT(&mainStream, bits) SAVE_BITSTREAM(&mainStream) SAVE_BITSTREAM(&sideStream) bytes = WriteFrame(si_bits, bits, pOutputData); return bytes; }}; // namespace UMC/*******************************************************************/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -