?? layer3.c
字號:
x[25] = x[28] = MAD_F_MLZ(hi, lo) + t4; MAD_F_ML0(hi, lo, X[1], -MAD_F(0x0fdcf549)); MAD_F_MLA(hi, lo, X[7], -MAD_F(0x0cb19346)); MAD_F_MLA(hi, lo, X[10], -MAD_F(0x09bd7ca0)); MAD_F_MLA(hi, lo, X[16], -MAD_F(0x0216a2a2)); t5 = MAD_F_MLZ(hi, lo) - t6; MAD_F_ML0(hi, lo, X[0], MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[3], MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[5], MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[6], MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[8], -MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[9], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[12], MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[14], -MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[15], MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x0d7e8807)); x[2] = MAD_F_MLZ(hi, lo) + t5; x[15] = -x[2]; MAD_F_ML0(hi, lo, X[0], MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[3], MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[5], MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[6], -MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[8], MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[9], -MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[11], MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[14], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[15], -MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[17], MAD_F(0x0e313245)); x[3] = MAD_F_MLZ(hi, lo) + t5; x[14] = -x[3]; MAD_F_ML0(hi, lo, X[0], -MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[2], -MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[3], -MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[5], -MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[6], -MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[8], -MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[9], -MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[14], -MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[15], -MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x00b2aa3e)); x[26] = x[27] = MAD_F_MLZ(hi, lo) + t5;}# endif/* * NAME: III_imdct_l() * DESCRIPTION: perform IMDCT and windowing for long blocks */# ifndef __WINS__void III_imdct_l(mad_fixed_t const X[18], mad_fixed_t z[36], unsigned int block_type);# elsestaticvoid III_imdct_l(mad_fixed_t const X[18], mad_fixed_t z[36], unsigned int block_type){ unsigned int i; /* IMDCT */ imdct36(X, z); /* windowing */ switch (block_type) { case 0: /* normal window */# if defined(ASO_INTERLEAVE1) { register mad_fixed_t tmp1, tmp2; tmp1 = window_l[0]; tmp2 = window_l[1]; for (i = 0; i < 34; i += 2) { z[i + 0] = mad_f_mul(z[i + 0], tmp1); tmp1 = window_l[i + 2]; z[i + 1] = mad_f_mul(z[i + 1], tmp2); tmp2 = window_l[i + 3]; } z[34] = mad_f_mul(z[34], tmp1); z[35] = mad_f_mul(z[35], tmp2); }# elif defined(ASO_INTERLEAVE2) { register mad_fixed_t tmp1, tmp2; tmp1 = z[0]; tmp2 = window_l[0]; for (i = 0; i < 35; ++i) { z[i] = mad_f_mul(tmp1, tmp2); tmp1 = z[i + 1]; tmp2 = window_l[i + 1]; } z[35] = mad_f_mul(tmp1, tmp2); }# elif 1 for (i = 0; i < 36; i += 4) { z[i + 0] = mad_f_mul(z[i + 0], window_l[i + 0]); z[i + 1] = mad_f_mul(z[i + 1], window_l[i + 1]); z[i + 2] = mad_f_mul(z[i + 2], window_l[i + 2]); z[i + 3] = mad_f_mul(z[i + 3], window_l[i + 3]); }# else for (i = 0; i < 36; ++i) z[i] = mad_f_mul(z[i], window_l[i]);# endif break; case 1: /* start block */ for (i = 0; i < 18; i += 3) { z[i + 0] = mad_f_mul(z[i + 0], window_l[i + 0]); z[i + 1] = mad_f_mul(z[i + 1], window_l[i + 1]); z[i + 2] = mad_f_mul(z[i + 2], window_l[i + 2]); } /* (i = 18; i < 24; ++i) z[i] unchanged */ for (i = 24; i < 30; ++i) z[i] = mad_f_mul(z[i], window_s[i - 18]); for (i = 30; i < 36; ++i) z[i] = 0; break; case 3: /* stop block */ for (i = 0; i < 6; ++i) z[i] = 0; for (i = 6; i < 12; ++i) z[i] = mad_f_mul(z[i], window_s[i - 6]); /* (i = 12; i < 18; ++i) z[i] unchanged */ for (i = 18; i < 36; i += 3) { z[i + 0] = mad_f_mul(z[i + 0], window_l[i + 0]); z[i + 1] = mad_f_mul(z[i + 1], window_l[i + 1]); z[i + 2] = mad_f_mul(z[i + 2], window_l[i + 2]); } break; }}# endif# endif /* ASO_IMDCT *//* * NAME: III_imdct_s() * DESCRIPTION: perform IMDCT and windowing for short blocks */staticvoid III_imdct_s(mad_fixed_t const X[18], mad_fixed_t z[36]){ mad_fixed_t y[36], *yptr; mad_fixed_t const *wptr; int w, i; register mad_fixed64hi_t hi; register mad_fixed64lo_t lo; /* IMDCT */ yptr = &y[0]; for (w = 0; w < 3; ++w) { register mad_fixed_t const (*s)[6]; s = imdct_s; for (i = 0; i < 3; ++i) { MAD_F_ML0(hi, lo, X[0], (*s)[0]); MAD_F_MLA(hi, lo, X[1], (*s)[1]); MAD_F_MLA(hi, lo, X[2], (*s)[2]); MAD_F_MLA(hi, lo, X[3], (*s)[3]); MAD_F_MLA(hi, lo, X[4], (*s)[4]); MAD_F_MLA(hi, lo, X[5], (*s)[5]); yptr[i + 0] = MAD_F_MLZ(hi, lo); yptr[5 - i] = -yptr[i + 0]; ++s; MAD_F_ML0(hi, lo, X[0], (*s)[0]); MAD_F_MLA(hi, lo, X[1], (*s)[1]); MAD_F_MLA(hi, lo, X[2], (*s)[2]); MAD_F_MLA(hi, lo, X[3], (*s)[3]); MAD_F_MLA(hi, lo, X[4], (*s)[4]); MAD_F_MLA(hi, lo, X[5], (*s)[5]); yptr[ i + 6] = MAD_F_MLZ(hi, lo); yptr[11 - i] = yptr[i + 6]; ++s; } yptr += 12; X += 6; } /* windowing, overlapping and concatenation */ yptr = &y[0]; wptr = &window_s[0]; for (i = 0; i < 6; ++i) { z[i + 0] = 0; z[i + 6] = mad_f_mul(yptr[ 0 + 0], wptr[0]); MAD_F_ML0(hi, lo, yptr[ 0 + 6], wptr[6]); MAD_F_MLA(hi, lo, yptr[12 + 0], wptr[0]); z[i + 12] = MAD_F_MLZ(hi, lo); MAD_F_ML0(hi, lo, yptr[12 + 6], wptr[6]); MAD_F_MLA(hi, lo, yptr[24 + 0], wptr[0]); z[i + 18] = MAD_F_MLZ(hi, lo); z[i + 24] = mad_f_mul(yptr[24 + 6], wptr[6]); z[i + 30] = 0; ++yptr; ++wptr; }}/* * NAME: III_overlap() * DESCRIPTION: perform overlap-add of windowed IMDCT outputs */staticvoid III_overlap(mad_fixed_t const output[36], mad_fixed_t overlap[18], mad_fixed_t sample[18][32], unsigned int sb){ unsigned int i;# if defined(ASO_INTERLEAVE2) { register mad_fixed_t tmp1, tmp2; tmp1 = overlap[0]; tmp2 = overlap[1]; for (i = 0; i < 16; i += 2) { sample[i + 0][sb] = output[i + 0 + 0] + tmp1; overlap[i + 0] = output[i + 0 + 18]; tmp1 = overlap[i + 2]; sample[i + 1][sb] = output[i + 1 + 0] + tmp2; overlap[i + 1] = output[i + 1 + 18]; tmp2 = overlap[i + 3]; } sample[16][sb] = output[16 + 0] + tmp1; overlap[16] = output[16 + 18]; sample[17][sb] = output[17 + 0] + tmp2; overlap[17] = output[17 + 18]; }# elif 0 for (i = 0; i < 18; i += 2) { sample[i + 0][sb] = output[i + 0 + 0] + overlap[i + 0]; overlap[i + 0] = output[i + 0 + 18]; sample[i + 1][sb] = output[i + 1 + 0] + overlap[i + 1]; overlap[i + 1] = output[i + 1 + 18]; }# else for (i = 0; i < 18; ++i) { sample[i][sb] = output[i + 0] + overlap[i]; overlap[i] = output[i + 18]; }# endif}/* * NAME: III_overlap_z() * DESCRIPTION: perform "overlap-add" of zero IMDCT outputs */static #ifndef __WINS__inline#endifvoid III_overlap_z(mad_fixed_t overlap[18], mad_fixed_t sample[18][32], unsigned int sb){ unsigned int i;# if defined(ASO_INTERLEAVE2) { register mad_fixed_t tmp1, tmp2; tmp1 = overlap[0]; tmp2 = overlap[1]; for (i = 0; i < 16; i += 2) { sample[i + 0][sb] = tmp1; overlap[i + 0] = 0; tmp1 = overlap[i + 2]; sample[i + 1][sb] = tmp2; overlap[i + 1] = 0; tmp2 = overlap[i + 3]; } sample[16][sb] = tmp1; overlap[16] = 0; sample[17][sb] = tmp2; overlap[17] = 0; }# else for (i = 0; i < 18; ++i) { sample[i][sb] = overlap[i]; overlap[i] = 0; }# endif}/* * NAME: III_freqinver() * DESCRIPTION: perform subband frequency inversion for odd sample lines */staticvoid III_freqinver(mad_fixed_t sample[18][32], unsigned int sb){ unsigned int i;# if 1 || defined(ASO_INTERLEAVE1) || defined(ASO_INTERLEAVE2) { register mad_fixed_t tmp1, tmp2; tmp1 = sample[1][sb]; tmp2 = sample[3][sb]; for (i = 1; i < 13; i += 4) { sample[i + 0][sb] = -tmp1; tmp1 = sample[i + 4][sb]; sample[i + 2][sb] = -tmp2; tmp2 = sample[i + 6][sb]; } sample[13][sb] = -tmp1; tmp1 = sample[17][sb]; sample[15][sb] = -tmp2; sample[17][sb] = -tmp1; }# else for (i = 1; i < 18; i += 2) sample[i][sb] = -sample[i][sb];# endif}/* * NAME: III_decode() * DESCRIPTION: decode frame main_data */staticenum mad_error III_decode(struct mad_bitptr *ptr, struct mad_frame *frame, struct sideinfo *si, unsigned int nch){ struct mad_header *header = &frame->header; unsigned int sfreqi, ngr, gr; { unsigned int sfreq; sfreq = header->samplerate; if (header->flags & MAD_FLAG_MPEG_2_5_EXT) sfreq *= 2; /* 48000 => 0, 44100 => 1, 32000 => 2, 24000 => 3, 22050 => 4, 16000 => 5 */ sfreqi = ((sfreq >> 7) & 0x000f) + ((sfreq >> 15) & 0x0001) - 8; if (header->flags & MAD_FLAG_MPEG_2_5_EXT) sfreqi += 3; } /* scalefactors, Huffman decoding, requantization */ ngr = (header->flags & MAD_FLAG_LSF_EXT) ? 1 : 2; for (gr = 0; gr < ngr; ++gr) { struct granule *granule = &si->gr[gr]; unsigned char const *sfbwidth[2];#ifdef __WINS__ static #endif mad_fixed_t xr[2][576]; unsigned int ch; enum mad_error error; for (ch = 0; ch < nch; ++ch) { struct channel *channel = &granule->ch[ch]; unsigned int part2_length; sfbwidth[ch] = sfbwidth_table[sfreqi].l; if (channel->block_type == 2) { sfbwidth[ch] = (channel->flags & mixed_block_flag) ? sfbwidth_table[sfreqi].m : sfbwidth_table[sfreqi].s; } if (header->flags & MAD_FLAG_LSF_EXT) { part2_length = III_scalefactors_lsf(ptr, channel, ch == 0 ? 0 : &si->gr[1].ch[1], header->mode_extension); } else { part2_length = III_scalefactors(ptr, channel, &si->gr[0].ch[ch], gr == 0 ? 0 : si->scfsi[ch]); } error = III_huffdecode(ptr, xr[ch], channel, sfbwidth[ch], part2_length); if (error) return error; } /* joint stereo processing */ if (header->mode == MAD_MODE_JOINT_STEREO && header->mode_extension) { error = III_stereo(xr, granule, header, sfbwidth[0]); if (error) return error; } /* reordering, alias reduction, IMDCT, overlap-add, frequency inversion */ for (ch = 0; ch < nch; ++ch) { struct channel const *channel = &granule->ch[ch]; mad_fixed_t (*sample)[32] = &frame->sbsample[ch][18 * gr]; unsigned int sb, l, i, sblimit; mad_fixed_t output[36]; if (channel->block_type == 2) { III_reorder(xr[ch], channel, sfbwidth[ch]);# if !defined(OPT_STRICT) /* * According to ISO/IEC 11172-3, "Alias reduction is not applied for * granules with block_type == 2 (short block)." However, other * sources suggest alias reduction should indeed be performed on the * lower two subbands of mixed blocks. Most other implementations do * this, so by default we will too. */ if (channel->flags & mixed_block_flag) III_aliasreduce(xr[ch], 36);# endif } else III_aliasreduce(xr[ch], 576); l = 0; /* subbands 0-1 */ if (channel->block_type != 2 || (channel->flags & mixed_block_flag)) { unsigned int block_type; block_type = channel->block_type; if (channel->flags & mixed_block_flag) block_type = 0; /* long blocks */ for (sb = 0; sb < 2; ++sb, l += 18) { III_imdct_l(&xr[ch][l], output, block_type); III_overlap(output, (*frame->overlap)[ch][sb], sample, sb); } } else { /* short blocks */ for (sb = 0; sb < 2; ++sb, l += 18) { III_imdct_s(&xr[ch][l], output); III_overlap(output, (*frame->overlap)[ch][sb], sample, sb); } } III_freqinver(sample, 1); /* (nonzero) subbands 2-31 */ i = 576; while (i > 36 && xr[ch][i - 1] == 0) --i; sblimit = 32 - (576 - i) / 18; if (channel->block_type != 2) { /* long blocks */ for (sb = 2; sb < sblimit; ++sb, l += 18) { III_imdct_l(&xr[ch][l], output, channel->block_type); III_overlap(output, (*frame->overlap)[ch][sb], sample, sb); if (sb & 1) III_freqinver(sample, sb); } } else { /* short blocks */ for (sb = 2; sb < sblimit; ++sb, l += 18) { III_imdct_s(&xr[ch][l], output); III_overlap(output, (*frame->overlap)
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -