Loading lib_com/ivas_cov_smooth.c +77 −20 Original line number Diff line number Diff line Loading @@ -44,6 +44,28 @@ #define BAND_SMOOTH_REST_START_IDX ( 2 ) #ifdef IVAS_FLOAT_FIXED /*-----------------------------------------------------------------------------------------* * Function ivas_calculate_update_factor_fx() * * To calculate the update factor *-----------------------------------------------------------------------------------------*/ static Word32 ivas_calculate_update_factor_fx( Word32 *p_bin_to_band, Word16 active_bins ) { Word32 update_factor_temp = 0; Word16 k; FOR( k = 0; k < active_bins; k++ ) { update_factor_temp += p_bin_to_band[k]; // Q22 } return update_factor_temp; } #else /*-----------------------------------------------------------------------------------------* * Function ivas_calculate_update_factor() * Loading @@ -64,6 +86,7 @@ static float ivas_calculate_update_factor( return update_factor_temp; } #endif #ifdef IVAS_FLOAT_FIXED Loading @@ -86,7 +109,7 @@ static void ivas_calculate_smoothning_factor_fx( Word16 tmp, exp_diff = 0; tmp = BASOP_Util_Divide3232_Scale( update_factor, L_shl( L_deposit_l( min_pool_size ), Q22 ), &exp_diff ); // (Q15 - exp_diff) *Smoothing_factor = L_shl_sat( L_deposit_l( tmp ), ( Q15 + exp_diff ) ); // Q30 *Smoothing_factor = L_shl_sat( L_deposit_l( tmp ), add( Q13, exp_diff ) ); // Q28 IF( NE_32( smooth_mode, COV_SMOOTH_MC ) ) { Loading @@ -100,11 +123,11 @@ static void ivas_calculate_smoothning_factor_fx( } L_tmp = Mpy_32_16_1( smooth_fact, add( j, 1 ) ); // (Q31 , Q0) -> Q16 *Smoothing_factor = Mpy_32_32( *Smoothing_factor, L_tmp ); // (Q30, Q16) -> Q15 *Smoothing_factor = L_shl_sat( *Smoothing_factor, Q15 ); // Q30 *Smoothing_factor = Mpy_32_32( *Smoothing_factor, L_tmp ); // (Q28, Q16) -> Q13 *Smoothing_factor = L_shl_sat( *Smoothing_factor, Q15 ); // Q28 } IF( *Smoothing_factor > max_update_rate ) // Q30 IF( *Smoothing_factor > max_update_rate ) // Q28 { *Smoothing_factor = max_update_rate; } Loading Loading @@ -152,6 +175,51 @@ static void ivas_calculate_smoothning_factor( #endif #ifdef IVAS_FLOAT_FIXED /*-----------------------------------------------------------------------------------------* * Function ivas_set_up_cov_smoothing_fx() * * Setup for covariance smoothing *-----------------------------------------------------------------------------------------*/ static void ivas_set_up_cov_smoothing_fx( ivas_cov_smooth_state_t *hCovState, ivas_filterbank_t *pFb, const Word32 max_update_rate, const Word16 min_pool_size, const COV_SMOOTHING_TYPE smooth_mode, /* i : flag multichannel vs SPAR */ const Word32 ivas_total_brate ) { Word16 j; Word32 update_factor; IF( EQ_32( smooth_mode, COV_SMOOTH_MC ) ) { FOR( j = 0; j < pFb->filterbank_num_bands; j++ ) { Word16 active_bins = pFb->fb_bin_to_band.pFb_active_bins_per_band[j]; update_factor = ivas_calculate_update_factor_fx( pFb->fb_bin_to_band.pFb_bin_to_band_fx[j], active_bins ); ivas_calculate_smoothning_factor_fx( &hCovState->pSmoothing_factor_fx[j], update_factor, min_pool_size, max_update_rate, smooth_mode, ivas_total_brate, j ); hCovState->pSmoothing_factor[j] = (float) hCovState->pSmoothing_factor_fx[j] / ONE_IN_Q28; } } ELSE { FOR( j = 0; j < pFb->filterbank_num_bands; j++ ) { Word32 *p_bin_to_band = pFb->fb_bin_to_band.pp_short_stride_bin_to_band_fx[j]; Word16 active_bins = pFb->fb_bin_to_band.p_short_stride_num_bins_per_band[j]; update_factor = ivas_calculate_update_factor_fx( p_bin_to_band, active_bins ); ivas_calculate_smoothning_factor_fx( &hCovState->pSmoothing_factor_fx[j], update_factor, min_pool_size, max_update_rate, smooth_mode, ivas_total_brate, j ); hCovState->pSmoothing_factor[j] = (float) hCovState->pSmoothing_factor_fx[j] / ONE_IN_Q28; } } hCovState->prior_bank_idx = -1; return; } #else /*-----------------------------------------------------------------------------------------* * Function ivas_set_up_cov_smoothing() * Loading @@ -168,23 +236,13 @@ static void ivas_set_up_cov_smoothing( { int16_t j; float update_factor; #ifdef IVAS_FLOAT_FIXED Word32 update_factor_fx, max_update_rate_fx; max_update_rate_fx = (Word32) ( max_update_rate * ONE_IN_Q30 ); #endif if ( smooth_mode == COV_SMOOTH_MC ) { for ( j = 0; j < pFb->filterbank_num_bands; j++ ) { int16_t active_bins = pFb->fb_bin_to_band.pFb_active_bins_per_band[j]; update_factor = ivas_calculate_update_factor( pFb->fb_bin_to_band.pFb_bin_to_band[j], active_bins ); #ifdef IVAS_FLOAT_FIXED update_factor_fx = (Word32) ( update_factor * ONE_IN_Q22 ); ivas_calculate_smoothning_factor_fx( &hCovState->pSmoothing_factor_fx[j], update_factor_fx, min_pool_size, max_update_rate_fx, smooth_mode, ivas_total_brate, j ); hCovState->pSmoothing_factor[j] = (float) hCovState->pSmoothing_factor_fx[j] / ONE_IN_Q30; #else ivas_calculate_smoothning_factor( &hCovState->pSmoothing_factor[j], update_factor, min_pool_size, max_update_rate, smooth_mode, ivas_total_brate, j ); #endif } } else Loading @@ -194,13 +252,7 @@ static void ivas_set_up_cov_smoothing( float *p_bin_to_band = pFb->fb_bin_to_band.pp_short_stride_bin_to_band[j]; int16_t active_bins = pFb->fb_bin_to_band.p_short_stride_num_bins_per_band[j]; update_factor = ivas_calculate_update_factor( p_bin_to_band, active_bins ); #ifdef IVAS_FLOAT_FIXED update_factor_fx = (Word32) ( update_factor * ONE_IN_Q22 ); ivas_calculate_smoothning_factor_fx( &hCovState->pSmoothing_factor_fx[j], update_factor_fx, min_pool_size, max_update_rate_fx, smooth_mode, ivas_total_brate, j ); hCovState->pSmoothing_factor[j] = (float) hCovState->pSmoothing_factor_fx[j] / ONE_IN_Q30; #else ivas_calculate_smoothning_factor( &hCovState->pSmoothing_factor[j], update_factor, min_pool_size, max_update_rate, smooth_mode, ivas_total_brate, j ); #endif } } Loading @@ -208,6 +260,7 @@ static void ivas_set_up_cov_smoothing( return; } #endif /*------------------------------------------------------------------------- Loading Loading @@ -256,7 +309,11 @@ ivas_error ivas_spar_covar_smooth_enc_open( } } #ifdef IVAS_FLOAT_FIXED ivas_set_up_cov_smoothing_fx( hCovState, pFb, cov_smooth_cfg->max_update_rate_fx, cov_smooth_cfg->min_pool_size, smooth_mode, ivas_total_brate ); #else ivas_set_up_cov_smoothing( hCovState, pFb, cov_smooth_cfg->max_update_rate, cov_smooth_cfg->min_pool_size, smooth_mode, ivas_total_brate ); #endif *hCovState_out = hCovState; Loading lib_com/ivas_fb_mixer.c +85 −0 Original line number Diff line number Diff line Loading @@ -284,6 +284,12 @@ ivas_error ivas_FB_mixer_open( { return IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for FB mixer encoder" ); } #ifdef IVAS_FLOAT_FIXED IF( ( hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band_fx[i] = (Word32 *) malloc( sizeof( Word32 ) * pActive_bins_per_band_abs[i] ) ) == NULL ) { return IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for FB mixer encoder fixed" ); } #endif } } Loading Loading @@ -417,6 +423,10 @@ void ivas_FB_mixer_close( { free( hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band[i] ); hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band[i] = NULL; #ifdef IVAS_FLOAT_FIXED free( hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band_fx[i] ); hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band_fx[i] = NULL; #endif } } Loading Loading @@ -767,6 +777,9 @@ static int16_t ivas_calculate_abs_fr( { int16_t frame_len; float ppFilterbank_FRs_s[L_FRAME48k]; #ifdef IVAS_FLOAT_FIXED Word32 ppFilterbank_FRs_s_fx[L_FRAME48k]; #endif int16_t bands = pFb->filterbank_num_bands; int16_t i, j, num_active_bands = 0; int16_t idx_short_stride_bin_to_band = 0; Loading @@ -780,30 +793,55 @@ static int16_t ivas_calculate_abs_fr( int16_t short_mdft_start_bin = -1; float short_stride_pow_spec[MDFT_FB_BANDS_240]; float short_stride_nrg = 0.0f; #ifdef IVAS_FLOAT_FIXED Word32 short_stride_pow_spec_fx[MDFT_FB_BANDS_240]; Word32 short_stride_nrg_fx = 0; Word16 exp_diff = 0, tmp; #endif float cldfb_nrg = 0.0f; int16_t short_stride = pFb->fb_bin_to_band.short_stride; const int16_t num_bins_per_short_stride_bin = ( const int16_t )( ( sampling_rate / FRAMES_PER_SEC ) / short_stride ); const int16_t num_bins_per_cldfb_band = ( const int16_t )( ( sampling_rate / FRAMES_PER_SEC ) / pFb->fb_bin_to_band.num_cldfb_bands ); float short_stride_max_per_spar_band = 1e-9f; #ifdef IVAS_FLOAT_FIXED Word32 short_stride_max_per_spar_band_fx = 1; #endif /*loop over all stored Filter Bank Response MDFT coefficients*/ set_f( short_stride_pow_spec, 0, MDFT_FB_BANDS_240 ); #ifdef IVAS_FLOAT_FIXED set_l( short_stride_pow_spec_fx, 0, MDFT_FB_BANDS_240 ); #endif for ( j = start_offset; j < num_bins + start_offset; j++ ) { float sq_abs; #ifdef IVAS_FLOAT_FIXED Word32 sq_abs_fx; #endif /*calculate bin energy */ IVAS_CALCULATE_SQ_ABS( *long_mdft_ptr_re, *long_mdft_ptr_im, sq_abs ); #ifdef IVAS_FLOAT_FIXED sq_abs_fx = (Word32) ( sq_abs * ONE_IN_Q22 ); #endif long_mdft_ptr_re++; long_mdft_ptr_im++; /* accumulate bin energies within a short stride bin */ short_stride_nrg += sq_abs; #ifdef IVAS_FLOAT_FIXED short_stride_nrg_fx = L_add( short_stride_nrg_fx, sq_abs_fx ); #endif if ( !( ( j + 1 ) % num_bins_per_short_stride_bin ) ) { /* new short stride bin */ short_stride_pow_spec[j / num_bins_per_short_stride_bin] = short_stride_nrg; /* energy rather than magnitude works better for covariance weighting*/ short_stride_max_per_spar_band = max( short_stride_nrg, short_stride_max_per_spar_band ); /*compute highest magnitude per band*/ short_stride_nrg = 0.0f; #ifdef IVAS_FLOAT_FIXED short_stride_pow_spec_fx[j / num_bins_per_short_stride_bin] = short_stride_nrg_fx; /* energy rather than magnitude works better for covariance weighting*/ short_stride_max_per_spar_band_fx = max( short_stride_nrg_fx, short_stride_max_per_spar_band_fx ); /*compute highest magnitude per band*/ short_stride_nrg_fx = 0; #endif } /* accumulate bin energies within a CLDFB band */ Loading @@ -821,7 +859,17 @@ static int16_t ivas_calculate_abs_fr( /* normalize and sparsify the energies */ short_stride_pow_spec[j] /= short_stride_max_per_spar_band; short_stride_pow_spec[j] = max( short_stride_pow_spec[j] - 0.3f, 0.0f ) / 0.7f; #ifdef IVAS_FLOAT_FIXED tmp = BASOP_Util_Divide3232_Scale( short_stride_pow_spec_fx[j], short_stride_max_per_spar_band_fx, &exp_diff ); short_stride_pow_spec_fx[j] = L_shl( L_deposit_l( tmp ), add( Q7, exp_diff ) ); // Q22 short_stride_pow_spec_fx[j] = L_max( L_sub( short_stride_pow_spec_fx[j], (Word32) ( 0.3f * ONE_IN_Q22 ) ), 0 ); tmp = BASOP_Util_Divide3232_Scale( short_stride_pow_spec_fx[j], (Word32) ( 0.7f * ONE_IN_Q22 ), &exp_diff ); short_stride_pow_spec_fx[j] = L_shl( L_deposit_l( tmp ), add( Q7, exp_diff ) ); // Q22 IF( GT_32( short_stride_pow_spec_fx[j], 0 ) ) #else if ( short_stride_pow_spec[j] > 0.0f ) #endif { assert( idx_short_stride_bin_to_band < 2 * MDFT_FB_BANDS_240 ); /* array size of p_short_stride_bin_to_band */ if ( short_mdft_start_bin == -1 ) Loading @@ -829,8 +877,17 @@ static int16_t ivas_calculate_abs_fr( short_mdft_start_bin = j; pFb->fb_bin_to_band.p_short_stride_start_bin_per_band[i] = j; pFb->fb_bin_to_band.pp_short_stride_bin_to_band[i] = &pFb->fb_bin_to_band.p_short_stride_bin_to_band[idx_short_stride_bin_to_band]; } #ifdef IVAS_FLOAT_FIXED pFb->fb_bin_to_band.pp_short_stride_bin_to_band_fx[i] = &pFb->fb_bin_to_band.p_short_stride_bin_to_band_fx[idx_short_stride_bin_to_band]; #endif } #ifdef IVAS_FLOAT_FIXED pFb->fb_bin_to_band.p_short_stride_bin_to_band[idx_short_stride_bin_to_band] = short_stride_pow_spec[j]; pFb->fb_bin_to_band.p_short_stride_bin_to_band_fx[idx_short_stride_bin_to_band] = short_stride_pow_spec_fx[j]; idx_short_stride_bin_to_band++; #else pFb->fb_bin_to_band.p_short_stride_bin_to_band[idx_short_stride_bin_to_band++] = short_stride_pow_spec[j]; #endif pFb->fb_bin_to_band.p_short_stride_num_bins_per_band[i]++; } } Loading Loading @@ -872,6 +929,9 @@ static int16_t ivas_calculate_abs_fr( frame_len = (int16_t) ( sampling_rate / FRAMES_PER_SEC ); set_f( ppFilterbank_FRs_s, 0, frame_len ); #ifdef IVAS_FLOAT_FIXED set_l( ppFilterbank_FRs_s_fx, 0, frame_len ); #endif /*Commented logic is for calculating number of active bands, can be removed if not needed */ for ( i = 0; i < bands; i++ ) Loading Loading @@ -903,10 +963,19 @@ static int16_t ivas_calculate_abs_fr( if ( j < ( abs_active_bins + abs_start_offset ) && j >= abs_start_offset && alloc_fb_resp != -1 ) { #ifdef IVAS_FLOAT_FIXED pFb->fb_bin_to_band.pFb_bin_to_band[i][idx] = temp; pFb->fb_bin_to_band.pFb_bin_to_band_fx[i][idx] = (Word32) ( temp * ONE_IN_Q22 ); idx = add( idx, 1 ); #else pFb->fb_bin_to_band.pFb_bin_to_band[i][idx++] = temp; #endif } ppFilterbank_FRs_s[j] += temp; #ifdef IVAS_FLOAT_FIXED ppFilterbank_FRs_s_fx[j] = L_add( ppFilterbank_FRs_s_fx[j], (Word32) ( temp * ONE_IN_Q22 ) ); #endif } } Loading @@ -915,6 +984,9 @@ static int16_t ivas_calculate_abs_fr( if ( ppFilterbank_FRs_s[i] < 0.1f ) { ppFilterbank_FRs_s[i] = 0.1f; #ifdef IVAS_FLOAT_FIXED ppFilterbank_FRs_s_fx[i] = (Word32) ( 0.1f * ONE_IN_Q22 ); #endif } } Loading @@ -924,10 +996,17 @@ static int16_t ivas_calculate_abs_fr( { int16_t abs_active_bins = pFb->fb_bin_to_band.pFb_active_bins_per_band[j]; int16_t abs_start_offset = pFb->fb_bin_to_band.pFb_start_bin_per_band[j]; #ifdef IVAS_FLOAT_FIXED Word16 exp_diff = 0, tmp; #endif for ( i = 0; i < abs_active_bins; i++ ) { pFb->fb_bin_to_band.pFb_bin_to_band[j][i] /= ppFilterbank_FRs_s[i + abs_start_offset]; #ifdef IVAS_FLOAT_FIXED tmp = BASOP_Util_Divide3232_Scale( pFb->fb_bin_to_band.pFb_bin_to_band_fx[j][i], ppFilterbank_FRs_s_fx[i + abs_start_offset], &exp_diff ); pFb->fb_bin_to_band.pFb_bin_to_band_fx[j][i] = L_shl( L_deposit_l( tmp ), add( Q7, exp_diff ) ); // Q22 #endif /*if(pFb->fb_bin_to_band.pFb_bin_to_band[j][i] > 0.5f) { num_active_bands = j + 1; Loading Loading @@ -1047,6 +1126,9 @@ static ivas_error ivas_filterbank_setup( /*pFb->fb_bin_to_band.cldfb_stride = ( int16_t )( ( sampling_rate / FRAMES_PER_SEC ) / CLDFB_NO_COL_MAX );*/ /* equals num_cldfb_bands*/ pFb->fb_bin_to_band.short_stride = (int16_t) ( ( sampling_rate / FRAMES_PER_SEC ) / 4 ); set_f( pFb->fb_bin_to_band.p_short_stride_bin_to_band, 0.0f, 2 * MDFT_FB_BANDS_240 ); #ifdef IVAS_FLOAT_FIXED set_l( pFb->fb_bin_to_band.p_short_stride_bin_to_band_fx, 0, 2 * MDFT_FB_BANDS_240 ); #endif set_s( pFb->fb_bin_to_band.p_cldfb_map_to_spar_band, 0, CLDFB_NO_CHANNELS_MAX ); set_s( pFb->fb_bin_to_band.p_spar_start_bands, 0, CLDFB_NO_CHANNELS_MAX ); Loading @@ -1055,6 +1137,9 @@ static ivas_error ivas_filterbank_setup( pFb->fb_bin_to_band.p_short_stride_num_bins_per_band[j] = 0; /* aka num_active_bins per SPAR band */ pFb->fb_bin_to_band.p_short_stride_start_bin_per_band[j] = 0; /* first considered bin index per SPAR band */ pFb->fb_bin_to_band.pp_short_stride_bin_to_band[j] = NULL; #ifdef IVAS_FLOAT_FIXED pFb->fb_bin_to_band.pp_short_stride_bin_to_band_fx[j] = NULL; #endif for ( i = 0; i < CLDFB_NO_CHANNELS_MAX; i++ ) { pFb->fb_bin_to_band.pp_cldfb_weights_per_spar_band[i][j] = 0.0f; Loading lib_com/ivas_stat_com.h +8 −0 Original line number Diff line number Diff line Loading @@ -371,6 +371,9 @@ typedef struct ivas_cov_smooth_cfg_t int16_t min_pool_size; int16_t max_bands; int16_t num_bins; #ifdef IVAS_FLOAT_FIXED Word32 max_update_rate_fx; #endif } ivas_cov_smooth_cfg_t; Loading Loading @@ -770,6 +773,11 @@ typedef struct ivas_fb_bin_to_band_data_t float *pp_short_stride_bin_to_band[IVAS_MAX_NUM_FB_BANDS]; int16_t short_stride; int16_t num_cldfb_bands; #ifdef IVAS_FLOAT_FIXED Word32 *pFb_bin_to_band_fx[IVAS_MAX_NUM_FB_BANDS]; Word32 p_short_stride_bin_to_band_fx[2 * MDFT_FB_BANDS_240]; Word32 *pp_short_stride_bin_to_band_fx[IVAS_MAX_NUM_FB_BANDS]; #endif } ivas_fb_bin_to_band_data_t; Loading lib_enc/ivas_enc_cov_handler.c +12 −0 Original line number Diff line number Diff line Loading @@ -80,11 +80,19 @@ ivas_error ivas_spar_covar_enc_open( } cov_smooth_cfg.max_bands = IVAS_MAX_NUM_BANDS; #ifdef IVAS_FLOAT_FIXED cov_smooth_cfg.max_update_rate_fx = (Word32) ( MAX_UPDATE_RATE * ONE_IN_Q28 ); // Q28 #else cov_smooth_cfg.max_update_rate = MAX_UPDATE_RATE; #endif cov_smooth_cfg.min_pool_size = MIN_POOL_SIZE; if ( smooth_mode == COV_SMOOTH_MC ) { #ifdef IVAS_FLOAT_FIXED cov_smooth_cfg.max_update_rate_fx = (Word32) ( 1.0f * ONE_IN_Q28 ); // Q28 #else cov_smooth_cfg.max_update_rate = 1.0f; #endif cov_smooth_cfg.min_pool_size = 20; } Loading @@ -93,7 +101,11 @@ ivas_error ivas_spar_covar_enc_open( return error; } #ifdef IVAS_FLOAT_FIXED cov_smooth_cfg.max_update_rate_fx = (Word32) ( MAX_UPDATE_RATE_DTX * ONE_IN_Q28 ); // Q28 #else cov_smooth_cfg.max_update_rate = MAX_UPDATE_RATE_DTX; #endif cov_smooth_cfg.min_pool_size = MIN_POOL_SIZE_DTX; if ( ( error = ivas_spar_covar_smooth_enc_open( &hCovState->pCov_dtx_state, &cov_smooth_cfg, pFb, nchan_inp, smooth_mode, ivas_total_brate ) ) != IVAS_ERR_OK ) Loading Loading
lib_com/ivas_cov_smooth.c +77 −20 Original line number Diff line number Diff line Loading @@ -44,6 +44,28 @@ #define BAND_SMOOTH_REST_START_IDX ( 2 ) #ifdef IVAS_FLOAT_FIXED /*-----------------------------------------------------------------------------------------* * Function ivas_calculate_update_factor_fx() * * To calculate the update factor *-----------------------------------------------------------------------------------------*/ static Word32 ivas_calculate_update_factor_fx( Word32 *p_bin_to_band, Word16 active_bins ) { Word32 update_factor_temp = 0; Word16 k; FOR( k = 0; k < active_bins; k++ ) { update_factor_temp += p_bin_to_band[k]; // Q22 } return update_factor_temp; } #else /*-----------------------------------------------------------------------------------------* * Function ivas_calculate_update_factor() * Loading @@ -64,6 +86,7 @@ static float ivas_calculate_update_factor( return update_factor_temp; } #endif #ifdef IVAS_FLOAT_FIXED Loading @@ -86,7 +109,7 @@ static void ivas_calculate_smoothning_factor_fx( Word16 tmp, exp_diff = 0; tmp = BASOP_Util_Divide3232_Scale( update_factor, L_shl( L_deposit_l( min_pool_size ), Q22 ), &exp_diff ); // (Q15 - exp_diff) *Smoothing_factor = L_shl_sat( L_deposit_l( tmp ), ( Q15 + exp_diff ) ); // Q30 *Smoothing_factor = L_shl_sat( L_deposit_l( tmp ), add( Q13, exp_diff ) ); // Q28 IF( NE_32( smooth_mode, COV_SMOOTH_MC ) ) { Loading @@ -100,11 +123,11 @@ static void ivas_calculate_smoothning_factor_fx( } L_tmp = Mpy_32_16_1( smooth_fact, add( j, 1 ) ); // (Q31 , Q0) -> Q16 *Smoothing_factor = Mpy_32_32( *Smoothing_factor, L_tmp ); // (Q30, Q16) -> Q15 *Smoothing_factor = L_shl_sat( *Smoothing_factor, Q15 ); // Q30 *Smoothing_factor = Mpy_32_32( *Smoothing_factor, L_tmp ); // (Q28, Q16) -> Q13 *Smoothing_factor = L_shl_sat( *Smoothing_factor, Q15 ); // Q28 } IF( *Smoothing_factor > max_update_rate ) // Q30 IF( *Smoothing_factor > max_update_rate ) // Q28 { *Smoothing_factor = max_update_rate; } Loading Loading @@ -152,6 +175,51 @@ static void ivas_calculate_smoothning_factor( #endif #ifdef IVAS_FLOAT_FIXED /*-----------------------------------------------------------------------------------------* * Function ivas_set_up_cov_smoothing_fx() * * Setup for covariance smoothing *-----------------------------------------------------------------------------------------*/ static void ivas_set_up_cov_smoothing_fx( ivas_cov_smooth_state_t *hCovState, ivas_filterbank_t *pFb, const Word32 max_update_rate, const Word16 min_pool_size, const COV_SMOOTHING_TYPE smooth_mode, /* i : flag multichannel vs SPAR */ const Word32 ivas_total_brate ) { Word16 j; Word32 update_factor; IF( EQ_32( smooth_mode, COV_SMOOTH_MC ) ) { FOR( j = 0; j < pFb->filterbank_num_bands; j++ ) { Word16 active_bins = pFb->fb_bin_to_band.pFb_active_bins_per_band[j]; update_factor = ivas_calculate_update_factor_fx( pFb->fb_bin_to_band.pFb_bin_to_band_fx[j], active_bins ); ivas_calculate_smoothning_factor_fx( &hCovState->pSmoothing_factor_fx[j], update_factor, min_pool_size, max_update_rate, smooth_mode, ivas_total_brate, j ); hCovState->pSmoothing_factor[j] = (float) hCovState->pSmoothing_factor_fx[j] / ONE_IN_Q28; } } ELSE { FOR( j = 0; j < pFb->filterbank_num_bands; j++ ) { Word32 *p_bin_to_band = pFb->fb_bin_to_band.pp_short_stride_bin_to_band_fx[j]; Word16 active_bins = pFb->fb_bin_to_band.p_short_stride_num_bins_per_band[j]; update_factor = ivas_calculate_update_factor_fx( p_bin_to_band, active_bins ); ivas_calculate_smoothning_factor_fx( &hCovState->pSmoothing_factor_fx[j], update_factor, min_pool_size, max_update_rate, smooth_mode, ivas_total_brate, j ); hCovState->pSmoothing_factor[j] = (float) hCovState->pSmoothing_factor_fx[j] / ONE_IN_Q28; } } hCovState->prior_bank_idx = -1; return; } #else /*-----------------------------------------------------------------------------------------* * Function ivas_set_up_cov_smoothing() * Loading @@ -168,23 +236,13 @@ static void ivas_set_up_cov_smoothing( { int16_t j; float update_factor; #ifdef IVAS_FLOAT_FIXED Word32 update_factor_fx, max_update_rate_fx; max_update_rate_fx = (Word32) ( max_update_rate * ONE_IN_Q30 ); #endif if ( smooth_mode == COV_SMOOTH_MC ) { for ( j = 0; j < pFb->filterbank_num_bands; j++ ) { int16_t active_bins = pFb->fb_bin_to_band.pFb_active_bins_per_band[j]; update_factor = ivas_calculate_update_factor( pFb->fb_bin_to_band.pFb_bin_to_band[j], active_bins ); #ifdef IVAS_FLOAT_FIXED update_factor_fx = (Word32) ( update_factor * ONE_IN_Q22 ); ivas_calculate_smoothning_factor_fx( &hCovState->pSmoothing_factor_fx[j], update_factor_fx, min_pool_size, max_update_rate_fx, smooth_mode, ivas_total_brate, j ); hCovState->pSmoothing_factor[j] = (float) hCovState->pSmoothing_factor_fx[j] / ONE_IN_Q30; #else ivas_calculate_smoothning_factor( &hCovState->pSmoothing_factor[j], update_factor, min_pool_size, max_update_rate, smooth_mode, ivas_total_brate, j ); #endif } } else Loading @@ -194,13 +252,7 @@ static void ivas_set_up_cov_smoothing( float *p_bin_to_band = pFb->fb_bin_to_band.pp_short_stride_bin_to_band[j]; int16_t active_bins = pFb->fb_bin_to_band.p_short_stride_num_bins_per_band[j]; update_factor = ivas_calculate_update_factor( p_bin_to_band, active_bins ); #ifdef IVAS_FLOAT_FIXED update_factor_fx = (Word32) ( update_factor * ONE_IN_Q22 ); ivas_calculate_smoothning_factor_fx( &hCovState->pSmoothing_factor_fx[j], update_factor_fx, min_pool_size, max_update_rate_fx, smooth_mode, ivas_total_brate, j ); hCovState->pSmoothing_factor[j] = (float) hCovState->pSmoothing_factor_fx[j] / ONE_IN_Q30; #else ivas_calculate_smoothning_factor( &hCovState->pSmoothing_factor[j], update_factor, min_pool_size, max_update_rate, smooth_mode, ivas_total_brate, j ); #endif } } Loading @@ -208,6 +260,7 @@ static void ivas_set_up_cov_smoothing( return; } #endif /*------------------------------------------------------------------------- Loading Loading @@ -256,7 +309,11 @@ ivas_error ivas_spar_covar_smooth_enc_open( } } #ifdef IVAS_FLOAT_FIXED ivas_set_up_cov_smoothing_fx( hCovState, pFb, cov_smooth_cfg->max_update_rate_fx, cov_smooth_cfg->min_pool_size, smooth_mode, ivas_total_brate ); #else ivas_set_up_cov_smoothing( hCovState, pFb, cov_smooth_cfg->max_update_rate, cov_smooth_cfg->min_pool_size, smooth_mode, ivas_total_brate ); #endif *hCovState_out = hCovState; Loading
lib_com/ivas_fb_mixer.c +85 −0 Original line number Diff line number Diff line Loading @@ -284,6 +284,12 @@ ivas_error ivas_FB_mixer_open( { return IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for FB mixer encoder" ); } #ifdef IVAS_FLOAT_FIXED IF( ( hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band_fx[i] = (Word32 *) malloc( sizeof( Word32 ) * pActive_bins_per_band_abs[i] ) ) == NULL ) { return IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for FB mixer encoder fixed" ); } #endif } } Loading Loading @@ -417,6 +423,10 @@ void ivas_FB_mixer_close( { free( hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band[i] ); hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band[i] = NULL; #ifdef IVAS_FLOAT_FIXED free( hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band_fx[i] ); hFbMixer->pFb->fb_bin_to_band.pFb_bin_to_band_fx[i] = NULL; #endif } } Loading Loading @@ -767,6 +777,9 @@ static int16_t ivas_calculate_abs_fr( { int16_t frame_len; float ppFilterbank_FRs_s[L_FRAME48k]; #ifdef IVAS_FLOAT_FIXED Word32 ppFilterbank_FRs_s_fx[L_FRAME48k]; #endif int16_t bands = pFb->filterbank_num_bands; int16_t i, j, num_active_bands = 0; int16_t idx_short_stride_bin_to_band = 0; Loading @@ -780,30 +793,55 @@ static int16_t ivas_calculate_abs_fr( int16_t short_mdft_start_bin = -1; float short_stride_pow_spec[MDFT_FB_BANDS_240]; float short_stride_nrg = 0.0f; #ifdef IVAS_FLOAT_FIXED Word32 short_stride_pow_spec_fx[MDFT_FB_BANDS_240]; Word32 short_stride_nrg_fx = 0; Word16 exp_diff = 0, tmp; #endif float cldfb_nrg = 0.0f; int16_t short_stride = pFb->fb_bin_to_band.short_stride; const int16_t num_bins_per_short_stride_bin = ( const int16_t )( ( sampling_rate / FRAMES_PER_SEC ) / short_stride ); const int16_t num_bins_per_cldfb_band = ( const int16_t )( ( sampling_rate / FRAMES_PER_SEC ) / pFb->fb_bin_to_band.num_cldfb_bands ); float short_stride_max_per_spar_band = 1e-9f; #ifdef IVAS_FLOAT_FIXED Word32 short_stride_max_per_spar_band_fx = 1; #endif /*loop over all stored Filter Bank Response MDFT coefficients*/ set_f( short_stride_pow_spec, 0, MDFT_FB_BANDS_240 ); #ifdef IVAS_FLOAT_FIXED set_l( short_stride_pow_spec_fx, 0, MDFT_FB_BANDS_240 ); #endif for ( j = start_offset; j < num_bins + start_offset; j++ ) { float sq_abs; #ifdef IVAS_FLOAT_FIXED Word32 sq_abs_fx; #endif /*calculate bin energy */ IVAS_CALCULATE_SQ_ABS( *long_mdft_ptr_re, *long_mdft_ptr_im, sq_abs ); #ifdef IVAS_FLOAT_FIXED sq_abs_fx = (Word32) ( sq_abs * ONE_IN_Q22 ); #endif long_mdft_ptr_re++; long_mdft_ptr_im++; /* accumulate bin energies within a short stride bin */ short_stride_nrg += sq_abs; #ifdef IVAS_FLOAT_FIXED short_stride_nrg_fx = L_add( short_stride_nrg_fx, sq_abs_fx ); #endif if ( !( ( j + 1 ) % num_bins_per_short_stride_bin ) ) { /* new short stride bin */ short_stride_pow_spec[j / num_bins_per_short_stride_bin] = short_stride_nrg; /* energy rather than magnitude works better for covariance weighting*/ short_stride_max_per_spar_band = max( short_stride_nrg, short_stride_max_per_spar_band ); /*compute highest magnitude per band*/ short_stride_nrg = 0.0f; #ifdef IVAS_FLOAT_FIXED short_stride_pow_spec_fx[j / num_bins_per_short_stride_bin] = short_stride_nrg_fx; /* energy rather than magnitude works better for covariance weighting*/ short_stride_max_per_spar_band_fx = max( short_stride_nrg_fx, short_stride_max_per_spar_band_fx ); /*compute highest magnitude per band*/ short_stride_nrg_fx = 0; #endif } /* accumulate bin energies within a CLDFB band */ Loading @@ -821,7 +859,17 @@ static int16_t ivas_calculate_abs_fr( /* normalize and sparsify the energies */ short_stride_pow_spec[j] /= short_stride_max_per_spar_band; short_stride_pow_spec[j] = max( short_stride_pow_spec[j] - 0.3f, 0.0f ) / 0.7f; #ifdef IVAS_FLOAT_FIXED tmp = BASOP_Util_Divide3232_Scale( short_stride_pow_spec_fx[j], short_stride_max_per_spar_band_fx, &exp_diff ); short_stride_pow_spec_fx[j] = L_shl( L_deposit_l( tmp ), add( Q7, exp_diff ) ); // Q22 short_stride_pow_spec_fx[j] = L_max( L_sub( short_stride_pow_spec_fx[j], (Word32) ( 0.3f * ONE_IN_Q22 ) ), 0 ); tmp = BASOP_Util_Divide3232_Scale( short_stride_pow_spec_fx[j], (Word32) ( 0.7f * ONE_IN_Q22 ), &exp_diff ); short_stride_pow_spec_fx[j] = L_shl( L_deposit_l( tmp ), add( Q7, exp_diff ) ); // Q22 IF( GT_32( short_stride_pow_spec_fx[j], 0 ) ) #else if ( short_stride_pow_spec[j] > 0.0f ) #endif { assert( idx_short_stride_bin_to_band < 2 * MDFT_FB_BANDS_240 ); /* array size of p_short_stride_bin_to_band */ if ( short_mdft_start_bin == -1 ) Loading @@ -829,8 +877,17 @@ static int16_t ivas_calculate_abs_fr( short_mdft_start_bin = j; pFb->fb_bin_to_band.p_short_stride_start_bin_per_band[i] = j; pFb->fb_bin_to_band.pp_short_stride_bin_to_band[i] = &pFb->fb_bin_to_band.p_short_stride_bin_to_band[idx_short_stride_bin_to_band]; } #ifdef IVAS_FLOAT_FIXED pFb->fb_bin_to_band.pp_short_stride_bin_to_band_fx[i] = &pFb->fb_bin_to_band.p_short_stride_bin_to_band_fx[idx_short_stride_bin_to_band]; #endif } #ifdef IVAS_FLOAT_FIXED pFb->fb_bin_to_band.p_short_stride_bin_to_band[idx_short_stride_bin_to_band] = short_stride_pow_spec[j]; pFb->fb_bin_to_band.p_short_stride_bin_to_band_fx[idx_short_stride_bin_to_band] = short_stride_pow_spec_fx[j]; idx_short_stride_bin_to_band++; #else pFb->fb_bin_to_band.p_short_stride_bin_to_band[idx_short_stride_bin_to_band++] = short_stride_pow_spec[j]; #endif pFb->fb_bin_to_band.p_short_stride_num_bins_per_band[i]++; } } Loading Loading @@ -872,6 +929,9 @@ static int16_t ivas_calculate_abs_fr( frame_len = (int16_t) ( sampling_rate / FRAMES_PER_SEC ); set_f( ppFilterbank_FRs_s, 0, frame_len ); #ifdef IVAS_FLOAT_FIXED set_l( ppFilterbank_FRs_s_fx, 0, frame_len ); #endif /*Commented logic is for calculating number of active bands, can be removed if not needed */ for ( i = 0; i < bands; i++ ) Loading Loading @@ -903,10 +963,19 @@ static int16_t ivas_calculate_abs_fr( if ( j < ( abs_active_bins + abs_start_offset ) && j >= abs_start_offset && alloc_fb_resp != -1 ) { #ifdef IVAS_FLOAT_FIXED pFb->fb_bin_to_band.pFb_bin_to_band[i][idx] = temp; pFb->fb_bin_to_band.pFb_bin_to_band_fx[i][idx] = (Word32) ( temp * ONE_IN_Q22 ); idx = add( idx, 1 ); #else pFb->fb_bin_to_band.pFb_bin_to_band[i][idx++] = temp; #endif } ppFilterbank_FRs_s[j] += temp; #ifdef IVAS_FLOAT_FIXED ppFilterbank_FRs_s_fx[j] = L_add( ppFilterbank_FRs_s_fx[j], (Word32) ( temp * ONE_IN_Q22 ) ); #endif } } Loading @@ -915,6 +984,9 @@ static int16_t ivas_calculate_abs_fr( if ( ppFilterbank_FRs_s[i] < 0.1f ) { ppFilterbank_FRs_s[i] = 0.1f; #ifdef IVAS_FLOAT_FIXED ppFilterbank_FRs_s_fx[i] = (Word32) ( 0.1f * ONE_IN_Q22 ); #endif } } Loading @@ -924,10 +996,17 @@ static int16_t ivas_calculate_abs_fr( { int16_t abs_active_bins = pFb->fb_bin_to_band.pFb_active_bins_per_band[j]; int16_t abs_start_offset = pFb->fb_bin_to_band.pFb_start_bin_per_band[j]; #ifdef IVAS_FLOAT_FIXED Word16 exp_diff = 0, tmp; #endif for ( i = 0; i < abs_active_bins; i++ ) { pFb->fb_bin_to_band.pFb_bin_to_band[j][i] /= ppFilterbank_FRs_s[i + abs_start_offset]; #ifdef IVAS_FLOAT_FIXED tmp = BASOP_Util_Divide3232_Scale( pFb->fb_bin_to_band.pFb_bin_to_band_fx[j][i], ppFilterbank_FRs_s_fx[i + abs_start_offset], &exp_diff ); pFb->fb_bin_to_band.pFb_bin_to_band_fx[j][i] = L_shl( L_deposit_l( tmp ), add( Q7, exp_diff ) ); // Q22 #endif /*if(pFb->fb_bin_to_band.pFb_bin_to_band[j][i] > 0.5f) { num_active_bands = j + 1; Loading Loading @@ -1047,6 +1126,9 @@ static ivas_error ivas_filterbank_setup( /*pFb->fb_bin_to_band.cldfb_stride = ( int16_t )( ( sampling_rate / FRAMES_PER_SEC ) / CLDFB_NO_COL_MAX );*/ /* equals num_cldfb_bands*/ pFb->fb_bin_to_band.short_stride = (int16_t) ( ( sampling_rate / FRAMES_PER_SEC ) / 4 ); set_f( pFb->fb_bin_to_band.p_short_stride_bin_to_band, 0.0f, 2 * MDFT_FB_BANDS_240 ); #ifdef IVAS_FLOAT_FIXED set_l( pFb->fb_bin_to_band.p_short_stride_bin_to_band_fx, 0, 2 * MDFT_FB_BANDS_240 ); #endif set_s( pFb->fb_bin_to_band.p_cldfb_map_to_spar_band, 0, CLDFB_NO_CHANNELS_MAX ); set_s( pFb->fb_bin_to_band.p_spar_start_bands, 0, CLDFB_NO_CHANNELS_MAX ); Loading @@ -1055,6 +1137,9 @@ static ivas_error ivas_filterbank_setup( pFb->fb_bin_to_band.p_short_stride_num_bins_per_band[j] = 0; /* aka num_active_bins per SPAR band */ pFb->fb_bin_to_band.p_short_stride_start_bin_per_band[j] = 0; /* first considered bin index per SPAR band */ pFb->fb_bin_to_band.pp_short_stride_bin_to_band[j] = NULL; #ifdef IVAS_FLOAT_FIXED pFb->fb_bin_to_band.pp_short_stride_bin_to_band_fx[j] = NULL; #endif for ( i = 0; i < CLDFB_NO_CHANNELS_MAX; i++ ) { pFb->fb_bin_to_band.pp_cldfb_weights_per_spar_band[i][j] = 0.0f; Loading
lib_com/ivas_stat_com.h +8 −0 Original line number Diff line number Diff line Loading @@ -371,6 +371,9 @@ typedef struct ivas_cov_smooth_cfg_t int16_t min_pool_size; int16_t max_bands; int16_t num_bins; #ifdef IVAS_FLOAT_FIXED Word32 max_update_rate_fx; #endif } ivas_cov_smooth_cfg_t; Loading Loading @@ -770,6 +773,11 @@ typedef struct ivas_fb_bin_to_band_data_t float *pp_short_stride_bin_to_band[IVAS_MAX_NUM_FB_BANDS]; int16_t short_stride; int16_t num_cldfb_bands; #ifdef IVAS_FLOAT_FIXED Word32 *pFb_bin_to_band_fx[IVAS_MAX_NUM_FB_BANDS]; Word32 p_short_stride_bin_to_band_fx[2 * MDFT_FB_BANDS_240]; Word32 *pp_short_stride_bin_to_band_fx[IVAS_MAX_NUM_FB_BANDS]; #endif } ivas_fb_bin_to_band_data_t; Loading
lib_enc/ivas_enc_cov_handler.c +12 −0 Original line number Diff line number Diff line Loading @@ -80,11 +80,19 @@ ivas_error ivas_spar_covar_enc_open( } cov_smooth_cfg.max_bands = IVAS_MAX_NUM_BANDS; #ifdef IVAS_FLOAT_FIXED cov_smooth_cfg.max_update_rate_fx = (Word32) ( MAX_UPDATE_RATE * ONE_IN_Q28 ); // Q28 #else cov_smooth_cfg.max_update_rate = MAX_UPDATE_RATE; #endif cov_smooth_cfg.min_pool_size = MIN_POOL_SIZE; if ( smooth_mode == COV_SMOOTH_MC ) { #ifdef IVAS_FLOAT_FIXED cov_smooth_cfg.max_update_rate_fx = (Word32) ( 1.0f * ONE_IN_Q28 ); // Q28 #else cov_smooth_cfg.max_update_rate = 1.0f; #endif cov_smooth_cfg.min_pool_size = 20; } Loading @@ -93,7 +101,11 @@ ivas_error ivas_spar_covar_enc_open( return error; } #ifdef IVAS_FLOAT_FIXED cov_smooth_cfg.max_update_rate_fx = (Word32) ( MAX_UPDATE_RATE_DTX * ONE_IN_Q28 ); // Q28 #else cov_smooth_cfg.max_update_rate = MAX_UPDATE_RATE_DTX; #endif cov_smooth_cfg.min_pool_size = MIN_POOL_SIZE_DTX; if ( ( error = ivas_spar_covar_smooth_enc_open( &hCovState->pCov_dtx_state, &cov_smooth_cfg, pFb, nchan_inp, smooth_mode, ivas_total_brate ) ) != IVAS_ERR_OK ) Loading