From 0cc641b3d3cec3a52ed6a8bb19e87927652e7ed4 Mon Sep 17 00:00:00 2001 From: Sandesh Venkatesh Date: Tue, 17 Dec 2024 15:08:04 +0530 Subject: [PATCH 1/2] Fix for 3GPP issue 1098: Large differences in SBA DirAC azimuth angle causing noticeable difference in SBA downmix Link #1098 --- lib_com/ivas_dirac_com.c | 23 +++++++++- lib_com/ivas_prot_fx.h | 18 +++----- lib_com/options.h | 1 + lib_enc/ivas_dirac_enc.c | 94 ++++++++++++++++++++++++++++++++++---- lib_enc/ivas_mcmasa_enc.c | 7 ++- lib_enc/ivas_omasa_enc.c | 7 ++- lib_rend/ivas_mcmasa_ana.c | 7 ++- 7 files changed, 132 insertions(+), 25 deletions(-) diff --git a/lib_com/ivas_dirac_com.c b/lib_com/ivas_dirac_com.c index 138d86eaf..52a3e8d52 100644 --- a/lib_com/ivas_dirac_com.c +++ b/lib_com/ivas_dirac_com.c @@ -610,7 +610,12 @@ void computeDirectionVectors_fixed( Word32 *direction_vector_x, /* o: Q30*/ Word32 *direction_vector_y, /* o: Q30*/ Word32 *direction_vector_z, /* o: Q30*/ - Word16 i_e /*Exponent of all the intensity buffers*/ ) + Word16 i_e /*Exponent of all the intensity buffers*/ +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + , + Word16 *i_e_band +#endif +) { Word16 i; Word32 intensityNorm; @@ -628,9 +633,25 @@ void computeDirectionVectors_fixed( scaled_x = L_shl( *intensity_real_x, norm_x ); scaled_y = L_shl( *intensity_real_y, norm_y ); scaled_z = L_shl( *intensity_real_z, norm_z ); +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + IF( i_e_band != NULL ) + { + e_x = sub( i_e_band[i - enc_param_start_band], norm_x ); + e_y = sub( i_e_band[i - enc_param_start_band], norm_y ); + e_z = sub( i_e_band[i - enc_param_start_band], norm_z ); + } + ELSE + { + e_x = sub( i_e, norm_x ); + e_y = sub( i_e, norm_y ); + e_z = sub( i_e, norm_z ); + } +#else + e_x = sub( i_e, norm_x ); e_y = sub( i_e, norm_y ); e_z = sub( i_e, norm_z ); +#endif temp1 = BASOP_Util_Add_Mant32Exp( Mult_32_32( scaled_x, scaled_x ), shl( e_x, 1 ), Mult_32_32( scaled_y, scaled_y ), shl( e_y, 1 ), &exp1 ); intensityNorm = BASOP_Util_Add_Mant32Exp( temp1, exp1, Mult_32_32( scaled_z, scaled_z ), shl( e_z, 1 ), &intensityNorm_e ); diff --git a/lib_com/ivas_prot_fx.h b/lib_com/ivas_prot_fx.h index 6fd0c777f..111633d6e 100644 --- a/lib_com/ivas_prot_fx.h +++ b/lib_com/ivas_prot_fx.h @@ -3228,7 +3228,12 @@ void computeDirectionVectors_fixed( Word32 *direction_vector_x, /*Q30*/ Word32 *direction_vector_y, /*Q30*/ Word32 *direction_vector_z, /*Q30*/ - Word16 i_e /*Exponent of all the intensity buffers*/ ); + Word16 i_e /*Exponent of all the intensity buffers*/ +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + , + Word16 *i_e_band +#endif +); UWord8 ivas_masa_surrcoh_signicant_fx( @@ -4928,17 +4933,6 @@ void ivas_dirac_dec_set_md_map( const Word16 nCldfbTs /* i : number of CLDFB time slots */ ); -void computeDirectionVectors_fixed( - Word32 *intensity_real_x, - Word32 *intensity_real_y, - Word32 *intensity_real_z, - const Word16 enc_param_start_band, - const Word16 num_frequency_bands, - Word32 *direction_vector_x, /*Q30*/ - Word32 *direction_vector_y, /*Q30*/ - Word32 *direction_vector_z, /*Q30*/ - Word16 i_e /*Exponent of all the intensity buffers*/ ); - void computeDirectionVectors_fx( Word32 *intensity_real_x, Word32 *intensity_real_y, diff --git a/lib_com/options.h b/lib_com/options.h index 9ae9b3a40..131bcd1f7 100644 --- a/lib_com/options.h +++ b/lib_com/options.h @@ -92,6 +92,7 @@ #define FIX_1054_IF_ELSE_CMPLX /* VA: Fix 1054 incorrect counting of complexity when ELSE-IF sequence is encoutered in two functions */ #define FIX_1052_COPY_CMPLX_DISCREPANCY /* VA: modify IF-ELSE statements used in Copy*() functions to avoid dependency on x[] and y[] in RAM */ #define FIX_1049_SHR_RO_COMPLEXITY /* VA: fix for issue 1049: incorrect counting of complexity in the shr_ro() function */ +#define NONBE_IMPROVE_DIRAC_INTENSITY_PREC #define FIX_1103_OPT_L_NORM_ARR /* FhG: Optimize L_norm_arr(), avoid IF */ #define FIX_1105_OPT_MINIMUM_SL /* FhG: Optimize minimum_s(), minimum_l(), avoid IF */ #define FIX_1104_OPT_GETMINSCALEFAC /* FhG: Optimize get_min_scalefactor(), avoid IF */ diff --git a/lib_enc/ivas_dirac_enc.c b/lib_enc/ivas_dirac_enc.c index 51a446d38..d24e986c6 100644 --- a/lib_enc/ivas_dirac_enc.c +++ b/lib_enc/ivas_dirac_enc.c @@ -53,7 +53,13 @@ static void computeIntensityVector_enc_fx( Word32 Cldfb_ImagBuffer[DIRAC_MAX_ANA_CHANS][DIRAC_NO_FB_BANDS_MAX], const Word16 enc_param_start_band, /* i : first band to process */ const Word16 num_frequency_bands, - Word32 intensity_real[DIRAC_NUM_DIMS][DIRAC_MAX_NBANDS] ); + Word32 intensity_real[DIRAC_NUM_DIMS][DIRAC_MAX_NBANDS] +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + , + Word16 q_cldfb, + Word16 q_intensity_real[DIRAC_MAX_NBANDS] +#endif +); /*------------------------------------------------------------------------- * ivas_dirac_enc_open() @@ -936,7 +942,11 @@ void ivas_dirac_param_est_enc_fx( Word32 *p_Cldfb_ImagBuffer_fx[DIRAC_MAX_ANA_CHANS]; Word16 cldfb_q; Word32 intensity_real_fx[DIRAC_NUM_DIMS][DIRAC_MAX_NBANDS]; +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + Word16 intensity_real_q[DIRAC_MAX_NBANDS]; +#else Word16 intensity_real_q; +#endif Word32 direction_vector_fx[DIRAC_NUM_DIMS][DIRAC_MAX_NBANDS]; Word16 direction_vector_q; Word32 diffuseness_vector_fx[DIRAC_MAX_NBANDS]; @@ -965,8 +975,12 @@ void ivas_dirac_param_est_enc_fx( /* Initialization */ cldfb_q = 0; move16(); + +#ifndef NONBE_IMPROVE_DIRAC_INTENSITY_PREC intensity_real_q = 0; move16(); +#endif + direction_vector_q = 0; move16(); diffuseness_vector_q = 0; @@ -1081,10 +1095,16 @@ void ivas_dirac_param_est_enc_fx( Cldfb_ImagBuffer_fx, hDirAC->hConfig->enc_param_start_band, num_freq_bands, - intensity_real_fx ); - + intensity_real_fx +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + , + cldfb_q, + intensity_real_q +#endif + ); +#ifndef NONBE_IMPROVE_DIRAC_INTENSITY_PREC intensity_real_q = sub( shl( cldfb_q, 1 ), 31 ); // 2 * Q_Cldfb + 1 - 32; - +#endif IF( !hodirac_flag ) { computeDirectionVectors_fixed( @@ -1095,8 +1115,15 @@ void ivas_dirac_param_est_enc_fx( num_freq_bands, direction_vector_fx[0], direction_vector_fx[1], - direction_vector_fx[2], - sub( 31, intensity_real_q ) ); + direction_vector_fx[2] +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + , + 31, intensity_real_q +#else + , + sub( 31, intensity_real_q ) +#endif + ); direction_vector_q = Q30; move16(); @@ -1111,7 +1138,12 @@ void ivas_dirac_param_est_enc_fx( { /* only real part needed */ Copy32( intensity_real_fx[i], &( hDirAC->buffer_intensity_real_fx[i][index - 1][0] ), num_freq_bands ); +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + Copy( intensity_real_q, &hDirAC->buffer_intensity_real_q[i][index - 1][0], num_freq_bands ); +#else + set16_fx( &hDirAC->buffer_intensity_real_q[i][index - 1][0], intensity_real_q, num_freq_bands ); +#endif } Copy32( reference_power_fx[ts], &( hDirAC->buffer_energy_fx[( index - 1 ) * num_freq_bands] ), num_freq_bands ); set16_fx( &hDirAC->buffer_energy_q[( index - 1 ) * num_freq_bands], sub( 31, reference_power_exp ), num_freq_bands ); @@ -1289,7 +1321,12 @@ void ivas_dirac_param_est_enc_fx( Scale_sig32( dir_v_fx, 3, -1 ); ivas_qmetadata_direction_vector_to_azimuth_elevation_fx( dir_v_fx, +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + Q29, +#else + Q30, +#endif &q_direction->band_data[band_m_idx].azimuth_fx[block_m_idx], &q_direction->band_data[band_m_idx].elevation_fx[block_m_idx] ); } @@ -1381,7 +1418,13 @@ static void computeIntensityVector_enc_fx( Word32 Cldfb_ImagBuffer[DIRAC_MAX_ANA_CHANS][DIRAC_NO_FB_BANDS_MAX], const Word16 enc_param_start_band, /* i : first band to process */ const Word16 num_frequency_bands, - Word32 intensity_real[DIRAC_NUM_DIMS][DIRAC_MAX_NBANDS] ) + Word32 intensity_real[DIRAC_NUM_DIMS][DIRAC_MAX_NBANDS] +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + , + Word16 q_cldfb, + Word16 q_intensity_real[DIRAC_MAX_NBANDS] +#endif +) { /* Reminder * X = a + ib; Y = c + id @@ -1390,14 +1433,20 @@ static void computeIntensityVector_enc_fx( Word16 i, j; Word32 real, img; Word16 brange[2]; - +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + Word16 shift_value = sub( shl( q_cldfb, 1 ), 31 ); +#endif FOR( i = 0; i < num_frequency_bands; i++ ) { brange[0] = hDirAC->band_grouping[i + enc_param_start_band]; move16(); brange[1] = hDirAC->band_grouping[i + enc_param_start_band + 1]; move16(); - +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + Word16 num_bins = sub( brange[1], brange[0] ); + Word16 gb = find_guarded_bits_fx( num_bins ); + Word16 norm; +#endif intensity_real[0][i] = 0; move32(); intensity_real[1][i] = 0; @@ -1416,11 +1465,37 @@ static void computeIntensityVector_enc_fx( move32(); img = Cldfb_ImagBuffer[0][j]; move32(); +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + Word64 t1, t2, t3; + t1 = W_mac_32_32( W_mult_32_32( Cldfb_RealBuffer[3][j], real ), Cldfb_ImagBuffer[3][j], img ); + t2 = W_mac_32_32( W_mult_32_32( Cldfb_RealBuffer[1][j], real ), Cldfb_ImagBuffer[1][j], img ); + t3 = W_mac_32_32( W_mult_32_32( Cldfb_RealBuffer[2][j], real ), Cldfb_ImagBuffer[2][j], img ); + t1 = W_shr( t1, gb ); + t2 = W_shr( t2, gb ); + t3 = W_shr( t3, gb ); + /* Intensity is XYZ order, audio is WYZX order. */ + tmp_1 = W_add( tmp_1, t1 ); + tmp_2 = W_add( tmp_2, t2 ); + tmp_3 = W_add( tmp_3, t3 ); +#else /* Intensity is XYZ order, audio is WYZX order. */ tmp_1 = W_add( tmp_1, W_add( W_mult_32_32( Cldfb_RealBuffer[3][j], real ), W_mult_32_32( Cldfb_ImagBuffer[3][j], img ) ) ); tmp_2 = W_add( tmp_2, W_add( W_mult_32_32( Cldfb_RealBuffer[1][j], real ), W_mult_32_32( Cldfb_ImagBuffer[1][j], img ) ) ); tmp_3 = W_add( tmp_3, W_add( W_mult_32_32( Cldfb_RealBuffer[2][j], real ), W_mult_32_32( Cldfb_ImagBuffer[2][j], img ) ) ); +#endif } +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + norm = s_min( W_norm( tmp_1 ), W_norm( tmp_2 ) ); + norm = s_min( norm, W_norm( tmp_3 ) ); + intensity_real[0][i] = W_extract_h( W_shl( tmp_1, norm ) ); // output Q= 2* input_q + 1-gb+norm - 32 + move32(); + intensity_real[1][i] = W_extract_h( W_shl( tmp_2, norm ) ); // output Q= 2* input_q + 1-gb+norm - 32 + move32(); + intensity_real[2][i] = W_extract_h( W_shl( tmp_3, norm ) ); // output Q= 2* input_q + 1-gb+norm - 32 + move32(); + q_intensity_real[i] = sub( shift_value, sub( gb, norm ) ); + move16(); +#else intensity_real[0][i] = W_extract_h( tmp_1 ); // output Q= 2* input_q + 1 - 32 move32(); @@ -1428,6 +1503,7 @@ static void computeIntensityVector_enc_fx( move32(); intensity_real[2][i] = W_extract_h( tmp_3 ); // output Q= 2* input_q + 1 - 32 move32(); +#endif } return; diff --git a/lib_enc/ivas_mcmasa_enc.c b/lib_enc/ivas_mcmasa_enc.c index 43e16b81c..7fef09a4d 100644 --- a/lib_enc/ivas_mcmasa_enc.c +++ b/lib_enc/ivas_mcmasa_enc.c @@ -1182,7 +1182,12 @@ void ivas_mcmasa_param_est_enc_fx( num_freq_bands, direction_vector_fx[0], direction_vector_fx[1], - direction_vector_fx[2], c_e ); + direction_vector_fx[2], c_e +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + , + NULL +#endif + ); /* Power and intensity estimation for diffuseness */ computeIntensityVector_enc_fx( diff --git a/lib_enc/ivas_omasa_enc.c b/lib_enc/ivas_omasa_enc.c index 750db3616..53d5b53fa 100644 --- a/lib_enc/ivas_omasa_enc.c +++ b/lib_enc/ivas_omasa_enc.c @@ -1197,7 +1197,12 @@ static void ivas_omasa_param_est_enc_fx( computeIntensityVector_enc_fx( hOMasa->band_grouping, Foa_RealBuffer_fx, Foa_ImagBuffer_fx, num_freq_bands, intensity_real_fx, guard_bits ); intensity_real_e = sub( add( 62, guard_bits ), shl( q, 1 ) ); - computeDirectionVectors_fixed( intensity_real_fx[0], intensity_real_fx[1], intensity_real_fx[2], 0, num_freq_bands, direction_vector_fx[0], direction_vector_fx[1], direction_vector_fx[2], intensity_real_e ); + computeDirectionVectors_fixed( intensity_real_fx[0], intensity_real_fx[1], intensity_real_fx[2], 0, num_freq_bands, direction_vector_fx[0], direction_vector_fx[1], direction_vector_fx[2], intensity_real_e +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + , + NULL +#endif + ); /* Power estimation for diffuseness */ diff --git a/lib_rend/ivas_mcmasa_ana.c b/lib_rend/ivas_mcmasa_ana.c index 5327cd3c5..2f8edadf7 100644 --- a/lib_rend/ivas_mcmasa_ana.c +++ b/lib_rend/ivas_mcmasa_ana.c @@ -755,7 +755,12 @@ void ivas_mcmasa_param_est_ana_fx( /* Direction estimation */ computeIntensityVector_ana_fx( hMcMasa->band_grouping, Foa_RealBuffer_fx, Foa_ImagBuffer_fx, num_freq_bands, intensity_real_fx ); /* Q intensity_real_fx = 2*inp_q-31, e = 31 - 2*inp_q + 31 = 62 - 2*inp_q = 2*(31-inp_q)=2*c_e */ - computeDirectionVectors_fixed( intensity_real_fx[0], intensity_real_fx[1], intensity_real_fx[2], 0, num_freq_bands, direction_vector_fx[0], direction_vector_fx[1], direction_vector_fx[2], shl( c_e, 1 ) ); /* Q direction_vector_fx = Q30*/ + computeDirectionVectors_fixed( intensity_real_fx[0], intensity_real_fx[1], intensity_real_fx[2], 0, num_freq_bands, direction_vector_fx[0], direction_vector_fx[1], direction_vector_fx[2], shl( c_e, 1 ) +#ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC + , + NULL +#endif + ); /* Q direction_vector_fx = Q30*/ /* Power and intensity estimation for diffuseness */ computeIntensityVector_ana_fx( hMcMasa->band_grouping, FoaEven_RealBuffer_fx, FoaEven_ImagBuffer_fx, num_freq_bands, intensity_even_real_fx ); /*2*inp_q-31*/ -- GitLab From b174472f560e4e4ac571507ee23be99c60c0b021 Mon Sep 17 00:00:00 2001 From: Sandesh Venkatesh Date: Tue, 17 Dec 2024 17:11:26 +0530 Subject: [PATCH 2/2] Clang formatting changes --- lib_com/ivas_dirac_com.c | 2 +- lib_com/ivas_prot_fx.h | 2 +- lib_rend/ivas_mcmasa_ana.c | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/lib_com/ivas_dirac_com.c b/lib_com/ivas_dirac_com.c index 52a3e8d52..6aeff8ec5 100644 --- a/lib_com/ivas_dirac_com.c +++ b/lib_com/ivas_dirac_com.c @@ -610,7 +610,7 @@ void computeDirectionVectors_fixed( Word32 *direction_vector_x, /* o: Q30*/ Word32 *direction_vector_y, /* o: Q30*/ Word32 *direction_vector_z, /* o: Q30*/ - Word16 i_e /*Exponent of all the intensity buffers*/ + Word16 i_e /*Exponent of all the intensity buffers*/ #ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC , Word16 *i_e_band diff --git a/lib_com/ivas_prot_fx.h b/lib_com/ivas_prot_fx.h index 111633d6e..e65ce8b76 100644 --- a/lib_com/ivas_prot_fx.h +++ b/lib_com/ivas_prot_fx.h @@ -3228,7 +3228,7 @@ void computeDirectionVectors_fixed( Word32 *direction_vector_x, /*Q30*/ Word32 *direction_vector_y, /*Q30*/ Word32 *direction_vector_z, /*Q30*/ - Word16 i_e /*Exponent of all the intensity buffers*/ + Word16 i_e /*Exponent of all the intensity buffers*/ #ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC , Word16 *i_e_band diff --git a/lib_rend/ivas_mcmasa_ana.c b/lib_rend/ivas_mcmasa_ana.c index 2f8edadf7..dc2582212 100644 --- a/lib_rend/ivas_mcmasa_ana.c +++ b/lib_rend/ivas_mcmasa_ana.c @@ -755,7 +755,7 @@ void ivas_mcmasa_param_est_ana_fx( /* Direction estimation */ computeIntensityVector_ana_fx( hMcMasa->band_grouping, Foa_RealBuffer_fx, Foa_ImagBuffer_fx, num_freq_bands, intensity_real_fx ); /* Q intensity_real_fx = 2*inp_q-31, e = 31 - 2*inp_q + 31 = 62 - 2*inp_q = 2*(31-inp_q)=2*c_e */ - computeDirectionVectors_fixed( intensity_real_fx[0], intensity_real_fx[1], intensity_real_fx[2], 0, num_freq_bands, direction_vector_fx[0], direction_vector_fx[1], direction_vector_fx[2], shl( c_e, 1 ) + computeDirectionVectors_fixed( intensity_real_fx[0], intensity_real_fx[1], intensity_real_fx[2], 0, num_freq_bands, direction_vector_fx[0], direction_vector_fx[1], direction_vector_fx[2], shl( c_e, 1 ) #ifdef NONBE_IMPROVE_DIRAC_INTENSITY_PREC , NULL -- GitLab