📄 quantize.c
字号:
}/************************************************************************* * * amp_scalefac_bands() * * author/date?? * * Amplify the scalefactor bands that violate the masking threshold. * See ISO 11172-3 Section C.1.5.4.3.5 * * distort[] = noise/masking * distort[] > 1 ==> noise is not masked * distort[] < 1 ==> noise is masked * max_dist = maximum value of distort[] * * Three algorithms: * noise_shaping_amp * 0 Amplify all bands with distort[]>1. * * 1 Amplify all bands with distort[] >= max_dist^(.5); * ( 50% in the db scale) * * 2 Amplify first band with distort[] >= max_dist; * * * For algorithms 0 and 1, if max_dist < 1, then amplify all bands * with distort[] >= .95*max_dist. This is to make sure we always * amplify at least one band. * * *************************************************************************/static void amp_scalefac_bands( lame_global_flags *gfp, gr_info *const cod_info, FLOAT *distort, FLOAT xrpow[576], int bRefine){ lame_internal_flags *gfc=gfp->internal_flags; int j, sfb; FLOAT ifqstep34, trigger; int noise_shaping_amp; if (cod_info->scalefac_scale == 0) { ifqstep34 = 1.29683955465100964055; /* 2**(.75*.5)*/ } else { ifqstep34 = 1.68179283050742922612; /* 2**(.75*1) */ } /* compute maximum value of distort[] */ trigger = 0; for (sfb = 0; sfb < cod_info->sfbmax; sfb++) { if (trigger < distort[sfb]) trigger = distort[sfb]; } noise_shaping_amp = gfc->noise_shaping_amp; if (noise_shaping_amp == 3) { if (bRefine == 1) noise_shaping_amp = 2; else noise_shaping_amp = 1; } switch (noise_shaping_amp) { case 2: /* amplify exactly 1 band */ break; case 1: /* amplify bands within 50% of max (on db scale) */ if (trigger>1.0) trigger = pow(trigger, .5); else trigger *= .95; break; case 0: default: /* ISO algorithm. amplify all bands with distort>1 */ if (trigger>1.0) trigger=1.0; else trigger *= .95; break; } j = 0; for (sfb = 0; sfb < cod_info->sfbmax; sfb++ ) { int width = cod_info->width[sfb]; int l; j += width; if (distort[sfb] < trigger) continue; if (gfc->substep_shaping & 2) { gfc->pseudohalf[sfb] = !gfc->pseudohalf[sfb]; if (!gfc->pseudohalf[sfb] && gfc->noise_shaping_amp==2) return; } cod_info->scalefac[sfb]++; for (l = -width; l < 0; l++) { xrpow[j+l] *= ifqstep34; if (xrpow[j+l] > cod_info->xrpow_max) cod_info->xrpow_max = xrpow[j+l]; } if (gfc->noise_shaping_amp==2) return; }}/************************************************************************* * * inc_scalefac_scale() * * Takehiro Tominaga 2000-xx-xx * * turns on scalefac scale and adjusts scalefactors * *************************************************************************/ static voidinc_scalefac_scale ( gr_info * const cod_info, FLOAT xrpow[576] ){ int l, j, sfb; const FLOAT ifqstep34 = 1.29683955465100964055; j = 0; for (sfb = 0; sfb < cod_info->sfbmax; sfb++) { int width = cod_info->width[sfb]; int s = cod_info->scalefac[sfb]; if (cod_info->preflag) s += pretab[sfb]; j += width; if (s & 1) { s++; for (l = -width; l < 0; l++) { xrpow[j+l] *= ifqstep34; if (xrpow[j+l] > cod_info->xrpow_max) cod_info->xrpow_max = xrpow[j+l]; } } cod_info->scalefac[sfb] = s >> 1; } cod_info->preflag = 0; cod_info->scalefac_scale = 1;}/************************************************************************* * * inc_subblock_gain() * * Takehiro Tominaga 2000-xx-xx * * increases the subblock gain and adjusts scalefactors * *************************************************************************/ static int inc_subblock_gain ( const lame_internal_flags * const gfc, gr_info * const cod_info, FLOAT xrpow[576] ){ int sfb, window; int * const scalefac = cod_info->scalefac; /* subbloc_gain can't do anything in the long block region */ for (sfb = 0; sfb < cod_info->sfb_lmax; sfb++) { if (scalefac[sfb] >= 16) return 1; } for (window = 0; window < 3; window++) { int s1, s2, l, j; s1 = s2 = 0; for (sfb = cod_info->sfb_lmax+window; sfb < cod_info->sfbdivide; sfb += 3) { if (s1 < scalefac[sfb]) s1 = scalefac[sfb]; } for (; sfb < cod_info->sfbmax; sfb += 3) { if (s2 < scalefac[sfb]) s2 = scalefac[sfb]; } if (s1 < 16 && s2 < 8) continue; if (cod_info->subblock_gain[window] >= 7) return 1; /* even though there is no scalefactor for sfb12 * subblock gain affects upper frequencies too, that's why * we have to go up to SBMAX_s */ cod_info->subblock_gain[window]++; j = gfc->scalefac_band.l[cod_info->sfb_lmax]; for (sfb = cod_info->sfb_lmax+window; sfb < cod_info->sfbmax; sfb += 3) { FLOAT amp; int width = cod_info->width[sfb], s = scalefac[sfb]; assert(s >= 0); s = s - (4 >> cod_info->scalefac_scale); if (s >= 0) { scalefac[sfb] = s; j += width*3; continue; } scalefac[sfb] = 0; amp = IPOW20(210 + (s << (cod_info->scalefac_scale + 1))); j += width * (window+1); for (l = -width; l < 0; l++) { xrpow[j+l] *= amp; if (xrpow[j+l] > cod_info->xrpow_max) cod_info->xrpow_max = xrpow[j+l]; } j += width*(3 - window - 1); } { FLOAT amp = IPOW20(210 - 8); j += cod_info->width[sfb] * (window+1); for (l = -cod_info->width[sfb]; l < 0; l++) { xrpow[j+l] *= amp; if (xrpow[j+l] > cod_info->xrpow_max) cod_info->xrpow_max = xrpow[j+l]; } } } return 0;}/******************************************************************** * * balance_noise() * * Takehiro Tominaga /date?? * Robert Hegemann 2000-09-06: made a function of it * * amplifies scalefactor bands, * - if all are already amplified returns 0 * - if some bands are amplified too much: * * try to increase scalefac_scale * * if already scalefac_scale was set * try on short blocks to increase subblock gain * ********************************************************************/inlinestatic int balance_noise ( lame_global_flags *const gfp, gr_info * const cod_info, FLOAT * distort, FLOAT xrpow[576], int bRefine){ lame_internal_flags *const gfc = gfp->internal_flags; int status; amp_scalefac_bands ( gfp, cod_info, distort, xrpow, bRefine); /* check to make sure we have not amplified too much * loop_break returns 0 if there is an unamplified scalefac * scale_bitcount returns 0 if no scalefactors are too large */ status = loop_break (cod_info); if (status) return 0; /* all bands amplified */ /* not all scalefactors have been amplified. so these * scalefacs are possibly valid. encode them: */ if (gfc->mode_gr == 2) status = scale_bitcount (cod_info); else status = scale_bitcount_lsf (gfc, cod_info); if (!status) return 1; /* amplified some bands not exceeding limits */ /* some scalefactors are too large. * lets try setting scalefac_scale=1 */ if (gfc->noise_shaping > 1) { memset(&gfc->pseudohalf, 0, sizeof(gfc->pseudohalf)); if (!cod_info->scalefac_scale) { inc_scalefac_scale (cod_info, xrpow); status = 0; } else { if (cod_info->block_type == SHORT_TYPE && gfc->subblock_gain > 0) { status = inc_subblock_gain (gfc, cod_info, xrpow) || loop_break (cod_info); } } } if (!status) { if (gfc->mode_gr == 2) status = scale_bitcount (cod_info); else status = scale_bitcount_lsf (gfc, cod_info); } return !status;}/************************************************************************ * * outer_loop () * * Function: The outer iteration loop controls the masking conditions * of all scalefactorbands. It computes the best scalefac and * global gain. This module calls the inner iteration loop * * mt 5/99 completely rewritten to allow for bit reservoir control, * mid/side channels with L/R or mid/side masking thresholds, * and chooses best quantization instead of last quantization when * no distortion free quantization can be found. * * added VBR support mt 5/99 * * some code shuffle rh 9/00 ************************************************************************/static int outer_loop ( lame_global_flags *gfp, gr_info * const cod_info, const FLOAT * const l3_xmin, /* allowed distortion */ FLOAT xrpow[576], /* coloured magnitudes of spectral */ const int ch, const int targ_bits ) /* maximum allowed bits */{ lame_internal_flags *gfc=gfp->internal_flags; gr_info cod_info_w; FLOAT save_xrpow[576]; FLOAT distort[SFBMAX]; calc_noise_result best_noise_info; int huff_bits; int better; int over; int age; calc_noise_data prev_noise; int best_part2_3_length = 9999999; int bEndOfSearch = 0; int bRefine = 0; int best_ggain_pass1 = 0; bin_search_StepSize (gfc, cod_info, targ_bits, ch, xrpow); if (!gfc->noise_shaping) /* fast mode, no noise shaping, we are ready */ return 100; /* default noise_info.over_count */ memset(&prev_noise, 0, sizeof(calc_noise_data)); /* compute the distortion in this quantization */ /* coefficients and thresholds both l/r (or both mid/side) */ over = calc_noise (gfc, cod_info, l3_xmin, distort, &best_noise_info, &prev_noise); best_noise_info.bits = cod_info->part2_3_length; cod_info_w = *cod_info; age = 0; /* if (gfp->VBR == vbr_rh || gfp->VBR == vbr_mtrh)*/ memcpy(save_xrpow, xrpow, sizeof(FLOAT)*576); while (!bEndOfSearch) { /* BEGIN MAIN LOOP */ do { calc_noise_result noise_info; int search_limit; int maxggain = 255; /* When quantization with no distorted bands is found, * allow up to X new unsuccesful tries in serial. This * gives us more possibilities for different quant_compare modes. * Much more than 3 makes not a big difference, it is only slower. */ if (gfc->substep_shaping & 2) { search_limit = 20; }else { search_limit = 3; } /* Check if the last scalefactor band is distorted. * in VBR mode we can't get rid of the distortion, so quit now * and VBR mode will try again with more bits. * (makes a 10% speed increase, the files I tested were * binary identical, 2000/05/20 Robert Hegemann) * distort[] > 1 means noise > allowed noise */ if (gfc->sfb21_extra) { if (distort[cod_info_w.sfbmax] > 1.0) break; if (cod_info_w.block_type == SHORT_TYPE && (distort[cod_info_w.sfbmax+1] > 1.0 || distort[cod_info_w.sfbmax+2] > 1.0)) break; } /* try a new scalefactor conbination on cod_info_w */ if (balance_noise (gfp, &cod_info_w, distort, xrpow, bRefine) == 0) break; if (cod_info_w.scalefac_scale) maxggain = 254; /* inner_loop starts with the initial quantization step computed above * and slowly increases until the bits < huff_bits. * Thus it is important not to start with too large of an inital * quantization step. Too small is ok, but inner_loop will take longer */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -