From 8c3b5a588e44fa346b4aaa01ea6a9f45fb36c115 Mon Sep 17 00:00:00 2001 From: Sandesh Venkatesh Date: Mon, 6 Jan 2025 14:21:34 +0530 Subject: [PATCH] Fix for high mld for ISM LTV tests cases, Q-documentation for stereo_cng and stereo_dft encoder files --- lib_enc/ext_sig_ana_fx.c | 22 ++--- lib_enc/igf_enc.c | 146 ++++++++++++++++++++++++---- lib_enc/ivas_mct_core_enc.c | 6 +- lib_enc/ivas_mct_enc_mct.c | 7 +- lib_enc/ivas_stereo_cng_enc.c | 14 +-- lib_enc/ivas_stereo_dft_enc.c | 70 ++++++------- lib_enc/ivas_stereo_mdct_core_enc.c | 9 +- lib_enc/prot_fx_enc.h | 14 ++- lib_enc/tcx_utils_enc.c | 5 +- lib_enc/tcx_utils_enc_fx.c | 93 ++++++++++++++++++ 10 files changed, 307 insertions(+), 79 deletions(-) diff --git a/lib_enc/ext_sig_ana_fx.c b/lib_enc/ext_sig_ana_fx.c index 01a866d54..af9c2dbc4 100644 --- a/lib_enc/ext_sig_ana_fx.c +++ b/lib_enc/ext_sig_ana_fx.c @@ -657,13 +657,14 @@ void core_signal_analysis_high_bitrate_ivas_fx( Word16 i, frameno; Word16 L_subframe; Word16 left_overlap = -1, right_overlap = -1, folding_offset; - Word32 buf[N_MAX + L_MDCT_OVLP_MAX]; /* Buffer for TCX20/TCX10 windowing */ - Word32 buf_powerSPec[N_MAX + L_MDCT_OVLP_MAX]; /* Buffer for TCX20/TCX10 windowing */ - Word16 mdstWin[N_MAX + L_MDCT_OVLP_MAX]; /* Buffer for MDST windowing */ + Word32 buf[N_MAX + L_MDCT_OVLP_MAX]; /* Buffer for TCX20/TCX10 windowing */ + Word32 buf_powerSPec[N_MAX + L_MDCT_OVLP_MAX]; /* Buffer for TCX20/TCX10 windowing */ + Word16 buf_powerSPec_exp[N_MAX + L_MDCT_OVLP_MAX]; /* Buffer for TCX20/TCX10 windowing */ + Word16 mdstWin[N_MAX + L_MDCT_OVLP_MAX]; /* Buffer for MDST windowing */ Word16 *pMdstWin; Word16 lpc_left_overlap_mode, lpc_right_overlap_mode; Word32 *powerSpec = buf_powerSPec; - Word16 powerSpec_e; + Word16 *powerSpec_e = buf_powerSPec_exp; Word16 *tcx20Win = (Word16 *) buf; Word32 *tcx20Win_32 = buf; Word32 interleaveBuf[N_TCX10_MAX]; @@ -692,8 +693,6 @@ void core_signal_analysis_high_bitrate_ivas_fx( move16(); move16(); (void) vad_hover_flag; - powerSpec_e = 0; - move16(); Word16 *speech_ltp_fx = NULL; Word16 *wspeech_fx = NULL; @@ -702,6 +701,8 @@ void core_signal_analysis_high_bitrate_ivas_fx( move16(); Word16 win_len = 0; move16(); + set32_fx( buf_powerSPec, 0, N_MAX + L_MDCT_OVLP_MAX ); + set16_fx( buf_powerSPec_exp, 0, N_MAX + L_MDCT_OVLP_MAX ); if ( NE_16( last_element_mode, st->element_mode ) ) { @@ -1174,9 +1175,9 @@ void core_signal_analysis_high_bitrate_ivas_fx( } /* Compute noise-measure flags for spectrum filling and quantization */ - AnalyzePowerSpectrum_fx( st, div_l( L_mult( L_subframe, st->L_frame ), hTcxEnc->L_frameTCX ), - L_subframe, left_overlap, right_overlap, hTcxEnc->spectrum_fx[frameno], hTcxEnc->spectrum_e[frameno], - pMdstWin, powerSpec, &powerSpec_e ); + AnalyzePowerSpectrum_ivas_fx( st, div_l( L_mult( L_subframe, st->L_frame ), hTcxEnc->L_frameTCX ), + L_subframe, left_overlap, right_overlap, hTcxEnc->spectrum_fx[frameno], hTcxEnc->spectrum_e[frameno], + pMdstWin, powerSpec, powerSpec_e ); } } } @@ -1414,8 +1415,7 @@ void core_signal_analysis_high_bitrate_ivas_fx( IF( st->igf ) { Word16 q_spectrum = sub( Q31, hTcxEnc->spectrum_e[frameno] ); - Word16 q_powerSpec = sub( Q31, powerSpec_e ); - ProcessIGF_ivas_fx( st, hTcxEnc->spectrum_fx[frameno], hTcxEnc->spectrum_fx[frameno], &q_spectrum, powerSpec, &q_powerSpec, transform_type[frameno] == TCX_20, frameno, 0, vad_hover_flag ); + ProcessIGF_ivas_fx( st, hTcxEnc->spectrum_fx[frameno], hTcxEnc->spectrum_fx[frameno], &q_spectrum, powerSpec, powerSpec_e, transform_type[frameno] == TCX_20, frameno, 0, vad_hover_flag ); } } } diff --git a/lib_enc/igf_enc.c b/lib_enc/igf_enc.c index 72b8e9920..9ca1cd5fc 100644 --- a/lib_enc/igf_enc.c +++ b/lib_enc/igf_enc.c @@ -184,7 +184,7 @@ static Word16 IGF_getSFM_new_fx( const Word16 *logSpec, /* i : log of power spectrum */ const Word16 start, /* i : start subband index */ const Word16 stop, /* i : stop subband index */ - Word16 e_ps /*Stores exp related to power spectrum*/ + Word16 *e_ps /*Stores exp related to power spectrum*/ ) { Word16 n; @@ -215,7 +215,7 @@ static Word16 IGF_getSFM_new_fx( move32(); move16(); num = add( num, n ); - denom = BASOP_Util_Add_Mant32Exp( tmp, e_ps, denom, denom_e, &denom_e ); + denom = BASOP_Util_Add_Mant32Exp( tmp, e_ps[i], denom, denom_e, &denom_e ); } numf = BASOP_Util_Divide1616_Scale( num, sub( stop, start ), &numf_e ); @@ -232,8 +232,6 @@ static Word16 IGF_getSFM_new_fx( return sfm; } - - /*-------------------------------------------------------------------* * IGF_getTilt() * @@ -340,6 +338,94 @@ static Word32 IGF_getTNR_fx( return tonalToNoise; } +static Word32 IGF_getTNR_ivas_fx( + const Word32 *powerSpectrum, /* i : energies */ + const Word16 start, /* i : start subband index */ + const Word16 stop, /* i : stop subband index */ + const Word16 adap, /* i : SFB width adaptation */ + Word16 *e_ps, /*Stores exponent for powerSpectrum*/ + Word16 e_adap /*Stores exponent for adap*/ +) +{ + Word16 i; + Word16 width; + Word32 avg; + Word32 tonal; + Word16 tonal_e; /* holds exp for tonal*/ + Word32 noise; + Word16 noise_e; /* holds exp for noise*/ + Word32 tonalToNoise; + Word32 rootSpec[300]; + Word16 rootSpec_e[300]; /*rootSpec_e[i] holds exp for rootSpec[i]*/ + Word16 avg_e; /* holds exp for avg*/ + Word16 tmp_e; + avg = 0; + tonal = 0; + noise = EPSILON_FX; + tonal_e = 0; + noise_e = 0; + avg_e = 0; + tmp_e = 0; + move32(); + move32(); + move32(); + move16(); + move16(); + move16(); + move16(); + + set32_fx( rootSpec, 0, 300 ); + set16_fx( rootSpec_e, 0, 300 ); + + width = sub( stop, start ); + FOR( i = start; i < stop; i++ ) + { + rootSpec_e[( i - start )] = e_ps[i]; + move16(); + rootSpec[( i - start )] = Sqrt32( powerSpectrum[i], &rootSpec_e[( i - start )] ); /*rootSpec[i - start] = sqrtf( powerSpectrum[i] );*/ + move32(); + avg = BASOP_Util_Add_Mant32Exp( avg, avg_e, rootSpec[( i - start )], rootSpec_e[( i - start )], &avg_e ); /*avg += rootSpec[i - start];resultant exponent is avg_e*/ + } + avg = BASOP_Util_Divide3216_Scale( avg, width, &tmp_e ); /*avg /= width;*/ + avg_e = add( 16, sub( add( avg_e, tmp_e ), 15 ) ); + + FOR( i = start; i < stop; i++ ) + { + Word16 normSpec_e; /*stores resultant exponent for normSpec*/ + Word16 normSpec = BASOP_Util_Divide3232_Scale( rootSpec[i - start], avg, &normSpec_e ); /*rootSpec[i - start] / avg;*/ + normSpec_e = add( normSpec_e, sub( rootSpec_e[i - start], avg_e ) ); + IF( GT_32( normSpec, L_add_sat( L_shl_sat( 1, sub( 15, normSpec_e ) ), L_shl_sat( adap, sub( e_adap, normSpec_e ) ) ) ) ) + { + tonal = BASOP_Util_Add_Mant32Exp( tonal, tonal_e, rootSpec[( i - start )], rootSpec_e[( i - start )], &tonal_e ); /*tonal += rootSpec[i - start];*/ + } + ELSE IF( LT_32( normSpec, L_shl_sat( 1, sub( 15, normSpec_e ) ) ) ) + { + noise = BASOP_Util_Add_Mant32Exp( noise, noise_e, rootSpec[( i - start )], rootSpec_e[( i - start )], &noise_e ); /*noise += rootSpec[i - start];*/ + } + } + + /*tonalToNoise = 20.f * log10f( max( 1e-018f, tonal / noise ) )*/ + IF( noise == 0 ) // To handle condition if denom = 0 + { + tonalToNoise = imult3216( L_shr( L_add( L_shl( 18 /* log10f(1e-018f) */, Q25 ), Mpy_32_16_1( L_add( BASOP_Util_Log2( tonal ), L_shl( tonal_e, Q25 ) ) /*Q25*/, INV_Log2_10_Q15 ) /*25+15-15*/ ), 3 ) /*Q22*/, 20 ); + } + ELSE + { + Word16 temp = BASOP_Util_Divide3232_Scale( tonal, noise, &tmp_e ); /*tonal / noise*/ + tmp_e = add( tmp_e, sub( tonal_e, noise_e ) ); + IF( GE_16( temp, 1 ) ) + { + tonalToNoise = imult3216( Mult_32_16( L_add( BASOP_Util_Log2( temp ), L_shl( add( 16, tmp_e ), Q25 ) ) /*Q25*/, INV_Log2_10_Q12 ) /*25+12-15*/, 20 ); /*Q22*/ + } + ELSE + { + tonalToNoise = -1509949440; /*-360.f Q22*/ + move32(); + } + } + + return tonalToNoise; +} /*-------------------------------------------------------------------* * IGF_CalculateEnvelope() @@ -352,7 +438,7 @@ static void IGF_CalculateEnvelope_ivas_fx( Word32 *pMDCTSpectrum_fx, /* i : MDCT spectrum */ Word16 e_mdct, /* i : exp of MDCT spectrum */ Word32 *pPowerSpectrum_fx, /* i : MDCT^2 + MDST^2 spectrum, or estimate */ - Word16 e_ps, /* i : exp of power spectrum */ + Word16 *e_ps, /* i : exp of power spectrum */ const Word16 igfGridIdx, /* i : IGF grid index */ const Word16 isTransient, /* i : flag indicating if transient is detected */ const Word16 last_core_acelp, /* i : indicator if last frame was ACELP core */ @@ -438,7 +524,7 @@ static void IGF_CalculateEnvelope_ivas_fx( { IF( LT_32( 1, pPowerSpectrum_fx[sb] ) ) { - hPrivateData->logSpec[sb] = s_max( 0, (Word16) L_shr( L_add( BASOP_Util_Log2( pPowerSpectrum_fx[sb] ), L_shl( e_ps, Q25 ) ), Q25 ) ); + hPrivateData->logSpec[sb] = s_max( 0, (Word16) L_shr( L_add( BASOP_Util_Log2( pPowerSpectrum_fx[sb] ), L_shl( e_ps[sb], Q25 ) ), Q25 ) ); move16(); } ELSE @@ -478,7 +564,7 @@ static void IGF_CalculateEnvelope_ivas_fx( FOR( sb = swb_offset[sfb]; sb < swb_offset[sfb + 1]; sb++ ) { Word16 shift = norm_l( pPowerSpectrum_fx[sb] ); - sfbEnergyC = BASOP_Util_Add_Mant32Exp( sfbEnergyC, sfbEnergyC_e, L_shl( pPowerSpectrum_fx[sb], shift ), sub( e_ps, shift ), &sfbEnergyC_e ); + sfbEnergyC = BASOP_Util_Add_Mant32Exp( sfbEnergyC, sfbEnergyC_e, L_shl( pPowerSpectrum_fx[sb], shift ), sub( e_ps[sb], shift ), &sfbEnergyC_e ); // sfbEnergyTileR = BASOP_Util_Add_Mant32Exp( sfbEnergyTileR, sfbEnergyTileR_e, Mult_32_32( pMDCTSpectrum_fx[strt_cpy], pMDCTSpectrum_fx[strt_cpy] ), shl( e_mdct, 1 ), &sfbEnergyTileR_e ); Word64 tmp64 = W_mult_32_32( pMDCTSpectrum_fx[strt_cpy], pMDCTSpectrum_fx[strt_cpy] ); Word16 tmp64_e = W_norm( tmp64 ); @@ -486,7 +572,7 @@ static void IGF_CalculateEnvelope_ivas_fx( sfbEnergyTileR = BASOP_Util_Add_Mant32Exp( sfbEnergyTileR, sfbEnergyTileR_e, W_extract_h( tmp64 ), shl( e_mdct, 1 ) - tmp64_e, &sfbEnergyTileR_e ); shift = norm_l( pPowerSpectrum_fx[strt_cpy] ); - sfbEnergyTileC = BASOP_Util_Add_Mant32Exp( sfbEnergyTileC, sfbEnergyTileC_e, L_shl( pPowerSpectrum_fx[strt_cpy], shift ), sub( e_ps, shift ), &sfbEnergyTileC_e ); + sfbEnergyTileC = BASOP_Util_Add_Mant32Exp( sfbEnergyTileC, sfbEnergyTileC_e, L_shl( pPowerSpectrum_fx[strt_cpy], shift ), sub( e_ps[strt_cpy], shift ), &sfbEnergyTileC_e ); strt_cpy = add( strt_cpy, 1 ); } @@ -658,7 +744,7 @@ static void IGF_CalculateEnvelope_ivas_fx( } ELSE { - y = imult1616( 20, extract_l( L_shr( Mult_32_16( ( L_add( BASOP_Util_Log2( pPowerSpectrum_fx[sb] ), L_shl( e_ps, Q25 ) ) ), INV_Log2_10_Q15 ), Q25 ) ) ); /*Q0*/ + y = imult1616( 20, extract_l( L_shr( Mult_32_16( ( L_add( BASOP_Util_Log2( pPowerSpectrum_fx[sb] ), L_shl( e_ps[sb], Q25 ) ) ), INV_Log2_10_Q15 ), Q25 ) ) ); /*Q0*/ } mean_y_fx_tmp = L_mac0( mean_y_fx_tmp, y, 1 ); /*Q0*/ mean_xy_fx = L_add( mean_xy_fx, L_mult0( y, x ) ); /*Q0*/ @@ -730,7 +816,7 @@ static void IGF_CalculateEnvelope_ivas_fx( tonalToNoise_e = 9; move16(); adap = BASOP_Util_Divide1616_Scale( width, 40, &adap_e ); - tonalToNoise = IGF_getTNR_fx( pPowerSpectrum_fx, swb_offset[sfb], swb_offset[sfb + 1], adap, e_ps, adap_e ); /*Q22*/ + tonalToNoise = IGF_getTNR_ivas_fx( pPowerSpectrum_fx, swb_offset[sfb], swb_offset[sfb + 1], adap, e_ps, adap_e ); /*Q22*/ IF( EQ_16( BASOP_Util_Cmp_Mant32Exp( tonalToNoise, tonalToNoise_e, L_add( L_shl( 10, sub( 15, adap_e ) ), adap ), add( 16, adap_e ) ), -1 ) ) { @@ -1592,7 +1678,7 @@ static void IGF_Whitening_ivas_fx( IF( LT_32( powerSpectrum[sb], 1 ) ) hPrivateData->logSpec[sb] = 0; /* max(0,FLT_MIN_EXP )*/ ELSE - hPrivateData->logSpec[sb] = extract_l( L_max( 0, L_shr( L_add( BASOP_Util_Log2( powerSpectrum[sb] ), L_shl( *powerSpectrum_e, Q25 ) ), Q25 ) ) ); + hPrivateData->logSpec[sb] = extract_l( L_max( 0, L_shr( L_add( BASOP_Util_Log2( powerSpectrum[sb] ), L_shl( powerSpectrum_e[sb], Q25 ) ), Q25 ) ) ); move16(); } } @@ -1608,7 +1694,7 @@ static void IGF_Whitening_ivas_fx( } ELSE { - tmp = BASOP_Util_Divide1616_Scale( IGF_getSFM_new_fx( powerSpectrum, hPrivateData->logSpec, hGrid->tile[p], hGrid->tile[p + 1], *powerSpectrum_e ), IGF_getCrest_new_fx( hPrivateData->logSpec, hGrid->tile[p], hGrid->tile[p + 1], &crest_e ), &tmp_e ); + tmp = BASOP_Util_Divide1616_Scale( IGF_getSFM_new_fx( powerSpectrum, hPrivateData->logSpec, hGrid->tile[p], hGrid->tile[p + 1], powerSpectrum_e ), IGF_getCrest_new_fx( hPrivateData->logSpec, hGrid->tile[p], hGrid->tile[p + 1], &crest_e ), &tmp_e ); tmp_e = sub( tmp_e, crest_e ); } @@ -2489,7 +2575,7 @@ void IGFEncApplyMono_ivas_fx( Word32 *pMDCTSpectrum_fx, /* i/o: MDCT spectrum */ Word16 e_mdct, /* i : exponent of pMDCTspectrum */ Word32 *pPowerSpectrum_fx, /* i/o: MDCT^2 + MDST^2 spectrum, or estimate */ - Word16 e_ps, /* i : exponent of pPowerSpectrum */ + Word16 *e_ps, /* i : exponent of pPowerSpectrum */ const Word16 isTCX20, /* i : flag indicating if the input is TCX20 or TCX10/2xTCX5 */ const Word8 isTNSActive, /* i : flag indicating if the TNS is active */ const Word16 sp_aud_decision0, /* i : first stage switching decision */ @@ -2497,11 +2583,15 @@ void IGFEncApplyMono_ivas_fx( ) { Word32 *pPowerSpectrumParameter_fx; + Word16 *pPowerSpectrumParameter_exp; Word16 att_fx = MAX16B; Word16 last_core_acelp; Word16 highPassEner_exp; move16(); + Word32 common_pPowerSpectrum_fx[N_MAX + L_MDCT_OVLP_MAX]; + Word16 common_pPowerSpectrum_exp = MIN16B; + move16(); test(); IF( st->last_core == ACELP_CORE ) { @@ -2518,10 +2608,12 @@ void IGFEncApplyMono_ivas_fx( IF( !isTNSActive && isTCX20 ) { pPowerSpectrumParameter_fx = pPowerSpectrum_fx; + pPowerSpectrumParameter_exp = e_ps; } ELSE { pPowerSpectrumParameter_fx = NULL; + pPowerSpectrumParameter_exp = NULL; } IGF_UpdateInfo( st->hIGFEnc, igfGridIdx ); @@ -2532,28 +2624,43 @@ void IGFEncApplyMono_ivas_fx( calculate_hangover_attenuation_gain_ivas_fx( st, &att_fx, vad_hover_flag ); } - IGF_CalculateEnvelope_ivas_fx( st->hIGFEnc, pMDCTSpectrum_fx, e_mdct, pPowerSpectrumParameter_fx, e_ps, igfGridIdx, st->hTranDet->transientDetector.bIsAttackPresent, last_core_acelp, st->element_mode, att_fx ); + IGF_CalculateEnvelope_ivas_fx( st->hIGFEnc, pMDCTSpectrum_fx, e_mdct, pPowerSpectrumParameter_fx, pPowerSpectrumParameter_exp, igfGridIdx, st->hTranDet->transientDetector.bIsAttackPresent, last_core_acelp, st->element_mode, att_fx ); test(); IF( isTCX20 ) { pPowerSpectrumParameter_fx = pPowerSpectrum_fx; + pPowerSpectrumParameter_exp = e_ps; } ELSE { pPowerSpectrumParameter_fx = NULL; + pPowerSpectrumParameter_exp = NULL; } IF( EQ_16( st->element_mode, IVAS_CPE_MDCT ) ) { - IGF_Whitening_ivas_fx( st->hIGFEnc, pPowerSpectrumParameter_fx, &e_ps, igfGridIdx, st->hTranDet->transientDetector.bIsAttackPresent, last_core_acelp, isTNSActive, sp_aud_decision0, st->element_brate, st->element_mode ); + IGF_Whitening_ivas_fx( st->hIGFEnc, pPowerSpectrumParameter_fx, pPowerSpectrumParameter_exp, igfGridIdx, st->hTranDet->transientDetector.bIsAttackPresent, last_core_acelp, isTNSActive, sp_aud_decision0, st->element_brate, st->element_mode ); } ELSE { - IGF_Whitening_ivas_fx( st->hIGFEnc, pPowerSpectrumParameter_fx, &e_ps, igfGridIdx, st->hTranDet->transientDetector.bIsAttackPresent, last_core_acelp, isTNSActive, sp_aud_decision0, st->total_brate, st->element_mode ); + IGF_Whitening_ivas_fx( st->hIGFEnc, pPowerSpectrumParameter_fx, pPowerSpectrumParameter_exp, igfGridIdx, st->hTranDet->transientDetector.bIsAttackPresent, last_core_acelp, isTNSActive, sp_aud_decision0, st->total_brate, st->element_mode ); } - IGF_ErodeSpectrum( &highPassEner_exp, st->hIGFEnc, pMDCTSpectrum_fx, pPowerSpectrumParameter_fx, e_ps, igfGridIdx ); + IF( pPowerSpectrumParameter_fx ) + { + FOR( Word16 i = 0; i < N_MAX + L_MDCT_OVLP_MAX; i++ ) + { + common_pPowerSpectrum_exp = s_max( common_pPowerSpectrum_exp, pPowerSpectrumParameter_exp[i] ); + } + + FOR( Word16 i = 0; i < N_MAX + L_MDCT_OVLP_MAX; i++ ) + { + common_pPowerSpectrum_fx[i] = L_shl( common_pPowerSpectrum_fx[i], sub( pPowerSpectrumParameter_exp[i], common_pPowerSpectrum_exp ) ); + move16(); + } + } + IGF_ErodeSpectrum( &highPassEner_exp, st->hIGFEnc, pMDCTSpectrum_fx, pPowerSpectrumParameter_fx, common_pPowerSpectrum_exp, igfGridIdx ); } @@ -2583,6 +2690,7 @@ void IGFEncApplyStereo_fx( Word16 coreMsMask[N_MAX]; Word16 sfb, ch, last_core_acelp; STEREO_MDCT_BAND_PARAMETERS *sfbConf; + Word16 exp_pPowerSpectrum[L_FRAME48k]; /* assumptions: stereo filling was already done on the flattened spectra * IGF region is always coded M/S, never L/R (to be done in the encoder) @@ -2646,7 +2754,9 @@ void IGFEncApplyStereo_fx( pPowerSpectrumParameter_fx[ch] = NULL; } - IGF_Whitening_ivas_fx( hIGFEnc[ch], pPowerSpectrumParameter_fx[ch], &sts[ch]->hTcxEnc->spectrum_e[frameno], igfGridIdx, sts[ch]->hTranDet->transientDetector.bIsAttackPresent, last_core_acelp, ( sts[0]->hTcxEnc->fUseTns[frameno] || sts[1]->hTcxEnc->fUseTns[frameno] ), sp_aud_decision0, element_brate, sts[ch]->element_mode ); + set16_fx( exp_pPowerSpectrum, sts[ch]->hTcxEnc->spectrum_e[frameno], L_FRAME48k ); + + IGF_Whitening_ivas_fx( hIGFEnc[ch], pPowerSpectrumParameter_fx[ch], &exp_pPowerSpectrum[0], igfGridIdx, sts[ch]->hTranDet->transientDetector.bIsAttackPresent, last_core_acelp, ( sts[0]->hTcxEnc->fUseTns[frameno] || sts[1]->hTcxEnc->fUseTns[frameno] ), sp_aud_decision0, element_brate, sts[ch]->element_mode ); IGF_ErodeSpectrum( &highPassEner_exp, hIGFEnc[ch], sts[ch]->hTcxEnc->spectrum_fx[frameno], pPowerSpectrumParameter_fx[ch], sts[ch]->hTcxEnc->spectrum_e[frameno], igfGridIdx ); } diff --git a/lib_enc/ivas_mct_core_enc.c b/lib_enc/ivas_mct_core_enc.c index c3096d205..f5f179778 100644 --- a/lib_enc/ivas_mct_core_enc.c +++ b/lib_enc/ivas_mct_core_enc.c @@ -237,6 +237,7 @@ void ivas_mct_core_enc_fx( Word16 nCPE; Word32 *orig_spectrum_fx[MCT_MAX_CHANNELS][2]; /* Pointers to MDCT output for a short block (L/R) */ Word32 powerSpec_fx[MCT_MAX_CHANNELS][L_FRAME48k]; + Word16 exp_powerSpec[MCT_MAX_CHANNELS][N_MAX + L_MDCT_OVLP_MAX]; Word32 mdst_fx; Word32 powerSpecMsInv_long_fx[MCT_MAX_CHANNELS][L_FRAME48k]; /* MS inv power spectrum, also inverse MDST spectrum */ Word32 *powerSpecMsInv_fx[MCT_MAX_CHANNELS][2]; @@ -277,6 +278,8 @@ void ivas_mct_core_enc_fx( { set32_fx( powerSpecMsInv_long_fx[ch], 0, L_FRAME48k ); q_powSpec[ch] = 0; + move16(); + set16_fx( exp_powerSpec[ch], 0, N_MAX + L_MDCT_OVLP_MAX ); } #endif // MSAN_FIX FOR( ch = 0; ch < nChannels; ch++ ) @@ -638,8 +641,9 @@ void ivas_mct_core_enc_fx( FOR( n = 0; n < nSubframes; n++ ) { q_spectrum = sub( 31, st->hTcxEnc->spectrum_e[n] ); + set16_fx( exp_powerSpec[ch], sub( Q31, q_powSpec[ch] ), N_MAX + L_MDCT_OVLP_MAX ); - ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[ch][n], &q_spectrum, &powerSpec_fx[ch][n * L_subframeTCX], &q_powSpec[ch], st->core == TCX_20_CORE, n, sp_aud_decision0[ch], 0 ); + ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[ch][n], &q_spectrum, &powerSpec_fx[ch][n * L_subframeTCX], &exp_powerSpec[ch][n * L_subframeTCX], st->core == TCX_20_CORE, n, sp_aud_decision0[ch], 0 ); st->hIGFEnc->spec_be_igf_e = sub( 31, q_origSpec ); st->hTcxEnc->spectrum_e[n] = sub( 31, q_spectrum ); diff --git a/lib_enc/ivas_mct_enc_mct.c b/lib_enc/ivas_mct_enc_mct.c index ea916c673..863e39b84 100644 --- a/lib_enc/ivas_mct_enc_mct.c +++ b/lib_enc/ivas_mct_enc_mct.c @@ -997,6 +997,7 @@ void mctStereoIGF_enc_fx( Encoder_State *st; Word16 singleChEle[MCT_MAX_CHANNELS]; Word16 q_spectrum; + Word16 exp_powerSpec[MCT_MAX_CHANNELS][N_MAX + L_MDCT_OVLP_MAX]; L_subframeTCX = 0; /* to avoid compilation warning */ move16(); @@ -1104,7 +1105,8 @@ void mctStereoIGF_enc_fx( q_spectrum = sub( 31, st->hTcxEnc->spectrum_e[n] ); - ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[p_ch[ch]][n], &q_spectrum, &powerSpec_fx[p_ch[ch]][n * L_subframeTCX], &q_powerSpec[p_ch[ch]], st->core == TCX_20_CORE, n, sp_aud_decision0[ch], 0 ); + set16_fx( exp_powerSpec[p_ch[ch]], sub( Q31, q_powerSpec[p_ch[ch]] ), N_MAX + L_MDCT_OVLP_MAX ); + ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[p_ch[ch]][n], &q_spectrum, &powerSpec_fx[p_ch[ch]][n * L_subframeTCX], &exp_powerSpec[p_ch[ch]][n * L_subframeTCX], st->core == TCX_20_CORE, n, sp_aud_decision0[ch], 0 ); st->hTcxEnc->spectrum_e[n] = sub( 31, q_spectrum ); move16(); @@ -1144,7 +1146,8 @@ void mctStereoIGF_enc_fx( { q_spectrum = sub( 31, st->hTcxEnc->spectrum_e[n] ); - ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[ch][n], &q_spectrum, &powerSpec_fx[ch][n * L_subframeTCX], &q_powerSpec[ch], st->core == TCX_20_CORE, n, sp_aud_decision0[ch], 0 ); + set16_fx( exp_powerSpec[ch], sub( Q31, q_powerSpec[ch] ), N_MAX + L_MDCT_OVLP_MAX ); + ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[ch][n], &q_spectrum, &powerSpec_fx[ch][n * L_subframeTCX], &exp_powerSpec[ch][n * L_subframeTCX], st->core == TCX_20_CORE, n, sp_aud_decision0[ch], 0 ); st->hTcxEnc->spectrum_e[n] = sub( 31, q_spectrum ); move16(); diff --git a/lib_enc/ivas_stereo_cng_enc.c b/lib_enc/ivas_stereo_cng_enc.c index 0a3c84b1e..059eb5b8e 100644 --- a/lib_enc/ivas_stereo_cng_enc.c +++ b/lib_enc/ivas_stereo_cng_enc.c @@ -109,11 +109,11 @@ void stereo_dft_enc_sid_calc_coh_fx( xspec_scale = Sqrt32( L_tmp3, &L_tmp3_e ); // xspec_scale = L_shl(xspec_scale, L_tmp3_e);//Q31 - hStereoDft->xspec_smooth_fx[2 * k] = Mpy_32_32( hStereoDft->xspec_smooth_fx[2 * k], xspec_scale ); + hStereoDft->xspec_smooth_fx[2 * k] = Mpy_32_32( hStereoDft->xspec_smooth_fx[2 * k], xspec_scale ); // Q(31-(xspec_smooth_fx_e+tmp3_e)) move32(); hStereoDft->xspec_smooth_fx_e[2 * k] = add( hStereoDft->xspec_smooth_fx_e[2 * k], L_tmp3_e ); move16(); - hStereoDft->xspec_smooth_fx[2 * k + 1] = Mpy_32_32( hStereoDft->xspec_smooth_fx[2 * k + 1], xspec_scale ); + hStereoDft->xspec_smooth_fx[2 * k + 1] = Mpy_32_32( hStereoDft->xspec_smooth_fx[2 * k + 1], xspec_scale ); // Q(31-(xspec_smooth_fx_e+tmp3_e)) move32(); hStereoDft->xspec_smooth_fx_e[2 * k + 1] = add( hStereoDft->xspec_smooth_fx_e[2 * k + 1], L_tmp3_e ); move16(); @@ -231,10 +231,10 @@ void stereo_dft_enc_sid_calc_coh_fx( void stereo_dft_enc_sid_coh_fx( BSTR_ENC_HANDLE hBstr, /* i/o: bitstream handle */ - Word32 *mem_cohBand, /* i/o: Coherence memory */ + Word32 *mem_cohBand, /* i/o: Coherence memory Q31 */ const Word16 nbands, /* i : number of DFT stereo bands */ Word16 *nb_bits, /* i/o: number of bits written */ - Word32 *cohBand /* i/o: Coherence per band */ + Word32 *cohBand /* i/o: Coherence per band Q31 */ ) { Word16 b, k; @@ -384,7 +384,7 @@ void stereo_dft_enc_sid_coh_fx( alphaptr = &dft_cng_alpha_bits_fx[alpha_step][alpha_level]; pptr = dft_cng_coh_pred_fx[coh_pred_index]; /* Set pointer to selected predictor */ pred = 3277 /*0.4f in Q13*/; - + move16(); FOR( b = 0; b < nbands; b++ ) { /* Intra-frame prediction using quantized values */ @@ -429,7 +429,7 @@ void stereo_dft_enc_sid_coh_fx( move16(); } - mem_cohBand[b] = L_deposit_h( cohBandq[b] ); /* Update memory for next frame */ + mem_cohBand[b] = L_deposit_h( cohBandq[b] ); /* Update memory for next frame Q31*/ move32(); pred = 0; move16(); @@ -658,7 +658,7 @@ void stereo_cng_upd_counters_fx( STEREO_CNG_ENC_HANDLE hStereoCng, /* i/o: Stereo CNG data structure */ const Word32 element_mode, /* i : element mode */ const Word16 nbands, /* i : Number of bands in active */ - const Word32 sidSideGain[], /* i : SID side gains */ + const Word32 sidSideGain[], /* i : SID side gains Q31 */ const Word16 burst_ho_count, /* i : Hang-over count */ Word16 *coh_fade_counter /* i : Coherence fade counter */ ) diff --git a/lib_enc/ivas_stereo_dft_enc.c b/lib_enc/ivas_stereo_dft_enc.c index 4957aea13..119dfc313 100644 --- a/lib_enc/ivas_stereo_dft_enc.c +++ b/lib_enc/ivas_stereo_dft_enc.c @@ -821,7 +821,7 @@ void stereo_dft_enc_update_fx( move32(); /* Update the parameters and serial */ - FOR( i = 0; i < imult1616( k_offset, STEREO_DFT_BAND_MAX ); i++ ) + FOR( i = 0; i < ( k_offset * STEREO_DFT_BAND_MAX ); i++ ) { hStereoDft->side_gain_fx[i] = hStereoDft->side_gain_fx[STEREO_DFT_BAND_MAX + i]; move32(); @@ -939,9 +939,9 @@ void stereo_dft_enc_analyze_fx( const Word16 input_frame, /* i : input frame length */ STEREO_DFT_ENC_DATA_HANDLE hStereoDft, /* i/o: encoder stereo handle */ STEREO_MDCT_ENC_DATA_HANDLE hStereoMdct, /* i/o: encoder MDCT stereo handle */ - Word32 DFT[CPE_CHANNELS][STEREO_DFT_N_MAX_ENC], /* o : DFT buffers */ + Word32 DFT[CPE_CHANNELS][STEREO_DFT_N_MAX_ENC], /* o : DFT buffers Q(31-DFT_e) */ Word16 DFT_e[CPE_CHANNELS], /* o : DFT buffers */ - Word16 *input_mem[CPE_CHANNELS], /* i/o: input buffer memory */ + Word16 *input_mem[CPE_CHANNELS], /* i/o: input buffer memory Q(q_input_mem_ */ Word16 *q_input_mem ) { Word16 i, n; @@ -1013,10 +1013,10 @@ void stereo_dft_enc_analyze_fx( { trigo_enc[i] = pTrigo[i * trigo_step]; move16(); - trigo_enc[sub( shr( NFFT, 1 ), i )] = pTrigo[L_mult0( i, trigo_step )]; + trigo_enc[( ( NFFT / 2 ) - i )] = pTrigo[L_mult0( i, trigo_step )]; move16(); } - trigo_enc[shr( NFFT, 2 )] = pTrigo[L_mult0( shr( NFFT, 2 ), trigo_step )]; + trigo_enc[NFFT / 4] = pTrigo[( ( NFFT / 4 ) * trigo_step )]; move16(); /*Forwards FFT: L and R*/ @@ -1025,42 +1025,42 @@ void stereo_dft_enc_analyze_fx( { pDFT_L[i] = 0; move32(); - pDFT_L[sub( sub( NFFT, 1 ), i )] = 0; + pDFT_L[( ( NFFT - 1 ) - i )] = 0; move32(); pDFT_R[i] = 0; move32(); - pDFT_R[sub( sub( NFFT, 1 ), i )] = 0; + pDFT_R[( ( NFFT - 1 ) - i )] = 0; move32(); } FOR( n = 0; n < n_channels; n++ ) { - Scale_sig( &mem[n][0], dft_ovl, sts[n]->q_inp - q_input_mem[n] ); + Scale_sig( &mem[n][0], dft_ovl, sts[n]->q_inp - q_input_mem[n] ); // Q(sts[n]->q_inp) q_input_mem[n] = sts[n]->q_inp; move16(); } /*overlapping parts*/ FOR( i = 0; i < dft_ovl; i++ ) { - pDFT_L[add( dft_zp, i )] = L_mult0( mem[0][i], pWin[i] ); + pDFT_L[( dft_zp + i )] = L_mult0( mem[0][i], pWin[i] ); move32(); - pDFT_L[sub( add( add( dft_zp, N ), dft_ovl ) - 1, i )] = L_mult0( input[0][sub( add( add( offset, N ), dft_ovl ) - 1, i )], pWin[i] ); + pDFT_L[( ( ( dft_zp + N ) + dft_ovl ) - 1 - i )] = L_mult0( input[0][offset + N + dft_ovl - 1 - i], pWin[i] ); move32(); - pDFT_R[add( dft_zp, i )] = L_mult0( mem[1][i], pWin[i] ); + pDFT_R[dft_zp + i] = L_mult0( mem[1][i], pWin[i] ); move32(); - pDFT_R[sub( add( add( dft_zp, N ), dft_ovl ) - 1, i )] = L_mult0( input[1][sub( add( add( offset, N ), dft_ovl ) - 1, i )], pWin[i] ); + pDFT_R[( ( dft_zp + N ) + dft_ovl ) - 1 - i] = L_mult0( input[1][offset + N + dft_ovl - 1 - i], pWin[i] ); move32(); } /*middle part*/ FOR( i = 0; i < N - dft_ovl; i++ ) { - pDFT_L[add( add( dft_zp, dft_ovl ), i )] = L_shr( L_deposit_h( input[0][add( add( offset, dft_ovl ), i )] ), 1 ); + pDFT_L[dft_zp + dft_ovl + i] = L_shr( L_deposit_h( input[0][offset + dft_ovl + i] ), 1 ); move32(); - pDFT_R[add( add( dft_zp, dft_ovl ), i )] = L_shr( L_deposit_h( input[1][add( add( offset, dft_ovl ), i )] ), 1 ); + pDFT_R[dft_zp + dft_ovl + i] = L_shr( L_deposit_h( input[1][offset + dft_ovl + i] ), 1 ); move32(); } DFT_e[0] = sub( 31, add( 15, sts[0]->q_inp ) ); @@ -1098,13 +1098,14 @@ void stereo_dft_enc_analyze_fx( { mem[n] = &input[n][sub( N, dft_ovl )]; } - + test(); + test(); IF( hStereoDft != NULL && hStereoDft->hConfig->hybrid_itd_flag && hStereoDft->hItd->td_itd[STEREO_DFT_OFFSET] ) { FOR( n = 0; n < n_channels; n++ ) { #ifdef MSAN_FIX - Scale_sig( hStereoDft->input_mem_itd_fx[n], dft_ovl, sub( sts[n]->q_inp, hStereoDft->q_input_mem_itd[n] ) ); + Scale_sig( hStereoDft->input_mem_itd_fx[n], dft_ovl, sub( sts[n]->q_inp, hStereoDft->q_input_mem_itd[n] ) ); // Q(sts[n]->q_inp) #else Scale_sig( hStereoDft->input_mem_itd_fx[n], STEREO_DFT_OVL_MAX, sts[n]->q_inp - hStereoDft->q_input_mem_itd[n] ); #endif // MSAN_FIX @@ -1362,14 +1363,14 @@ Word32 stereo_dft_enc_synthesize_fx( offset = 0; move16(); - FOR( i = 0; i < shr( NFFT, 2 ); i++ ) + FOR( i = 0; i < NFFT / 4; i++ ) { - trigo_enc_fx[i] = trigo_fx[imult1616( i, trigo_step )]; + trigo_enc_fx[i] = trigo_fx[i * trigo_step]; move16(); - trigo_enc_fx[sub( shr( NFFT, 1 ), i )] = trigo_fx[imult1616( i, trigo_step )]; + trigo_enc_fx[( NFFT / 2 ) - i] = trigo_fx[i * trigo_step]; move16(); } - trigo_enc_fx[shr( NFFT, 2 )] = trigo_fx[imult1616( shr( NFFT, 2 ), trigo_step )]; + trigo_enc_fx[NFFT / 4] = trigo_fx[( NFFT / 4 ) * trigo_step]; move16(); /*-----------------------------------------------------------------* @@ -1861,8 +1862,8 @@ void stereo_dft_enc_process_fx( IF( pgIpd[0] != 0 ) { - c_fx = shl_sat( getCosWord16( (Word16) pgIpd[0] ), 1 ); // Q15 saturation expected - s_fx = getSinWord16( (Word16) pgIpd[0] ); // Q15 + c_fx = shl_sat( getCosWord16( extract_l( pgIpd[0] ) ), 1 ); // Q15 saturation expected + s_fx = getSinWord16( extract_l( pgIpd[0] ) ); // Q15 FOR( i = hStereoDft->band_limits_dmx[b]; i < hStereoDft->band_limits_dmx[b + 1]; i++ ) { /*rotate L*/ @@ -2415,7 +2416,7 @@ void stereo_dft_enc_process_fx( } FOR( i = 0; i < STEREO_DFT_N_MAX_ENC; i++ ) { - DFT_DMX[i] = L_shr_r( DFT_DMX[i], sub( max_exp, DFT_DMX_e[i] ) ); + DFT_DMX[i] = L_shr_r( DFT_DMX[i], sub( max_exp, DFT_DMX_e[i] ) ); // Q(31-max_exp) move32(); } hStereoDft->DFT_fx_e[0] = max_exp; @@ -2429,7 +2430,7 @@ void stereo_dft_enc_process_fx( } FOR( i = 0; i < STEREO_DFT_N_8k_ENC; i++ ) { - DFT_RES[i] = L_shr_r( DFT_RES[i], sub( max_exp, DFT_RES_e[i] ) ); + DFT_RES[i] = L_shr_r( DFT_RES[i], sub( max_exp, DFT_RES_e[i] ) ); // Q(31-max_exp) move32(); } hStereoDft->DFT_fx_e[1] = max_exp; @@ -2868,7 +2869,7 @@ void stereo_dft_enc_write_BS_fx( sp_aud_decision0 = 0; move16(); - IF( EQ_16( hCPE->last_element_mode, IVAS_CPE_DFT ) ) + if ( EQ_16( hCPE->last_element_mode, IVAS_CPE_DFT ) ) { sp_aud_decision0 = hCPE->hCoreCoder[0]->sp_aud_decision0; move16(); @@ -2883,7 +2884,7 @@ void stereo_dft_enc_write_BS_fx( move16(); test(); - IF( EQ_32( core_brate, FRAME_NO_DATA ) || EQ_32( core_brate, SID_2k40 ) ) + IF( ( core_brate == FRAME_NO_DATA ) || EQ_32( core_brate, SID_2k40 ) ) { NFFT_inner = s_min( STEREO_DFT_N_32k_ENC, STEREO_DFT_N_MAX_ENC * inner_frame_tbl[hCPE->hCoreCoder[0]->bwidth] / L_FRAME48k ); hStereoDft->band_res[k_offset] = hStereoDft->hConfig->band_res; @@ -2903,7 +2904,7 @@ void stereo_dft_enc_write_BS_fx( hStereoDft->nbands = stereo_dft_band_config_fx( hStereoDft->band_limits, hStereoDft->band_res[k_offset], NFFT_inner, ENC ); move16(); - IF( EQ_32( core_brate, FRAME_NO_DATA ) ) + IF( core_brate == FRAME_NO_DATA ) { /* No data frame */ ( *nb_bits ) = 0; @@ -3244,6 +3245,7 @@ ELSE } ( *nb_bits ) = add( *nb_bits, nb ); +move16(); IF( EQ_32( core_brate, SID_2k40 ) ) { @@ -3439,7 +3441,7 @@ static void stereo_dft_enc_compute_prm_fx( sum_past_dpi_e = 0; move16(); - WHILE( LT_16( hStereoDft->band_limits_dmx[b2], hStereoDft->band_limits[b + 1] ) ) + WHILE( hStereoDft->band_limits_dmx[b2] < hStereoDft->band_limits[b + 1] ) { pDFT_L = DFT_L_fx; // DFT_L_e = hStereoDft->DFT_fx_e[0]; @@ -3798,7 +3800,7 @@ static void stereo_dft_enc_compute_prm_fx( move32(); } // dItd32 = (int16_t) floorf( conversion_factor * hStereoDft->hItd->deltaItd[k_offset] + 0.5f ); - dItd32 = (Word16) L_shr_r( Mpy_32_32( conversion_factor, hStereoDft->hItd->deltaItd_fx[k_offset] ), Q15 ); // Q0 + dItd32 = extract_l( L_shr_r( Mpy_32_32( conversion_factor, hStereoDft->hItd->deltaItd_fx[k_offset] ), Q15 ) ); // Q0 gain_offset = stereo_dft_gain_offset_fx( c, c_e, dItd32 ); // Q31 pPredGain[b] = L_max( 0, L_sub( pPredGain[b], gain_offset ) ); @@ -3949,8 +3951,6 @@ static void stereo_dft_enc_compute_prm_fx( ELSE { stereo_dft_enc_get_reverb_flag_fx( hStereoDft, pPredGain, sub_nrg_DMX, sub_nrg_DMX_e, sub_nrg_L, sub_nrg_L_e, sub_nrg_R, sub_nrg_R_e, k_offset, bin_nrgL_fx, bin_nrgL_fx_e, bin_nrgR_fx, bin_nrgR_fx_e ); - // printf( "\n%d ", hStereoDft->reverb_flag ); - // printf( "\n%f ", (float)hStereoDft->res_pred_gain_fx[18]/0x7fffffff); } @@ -4271,6 +4271,7 @@ static Word32 stereo_dft_calc_mean_bipd_fx( { ipd_buf[i] = L_add( ipd_buf[i], 2 * EVS_PI_FX ); } + move32(); } // ipd_smooth = (i / (float)(i + 1)) * ipd_smooth + (1 / (float)(i + 1)) * ipd_buf[i]; ipd_smooth = L_add( Mpy_32_16_1( ipd_smooth, ipd_table1[i] ), Mpy_32_16_1( ipd_buf[i], ipd_table2[i] ) ); // Q13 @@ -4328,7 +4329,7 @@ static Word32 stereo_dft_calc_mean_ipd_change_fx( // ipd_mean_change /= gipd_band_max; ipd_mean_change = BASOP_Util_Divide3232_Scale_cadence( ipd_mean_change, gipd_band_max, &ipd_mean_change_e ); ipd_mean_change_e = add( ipd_mean_change_e, 18 - 31 ); - ipd_mean_change = L_shr( ipd_mean_change, sub( 18, ipd_mean_change_e ) ); + ipd_mean_change = L_shr( ipd_mean_change, sub( 18, ipd_mean_change_e ) ); // Q13 return ipd_mean_change; } @@ -4436,6 +4437,7 @@ static void stereo_dft_enc_get_nipd_flag_fx( hStereoDft->no_ipd_flag = hStereoDft->prev_no_ipd_flag; move16(); hStereoDft->no_ipd_cnt = add( hStereoDft->no_ipd_cnt, 1 ); + move16(); } ELSE { @@ -4456,8 +4458,8 @@ static void stereo_dft_enc_get_nipd_flag_fx( * ---------------------------------------------------------------*/ static void stereo_dft_enc_get_reverb_flag_fx( STEREO_DFT_ENC_DATA_HANDLE hStereoDft, - Word32 *pPredGain, // Q31 - Word32 *sub_nrg_DMX, + Word32 *pPredGain, // Q31 + Word32 *sub_nrg_DMX, // Q(31-sub_nrg_DMX_e) Word16 *sub_nrg_DMX_e, const Word32 *sub_nrg_L, // Q(31-sub_nrg_L_e[]) const Word16 *sub_nrg_L_e, diff --git a/lib_enc/ivas_stereo_mdct_core_enc.c b/lib_enc/ivas_stereo_mdct_core_enc.c index 8ebcbf570..d8dcf5653 100644 --- a/lib_enc/ivas_stereo_mdct_core_enc.c +++ b/lib_enc/ivas_stereo_mdct_core_enc.c @@ -139,6 +139,7 @@ void stereo_mdct_core_enc_fx( Word32 *orig_spectrum_fx[CPE_CHANNELS][NB_DIV]; /* Pointers to MDCT output for a short block (L/R) */ Word32 powerSpec_fx[CPE_CHANNELS][N_MAX]; Word32 *p_powerSpec_fx[CPE_CHANNELS]; + Word16 exp_powerSpec[CPE_CHANNELS][N_MAX + L_MDCT_OVLP_MAX]; Word32 powerSpecMsInv_long_fx[CPE_CHANNELS][N_MAX]; /* MS inv power spectrum, also inverse MDST spectrum */ Word32 *powerSpecMsInv_fx[CPE_CHANNELS][NB_DIV]; Word32 quantized_spectrum_long_fx[CPE_CHANNELS][N_MAX]; /* quantized MDCT spectrum, inv ms mask mdst spectrum, scratch for MS spectra in the MS decision */ @@ -651,7 +652,9 @@ void stereo_mdct_core_enc_fx( Scale_sig32( orig_spectrum_fx[ch][n], N_TCX10_MAX, sub( q_spectrum, sub( Q31, p_orig_spectrum_e[ch] ) ) ); /* q_spectrum */ q_spectrum = sub( Q31, st->hTcxEnc->spectrum_e[n] ); - ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[ch][n], &q_spectrum, &powerSpec_fx[ch][n * L_subframeTCX], &q_powSpec[ch], st->core == TCX_20_CORE, n, hCPE->hCoreCoder[0]->sp_aud_decision0, 0 ); + set16_fx( exp_powerSpec[ch], sub( Q31, q_powSpec[ch] ), N_MAX + L_MDCT_OVLP_MAX ); + + ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[ch][n], &q_spectrum, &powerSpec_fx[ch][n * L_subframeTCX], &exp_powerSpec[ch][n * L_subframeTCX], st->core == TCX_20_CORE, n, hCPE->hCoreCoder[0]->sp_aud_decision0, 0 ); } } } @@ -690,7 +693,9 @@ void stereo_mdct_core_enc_fx( Scale_sig32( orig_spectrum_fx[ch][n], N_TCX10_MAX, sub( q_spectrum, sub( Q31, p_orig_spectrum_e[ch] ) ) ); /* q_spectrum */ q_spectrum = sub( Q31, st->hTcxEnc->spectrum_e[n] ); - ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[ch][n], &q_spectrum, &powerSpec_fx[ch][n * L_subframeTCX], &q_powSpec[ch], st->core == TCX_20_CORE, n, hCPE->hCoreCoder[0]->sp_aud_decision0, 0 ); + set16_fx( exp_powerSpec[ch], sub( Q31, q_powSpec[ch] ), N_MAX + L_MDCT_OVLP_MAX ); + + ProcessIGF_ivas_fx( st, st->hTcxEnc->spectrum_fx[n], orig_spectrum_fx[ch][n], &q_spectrum, &powerSpec_fx[ch][n * L_subframeTCX], &exp_powerSpec[ch][n * L_subframeTCX], st->core == TCX_20_CORE, n, hCPE->hCoreCoder[0]->sp_aud_decision0, 0 ); } } } diff --git a/lib_enc/prot_fx_enc.h b/lib_enc/prot_fx_enc.h index 4f1d4a5a7..621b77e33 100644 --- a/lib_enc/prot_fx_enc.h +++ b/lib_enc/prot_fx_enc.h @@ -1279,6 +1279,18 @@ void AnalyzePowerSpectrum_fx( Word32 powerSpec[], /* o : Power spectrum. Can point to signal */ Word16 *powerSpec_e ); +void AnalyzePowerSpectrum_ivas_fx( + Encoder_State *st, /* i/o: encoder states */ + Word16 L_frame, /* i : frame length */ + Word16 L_frameTCX, /* i : full band frame length */ + Word16 left_overlap, /* i : left overlap length */ + Word16 right_overlap, /* i : right overlap length */ + Word32 const mdctSpectrum[], /* i : MDCT spectrum */ + Word16 mdctSpectrum_e, + Word16 const signal[], /* i : windowed signal corresponding to mdctSpectrum */ + Word32 powerSpec[], /* o : Power spectrum. Can point to signal */ + Word16 powerSpec_e[] ); + void AdaptLowFreqEmph_fx( Word32 x[], Word16 x_e, Word16 xq[], @@ -3036,7 +3048,7 @@ void IGFEncApplyMono_ivas_fx( Encoder_State *st, /* i : Encoder st Word32 *pMDCTSpectrum_fx, /* i/o: MDCT spectrum */ Word16 e_mdct, /* i : exponent of pMDCTspectrum */ Word32 *pPowerSpectrum_fx, /* i/o: MDCT^2 + MDST^2 spectrum, or estimate */ - Word16 e_ps, /* i : exponent of pPowerSpectrum */ + Word16 *e_ps, /* i : exponent of pPowerSpectrum */ const int16_t isTCX20, /* i : flag indicating if the input is TCX20 or TCX10/2xTCX5 */ const int8_t isTNSActive, /* i : flag indicating if the TNS is active */ const int16_t sp_aud_decision0, /* i : first stage switching decision */ diff --git a/lib_enc/tcx_utils_enc.c b/lib_enc/tcx_utils_enc.c index 4ea9a52fc..cf330dfa2 100644 --- a/lib_enc/tcx_utils_enc.c +++ b/lib_enc/tcx_utils_enc.c @@ -68,7 +68,7 @@ void ProcessIGF_ivas_fx( const Word32 *pITFMDCTSpectrum, /* i : MDCT spectrum fir ITF */ Word16 *q_spectrum, /* i/o: Q of spectrum */ Word32 *pPowerSpectrum, /* i : MDCT^2 + MDST^2 spectrum, or estimate (*q_powerSpec) */ - Word16 *q_powerSpec, /* i/o: Q of power spectrum */ + Word16 *exp_powerSpec, /* i/o: Q of power spectrum */ const Word16 isTCX20, /* i : flag indicating if the input is TCX20 or TCX10/2xTCX5 */ const Word16 frameno, /* i : flag indicating index of current subframe */ const Word16 sp_aud_decision0, /* i : first stage switching decision */ @@ -110,7 +110,7 @@ void ProcessIGF_ivas_fx( IGFSaveSpectrumForITF_ivas_fx( hIGFEnc, igfGridIdx, pITFMDCTSpectrum, sub( Q31, *q_spectrum ) ); - IGFEncApplyMono_ivas_fx( st, igfGridIdx, pMDCTSpectrum, sub( Q31, *q_spectrum ), pPowerSpectrum, sub( Q31, *q_powerSpec ), isTCX20, st->hTcxEnc->fUseTns[frameno], sp_aud_decision0, vad_hover_flag ); + IGFEncApplyMono_ivas_fx( st, igfGridIdx, pMDCTSpectrum, sub( Q31, *q_spectrum ), pPowerSpectrum, exp_powerSpec, isTCX20, st->hTcxEnc->fUseTns[frameno], sp_aud_decision0, vad_hover_flag ); curr_order = 0; move16(); @@ -154,7 +154,6 @@ void ProcessIGF_ivas_fx( return; } - /*---------------------------------------------------------------------* * ProcessStereoIGF() * diff --git a/lib_enc/tcx_utils_enc_fx.c b/lib_enc/tcx_utils_enc_fx.c index c6f2b8502..9beb4bc37 100644 --- a/lib_enc/tcx_utils_enc_fx.c +++ b/lib_enc/tcx_utils_enc_fx.c @@ -319,6 +319,99 @@ void AnalyzePowerSpectrum_fx( } } +void AnalyzePowerSpectrum_ivas_fx( + Encoder_State *st, /* i/o: encoder states */ + Word16 L_frame, /* input: frame length */ + Word16 L_frameTCX, /* input: full band frame length */ + Word16 left_overlap, /* input: left overlap length */ + Word16 right_overlap, /* input: right overlap length */ + Word32 const mdctSpectrum[], /* input: MDCT spectrum */ + Word16 mdctSpectrum_e, + Word16 const signal[], /* input: windowed signal corresponding to mdctSpectrum */ + Word32 powerSpec[], /* output: Power spectrum. Can point to signal */ + Word16 powerSpec_e[] ) +{ + Word16 i, iStart, iEnd, lowpassLine; + Word16 shift; + Word32 tmp32; + Word8 tmp8; + TCX_ENC_HANDLE hTcxEnc = st->hTcxEnc; + Word32 common_powerSpec[N_MAX + L_MDCT_OVLP_MAX]; + lowpassLine = L_frameTCX; + move16(); + + Word16 temp_powerSpec_e = 16; + move16(); + TCX_MDST( signal, powerSpec, &temp_powerSpec_e, left_overlap, sub( L_frameTCX, shr( add( left_overlap, right_overlap ), 1 ) ), right_overlap, st->element_mode ); + + shift = L_norm_arr( powerSpec, N_MAX + L_MDCT_OVLP_MAX ); + scale_sig32( powerSpec, N_MAX + L_MDCT_OVLP_MAX, shift ); + set16_fx( powerSpec_e, sub( temp_powerSpec_e, shift ), N_MAX + L_MDCT_OVLP_MAX ); + + iStart = 0; + move16(); + iEnd = L_frameTCX; + move16(); + + IF( st->narrowBand != 0 ) + { + attenuateNbSpectrum_fx( L_frameTCX, powerSpec ); + } + + temp_powerSpec_e = MIN16B; + move16(); + /* power spectrum: MDCT^2 + MDST^2 */ + FOR( i = iStart; i < iEnd; i++ ) + { + powerSpec[i] = Mpy_32_32( powerSpec[i], powerSpec[i] ); + move32(); + shift = norm_l( mdctSpectrum[i] ); + tmp32 = L_shl( mdctSpectrum[i], shift ); + powerSpec[i] = BASOP_Util_Add_Mant32Exp( powerSpec[i], shl( powerSpec_e[i], 1 ), Mpy_32_32( tmp32, tmp32 ), shl( sub( mdctSpectrum_e, shift ), 1 ), &powerSpec_e[i] ); + move32(); + temp_powerSpec_e = s_max( temp_powerSpec_e, powerSpec_e[i] ); + } + + FOR( i = 0; i < N_MAX + L_MDCT_OVLP_MAX; i++ ) + { + common_powerSpec[i] = L_shl( powerSpec[i], sub( powerSpec_e[i], temp_powerSpec_e ) ); + move32(); + } + + tmp8 = 0; + move16(); + test(); + if ( L_msu0( L_mult0( st->L_frame, extract_l( st->last_sr_core ) ), st->L_frame_past, extract_l( st->sr_core ) ) != 0 || NE_16( st->last_core, TCX_20_CORE ) ) + { + tmp8 = 1; + move16(); + } + + ComputeSpectrumNoiseMeasure_fx( common_powerSpec, + L_frameTCX, + divide3216( L_mult( hTcxEnc->nmStartLine, L_frame ), st->L_frame ), + tmp8, + hTcxEnc->memQuantZeros, + lowpassLine ); + + IF( LE_32( st->total_brate, ACELP_24k40 ) ) + { + lowpassLine = shl( mult( st->hTcxCfg->bandwidth, L_frame ), 1 ); + + test(); + detectLowpassFac( common_powerSpec, temp_powerSpec_e, + L_frame, + sub( st->last_core, ACELP_CORE ) == 0, + &hTcxEnc->measuredBwRatio, + lowpassLine ); + } + ELSE + { + hTcxEnc->measuredBwRatio = 0x4000; + move16(); + } +} + void AdaptLowFreqEmph_fx( Word32 x[], Word16 x_e, Word16 xq[], -- GitLab