diff --git a/lib_com/cnst.h b/lib_com/cnst.h index 16ebf808c33c58865313a23e02044ad628b4c7f1..9cf45d203b507225b0a7fd227e427bb808c59b48 100644 --- a/lib_com/cnst.h +++ b/lib_com/cnst.h @@ -566,7 +566,7 @@ enum #define FRAMES_PER_SEC 50 #ifdef IVAS_FLOAT_FIXED -#define MAX_PARAM__SPATIAL_SUB_FRAMES_PER_SEC 200 //(FRAMES_PER_SEC * MAX_PARAM_SPATIAL_SUBFRAMES) +#define MAX_PARAM_SPATIAL_SUB_FRAMES_PER_SEC 200 //(FRAMES_PER_SEC * MAX_PARAM_SPATIAL_SUBFRAMES) #define ONE_BY_FRAMES_PER_SEC ((Word32)(0x028F5C29)) #define FRAMES_PER_SEC_BY_2 (FRAMES_PER_SEC >> 1) #endif diff --git a/lib_com/ivas_prot.h b/lib_com/ivas_prot.h index fce1edd5d465f7c5531fa59fdbb2d662961a8e28..b8469c0f16e5b1861da5a2320f7221b6f9588979 100644 --- a/lib_com/ivas_prot.h +++ b/lib_com/ivas_prot.h @@ -6577,12 +6577,15 @@ void ivas_ism_render_sf( const int16_t n_samples_to_render /* i : output frame length per channel */ ); +#ifndef IVAS_FLOAT_FIXED void ivas_ism_get_stereo_gains( const float azimuth, /* i : object azimuth */ const float elevation, /* i : object elevation */ float *left_gain, /* o : left channel gain */ float *right_gain /* o : right channel gain */ ); +#endif + #ifdef IVAS_FLOAT_FIXED void ivas_mc2sba_fx( IVAS_OUTPUT_SETUP hIntSetup, /* i : Format of decoder output */ diff --git a/lib_dec/ivas_dirac_dec.c b/lib_dec/ivas_dirac_dec.c index 4923fa24181ecd62da743785391e1634f489993b..9a5e1e5a5a3d5b0decb5849bd628db9b24e3b690 100644 --- a/lib_dec/ivas_dirac_dec.c +++ b/lib_dec/ivas_dirac_dec.c @@ -735,10 +735,6 @@ static ivas_error ivas_dirac_rend_config_fx( IF( ( EQ_16( flag_config, DIRAC_OPEN) && hDirACRend->proto_signal_decorr_on ) || ( EQ_16( flag_config, DIRAC_RECONFIGURE ) && ( hDirACRend->proto_signal_decorr_on && !proto_signal_decorr_on_old ) ) ) { #ifdef IVAS_FLOAT_FIXED - FOR( int ii = 0; ii < st_ivas->hSpatParamRendCom->num_freq_bands; ii++ ) - { - hDirACRend->frequency_axis_fx[ii] = (Word16) hDirACRend->frequency_axis[ii]; - } IF( ( error = ivas_dirac_dec_decorr_open_fx( &( hDirACRend->h_freq_domain_decorr_ap_params ), &( hDirACRend->h_freq_domain_decorr_ap_state ), hSpatParamRendCom->num_freq_bands, hDirACRend->num_outputs_diff, hDirACRend->num_protos_diff, hDirACRend->synthesisConf, hDirACRend->frequency_axis_fx, nchan_transport > 2 ? 4 : nchan_transport, output_Fs ) ) != IVAS_ERR_OK ) { @@ -763,10 +759,6 @@ static ivas_error ivas_dirac_rend_config_fx( /* close and reopen the decorrelator */ ivas_dirac_dec_decorr_close( &hDirACRend->h_freq_domain_decorr_ap_params, &hDirACRend->h_freq_domain_decorr_ap_state ); #ifdef IVAS_FLOAT_FIXED - FOR( int ii = 0; ii < st_ivas->hSpatParamRendCom->num_freq_bands; ii++ ) - { - hDirACRend->frequency_axis_fx[ii] = (Word16) hDirACRend->frequency_axis[ii]; - } IF( ( error = ivas_dirac_dec_decorr_open_fx( &( hDirACRend->h_freq_domain_decorr_ap_params ), &( hDirACRend->h_freq_domain_decorr_ap_state ), hSpatParamRendCom->num_freq_bands, hDirACRend->num_outputs_diff, hDirACRend->num_protos_diff, hDirACRend->synthesisConf, hDirACRend->frequency_axis_fx, nchan_transport > 2 ? 4 : nchan_transport, output_Fs ) ) != IVAS_ERR_OK ) { diff --git a/lib_dec/ivas_sce_dec_fx.c b/lib_dec/ivas_sce_dec_fx.c index 8d3ff85181c55aecd9b6ec64af5c7767037d8ff7..b27f665e34bb475823816a01900a4a44129f7db3 100644 --- a/lib_dec/ivas_sce_dec_fx.c +++ b/lib_dec/ivas_sce_dec_fx.c @@ -385,7 +385,7 @@ ivas_error create_sce_dec( IF( EQ_16( (Word16) st_ivas->ivas_format, SBA_FORMAT ) && ( EQ_16( (Word16) st_ivas->hDecoderConfig->output_config, IVAS_AUDIO_CONFIG_STEREO ) || ( EQ_16( (Word16) st_ivas->hDecoderConfig->output_config, IVAS_AUDIO_CONFIG_MONO ) && EQ_16( st_ivas->nchan_transport, 1 ) ) ) ) { - IF( ( error = openCldfb_ivas( &st->cldfbSynHB, CLDFB_SYNTHESIS, st->output_Fs, CLDFB_PROTOTYPE_1_25MS ) ) != IVAS_ERR_OK ) + IF( ( error = openCldfb_ivas_fx( &st->cldfbSynHB, CLDFB_SYNTHESIS, st->output_Fs, CLDFB_PROTOTYPE_1_25MS ) ) != IVAS_ERR_OK ) { return error; } diff --git a/lib_dec/jbm_pcmdsp_apa.c b/lib_dec/jbm_pcmdsp_apa.c index 1586051d64aaec0ef1b246dc575cf976fb36d4e5..f2dc98789cc456cc1d2b7bc7038fc64b8ab7b36a 100644 --- a/lib_dec/jbm_pcmdsp_apa.c +++ b/lib_dec/jbm_pcmdsp_apa.c @@ -56,6 +56,9 @@ #ifdef IVAS_FLOAT_FIXED #include "prot_fx2.h" #endif + +#define IVAS_FLOAT_FIXED_TO_BE_REMOVED + /*---------------------------------------------------------------------* * Local state structure *---------------------------------------------------------------------*/ @@ -68,66 +71,72 @@ struct apa_state_t { Word16 signalScaleForCorrelation; Word16 frmInScaled[6 * 2 * 48000 / 50 * 2 ]; + /* output buffer */ bool evs_compat_mode; + float *buf_out; - uint16_t buf_out_capacity; - uint16_t l_buf_out; - Word16 win_incrementor; - const Word16 *win_fx; + Word16 *buf_out_fx; + UWord16 buf_out_capacity; + UWord16 l_buf_out; /* Hann window */ float win[APA_BUF_PER_CHANNEL]; - uint16_t l_halfwin; - Word16 l_halfwin_fx; + Word16 *win_fx; + //const Word16 *win_fx; + UWord16 l_halfwin; + + Word16 win_incrementor; /* sampling rate [Hz] */ - uint16_t rate; + UWord16 rate; /* length of a segment [samples] */ - uint16_t l_seg; + UWord16 l_seg; /* length of a frame [samples] */ - uint16_t l_frm; + UWord16 l_frm; /* total number of processed input samples since apa_reset() */ - uint32_t l_in_total; + UWord32 l_in_total; /* time resolution in samples of the IVAS renderer*/ - uint16_t l_ts; + UWord16 l_ts; /* samples already available in the renderer buffer */ - uint16_t l_r_buf; + UWord16 l_r_buf; /* sum of inserted/removed samples since last apa_set_scale() */ - int32_t diffSinceSetScale; + Word32 diffSinceSetScale; /* number of input frames since last apa_set_scale() */ - uint32_t nFramesSinceSetScale; + UWord32 nFramesSinceSetScale; /* current and previous scaling ratio [%] */ - uint16_t scale; + UWord16 scale; /* minimum pitch length [samples] */ - uint16_t p_min; + UWord16 p_min; /* search length [samples] */ - uint16_t l_search; + UWord16 l_search; - uint16_t wss; /* waveform subsampling per channel */ - uint16_t css; /* correlation subsampling per channel */ + UWord16 wss; /* waveform subsampling per channel */ + UWord16 css; /* correlation subsampling per channel */ float targetQuality; - uint16_t qualityred; /* quality reduction threshold */ - uint16_t qualityrise; /* quality rising for adaptive quality thresholds */ + Word32 targetQualityQ16; + UWord16 qualityred; /* quality reduction threshold */ + UWord16 qualityrise; /* quality rising for adaptive quality thresholds */ - uint16_t last_pitch; /* last pitch/sync position */ - uint16_t bad_frame_count; /* # frames before quality threshold is lowered */ - uint16_t good_frame_count; /* # scaled frames */ + UWord16 last_pitch; /* last pitch/sync position */ + UWord16 bad_frame_count; /* # frames before quality threshold is lowered */ + UWord16 good_frame_count; /* # scaled frames */ - uint16_t num_channels; /* number of input/output channels */ + UWord16 num_channels; /* number of input/output channels */ }; + /*---------------------------------------------------------------------* * Local function prototypes *---------------------------------------------------------------------*/ @@ -158,11 +167,78 @@ static bool shrink_frm( apa_state_t *ps, const float frm_in[], uint16_t maxScali static bool extend_frm( apa_state_t *ps, const float frm_in[], float frm_out[], uint16_t *l_frm_out ); +static Word16 find_synch_fx( apa_state_t *ps, + const Word16 *in, + Word16 l_in, + Word16 s_start, + Word16 s_len, + Word16 fixed_pos, + Word16 corr_len, + Word16 offset, + Word16 *energydBQ8, + Word32 *qualityQ16, + Word16 *synch_pos ); + +static Word16 norm(float num); + + +static Word16 norm(float num) { + if( ( Word16 ) num == 0 ) { + return 15; + } + else + return norm_s(( Word16 ) num); +} + + /*---------------------------------------------------------------------* * Public functions *---------------------------------------------------------------------*/ /* Allocates memory for state struct and initializes elements. */ +#ifdef IVAS_FLOAT_FIXED +ivas_error apa_init( + apa_state_t **pps, + const Word32 num_channels ) +{ + apa_state_t *ps = NULL; + + /* make sure pointer is valid */ + IF ( !pps ) + { + return 1; + } + + /* allocate state struct */ + IF ( ( ps = (apa_state_t *) malloc( sizeof( apa_state_t ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for JBM\n" ) ); + } + + ps->num_channels = (UWord16) num_channels; + move16(); + ps->buf_out_capacity = (UWord16) ( APA_BUF_PER_CHANNEL * num_channels ); + +#ifdef IVAS_FLOAT_FIXED_TO_BE_REMOVED + IF ( ( ps->buf_out = malloc( sizeof( float ) * ps->buf_out_capacity ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for JBM\n" ) ); + } +#endif + + IF ( ( ps->buf_out_fx = malloc( sizeof( Word16 ) * ps->buf_out_capacity ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for JBM\n" ) ); + } + + ps->evs_compat_mode = false; + + apa_reset( ps ); + *pps = ps; + + return IVAS_ERR_OK; +} +#else ivas_error apa_init( apa_state_t **pps, const int32_t num_channels ) @@ -196,8 +272,65 @@ ivas_error apa_init( return IVAS_ERR_OK; } +#endif + /* Sets state variables to initial value. */ +#ifdef IVAS_FLOAT_FIXED +void apa_reset( + apa_state_t *ps ) +{ + /* init state struct */ + ps->signalScaleForCorrelation = 0; + move16(); + ps->l_buf_out = 0; + move16(); + ps->l_halfwin = 0; + move16(); + ps->rate = 0; + move16(); + ps->l_seg = 0; + move16(); + ps->l_frm = 0; + move16(); + ps->l_in_total = 0; + move32(); + ps->diffSinceSetScale = 0; + move32(); + ps->nFramesSinceSetScale = 0; + move32(); + ps->scale = 100; + move32(); + ps->p_min = 0; + move16(); + ps->l_search = 0; + move16(); + ps->wss = 1; + move16(); + ps->css = 1; + move16(); + ps->targetQuality = 0.0f; + ps->targetQualityQ16 = 0; + move32(); + + ps->qualityred = 0; + move16(); + ps->qualityrise = 0; + move16(); + ps->last_pitch = 0; + move16(); + ps->bad_frame_count = 0; + move16(); + ps->good_frame_count = 0; + move16(); + + ps->l_ts = 1; + move16(); + ps->l_r_buf = 0; + move16(); + return; +} +#else void apa_reset( apa_state_t *ps ) { @@ -229,6 +362,7 @@ void apa_reset( ps->l_r_buf = 0; return; } +#endif uint8_t apa_reconfigure( apa_state_t *ps, @@ -241,7 +375,8 @@ uint8_t apa_reconfigure( ps->num_channels = (uint16_t) num_channels; ps->buf_out_capacity = (uint16_t) ( APA_BUF_PER_CHANNEL * num_channels ); ps->buf_out = (float *) malloc( sizeof( float ) * ps->buf_out_capacity ); - if ( !ps->buf_out ) + ps->buf_out_fx = (Word16 *)malloc(sizeof(float) * ps->buf_out_capacity); + if ( !ps->buf_out || !ps->buf_out_fx ) { return 2; } @@ -341,7 +476,7 @@ bool apa_set_rate( #ifdef IVAS_FLOAT_FIXED ps->win_fx = pcmdsp_window_hann_640; move16(); - ps->l_halfwin_fx = 320; + ps->l_halfwin = 320; move16(); ps->win_incrementor = 1; move16(); @@ -349,14 +484,14 @@ bool apa_set_rate( { ps->win_fx = pcmdsp_window_hann_960; move16(); - ps->l_halfwin_fx = 480; + ps->l_halfwin = 480; move16(); } IF( EQ_32( ps->rate, 24000 ) ) { ps->win_fx = pcmdsp_window_hann_960; move16(); - ps->l_halfwin_fx = 480; + ps->l_halfwin = 480; move16(); ps->win_incrementor = 2; move16(); @@ -382,6 +517,43 @@ bool apa_set_rate( /* Set scaling. */ +#ifdef IVAS_FLOAT_FIXED +bool apa_set_scale( + apa_state_t *ps, + UWord16 scale ) +{ + /* make sure pointer is valid */ + IF ( ps == NULL ) + { + return 1; + } + + /* check range */ + IF ( ( LT_32( (Word32) scale, APA_MIN_SCALE ) ) || GT_32( (Word32) scale, APA_MAX_SCALE ) ) + { + return 1; + } + + /* do nothing if same scale is set multiple times */ + /* (otherwise scale control is confused) */ + IF ( EQ_32( (Word32 ) ps->scale, ( Word32 ) scale ) ) + { + return 0; + } + + /* copy to state struct */ + ps->scale = scale; + move16(); + + /* reset scaling statistics */ + ps->diffSinceSetScale = 0; + move32(); + ps->nFramesSinceSetScale = 0; + move32(); + + return 0; +} +#else bool apa_set_scale( apa_state_t *ps, uint16_t scale ) @@ -414,7 +586,25 @@ bool apa_set_scale( return 0; } +#endif +#ifdef IVAS_FLOAT_FIXED +bool apa_set_renderer_granularity( + apa_state_t *ps, + UWord16 l_ts ) +{ + /* make sure pointer is valid */ + IF ( ps == NULL ) + { + return 1; + } + + + /* copy to state struct */ + ps->l_ts = l_ts * ps->num_channels; + return 0; +} +#else bool apa_set_renderer_granularity( apa_state_t *ps, uint16_t l_ts ) @@ -430,7 +620,25 @@ bool apa_set_renderer_granularity( ps->l_ts = l_ts * ps->num_channels; return 0; } +#endif +#ifdef IVAS_FLOAT_FIXED +bool apa_set_renderer_residual_samples( + apa_state_t *ps, + UWord16 l_r_buf ) +{ + /* make sure pointer is valid */ + IF ( ps == NULL ) + { + return 1; + } + + + /* copy to state struct */ + ps->l_r_buf = l_r_buf * ps->num_channels; + return 0; +} +#else bool apa_set_renderer_residual_samples( apa_state_t *ps, uint16_t l_r_buf ) @@ -446,7 +654,24 @@ bool apa_set_renderer_residual_samples( ps->l_r_buf = l_r_buf * ps->num_channels; return 0; } +#endif +#ifdef IVAS_FLOAT_FIXED +bool apa_set_evs_compat_mode( + apa_state_t *ps, + bool mode ) +{ + /* make sure pointer is valid */ + IF ( ps == NULL ) + { + return 1; + } + + ps->evs_compat_mode = mode; + + return 0; +} +#else bool apa_set_evs_compat_mode( apa_state_t *ps, bool mode ) @@ -462,6 +687,8 @@ bool apa_set_evs_compat_mode( return 0; } +#endif + /* ******************************************************************************** * @@ -520,6 +747,36 @@ bool apa_set_quality( * ******************************************************************************** */ +#ifdef IVAS_FLOAT_FIXED +bool apa_set_complexity_options( + apa_state_t *ps, + UWord16 wss, + UWord16 css ) +{ + /* make sure pointer is valid */ + IF ( ps == NULL ) + { + return 1; + } + + IF ( wss == 0 || wss > 1000 ) + { + return 1; + } + + IF ( css == 0 || css > 1000 ) + { + return 1; + } + + ps->wss = wss; + move16(); + ps->css = css; + move16(); + + return 0; +} +#else bool apa_set_complexity_options( apa_state_t *ps, uint16_t wss, @@ -546,6 +803,7 @@ bool apa_set_complexity_options( return 0; } +#endif /* ******************************************************************************** @@ -848,6 +1106,7 @@ static void get_scaling_quality( offset = 0; pitch_cn = normalized_cross_correlation_self( signal, pitch + offset, offset, corr_len, ps->num_channels * 2, &pitch_energy ); + if ( pitch_cn > 0.0f ) { /* calculate correlation for double pitch */ @@ -912,123 +1171,125 @@ static void get_scaling_quality( static void get_scaling_quality_fx(const apa_state_t * ps, - const Word16 * signal, - Word16 s_len, - Word16 offset, - Word16 corr_len, - Word16 pitch, - Word16 * energydBQ8, - Word32 * qualityQ16) + const Word16 * signal, + Word16 s_len, + Word16 offset, + Word16 corr_len, + Word16 pitch, + Word16 * energydBQ8, + Word32 * qualityQ16) { - Word32 energy, maxEnergy; - Word32 qualityOfMaxEnergy; /* we measure the quality for all channels and select the one with highest energy */ - Word16 half_pitch_cn; - Word16 pitch_cn; - Word16 three_halves_pitch_cn; - Word16 double_pitch_cn; - Word32 pitch_energy; - Word32 half_pitch_energy; - Word32 three_halves_pitch_energy; - Word32 double_pitch_energy; - Word16 i; + Word32 energy, maxEnergy; + Word32 qualityOfMaxEnergy; /* we measure the quality for all channels and select the one with highest energy */ + Word16 half_pitch_cn; + Word16 pitch_cn; + Word16 three_halves_pitch_cn; + Word16 double_pitch_cn; + Word32 pitch_energy; + Word32 half_pitch_energy; + Word32 three_halves_pitch_energy; + Word32 double_pitch_energy; + Word16 i; - maxEnergy = L_deposit_l(0); - qualityOfMaxEnergy = L_deposit_l(0); + maxEnergy = L_deposit_l(0); + qualityOfMaxEnergy = L_deposit_l(0); - FOR(i = 0; i < ps->num_channels; i++) - { - offset = 0; - move16(); + FOR(i = 0; i < ps->num_channels; i++) + { + offset = 0; + move16(); - pitch_cn = normalized_cross_correlation_self_fx(signal, add(pitch, offset), offset, corr_len, - shl(ps->num_channels, 1), &pitch_energy); - IF(pitch_cn > 0) - { - /* calculate correlation for double pitch */ - IF(LE_16(add(add(shl(pitch, 1), offset), corr_len), s_len)) - { - double_pitch_cn = normalized_cross_correlation_self_fx(signal, add(shl(pitch, 1), offset), - offset, corr_len, shl(ps->num_channels, 1), &double_pitch_energy); - } - ELSE - { - double_pitch_cn = pitch_cn; - move16(); - double_pitch_energy = L_add(pitch_energy, 0); - } - /* calculate correlation for three/half pitch */ - IF(LE_16(add(add(shr(i_mult2(pitch, 3), 1), offset), corr_len), s_len)) - { - three_halves_pitch_cn = normalized_cross_correlation_self_fx(signal, add(shr(i_mult2(pitch, 3), 1), - offset), offset, corr_len, shl(ps->num_channels, 1), &three_halves_pitch_energy); - } - ELSE - { - three_halves_pitch_cn = pitch_cn; - move16(); - three_halves_pitch_energy = L_add(pitch_energy, 0); - } - /* calculate correlation for half pitch */ - IF(LE_16(add(add(shr(pitch, 1), offset), corr_len), s_len)) - { - half_pitch_cn = normalized_cross_correlation_self_fx(signal, add(shr(pitch, 1), offset), - offset, corr_len, shl(ps->num_channels, 1), &half_pitch_energy); - } - ELSE - { - half_pitch_cn = pitch_cn; - move16(); - half_pitch_energy = L_add(pitch_energy, 0); - } + pitch_cn = normalized_cross_correlation_self_fx(signal, add(pitch, offset), offset, corr_len, + shl(ps->num_channels, 1), &pitch_energy); + IF(pitch_cn > 0) + { + /* calculate correlation for double pitch */ + IF(LE_16(add(add(shl(pitch, 1), offset), corr_len), s_len)) + { + double_pitch_cn = normalized_cross_correlation_self_fx(signal, add(shl(pitch, 1), offset), + offset, corr_len, shl(ps->num_channels, 1), &double_pitch_energy); + } + ELSE + { + double_pitch_cn = pitch_cn; + move16(); + double_pitch_energy = L_add(pitch_energy, 0); + } + /* calculate correlation for three/half pitch */ + IF(LE_16(add(add(shr(i_mult2(pitch, 3), 1), offset), corr_len), s_len)) + { + three_halves_pitch_cn = normalized_cross_correlation_self_fx(signal, add(shr(i_mult2(pitch, 3), 1), + offset), offset, corr_len, shl(ps->num_channels, 1), &three_halves_pitch_energy); + } + ELSE + { + three_halves_pitch_cn = pitch_cn; + move16(); + three_halves_pitch_energy = L_add(pitch_energy, 0); + } + /* calculate correlation for half pitch */ + IF(LE_16(add(add(shr(pitch, 1), offset), corr_len), s_len)) + { + half_pitch_cn = normalized_cross_correlation_self_fx(signal, add(shr(pitch, 1), offset), + offset, corr_len, shl(ps->num_channels, 1), &half_pitch_energy); + } + ELSE + { + half_pitch_cn = pitch_cn; + move16(); + half_pitch_energy = L_add(pitch_energy, 0); + } - /* combine correlation results: Q15.16 */ - *qualityQ16 = L_shr(L_mac0(L_mult0(half_pitch_cn, three_halves_pitch_cn), - pitch_cn, double_pitch_cn), 14); - BASOP_SATURATE_WARNING_OFF_EVS - energy = L_add(L_add(L_add(pitch_energy, half_pitch_energy), three_halves_pitch_energy), double_pitch_energy); - BASOP_SATURATE_WARNING_ON_EVS - } - ELSE - { - *qualityQ16 = L_shl(L_deposit_l(pitch_cn), 1); /* value is negative, thus pass it */ - energy = L_add(pitch_energy, 0); - } + /* combine correlation results: Q15.16 */ + *qualityQ16 = L_shr(L_mac0(L_mult0(half_pitch_cn, three_halves_pitch_cn), + pitch_cn, double_pitch_cn), 14); + BASOP_SATURATE_WARNING_OFF_EVS + energy = L_add(L_add(L_add(pitch_energy, half_pitch_energy), three_halves_pitch_energy), double_pitch_energy); + BASOP_SATURATE_WARNING_ON_EVS + } + ELSE + { + *qualityQ16 = L_shl(L_deposit_l(pitch_cn), 1); /* value is negative, thus pass it */ + energy = L_add(pitch_energy, 0); + } - /* update the quality by the quality of the signal with the highest energy */ - IF(GT_32(energy, maxEnergy)) - { - qualityOfMaxEnergy = L_add(*qualityQ16, 0); - maxEnergy = L_add(energy, 0); - } + /* update the quality by the quality of the signal with the highest energy */ + IF(GT_32(energy, maxEnergy)) + { + qualityOfMaxEnergy = L_add(*qualityQ16, 0); + maxEnergy = L_add(energy, 0); + } - /* go to next channel */ - ++signal; - } - *qualityQ16 = qualityOfMaxEnergy; - move32(); + /* go to next channel */ + ++signal; + } + *qualityQ16 = qualityOfMaxEnergy; + move32(); - /* increase calculated quality of signals with low energy */ - *energydBQ8 = apa_corrEnergy2dB_fx(maxEnergy, shl(ps->signalScaleForCorrelation, 1), corr_len); - *qualityQ16 = L_add(*qualityQ16, L_shl(L_deposit_l(apa_getQualityIncreaseForLowEnergy_fx(*energydBQ8)), 8)); + /* increase calculated quality of signals with low energy */ + *energydBQ8 = apa_corrEnergy2dB_fx(maxEnergy, shl(ps->signalScaleForCorrelation, 1), corr_len); + *qualityQ16 = L_add(*qualityQ16, L_shl(L_deposit_l(apa_getQualityIncreaseForLowEnergy_fx(*energydBQ8)), 8)); } - Word16 apa_corrEnergy2dB_fx(Word32 energy, Word16 energyExp, Word16 corr_len) - { - Word16 result, tmpScale; +Word16 apa_corrEnergy2dB_fx(Word32 energy, Word16 energyExp, Word16 corr_len) +{ - /* normalise before dividing */ - tmpScale = norm_l(energy); - energy = L_shl(energy, tmpScale); - energyExp = sub(energyExp, tmpScale); + Word16 result, tmpScale; - /* divide energy by corr_len */ - result = BASOP_Util_Divide3216_Scale(energy, corr_len, &tmpScale); - energyExp = add(energyExp, tmpScale); + /* normalise before dividing */ + tmpScale = norm_l(energy); + energy = L_shl(energy, tmpScale); + energyExp = sub(energyExp, tmpScale); + + /* divide energy by corr_len */ + result = BASOP_Util_Divide3216_Scale(energy, corr_len, &tmpScale); + energyExp = add(energyExp, tmpScale); + + result = BASOP_Util_lin2dB(L_deposit_l(result), energyExp, 1); + return result; +} - result = BASOP_Util_lin2dB(L_deposit_l(result), energyExp, 1); - return result; - } /* Converts the correlation energy to dB. */ static float apa_corrEnergy2dB( float energy, @@ -1601,11 +1862,11 @@ static bool shrink_frm( IF ( ps->evs_compat_mode == true ) { //overlapAddEvs_fx( frm_in_fx, frm_in_fx + xtract, frm_out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin_fx, ps->win_fx ); - overlapAdd( frm_in_fx, frm_in_fx + xtract, frm_out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin_fx, ps->win_fx , ps->win_incrementor); + overlapAdd( frm_in_fx, frm_in_fx + xtract, frm_out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin, ps->win_fx , ps->win_incrementor); } ELSE { - overlapAdd( frm_in_fx, frm_in_fx + xtract, frm_out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin_fx, ps->win_fx , ps->win_incrementor); + overlapAdd( frm_in_fx, frm_in_fx + xtract, frm_out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin, ps->win_fx , ps->win_incrementor); } for ( i = 0; i < l_seg; i++ ) frm_out[i] = (float)frm_out_fx[i]; @@ -2018,11 +2279,11 @@ static bool extend_frm( IF ( ps->evs_compat_mode == true ) { //overlapAddEvs_fx( fadeOut_fx, fadeIn_fx, out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin_fx, ps->win_fx ); - overlapAdd( fadeOut_fx, fadeIn_fx, out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin_fx, ps->win_fx ,ps->win_incrementor); + overlapAdd( fadeOut_fx, fadeIn_fx, out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin, ps->win_fx ,ps->win_incrementor); } ELSE { - overlapAdd( fadeOut_fx, fadeIn_fx, out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin_fx, ps->win_fx ,ps->win_incrementor); + overlapAdd( fadeOut_fx, fadeIn_fx, out_fx, l_seg, ps->num_channels, ps->win_fx + ps->l_halfwin, ps->win_fx ,ps->win_incrementor); } for ( i = 0; i < l_seg; i++ ) out[i] = (float) out_fx[i]; diff --git a/lib_dec/jbm_pcmdsp_apa.h b/lib_dec/jbm_pcmdsp_apa.h index ca7a5b290c1d8690f28d7457f79a16b1662116e3..cb3a2fc5b25fea72962bb07b2ee5965a76c6ef96 100644 --- a/lib_dec/jbm_pcmdsp_apa.h +++ b/lib_dec/jbm_pcmdsp_apa.h @@ -112,17 +112,33 @@ bool apa_set_rate( apa_state_t *ps, const int32_t output_Fs ); * The scale is given in % and will be valid until changed again. * Must be in range [APA_MIN_SCALE,APA_MAX_SCALE]. * @return 0 on success, 1 on failure */ +#ifdef IVAS_FLOAT_FIXED +bool apa_set_scale( apa_state_t *s, UWord16 scale ); +#else bool apa_set_scale( apa_state_t *s, uint16_t scale ); +#endif +#ifdef IVAS_FLOAT_FIXED +bool apa_set_renderer_granularity( apa_state_t *ps, UWord16 l_ts ); +#else bool apa_set_renderer_granularity( apa_state_t *ps, uint16_t l_ts ); +#endif +#ifdef IVAS_FLOAT_FIXED +bool apa_set_renderer_residual_samples( apa_state_t *ps, UWord16 l_r_buf ); +#else bool apa_set_renderer_residual_samples( apa_state_t *ps, uint16_t l_r_buf ); +#endif bool apa_set_evs_compat_mode( apa_state_t *ps, bool mode ); uint8_t apa_reconfigure( apa_state_t *ps, uint16_t num_channels, uint16_t l_ts ); +#ifdef IVAS_FLOAT_FIXED +bool apa_set_complexity_options( apa_state_t *s, UWord16 wss, UWord16 css ); +#else bool apa_set_complexity_options( apa_state_t *s, uint16_t wss, uint16_t css ); +#endif bool apa_set_quality( apa_state_t *s, float quality, uint16_t qualityred, uint16_t qualityrise ); diff --git a/lib_rend/ivas_dirac_dec_binaural_functions.c b/lib_rend/ivas_dirac_dec_binaural_functions.c index cbc7f732bb3868653de31978246274cffb7fde1d..a36599cf0cf77171316b5952ed9f819f1ea8ff09 100644 --- a/lib_rend/ivas_dirac_dec_binaural_functions.c +++ b/lib_rend/ivas_dirac_dec_binaural_functions.c @@ -1185,7 +1185,7 @@ static void ivas_dirac_dec_binaural_internal( IF( st_ivas->hSCE[0] && st_ivas->hSCE[0]->hCoreCoder[0] ) FOR( Word16 ind = 0; ind < FFTCLDFBLEN; ind++ ) { - st_ivas->hSCE[0]->hCoreCoder[0]->hFdCngDec->hFdCngCom->cngNoiseLevel[ind] = (Word32) ( st_ivas->hSCE[0]->hCoreCoder[0]->hFdCngDec->hFdCngCom->cngNoiseLevel_flt[ind] * ( 1 << ( 31 - st_ivas->hSCE[0]->hCoreCoder[0]->hFdCngDec->hFdCngCom->cngNoiseLevelExp ) ) ); + st_ivas->hSCE[0]->hCoreCoder[0]->hFdCngDec->hFdCngCom->cngNoiseLevel[ind] = (Word32) ( st_ivas->hSCE[0]->hCoreCoder[0]->hFdCngDec->hFdCngCom->cngNoiseLevel_flt[ind] * ( 1LL << ( 31 - st_ivas->hSCE[0]->hCoreCoder[0]->hFdCngDec->hFdCngCom->cngNoiseLevelExp ) ) ); } Word16 q_cldfb[6][CLDFB_SLOTS_PER_SUBFRAME] = { 0 }; FOR( Word16 ind = 0; ind < 6; ind++ ) diff --git a/lib_rend/ivas_dirac_output_synthesis_dec.c b/lib_rend/ivas_dirac_output_synthesis_dec.c index 9cad5d1ff966b171ac228a6c8c58b68a6fc86eab..25f5b5c2686311208efe6cd2ba9b33e37206b2b4 100644 --- a/lib_rend/ivas_dirac_output_synthesis_dec.c +++ b/lib_rend/ivas_dirac_output_synthesis_dec.c @@ -379,9 +379,6 @@ ivas_error ivas_dirac_dec_output_synthesis_open_fx( } Copy(temp_alpha_synthesis_fx, dirac_output_synthesis_params->alpha_synthesis_fx, dirac_output_synthesis_params->numAlphas); - for (int k = 1; k < hSpatParamRendCom->num_freq_bands; k++) { - hDirACRend->frequency_axis_fx[k] = float_to_fix16(hDirACRend->frequency_axis[k], 0); - } computeAlphaSynthesis_fx( temp_alpha_synthesis_fx, DIRAC_AVG_LENGTH_SYNTH_MS_FAST, DIRAC_ALPHA_MAX_FAST_Q15, &dirac_output_synthesis_params->numAlphasFast, hSpatParamRendCom->slot_size, hSpatParamRendCom->num_freq_bands , hDirACRend->frequency_axis_fx, output_Fs); for (int k = 0; k < hSpatParamRendCom->num_freq_bands; k++) { temp_alpha_synthesis[k] = fix16_to_float(temp_alpha_synthesis_fx[k], 15); diff --git a/lib_rend/ivas_masa_merge.c b/lib_rend/ivas_masa_merge.c index b6b9ce3a0fb7a4b8d6ef46a68612f7c430585b38..527e19bbdb19be839f7872954ea1d817dd5071bc 100644 --- a/lib_rend/ivas_masa_merge.c +++ b/lib_rend/ivas_masa_merge.c @@ -38,6 +38,10 @@ #include "ivas_cnst.h" #include "prot.h" #include "wmc_auto.h" +#ifdef IVAS_FLOAT_FIXED +#include "prot_fx2.h" +#include "ivas_prot_fx.h" +#endif // IVAS_FLOAT_FIXED /*---------------------------------------------------------------------* @@ -46,10 +50,16 @@ static void copy_masa_meta_tile( MASA_DECODER_EXT_OUT_META_HANDLE outMeta, MASA_DECODER_EXT_OUT_META_HANDLE inMeta, const uint8_t sf, const uint8_t band ); +#ifdef IVAS_FLOAT_FIXED +static void full_stream_merge_fx( MASA_DECODER_EXT_OUT_META_HANDLE outMeta, MASA_DECODER_EXT_OUT_META_HANDLE inMeta1, Word32 inEne1[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], Word16 *inEne1_e, MASA_DECODER_EXT_OUT_META_HANDLE inMeta2, Word32 inEne2[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], Word16 *inEne2_e ); + +static void diffuse_meta_merge_1x1_fx( MASA_DECODER_EXT_OUT_META_HANDLE outMeta, MASA_DECODER_EXT_OUT_META_HANDLE inMeta, Word32 inEne[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], Word16 *inEne1_e, MASA_DECODER_EXT_OUT_META_HANDLE inMetaISM, Word32 inEneISM[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], Word16 *inEne2_e); +#else static void full_stream_merge( MASA_DECODER_EXT_OUT_META_HANDLE outMeta, MASA_DECODER_EXT_OUT_META_HANDLE inMeta1, float inEne1[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], MASA_DECODER_EXT_OUT_META_HANDLE inMeta2, float inEne2[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS] ); static void diffuse_meta_merge_1x1( MASA_DECODER_EXT_OUT_META_HANDLE outMeta, MASA_DECODER_EXT_OUT_META_HANDLE inMeta, float inEne[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], MASA_DECODER_EXT_OUT_META_HANDLE inMetaISM, float inEneISM[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS] ); +#endif /*---------------------------------------------------------------------* * copy_masa_meta_tile() @@ -197,6 +207,125 @@ void diffuse_meta_merge_1x1( } +#ifdef IVAS_FLOAT_FIXED +void diffuse_meta_merge_1x1_fx( + MASA_DECODER_EXT_OUT_META_HANDLE outMeta, /* o : Merged metadata output */ + MASA_DECODER_EXT_OUT_META_HANDLE inMeta, /* i : Input metadata 1 */ + Word32 inEne_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : TF-energy of input 1 */ + Word16 *inEne_e, /* i : TF-energy of input 1 */ + MASA_DECODER_EXT_OUT_META_HANDLE inMetaISM, /* i : Input metadata 2 */ + Word32 inEneISM_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : TF-energy of input 2 */ + Word16 *inEneISM_e /* i : TF-energy of input 2 */ +) +{ + Word8 sf, band; + Word16 i,j, max_e, in1_e[MASA_FREQUENCY_BANDS]; + + FOR ( sf = 0; sf < MAX_PARAM_SPATIAL_SUBFRAMES; sf++ ) + { + + FOR ( band = 0; band < MASA_FREQUENCY_BANDS; band++ ) + { + Word32 energyTimesRatio_fx, energyTimesRatioISM_fx, total_diff_nrg_fx, dir_nrg_ratio_fx, total_nrg_fx; + Word32 dir_ratio_ism_fx, L_tmp1,L_tmp2; + Word16 scale, energyTimesRatio_e, tmp, total_nrg_e, total_diff_nrg_e, dir_ratio_ism_e, energyTimesRatioISM_e, dir_nrg_ratio_e ; + + tmp = BASOP_Util_Divide1616_Scale((Word16)inMeta->directToTotalRatio[0][sf][band], (Word16) UINT8_MAX, &scale); + energyTimesRatio_fx = Mpy_32_16_r( inEne_fx[sf][band], tmp); + energyTimesRatio_e = inEne_e[sf] + scale; + + /* target is original MASA diffuseness */ + tmp = BASOP_Util_Divide1616_Scale((Word16)inMeta->directToTotalRatio[0][sf][band], (Word16)UINT8_MAX, &scale); + total_diff_nrg_fx = Mpy_32_16_r(inEne_fx[sf][band], tmp); + total_diff_nrg_e = inEne_e[sf] + scale; + + /* criterion is mean of ISM ratio and new ratio */ + dir_ratio_ism_fx = L_deposit_h( BASOP_Util_Divide1616_Scale((Word16)inMeta->directToTotalRatio[0][sf][band], (Word16)UINT8_MAX, &dir_ratio_ism_e) ); + tmp = BASOP_Util_Divide3232_Scale(total_diff_nrg_fx, L_add(total_nrg_fx, EPSILON_FX), &scale); + L_tmp1 = L_deposit_h(tmp); + scale = scale + (total_diff_nrg_e - total_nrg_e); + L_tmp2 = L_sub(L_shl(1, scale), L_tmp1); + + L_tmp1 = BASOP_Util_Add_Mant32Exp(dir_ratio_ism_fx, dir_ratio_ism_e, L_tmp2, scale, &tmp); + L_tmp1 = L_shr(L_tmp1, 1); + energyTimesRatioISM_fx = Mpy_32_32(L_tmp1, inEneISM_fx[sf][band]); + energyTimesRatioISM_e = tmp + inEneISM_e[sf]; + + IF ( (BASOP_Util_Cmp_Mant32Exp( energyTimesRatioISM_fx, energyTimesRatioISM_e, energyTimesRatio_fx, energyTimesRatio_e ) > 1 ) ) + { + Word32 new_dir_ratio_fx, new_diff_ratio_fx; + Word16 new_dir_ratio_e; + outMeta->directionIndex[0][sf][band] = inMetaISM->directionIndex[0][sf][band]; + outMeta->directToTotalRatio[0][sf][band] = inMetaISM->directToTotalRatio[0][sf][band]; + outMeta->spreadCoherence[0][sf][band] = inMetaISM->spreadCoherence[0][sf][band]; + + outMeta->surroundCoherence[sf][band] = inMetaISM->surroundCoherence[sf][band]; + + tmp = BASOP_Util_Divide3232_Scale(total_diff_nrg_fx, L_add(EPSILON_FX, total_nrg_fx), &scale); + scale = scale + (total_diff_nrg_e - total_nrg_e); + dir_nrg_ratio_fx = L_sub(L_shl(1, scale), L_deposit_h(tmp)); + dir_nrg_ratio_e = scale; + + new_dir_ratio_fx = dir_nrg_ratio_fx; + new_dir_ratio_e = dir_nrg_ratio_e; + tmp = BASOP_Util_Cmp_Mant32Exp(dir_nrg_ratio_fx, dir_nrg_ratio_e, dir_ratio_ism_fx, dir_ratio_ism_e); + IF (tmp <= 0) + { + new_dir_ratio_fx = dir_nrg_ratio_fx; + new_dir_ratio_e = dir_nrg_ratio_e; + } + + outMeta->directToTotalRatio[0][sf][band] = (uint8_t) ( L_shr( new_dir_ratio_fx, 31 - new_dir_ratio_e ) * UINT8_MAX ); + new_diff_ratio_fx = L_shl( 1, 31 - new_dir_ratio_e ) - new_dir_ratio_fx; + outMeta->diffuseToTotalRatio[sf][band] = (uint8_t) floorf( L_shr( new_diff_ratio_fx, new_dir_ratio_e) * UINT8_MAX ); + } + ELSE + { + /* use the plain original meta for this tile */ + outMeta->directionIndex[0][sf][band] = inMeta->directionIndex[0][sf][band]; + outMeta->directToTotalRatio[0][sf][band] = inMeta->directToTotalRatio[0][sf][band]; + outMeta->spreadCoherence[0][sf][band] = inMeta->spreadCoherence[0][sf][band]; + + outMeta->surroundCoherence[sf][band] = inMeta->surroundCoherence[sf][band]; + outMeta->diffuseToTotalRatio[sf][band] = inMeta->diffuseToTotalRatio[sf][band]; + } + outMeta->directionIndex[1][sf][band] = SPH_IDX_FRONT; + outMeta->directToTotalRatio[1][sf][band] = 0u; + outMeta->spreadCoherence[1][sf][band] = 0u; + + inEne_fx[sf][band] = BASOP_Util_Add_Mant32Exp(inEne_fx[sf][band], inEne_e[sf], inEneISM_fx[sf][band], inEneISM_e[sf], &in1_e[band]); /* Update energy for subsequent mergings */ + } + + max_e = in1_e[0]; + FOR(Word16 i = 1; i < MASA_FREQUENCY_BANDS; i++) + { + IF(max_e < in1_e[i]) + max_e = in1_e[i]; + } + + FOR(Word16 i = 0; i < MASA_FREQUENCY_BANDS; i++) + { + inEne_fx[sf][i] = L_shr(inEne_fx[sf][i], max_e - in1_e[i]); + } + + inEne_e[sf] = max_e; + + } + + /* Set descriptive meta for mixed format */ + outMeta->descriptiveMeta.sourceFormat = 0u; + outMeta->descriptiveMeta.transportDefinition = 0u; + outMeta->descriptiveMeta.channelAngle = 0u; + outMeta->descriptiveMeta.channelDistance = 0u; + outMeta->descriptiveMeta.channelLayout = 0u; + outMeta->descriptiveMeta.numberOfDirections = 0u; + /* Number of transports should be set outside. */ + + return; +} + +#endif + /*---------------------------------------------------------------------* * full_stream_merge() * @@ -268,6 +397,107 @@ void full_stream_merge( return; } +#ifdef IVAS_FLOAT_FIXED +void full_stream_merge_fx( + MASA_DECODER_EXT_OUT_META_HANDLE outMeta, /* o : Merged metadata output */ + MASA_DECODER_EXT_OUT_META_HANDLE inMeta1, /* i : Input metadata 1 */ + Word32 inEne1_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i/o: TF-energy of input 1. after merge, contains the energy of the merged signal */ + Word16 *inEne1_e, + MASA_DECODER_EXT_OUT_META_HANDLE inMeta2, /* i : Input metadata 2 */ + Word32 inEne2_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : TF-energy of input 2 */ + Word16 *inEne2_e +) +{ + uint8_t n_dirs_1, n_dirs_2; + uint8_t sf, band; + Word16 scale, tmp, dir_nrg_1_e = 0, dir_nrg_2_e = 0, max_e; + Word16 in1_e[MASA_FREQUENCY_BANDS]; + Word32 dir_nrg_1_fx, dir_nrg_2_fx, L_tmp; + + /* full stream select based on total direct energy */ + n_dirs_1 = inMeta1->descriptiveMeta.numberOfDirections + 1u; /* to 1-based */ + n_dirs_2 = inMeta2->descriptiveMeta.numberOfDirections + 1u; + + FOR ( sf = 0; sf < MAX_PARAM_SPATIAL_SUBFRAMES; sf++ ) + { + FOR ( band = 0; band < MASA_FREQUENCY_BANDS; band++ ) + { + tmp = BASOP_Util_Divide1616_Scale((Word16)inMeta1->directToTotalRatio[0][sf][band], (Word16)UINT8_MAX, &scale); + dir_nrg_1_fx = Mpy_32_32(L_deposit_h(tmp), inEne1_fx[sf][band]); + dir_nrg_1_e = scale + inEne1_e[sf]; + + + tmp = BASOP_Util_Divide1616_Scale((Word16)inMeta1->directToTotalRatio[0][sf][band], (Word16)UINT8_MAX, &scale); + dir_nrg_2_fx = Mpy_32_32(L_deposit_h(tmp), inEne2_fx[sf][band]); + dir_nrg_2_e = scale + inEne2_e[sf]; + + + IF ( n_dirs_1 == 2 ) + { + + tmp = BASOP_Util_Divide1616_Scale((Word16)inMeta1->directToTotalRatio[1][sf][band], (Word16)UINT8_MAX, &scale); + L_tmp = Mpy_32_32(L_deposit_h(tmp), inEne1_fx[sf][band]); + scale = scale + inEne1_e[sf]; + dir_nrg_1_fx = BASOP_Util_Add_Mant32Exp(L_tmp, scale, dir_nrg_1_fx, dir_nrg_1_e, &dir_nrg_1_e); + } + + IF ( n_dirs_2 == 2 ) + { + tmp = BASOP_Util_Divide1616_Scale((Word16)inMeta2->directToTotalRatio[1][sf][band], (Word16)UINT8_MAX, &scale); + L_tmp = Mpy_32_32(L_deposit_h(tmp), inEne2_fx[sf][band]); + scale = scale + inEne2_e[sf]; + dir_nrg_2_fx = BASOP_Util_Add_Mant32Exp(L_tmp, scale, dir_nrg_2_fx, dir_nrg_2_e, &dir_nrg_2_e); + } + + IF (BASOP_Util_Cmp_Mant32Exp( dir_nrg_1_fx, dir_nrg_1_e, dir_nrg_2_fx, dir_nrg_2_e ) > 1 ) + { + copy_masa_meta_tile( outMeta, inMeta1, sf, band ); + } + ELSE + { + copy_masa_meta_tile( outMeta, inMeta2, sf, band ); + } + + inEne1_fx[sf][band] = BASOP_Util_Add_Mant32Exp(inEne1_fx[sf][band], inEne1_e[sf], inEne2_fx[sf][band], inEne2_e[sf], &in1_e[band]); + } + + max_e = in1_e[0]; + FOR (Word16 i = 1; i < MASA_FREQUENCY_BANDS; i++) + { + IF (max_e < in1_e[i]) + max_e = in1_e[i]; + } + + FOR (Word16 i = 0; i < MASA_FREQUENCY_BANDS; i++) + { + inEne1_fx[sf][i] = L_shr(inEne1_fx[sf][i], max_e - in1_e[i]); + } + + inEne1_e[sf] = max_e; + + } + + /* Set descriptive meta for mixed format */ + outMeta->descriptiveMeta.sourceFormat = 0u; + outMeta->descriptiveMeta.transportDefinition = 0u; + outMeta->descriptiveMeta.channelAngle = 0u; + outMeta->descriptiveMeta.channelDistance = 0u; + outMeta->descriptiveMeta.channelLayout = 0u; + IF ( n_dirs_1 == 2 || n_dirs_2 == 2 ) + { + outMeta->descriptiveMeta.numberOfDirections = 1u; + } + ELSE + { + outMeta->descriptiveMeta.numberOfDirections = 0u; + } + + /* Number of transports should be set outside. */ + + return; +} + +#endif /*---------------------------------------------------------------------* * ivas_prerend_merge_masa_metadata() @@ -304,6 +534,40 @@ void ivas_prerend_merge_masa_metadata( return; } +#ifdef IVAS_FLOAT_FIXED +void ivas_prerend_merge_masa_metadata_fx( + MASA_DECODER_EXT_OUT_META_HANDLE outMeta, /* o : Merged metadata output */ + MASA_DECODER_EXT_OUT_META_HANDLE inMeta1, /* i : Input metadata 1 */ + IVAS_REND_AudioConfigType inType1, /* i : Type of input 1 */ + Word32 inEne1_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i/o: TF-energy of input 1. after merge, contains the energy of the merged signal */ + Word16 *inEne1_e, + MASA_DECODER_EXT_OUT_META_HANDLE inMeta2, /* i : Input metadata 2 */ + IVAS_REND_AudioConfigType inType2, /* i : Type of input 2 */ + Word32 inEne2_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : TF-energy of input 2 */ + Word16 *inEne2_e /* i : TF-energy of input 2 */ +) +{ + /* mixing ISMs with non-ISM use different merge */ + IF ( inType1 == IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED && inType2 != IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED && ( inMeta1->descriptiveMeta.numberOfDirections == 0u && inMeta2->descriptiveMeta.numberOfDirections == 0u ) ) + { + /* meta_1 is ISM and both are 1dir */ + diffuse_meta_merge_1x1_fx( outMeta, inMeta2, inEne2_fx, inEne2_e, inMeta1, inEne1_fx, inEne1_e ); + } + ELSE IF ( inType2 == IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED && inType1 != IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED && ( inMeta1->descriptiveMeta.numberOfDirections == 0u && inMeta2->descriptiveMeta.numberOfDirections == 0u ) ) + { + /* meta_2 is ISM and both are 1dir */ + diffuse_meta_merge_1x1_fx( outMeta, inMeta1, inEne1_fx, inEne1_e, inMeta2, inEne2_fx, inEne2_e ); + } + ELSE + { + + full_stream_merge_fx( outMeta, inMeta1, inEne1_fx, inEne1_e, inMeta2, inEne2_fx, inEne2_e ); + } + + return; +} + +#endif /*---------------------------------------------------------------------* * masaPrerendOpen() @@ -311,6 +575,7 @@ void ivas_prerend_merge_masa_metadata( * *---------------------------------------------------------------------*/ +#ifndef IVAS_FLOAT_FIXED ivas_error masaPrerendOpen( MASA_PREREND_HANDLE *hMasaPrerendPtr, /* o : handle to the opened prerenderer */ int16_t numTransports, /* i : number of transport channels */ @@ -361,6 +626,58 @@ ivas_error masaPrerendOpen( return error; } +#else +ivas_error masaPrerendOpen( + MASA_PREREND_HANDLE *hMasaPrerendPtr, /* o : handle to the opened prerenderer */ + Word16 numTransports, /* i : number of transport channels */ + Word32 input_Fs /* i : signal sampling rate */ +) +{ + MASA_PREREND_HANDLE hMasaPrerend; + Word16 i; + ivas_error error; + + error = IVAS_ERR_OK; + + hMasaPrerend = (MASA_PREREND_HANDLE) malloc( sizeof( MASA_PREREND_DATA ) ); + IF ( hMasaPrerend == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for MASA prerenderer\n" ) ); + } + + hMasaPrerend->num_Cldfb_instances = numTransports; + move16(); + FOR ( i = 0; i < hMasaPrerend->num_Cldfb_instances; i++ ) + { + IF ( ( error = openCldfb_ivas_fx( &( hMasaPrerend->cldfbAnaEnc[i] ), CLDFB_ANALYSIS, input_Fs, CLDFB_PROTOTYPE_5_00MS ) ) != IVAS_ERR_OK ) + { + return error; + } + } + FOR ( ; i < MASA_MAX_TRANSPORT_CHANNELS; i++ ) + { + hMasaPrerend->cldfbAnaEnc[i] = NULL; + } + + IF ( ( hMasaPrerend->hMasaOut = (MASA_DECODER_EXT_OUT_META_HANDLE) malloc( sizeof( MASA_DECODER_EXT_OUT_META ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for MASA prerenderer\n" ) ); + } + + IF ( ( hMasaPrerend->sph_grid16 = (SPHERICAL_GRID_DATA *) malloc( sizeof( SPHERICAL_GRID_DATA ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for MASA prerenderer\n" ) ); + } + generate_gridEq_fx( hMasaPrerend->sph_grid16 ); + + IF ( error == IVAS_ERR_OK ) + { + *hMasaPrerendPtr = hMasaPrerend; + } + + return error; +} +#endif // IVAS_FLOAT_FIXED /*---------------------------------------------------------------------* * masaPrerendClose() diff --git a/lib_rend/ivas_mcmasa_ana.c b/lib_rend/ivas_mcmasa_ana.c index 468a7ce8fe52a4d0b9bb894dad2ccf9d80285ee6..7ca34554ebc9e49cd8d823efa8a687dc4aae88c6 100644 --- a/lib_rend/ivas_mcmasa_ana.c +++ b/lib_rend/ivas_mcmasa_ana.c @@ -2352,39 +2352,34 @@ static void computeEvenLayout( return; } -#ifdef IVAS_FLOAT_FIXED /*------------------------------------------------------------------------- * ivas_create_masa_out_meta() * * *------------------------------------------------------------------------*/ -void ivas_create_masa_out_meta_fx( - MASA_DECODER_EXT_OUT_META_HANDLE extOutMeta, /* i/o: MASA metadata handle */ - SPHERICAL_GRID_DATA *Sph_Grid16, /* i : Spherical grid */ - const Word16 nchan_transport, /* i : Number of transport channels */ - Word32 elevation_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated elevation */ - Word32 azimuth_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated azimuth */ - Word32 energyRatio[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated direct-to-total ratio */ - Word32 spreadCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated spread coherence */ - Word32 surroundingCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated surround coherence */ - Word16 energyRatio_q, - Word16 spreadCoherence_q, - Word16 surroundingCoherence_q - +void ivas_create_masa_out_meta( + MASA_DECODER_EXT_OUT_META_HANDLE extOutMeta, /* i/o: MASA metadata handle */ + SPHERICAL_GRID_DATA *Sph_Grid16, /* i : Spherical grid */ + const int16_t nchan_transport, /* i : Number of transport channels */ + float elevation_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated elevation */ + float azimuth_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated azimuth */ + float energyRatio[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated direct-to-total ratio */ + float spreadCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated spread coherence */ + float surroundingCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS] /* i : Estimated surround coherence */ ) { - const uint8_t ivasmasaFormatDescriptor[8] = { 0x49, 0x56, 0x41, 0x53, 0x4D, 0x41, 0x53, 0x41 }; /* "IVASMASA" */ - int16_t i, sf, band; - uint8_t numFrequencyBands; - uint8_t numDirections; - uint16_t spherical_index; + const UWord8 ivasmasaFormatDescriptor[8] = { 0x49, 0x56, 0x41, 0x53, 0x4D, 0x41, 0x53, 0x41 }; /* "IVASMASA" */ + Word16 i, sf, band; + UWord8 numFrequencyBands; + UWord8 numDirections; + UWord16 spherical_index; numDirections = 1; numFrequencyBands = MASA_FREQUENCY_BANDS; /* Construct descriptive meta */ - for ( i = 0; i < 8; i++ ) + FOR ( i = 0; i < 8; i++ ) { extOutMeta->descriptiveMeta.formatDescriptor[i] = ivasmasaFormatDescriptor[i]; } @@ -2398,62 +2393,69 @@ void ivas_create_masa_out_meta_fx( extOutMeta->descriptiveMeta.channelLayout = 0x0u; /* Construct spatial metadata from estimated values */ - for ( sf = 0; sf < MAX_PARAM_SPATIAL_SUBFRAMES; sf++ ) + FOR ( sf = 0; sf < MAX_PARAM_SPATIAL_SUBFRAMES; sf++ ) { /* Spherical index */ - for ( band = 0; band < numFrequencyBands; band++ ) + FOR ( band = 0; band < numFrequencyBands; band++ ) { - spherical_index = index_theta_phi_16_fx( &elevation_m_values[sf][band], &azimuth_m_values[sf][band], Sph_Grid16 ); + spherical_index = index_theta_phi_16( &elevation_m_values[sf][band], &azimuth_m_values[sf][band], Sph_Grid16 ); + move16(); extOutMeta->directionIndex[0][sf][band] = spherical_index; + move16(); extOutMeta->directionIndex[1][sf][band] = SPH_IDX_FRONT; + move16(); } /* Direct-to-total ratio */ - for ( band = 0; band < numFrequencyBands; band++ ) + FOR ( band = 0; band < numFrequencyBands; band++ ) { - extOutMeta->directToTotalRatio[0][sf][band] = (uint8_t) L_shr( energyRatio[sf][band], energyRatio_q - 8 ); + extOutMeta->directToTotalRatio[0][sf][band] = (UWord8) floorf( energyRatio[sf][band] * UINT8_MAX ); extOutMeta->directToTotalRatio[1][sf][band] = 0; } /* Spread coherence */ - for ( band = 0; band < numFrequencyBands; band++ ) + FOR ( band = 0; band < numFrequencyBands; band++ ) { - extOutMeta->spreadCoherence[0][sf][band] = (uint8_t) L_shr( spreadCoherence[sf][band], spreadCoherence_q - 8 ); + extOutMeta->spreadCoherence[0][sf][band] = (UWord8) floorf( spreadCoherence[sf][band] * UINT8_MAX ); extOutMeta->spreadCoherence[1][sf][band] = 0; } /* Diffuse-to-total ratio = 1 - sum(direct-to-total ratios) */ - for ( band = 0; band < numFrequencyBands; band++ ) + FOR ( band = 0; band < numFrequencyBands; band++ ) { - extOutMeta->diffuseToTotalRatio[sf][band] = UINT8_MAX - (uint8_t) L_shr( energyRatio[sf][band], energyRatio_q - 8 ); + extOutMeta->diffuseToTotalRatio[sf][band] = UINT8_MAX - (UWord8) floorf( energyRatio[sf][band] * UINT8_MAX ); } /* Surround coherence */ - for ( band = 0; band < numFrequencyBands; band++ ) + FOR ( band = 0; band < numFrequencyBands; band++ ) { - extOutMeta->surroundCoherence[sf][band] = (uint8_t) L_shr( surroundingCoherence[sf][band], surroundingCoherence_q - 8 ); + extOutMeta->surroundCoherence[sf][band] = (UWord8) floorf( surroundingCoherence[sf][band] * UINT8_MAX ); } } return; } -#endif +#ifdef IVAS_FLOAT_FIXED /*------------------------------------------------------------------------- * ivas_create_masa_out_meta() * * *------------------------------------------------------------------------*/ -void ivas_create_masa_out_meta( - MASA_DECODER_EXT_OUT_META_HANDLE extOutMeta, /* i/o: MASA metadata handle */ - SPHERICAL_GRID_DATA *Sph_Grid16, /* i : Spherical grid */ - const int16_t nchan_transport, /* i : Number of transport channels */ - float elevation_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated elevation */ - float azimuth_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated azimuth */ - float energyRatio[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated direct-to-total ratio */ - float spreadCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated spread coherence */ - float surroundingCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS] /* i : Estimated surround coherence */ +void ivas_create_masa_out_meta_fx( + MASA_DECODER_EXT_OUT_META_HANDLE extOutMeta, /* i/o: MASA metadata handle */ + SPHERICAL_GRID_DATA *Sph_Grid16, /* i : Spherical grid */ + const Word16 nchan_transport, /* i : Number of transport channels */ + Word32 elevation_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated elevation */ + Word32 azimuth_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated azimuth */ + Word32 energyRatio[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated direct-to-total ratio */ + Word32 spreadCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated spread coherence */ + Word32 surroundingCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : Estimated surround coherence */ + Word16 energyRatio_q, + Word16 spreadCoherence_q, + Word16 surroundingCoherence_q + ) { const uint8_t ivasmasaFormatDescriptor[8] = { 0x49, 0x56, 0x41, 0x53, 0x4D, 0x41, 0x53, 0x41 }; /* "IVASMASA" */ @@ -2485,7 +2487,7 @@ void ivas_create_masa_out_meta( /* Spherical index */ for ( band = 0; band < numFrequencyBands; band++ ) { - spherical_index = index_theta_phi_16( &elevation_m_values[sf][band], &azimuth_m_values[sf][band], Sph_Grid16 ); + spherical_index = index_theta_phi_16_fx( &elevation_m_values[sf][band], &azimuth_m_values[sf][band], Sph_Grid16 ); extOutMeta->directionIndex[0][sf][band] = spherical_index; extOutMeta->directionIndex[1][sf][band] = SPH_IDX_FRONT; } @@ -2493,29 +2495,30 @@ void ivas_create_masa_out_meta( /* Direct-to-total ratio */ for ( band = 0; band < numFrequencyBands; band++ ) { - extOutMeta->directToTotalRatio[0][sf][band] = (uint8_t) floorf( energyRatio[sf][band] * UINT8_MAX ); + extOutMeta->directToTotalRatio[0][sf][band] = (uint8_t) L_shr( energyRatio[sf][band], energyRatio_q - 8 ); extOutMeta->directToTotalRatio[1][sf][band] = 0; } /* Spread coherence */ for ( band = 0; band < numFrequencyBands; band++ ) { - extOutMeta->spreadCoherence[0][sf][band] = (uint8_t) floorf( spreadCoherence[sf][band] * UINT8_MAX ); + extOutMeta->spreadCoherence[0][sf][band] = (uint8_t) L_shr( spreadCoherence[sf][band], spreadCoherence_q - 8 ); extOutMeta->spreadCoherence[1][sf][band] = 0; } /* Diffuse-to-total ratio = 1 - sum(direct-to-total ratios) */ for ( band = 0; band < numFrequencyBands; band++ ) { - extOutMeta->diffuseToTotalRatio[sf][band] = UINT8_MAX - (uint8_t) floorf( energyRatio[sf][band] * UINT8_MAX ); + extOutMeta->diffuseToTotalRatio[sf][band] = UINT8_MAX - (uint8_t) L_shr( energyRatio[sf][band], energyRatio_q - 8 ); } /* Surround coherence */ for ( band = 0; band < numFrequencyBands; band++ ) { - extOutMeta->surroundCoherence[sf][band] = (uint8_t) floorf( surroundingCoherence[sf][band] * UINT8_MAX ); + extOutMeta->surroundCoherence[sf][band] = (uint8_t) L_shr( surroundingCoherence[sf][band], surroundingCoherence_q - 8 ); } } return; -} \ No newline at end of file +} +#endif \ No newline at end of file diff --git a/lib_rend/ivas_objectRenderer.c b/lib_rend/ivas_objectRenderer.c index a2eac77dc1e7a66f6417d0395c6c7b73fe6c64a6..545fddc1bff03fd352cd5a6428ddde38f15dfb8d 100644 --- a/lib_rend/ivas_objectRenderer.c +++ b/lib_rend/ivas_objectRenderer.c @@ -820,24 +820,11 @@ ivas_error ivas_td_binaural_renderer_unwrap( tmp_Pos = &Pos[hCombinedOrientationData->subframe_idx]; } - // Float to fixed - float max_val = 0; - max_val = (float)max(max_val, fabs(tmp_Quaternions->w)); - max_val = (float)max(max_val, fabs(tmp_Quaternions->x)); - max_val = (float)max(max_val, fabs(tmp_Quaternions->y)); - max_val = (float)max(max_val, fabs(tmp_Quaternions->z)); - Word16 quat_q = Q_factor_L(max_val); - tmp_Quaternions->w_fx = float_to_fix(tmp_Quaternions->w, quat_q); - tmp_Quaternions->x_fx = float_to_fix(tmp_Quaternions->x, quat_q); - tmp_Quaternions->y_fx = float_to_fix(tmp_Quaternions->y, quat_q); - tmp_Quaternions->z_fx = float_to_fix(tmp_Quaternions->z, quat_q); - tmp_Quaternions->q_fact = quat_q; - Word16 pos_q = Q25; - tmp_Pos->x_fx = (Word32)float_to_fix(tmp_Pos->x, pos_q); - tmp_Pos->y_fx = (Word32)float_to_fix(tmp_Pos->y, pos_q); - tmp_Pos->z_fx = (Word32)float_to_fix(tmp_Pos->z, pos_q); - tmp_Pos->q_fact= pos_q; + tmp_Pos->x_fx = L_shr( tmp_Pos->x_fx, sub(tmp_Pos->q_fact, pos_q) ); + tmp_Pos->y_fx = L_shr( tmp_Pos->y_fx, sub( tmp_Pos->q_fact, pos_q ) ); + tmp_Pos->z_fx = L_shr( tmp_Pos->z_fx, sub( tmp_Pos->q_fact, pos_q ) ); + tmp_Pos->q_fact = pos_q; // end float to fix IF ( ( error = TDREND_Update_listener_orientation_fx( hBinRendererTd, tmp_headRotEnabled, tmp_Quaternions, tmp_Pos ) ) != IVAS_ERR_OK ) diff --git a/lib_rend/ivas_omasa_ana.c b/lib_rend/ivas_omasa_ana.c index b8afd6474c78956f5ba781c97101421927e8f7b6..e7165ed25aba6770826776f07fba87ac672606fc 100644 --- a/lib_rend/ivas_omasa_ana.c +++ b/lib_rend/ivas_omasa_ana.c @@ -41,6 +41,8 @@ #include "ivas_stat_rend.h" #include "ivas_rom_com.h" #include "wmc_auto.h" +#include "prot_fx2.h" +#define IVAS_FLOAT_FIXED_TO_BE_REMOVED /*------------------------------------------------------------------------- @@ -49,8 +51,38 @@ static void ivas_omasa_param_est_ana( OMASA_ANA_HANDLE hOMasa, float data_f[][L_FRAME48k], float elevation_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], float azimuth_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], float energyRatio[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], float spreadCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], float surroundingCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], const int16_t input_frame, const int16_t nchan_ism ); +#ifndef IVAS_FLOAT_FIXED static void ivas_omasa_dmx( float data_in_f[][L_FRAME48k], const int16_t input_frame, const int16_t nchan_transport, const int16_t nchan_ism, const float ism_azimuth[MAX_NUM_OBJECTS], const float ism_elevation[MAX_NUM_OBJECTS], float prev_gains[][MASA_MAX_TRANSPORT_CHANNELS], const float interpolator[L_FRAME48k] ); +#endif +#ifdef IVAS_FLOAT_FIXED +static void ivas_omasa_dmx_fx( + Word32 data_in_f_fx[][L_FRAME48k], + Word16 *data_in_q, + const Word16 input_frame, + const Word16 nchan_transport, + const Word16 nchan_ism, + const Word32 ism_azimuth_fx[MAX_NUM_OBJECTS], + const Word32 ism_elevation_fx[MAX_NUM_OBJECTS], + Word32 prev_gains_fx[][MASA_MAX_TRANSPORT_CHANNELS], + const Word16 interpolator_fx[L_FRAME48k]); + + +static void ivas_omasa_param_est_ana_fx( + OMASA_ANA_HANDLE hOMasa, + Word32 data_f_fx[][L_FRAME48k], + Word16 data_f_q, + Word32 elevation_m_values_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], // Q22 + Word32 azimuth_m_values_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], // Q22 + Word32 energyRatio_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], + Word16 *energyRatio_q, + Word32 spreadCoherence_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], + Word16 *spreadCoherence_q, + Word32 surroundingCoherence_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], + Word16 *surroundingCoherence_q, + const Word16 input_frame, + const Word16 nchan_ism ); +#endif /*--------------------------------------------------------------------------* * ivas_omasa_ana_open() @@ -58,6 +90,148 @@ static void ivas_omasa_dmx( float data_in_f[][L_FRAME48k], const int16_t input_f * Allocate and initialize OMASA handle *--------------------------------------------------------------------------*/ +#ifdef IVAS_FLOAT_FIXED +ivas_error ivas_omasa_ana_open( + OMASA_ANA_HANDLE *hOMasaPtr, /* i/o: OMASA data handle pointer */ + Word32 input_Fs, /* i : Sampling frequency */ + UWord16 total_num_objects /* i : Number of objects */ +) +{ + Word16 i, j; + OMASA_ANA_HANDLE hOMasa; + Word16 numAnalysisChannels; + Word16 maxBin, input_frame; + ivas_error error; + Word16 scale; + + error = IVAS_ERR_OK; + + IF ( ( hOMasa = (OMASA_ANA_HANDLE) malloc( sizeof( OMASA_ANA_DATA ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for OMASA\n" ) ); + } + + numAnalysisChannels = (Word16) total_num_objects; + move16(); + + /* Determine the number of bands */ + hOMasa->nbands = MASA_FREQUENCY_BANDS; + move16(); + + /* Determine band grouping */ + mvs2s( MASA_band_grouping_24, hOMasa->band_grouping, 24 + 1 ); + + maxBin = (Word16) BASOP_Util_Divide3232_Scale( input_Fs, 800, &scale ); + maxBin = shr( maxBin, sub( 15, scale ) ); + + FOR ( i = 1; i < hOMasa->nbands + 1; i++ ) + { + IF ( GE_16( hOMasa->band_grouping[i], maxBin ) ) + { + hOMasa->band_grouping[i] = maxBin; + move16(); + hOMasa->nbands = i; + move16(); + BREAK; + } + } + + /* Determine block grouping */ + mvs2s( DirAC_block_grouping, hOMasa->block_grouping, MAX_PARAM_SPATIAL_SUBFRAMES + 1 ); + + /* open/initialize CLDFB */ + hOMasa->num_Cldfb_instances = numAnalysisChannels; + FOR ( i = 0; i < hOMasa->num_Cldfb_instances; i++ ) + { + IF ( ( error = openCldfb_ivas( &( hOMasa->cldfbAnaEnc[i] ), CLDFB_ANALYSIS, input_Fs, CLDFB_PROTOTYPE_5_00MS ) ) != IVAS_ERR_OK ) + { + return error; + } + } + + FOR ( ; i < MAX_NUM_OBJECTS; i++ ) + { + hOMasa->cldfbAnaEnc[i] = NULL; + } + + FOR ( i = 0; i < DIRAC_NUM_DIMS; i++ ) + { + IF ( ( hOMasa->direction_vector_m_fx[i] = (Word32 **) malloc( MAX_PARAM_SPATIAL_SUBFRAMES * sizeof( Word32 * ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for OMASA data\n" ) ); + } + + FOR ( j = 0; j < MAX_PARAM_SPATIAL_SUBFRAMES; j++ ) + { + IF ( ( hOMasa->direction_vector_m_fx[i][j] = (Word32 *) malloc( MASA_FREQUENCY_BANDS * sizeof( Word32 ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for OMASA data\n" ) ); + } + set_zero_fx( hOMasa->direction_vector_m_fx[i][j], MASA_FREQUENCY_BANDS ); + } + } + + FOR ( i = 0; i < DIRAC_NUM_DIMS; i++ ) + { + FOR ( j = 0; j < DIRAC_NO_COL_AVG_DIFF; j++ ) + { + IF ( ( hOMasa->buffer_intensity_real_fx[i][j] = (Word32 *) malloc( MASA_FREQUENCY_BANDS * sizeof( Word32 ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for OMASA data\n" ) ); + } + set_zero_fx( hOMasa->buffer_intensity_real_fx[i][j], MASA_FREQUENCY_BANDS ); + } + } + + set_zero_fx( hOMasa->buffer_energy_fx, DIRAC_NO_COL_AVG_DIFF * MASA_FREQUENCY_BANDS ); + + FOR ( i = 0; i < MAX_NUM_OBJECTS; i++ ) + { + set32_fx( hOMasa->prev_object_dm_gains_fx[i], INV_SQRT_2_Q31, MASA_MAX_TRANSPORT_CHANNELS ); + } + + input_frame = BASOP_Util_Divide3232_Scale( input_Fs, FRAMES_PER_SEC, &scale ); + input_frame = shr (input_frame, sub( 15, scale ) ); + + + + FOR ( i = 0; i < input_frame; i++ ) + { + hOMasa->interpolator_fx[i] = BASOP_Util_Divide1616_Scale(i, input_frame, &scale ); + hOMasa->interpolator_fx[i] = shl( hOMasa->interpolator_fx[i], scale ); // Q15 + } + + hOMasa->index_buffer_intensity = 0; + move16(); + + IF ( ( hOMasa->hMasaOut = (MASA_DECODER_EXT_OUT_META_HANDLE) malloc( sizeof( MASA_DECODER_EXT_OUT_META ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for MASA decoder\n" ) ); + } + + IF ( ( hOMasa->sph_grid16 = (SPHERICAL_GRID_DATA *) malloc( sizeof( SPHERICAL_GRID_DATA ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for MASA decoder\n" ) ); + } + + generate_gridEq_fx( hOMasa->sph_grid16 ); + + FOR ( i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++ ) + { + set_zero_fx( hOMasa->energy_fx[i], MASA_FREQUENCY_BANDS ); + } + + set_zero_fx( hOMasa->ism_azimuth_fx, MAX_NUM_OBJECTS ); + set_zero_fx( hOMasa->ism_elevation_fx, MAX_NUM_OBJECTS ); + +#ifdef IVAS_FLOAT_FIXED_TO_BE_REMOVED +#endif + + ( *hOMasaPtr ) = hOMasa; + + return error; +} +#else ivas_error ivas_omasa_ana_open( OMASA_ANA_HANDLE *hOMasaPtr, /* i/o: OMASA data handle pointer */ int32_t input_Fs, /* i : Sampling frequency */ @@ -183,6 +357,7 @@ ivas_error ivas_omasa_ana_open( return error; } +#endif /*--------------------------------------------------------------------------* * ivas_omasa_ana_close() @@ -190,6 +365,52 @@ ivas_error ivas_omasa_ana_open( * Close OMASA handle *--------------------------------------------------------------------------*/ +#ifdef IVAS_FLOAT_FIXED +void ivas_omasa_ana_close( + OMASA_ANA_HANDLE *hOMasa /* i/o: analysis OMASA handle */ +) +{ + Word16 i, j; + + IF ( hOMasa == NULL || *hOMasa == NULL ) + { + return; + } + + FOR ( i = 0; i < ( *hOMasa )->num_Cldfb_instances; i++ ) + { + deleteCldfb_ivas( &( ( *hOMasa )->cldfbAnaEnc[i] ) ); + } + + FOR ( i = 0; i < DIRAC_NUM_DIMS; i++ ) + { + FOR ( j = 0; j < MAX_PARAM_SPATIAL_SUBFRAMES; j++ ) + { + free( ( *hOMasa )->direction_vector_m_fx[i][j] ); + ( *hOMasa )->direction_vector_m_fx[i][j] = NULL; + } + + FOR ( j = 0; j < DIRAC_NO_COL_AVG_DIFF; j++ ) + { + free( ( *hOMasa )->buffer_intensity_real_fx[i][j] ); + ( *hOMasa )->buffer_intensity_real_fx[i][j] = NULL; + } + + free( ( *hOMasa )->direction_vector_m_fx[i] ); + ( *hOMasa )->direction_vector_m_fx[i] = NULL; + } + + free( ( *hOMasa )->hMasaOut ); + ( *hOMasa )->hMasaOut = NULL; + free( ( *hOMasa )->sph_grid16 ); + ( *hOMasa )->sph_grid16 = NULL; + + free( ( *hOMasa ) ); + ( *hOMasa ) = NULL; + + return; +} +#else void ivas_omasa_ana_close( OMASA_ANA_HANDLE *hOMasa /* i/o: analysis OMASA handle */ ) @@ -234,7 +455,7 @@ void ivas_omasa_ana_close( return; } - +#endif /*--------------------------------------------------------------------------* * ivas_omasa_ana() @@ -242,6 +463,7 @@ void ivas_omasa_ana_close( * OMASA analysis function *--------------------------------------------------------------------------*/ +#ifndef IVAS_FLOAT_FIXED void ivas_omasa_ana( OMASA_ANA_HANDLE hOMasa, /* i/o: OMASA analysis handle */ float data_in_f[][L_FRAME48k], /* i/o: Input / transport audio signals */ @@ -267,13 +489,47 @@ void ivas_omasa_ana( return; } +#endif + +#ifdef IVAS_FLOAT_FIXED +void ivas_omasa_ana_fx( + OMASA_ANA_HANDLE hOMasa, /* i/o: OMASA analysis handle */ + float data_in_f[][L_FRAME48k], /* i/o: Input / transport audio signals */ + Word32 data_in_f_fx[][L_FRAME48k], /* i/o: Input / transport audio signals */ + Word16 *data_in_q, + const Word16 input_frame, /* i : Input frame size */ + const Word16 nchan_transport, /* i : Number of transport channels */ + const Word16 nchan_ism /* i : Number of objects for parameter analysis */ +) +{ + Word32 elevation_m_values_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word32 azimuth_m_values_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word32 energyRatio_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word32 spreadCoherence_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word32 surroundingCoherence_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word16 spreadCoherence_q, sorroundingCoherence_q, energyRatio_q; + + /* Estimate MASA parameters from the objects */ + ivas_omasa_param_est_ana_fx(hOMasa, data_in_f_fx, *data_in_q, elevation_m_values_fx, azimuth_m_values_fx, energyRatio_fx, &energyRatio_q, spreadCoherence_fx, &spreadCoherence_q, surroundingCoherence_fx, &sorroundingCoherence_q, input_frame, nchan_ism); + + /* Create MASA metadata buffer from the estimated values */ + + ivas_create_masa_out_meta_fx( hOMasa->hMasaOut, hOMasa->sph_grid16, nchan_transport, elevation_m_values_fx, azimuth_m_values_fx, energyRatio_fx, spreadCoherence_fx, surroundingCoherence_fx, energyRatio_q, spreadCoherence_q, sorroundingCoherence_q ); + + /* Downmix */ + ivas_omasa_dmx_fx( data_in_f_fx, data_in_q, input_frame, nchan_transport, nchan_ism, hOMasa->ism_azimuth_fx, hOMasa->ism_elevation_fx, hOMasa->prev_object_dm_gains_fx, hOMasa->interpolator_fx ); + return; +} +#endif /*--------------------------------------------------------------------------* * Local functions *--------------------------------------------------------------------------*/ /* Estimate MASA parameters from the objects */ + +#ifndef IVAS_FLOAT_FIXED static void ivas_omasa_param_est_ana( OMASA_ANA_HANDLE hOMasa, float data_f[][L_FRAME48k], @@ -461,9 +717,445 @@ static void ivas_omasa_param_est_ana( return; } +#endif + +#ifdef IVAS_FLOAT_FIXED +static void ivas_omasa_param_est_ana_fx( + OMASA_ANA_HANDLE hOMasa, + Word32 data_f_fx[][L_FRAME48k], + Word16 data_f_q, + Word32 elevation_m_values_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], // Q22 + Word32 azimuth_m_values_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], // Q22 + Word32 energyRatio_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], + Word16 *energyRatio_q, + Word32 spreadCoherence_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], + Word16 *spreadCoherence_q, + Word32 surroundingCoherence_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], + Word16 *surroundingCoherence_q, + const Word16 input_frame, + const Word16 nchan_ism ) +{ + Word16 ts, i, d, j; + Word16 num_freq_bins, num_freq_bands, index; + Word16 l_ts; + + Word32 reference_power_fx[MASA_FREQUENCY_BANDS]; + Word32 Chnl_RealBuffer_fx[MAX_NUM_OBJECTS][CLDFB_NO_CHANNELS_MAX]; + Word16 Chnl_RealBuffer_q; + Word16 Chnl_ImagBuffer_q; + Word32 Chnl_ImagBuffer_fx[MAX_NUM_OBJECTS][CLDFB_NO_CHANNELS_MAX]; + Word32 Foa_RealBuffer_fx[FOA_CHANNELS][CLDFB_NO_CHANNELS_MAX]; + Word32 Foa_ImagBuffer_fx[FOA_CHANNELS][CLDFB_NO_CHANNELS_MAX]; + Word32 intensity_real_fx[DIRAC_NUM_DIMS][MASA_FREQUENCY_BANDS]; + Word32 direction_vector_fx[DIRAC_NUM_DIMS][MASA_FREQUENCY_BANDS]; + Word32 diffuseness_vector_fx[MASA_FREQUENCY_BANDS]; + Word16 diffuseness_q; + Word32 diffuseness_m_fx[MASA_FREQUENCY_BANDS]; + Word16 diffuseness_m_q; + Word32 renormalization_factor_diff_fx[MASA_FREQUENCY_BANDS]; + Word16 renormalization_factor_diff_q; + Word32 norm_tmp_fx; + Word16 scale; + + Word32 dir_v_fx[DIRAC_NUM_DIMS], L_tmp1, L_tmp2; + Word16 dir_v_q, norm_tmp_q; + Word16 foa_q; + + int16_t band_m_idx, block_m_idx; + + //float norm_tmp; + Word16 mrange[2]; + Word16 brange[2]; + + num_freq_bins = hOMasa->cldfbAnaEnc[0]->no_channels; + move16(); + num_freq_bands = hOMasa->nbands; + move16(); + l_ts = input_frame / CLDFB_NO_COL_MAX; + + Word16 intensity_q; + Word16 direction_q, reference_power_q; + + /* Compute ISM to FOA matrices */ + FOR ( i = 0; i < nchan_ism; i++ ) + { + Word16 tmp, tmp1, scale; + // 180 in Q22 754974720 + hOMasa->chnlToFoaMtx_fx[0][i] = 32767; // 1 in Q15 + move16(); + + tmp = BASOP_Util_Divide3232_Scale(hOMasa->ism_azimuth_fx[i], 754974720, &scale); + tmp = mult( tmp, EVS_PI_FX ); // Q13 + Q15 - Q15 --> Q13 + tmp = getSinWord16(tmp); // Q15 sine value + + tmp1 = BASOP_Util_Divide3232_Scale(hOMasa->ism_elevation_fx[i], 754974720, &scale); + tmp1 = mult(tmp1, EVS_PI_FX ); + tmp1 = getCosWord16(tmp1); + hOMasa->chnlToFoaMtx_fx[1][i] = shl(mult(tmp, tmp1), 1); // Q14 + Q15 - Q15 + Q1 -> Q15 + + tmp = BASOP_Util_Divide3232_Scale(hOMasa->ism_elevation_fx[i], 754974720, &scale); + tmp = mult(tmp, EVS_PI_FX); // Q13 + Q15 - Q15 --> Q13 + hOMasa->chnlToFoaMtx_fx[2][i] = getSinWord16( tmp ); // Q15 + + tmp = BASOP_Util_Divide3232_Scale(hOMasa->ism_azimuth_fx[i], 754974720, &scale); + tmp = mult(tmp, EVS_PI_FX); // Q13 + Q15 - Q15 --> Q13 + tmp= getCosWord16(tmp); // Q14 + + + tmp1 = BASOP_Util_Divide3232_Scale(hOMasa->ism_elevation_fx[i], 754974720, &scale); + tmp1 = mult(tmp, EVS_PI_FX); // Q13 + Q15 - Q15 --> Q13 + tmp1 = getCosWord16(tmp); // Q14 + + hOMasa->chnlToFoaMtx_fx[3][i] = shl( mult(tmp, tmp1), 2 ); // Q14 + Q14 - Q15 + Q2-> Q13 + Q2 -> Q15 + } + + /* do processing over all CLDFB time slots */ + FOR ( block_m_idx = 0; block_m_idx < MAX_PARAM_SPATIAL_SUBFRAMES; block_m_idx++ ) + { + mrange[0] = hOMasa->block_grouping[block_m_idx]; + move16(); + mrange[1] = hOMasa->block_grouping[block_m_idx + 1]; + move16(); + + FOR ( band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++ ) + { + hOMasa->direction_vector_m_fx[0][block_m_idx][band_m_idx] = 0; + move32(); + hOMasa->direction_vector_m_fx[1][block_m_idx][band_m_idx] = 0; + move32(); + hOMasa->direction_vector_m_fx[2][block_m_idx][band_m_idx] = 0; + move32(); + } + + /* Need to initialize renormalization_factors, and variables to be normalized */ + + set_zero_fx( renormalization_factor_diff_fx, hOMasa->nbands ); + set_zero_fx( diffuseness_m_fx, hOMasa->nbands ); + set_zero_fx( hOMasa->energy_fx[block_m_idx], MASA_FREQUENCY_BANDS ); + + FOR ( ts = mrange[0]; ts < mrange[1]; ts++ ) + { + FOR ( i = 0; i < nchan_ism; i++ ) + { + Word16 in_q; + in_q = data_f_q; + move16(); + + cldfbAnalysis_ts_fx( &( data_f_fx[i][l_ts * ts] ), Chnl_RealBuffer_fx[i], Chnl_ImagBuffer_fx[i], l_ts, hOMasa->cldfbAnaEnc[i], &in_q); + + FOR (Word16 ind = 0; ind < CLDFB_NO_CHANNELS_MAX; ind++) + { + Chnl_RealBuffer_fx[i][ind] = Chnl_RealBuffer_fx[i][ind] / (1 << 4); + Chnl_ImagBuffer_fx[i][ind] = Chnl_ImagBuffer_fx[i][ind] / (1 << 4); + + } + + Chnl_RealBuffer_q = sub(in_q, 4); + Chnl_ImagBuffer_q = sub(in_q, 4); + } + + + /* Compute channel-based energy for metadata processing */ + FOR ( band_m_idx = 0; band_m_idx < num_freq_bands; band_m_idx++ ) + { + brange[0] = hOMasa->band_grouping[band_m_idx]; + move16(); + brange[1] = hOMasa->band_grouping[band_m_idx + 1]; + move16(); + FOR ( j = brange[0]; j < brange[1]; j++ ) + { + FOR ( i = 0; i < nchan_ism; i++ ) + { + L_tmp1 = Mpy_32_32(Chnl_RealBuffer_fx[i][j], Chnl_RealBuffer_fx[i][j]); + L_tmp2 = Mpy_32_32(Chnl_ImagBuffer_fx[i][j], Chnl_ImagBuffer_fx[i][j]); + hOMasa->energy_fx[block_m_idx][band_m_idx] = L_add(hOMasa->energy_fx[block_m_idx][band_m_idx], L_add(L_tmp1, L_tmp2));// Chnl_RealBuffer_q + Chnl_RealBuffer_q - 31 + hOMasa->energy_q = sub( add( Chnl_RealBuffer_q, Chnl_RealBuffer_q ), 31 ); + } + } + } + + /* Compute FOA */ + /* W */ + + Copy32( Chnl_RealBuffer_fx[0], Foa_RealBuffer_fx[0], num_freq_bins ); + Copy32( Chnl_ImagBuffer_fx[0], Foa_ImagBuffer_fx[0], num_freq_bins ); + + FOR ( i = 1; i < nchan_ism; i++ ) + { + v_add_fixed(Chnl_RealBuffer_fx[i], Foa_RealBuffer_fx[0], Foa_RealBuffer_fx[0], num_freq_bins, 0); + v_add_fixed(Chnl_ImagBuffer_fx[i], Foa_ImagBuffer_fx[0], Foa_ImagBuffer_fx[0], num_freq_bins, 0); + } + + /* Y */ + + v_multc_fixed(Chnl_RealBuffer_fx[0], L_deposit_h(hOMasa->chnlToFoaMtx_fx[1][0]), Foa_RealBuffer_fx[1], num_freq_bins); + v_multc_fixed(Chnl_ImagBuffer_fx[0], L_deposit_h(hOMasa->chnlToFoaMtx_fx[1][0]), Foa_ImagBuffer_fx[1], num_freq_bins); + + FOR ( i = 1; i < nchan_ism; i++ ) + { + v_multc_acc_32_16( Chnl_RealBuffer_fx[i], hOMasa->chnlToFoaMtx_fx[1][i], Foa_RealBuffer_fx[1], num_freq_bins ); + v_multc_acc_32_16( Chnl_ImagBuffer_fx[i], hOMasa->chnlToFoaMtx_fx[1][i], Foa_ImagBuffer_fx[1], num_freq_bins ); + } + + /* Z */ + + v_multc_fixed( Chnl_RealBuffer_fx[0], L_deposit_h(hOMasa->chnlToFoaMtx_fx[2][0]), Foa_RealBuffer_fx[2], num_freq_bins ); + v_multc_fixed( Chnl_ImagBuffer_fx[0], L_deposit_h(hOMasa->chnlToFoaMtx_fx[2][0]), Foa_ImagBuffer_fx[2], num_freq_bins ); + + FOR ( i = 1; i < nchan_ism; i++ ) + { + v_multc_acc_32_16( Chnl_RealBuffer_fx[i], hOMasa->chnlToFoaMtx_fx[2][i], Foa_RealBuffer_fx[2], num_freq_bins ); + v_multc_acc_32_16( Chnl_ImagBuffer_fx[i], hOMasa->chnlToFoaMtx_fx[2][i], Foa_ImagBuffer_fx[2], num_freq_bins ); + } + + v_multc_fixed( Chnl_RealBuffer_fx[0], L_deposit_h(hOMasa->chnlToFoaMtx_fx[3][0]), Foa_RealBuffer_fx[2], num_freq_bins ); + v_multc_fixed( Chnl_ImagBuffer_fx[0], L_deposit_h(hOMasa->chnlToFoaMtx_fx[3][0]), Foa_ImagBuffer_fx[2], num_freq_bins ); + + FOR ( i = 1; i < nchan_ism; i++ ) + { + v_multc_acc_32_16(Chnl_RealBuffer_fx[i], hOMasa->chnlToFoaMtx_fx[3][i], Foa_RealBuffer_fx[3], num_freq_bins); + v_multc_acc_32_16(Chnl_ImagBuffer_fx[i], hOMasa->chnlToFoaMtx_fx[3][i], Foa_ImagBuffer_fx[3], num_freq_bins); + } + + /* Direction estimation */ + FOR (i = 0; i < FOA_CHANNELS; i++) + { + FOR (j = 0; j < CLDFB_NO_CHANNELS_MAX; j++) + { + Foa_RealBuffer_fx[i][j] = L_shr(Foa_RealBuffer_fx[i][j], 5); + Foa_ImagBuffer_fx[i][j] = L_shr(Foa_ImagBuffer_fx[i][j], 5); + } + } + foa_q = sub( Chnl_ImagBuffer_q, 5 ); + computeIntensityVector_ana_fx( hOMasa->band_grouping, Foa_RealBuffer_fx, Foa_ImagBuffer_fx, num_freq_bands, intensity_real_fx ); + + intensity_q = sub( shl( add(foa_q, Q1), 1 ), 31 ); + direction_q, reference_power_q; + + computeDirectionVectors_fx( 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], &direction_q ); + + /* Power estimation for diffuseness */ + + computeReferencePower_ana_fx( hOMasa->band_grouping, Foa_RealBuffer_fx, Foa_ImagBuffer_fx, reference_power_fx, num_freq_bands ); // 2*inputq - 30 + reference_power_q = sub( shl( Chnl_ImagBuffer_q, 1 ), 30 ); + + /* Fill buffers of length "averaging_length" time slots for intensity and energy */ + hOMasa->index_buffer_intensity = ( hOMasa->index_buffer_intensity % DIRAC_NO_COL_AVG_DIFF ) + 1; /* averaging_length = 32 */ + index = hOMasa->index_buffer_intensity; + + FOR ( i = 0; i < DIRAC_NUM_DIMS; i++ ) + { + /* only real part needed */ + Copy32( intensity_real_fx[i], &( hOMasa->buffer_intensity_real_fx[i][index - 1][0] ), num_freq_bands ); + } + hOMasa->buffer_intensity_real_q[index - 1] = intensity_q; + move16(); + Copy32( reference_power_fx, &( hOMasa->buffer_energy_fx[( index - 1 ) * num_freq_bands] ), num_freq_bands ); + hOMasa->buffer_energy_q[index - 1] = reference_power_q; + move16(); + + computeDiffuseness_fixed(hOMasa->buffer_intensity_real_fx, hOMasa->buffer_energy_fx, num_freq_bands, diffuseness_vector_fx, hOMasa->buffer_intensity_real_q, hOMasa->buffer_energy_q, &diffuseness_q); + + FOR ( band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++ ) + { + norm_tmp_fx = Mpy_32_32(reference_power_fx[band_m_idx], L_sub(1073741824, diffuseness_vector_fx[band_m_idx] )); // reference_power_q + 30 - 31 + norm_tmp_q = sub( add( reference_power_q, 30 ), 31 ); + + hOMasa->direction_vector_m_fx[0][block_m_idx][band_m_idx] = L_add( hOMasa->direction_vector_m_fx[0][block_m_idx][band_m_idx], Mpy_32_32( norm_tmp_fx, direction_vector_fx[0][band_m_idx] ) ); + + hOMasa->direction_vector_m_fx[1][block_m_idx][band_m_idx] = L_add(hOMasa->direction_vector_m_fx[0][block_m_idx][band_m_idx], Mpy_32_32( norm_tmp_fx, direction_vector_fx[1][band_m_idx] ) ); + hOMasa->direction_vector_m_fx[2][block_m_idx][band_m_idx] = L_add( hOMasa->direction_vector_m_fx[0][block_m_idx][band_m_idx], Mpy_32_32( norm_tmp_fx, direction_vector_fx[2][band_m_idx] ) ); + + hOMasa->direction_vector_m_q = sub( add( norm_tmp_q, direction_q ), 31 ); + + + diffuseness_m_fx[band_m_idx] = L_add( diffuseness_m_fx[band_m_idx], Mpy_32_32( reference_power_fx[band_m_idx], diffuseness_vector_fx[band_m_idx] ) ); + diffuseness_m_q = sub( add( reference_power_q, diffuseness_q ), 31 ); + renormalization_factor_diff_fx[band_m_idx] = L_add( renormalization_factor_diff_fx[band_m_idx], reference_power_fx[band_m_idx] ); + renormalization_factor_diff_q = reference_power_q; + move16(); + } + } + + FOR (band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++) + { + FOR (d = 0; d < DIRAC_NUM_DIMS; d++) + { + dir_v_fx[d] = hOMasa->direction_vector_m_fx[d][block_m_idx][band_m_idx]; + move32(); + } + dir_v_q = hOMasa->direction_vector_m_q; + + FOR (Word16 i = 0; i < DIRAC_NUM_DIMS; i++) + { + dir_v_fx[i] = L_shr(dir_v_fx[i], 1); + } + + dir_v_q = sub( dir_v_q, 1 ); + ivas_qmetadata_direction_vector_to_azimuth_elevation_fx( dir_v_fx, dir_v_q, &azimuth_m_values_fx[block_m_idx][band_m_idx], &elevation_m_values_fx[block_m_idx][band_m_idx] ); + } + + /* Determine energy ratios */ + FOR ( band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++ ) + { + IF ( BASOP_Util_Cmp_Mant32Exp( renormalization_factor_diff_fx[band_m_idx], sub( 31, renormalization_factor_diff_q ), L_deposit_h(EPSILON_FX), 2 ) > 0) + { + diffuseness_m_fx[band_m_idx] = BASOP_Util_Divide3232_Scale( diffuseness_m_fx[band_m_idx], renormalization_factor_diff_fx[band_m_idx], &scale ); + scale = add( scale, sub(sub(31, diffuseness_m_q), sub(31, renormalization_factor_diff_q)) ); + + diffuseness_m_fx[band_m_idx] = L_shr(diffuseness_m_fx[band_m_idx], sub( 31, add( scale, diffuseness_m_q ) ) ); + } + ELSE + { + diffuseness_m_fx[band_m_idx] = 0; + move32(); + } + energyRatio_fx[block_m_idx][band_m_idx] = L_sub( L_shl(1, diffuseness_m_q ), diffuseness_m_fx[band_m_idx] ); + } + + /* Set coherences to zero, as this mode is used at lowest bit rates where the coherences are not transmitted */ + FOR ( band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++ ) + { + spreadCoherence_fx[block_m_idx][band_m_idx] = 0; + move32(); + surroundingCoherence_fx[block_m_idx][band_m_idx] = 0; + move32(); + } + } + + *spreadCoherence_q = 0; + move16(); + *surroundingCoherence_q = 0; + move16(); + *energyRatio_q = 0; + move16(); + + return; +} + +#endif + +#ifdef IVAS_FLOAT_FIXED +/* Compute downmix */ +static void ivas_omasa_dmx_fx( + Word32 data_in_f_fx[][L_FRAME48k], + Word16 *data_in_q, + const Word16 input_frame, + const Word16 nchan_transport, + const Word16 nchan_ism, + const Word32 ism_azimuth_fx[MAX_NUM_OBJECTS], + const Word32 ism_elevation_fx[MAX_NUM_OBJECTS], + Word32 prev_gains_fx[][MASA_MAX_TRANSPORT_CHANNELS], + const Word16 interpolator_fx[L_FRAME48k]) +{ + Word16 i, j, k, l, tmp1, tmp2; + + Word16 azimuth_fx, elevation_fx; + Word16 gains_fx[MASA_MAX_TRANSPORT_CHANNELS]; + Word16 g1_fx, g2_fx, scale; + Word32 data_out_f_fx[MASA_MAX_TRANSPORT_CHANNELS][L_FRAME48k], L_tmp; + Word16 max_e, tmp_e; + Word16 in_e[960]; + Word16 data_e[4]; + + FOR ( i = 0; i < nchan_transport; i++ ) + { + set_zero_fx( data_out_f_fx[i], input_frame ); + } + set_s(data_e, 0, 4); + set_s(in_e, 0, 960); + + FOR ( i = 0; i < nchan_ism; i++ ) + { + + azimuth_fx = extract_l(L_shr( ism_azimuth_fx[i], Q22)); + elevation_fx = extract_l(L_shr( ism_elevation_fx[i], Q22 )); + + ivas_ism_get_stereo_gains_fx( azimuth_fx, elevation_fx, &gains_fx[0], &gains_fx[1] ); + + /* Downmix using the panning gains */ + FOR ( j = 0; j < nchan_transport; j++ ) + { + IF ( GT_32( L_abs( L_deposit_h( gains_fx[j] ) ), 0 ) || GT_32( L_abs( prev_gains_fx[i][j] ), 0 ) ) + { + FOR ( k = 0; k < input_frame; k++ ) + { + + g1_fx = interpolator_fx[k]; // Q15 + move16(); + scale = BASOP_Util_Add_MantExp(16384, 1, negate(g1_fx), 0, &g2_fx); + + tmp1 = mult(g1_fx, gains_fx[j]); + tmp2 = mult(g2_fx, (Word16)L_shr(prev_gains_fx[i][j], 16)); + scale = BASOP_Util_Add_MantExp(tmp1, 0, tmp2, scale, &tmp1); + + L_tmp = data_in_f_fx[i][k]; + move32(); + tmp_e = sub( 31, *data_in_q ); + move16(); + + L_tmp = Mpy_32_16_1(L_tmp, tmp1); + scale = add( scale, tmp_e ); + + data_out_f_fx[j][k] = BASOP_Util_Add_Mant32Exp(data_out_f_fx[j][k], data_e[j], L_tmp, scale, &in_e[k]); + + } + } + max_e = in_e[0]; + move16(); + FOR(l = 1; l < L_FRAME48k; l++) + { + IF(LT_16( max_e, in_e[l] ) ) + { + max_e = in_e[l]; + move16(); + } + } + + FOR(l = 0; l < L_FRAME48k; l++) + { + data_out_f_fx[j][l] = L_shr(data_out_f_fx[j][l], sub( max_e, in_e[l] ) ); + } + data_e[j] = max_e; + move16(); + + prev_gains_fx[i][j] = L_deposit_h( gains_fx[j] ); // Q31 + + } + } + + max_e = data_e[0]; + move16(); + FOR(i = 1; i < nchan_transport; i++) + { + IF( LT_16( max_e, data_e[i] ) ) + { + max_e = data_e[i]; + move16(); + } + } + + FOR(i = 0; i < nchan_transport; i++) + { + FOR(j = 0; j < input_frame; j++) + { + data_out_f_fx[i][j] = L_shr(data_out_f_fx[i][j], max_e - data_e[i]); + } + } + FOR ( i = 0; i < nchan_transport; i++ ) + { + Copy32(data_out_f_fx[i], data_in_f_fx[i], input_frame); + *data_in_q = sub( 31, max_e ); + move16(); + } + + return; +} +#endif /* Compute downmix */ +#ifndef IVAS_FLOAT_FIXED static void ivas_omasa_dmx( float data_in_f[][L_FRAME48k], const int16_t input_frame, @@ -490,14 +1182,7 @@ static void ivas_omasa_dmx( { azimuth = ism_azimuth[i]; elevation = ism_elevation[i]; -#ifdef IVAS_FLOAT_FIXED - Word16 gains_fx[2]; - ivas_ism_get_stereo_gains_fx( (Word16)azimuth, (Word16)elevation, &gains_fx[0], &gains_fx[1] ); - gains[0] = (float)gains_fx[0] / 32768.f; - gains[1] = (float)gains_fx[1] / 32768.f; -#else ivas_ism_get_stereo_gains( azimuth, elevation, &gains[0], &gains[1] ); -#endif /* Downmix using the panning gains */ for ( j = 0; j < nchan_transport; j++ ) @@ -522,6 +1207,8 @@ static void ivas_omasa_dmx( return; } +#endif + #ifdef IVAS_FLOAT_FIXED /*--------------------------------------------------------------------------* diff --git a/lib_rend/ivas_prot_rend.h b/lib_rend/ivas_prot_rend.h index 6c96ade839d3e18c0528787b49ecf9090cee82d6..727326b40ede03d04b7da26209a2b4fab8eadfa3 100644 --- a/lib_rend/ivas_prot_rend.h +++ b/lib_rend/ivas_prot_rend.h @@ -2646,11 +2646,19 @@ void ivas_mcmasa_ana_close( MCMASA_ANA_HANDLE *hMcMasa /* i/o: analysis McMASA handle */ ); +#ifdef IVAS_FLOAT_FIXED +ivas_error ivas_omasa_ana_open( + OMASA_ANA_HANDLE *hOMasaPtr, /* i/o: OMASA data handle pointer */ + Word32 input_Fs, /* i : Sampling frequency */ + UWord16 total_num_objects /* i : Number of objects */ +); +#else ivas_error ivas_omasa_ana_open( OMASA_ANA_HANDLE *hOMasaPtr, /* i/o: OMASA data handle pointer */ int32_t input_Fs, /* i : Sampling frequency */ uint16_t total_num_objects /* i : Number of objects */ ); +#endif void ivas_omasa_ana( OMASA_ANA_HANDLE hOMasa, /* i/o: OMASA analysis handle */ @@ -2660,6 +2668,18 @@ void ivas_omasa_ana( const int16_t nchan_ism /* i : Number of objects for parameter analysis*/ ); +#ifdef IVAS_FLOAT_FIXED +void ivas_omasa_ana_fx( + OMASA_ANA_HANDLE hOMasa, /* i/o: OMASA analysis handle */ + float data_in_f[][L_FRAME48k], /* i/o: Input / transport audio signals */ + Word32 data_in_f_fx[][L_FRAME48k], /* i/o: Input / transport audio signals */ + Word16 *q, + const Word16 input_frame, /* i : Input frame size */ + const Word16 nchan_transport, /* i : Number of transport channels */ + const Word16 nchan_ism /* i : Number of objects for parameter analysis*/ +); +#endif + void ivas_omasa_ana_close( OMASA_ANA_HANDLE *hOMasa /* i/o: analysis OMASA handle */ ); @@ -2695,6 +2715,7 @@ void computeReferencePower_ana( float *reference_power, /* o : Estimated power */ const int16_t num_freq_bands /* i : Number of frequency bands */ ); + #ifdef IVAS_FLOAT_FIXED void ivas_create_masa_out_meta_fx( MASA_DECODER_EXT_OUT_META_HANDLE extOutMeta, /* i/o: MASA metadata handle */ @@ -2708,9 +2729,9 @@ void ivas_create_masa_out_meta_fx( Word16 energyRatio_q, Word16 spreadCoherence_q, Word16 surroundingCoherence_q - ); #endif + void ivas_create_masa_out_meta( MASA_DECODER_EXT_OUT_META_HANDLE extOutMeta, /* i/o: MASA metadata handle */ SPHERICAL_GRID_DATA *Sph_Grid16, /* i : Spherical grid */ @@ -2770,17 +2791,39 @@ void ivas_prerend_merge_masa_metadata( float inEne2[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS] /* i : TF-energy of input 2 */ ); +#ifdef IVAS_FLOAT_FIXED +void ivas_prerend_merge_masa_metadata_fx( + MASA_DECODER_EXT_OUT_META_HANDLE outMeta, /* o : Merged metadata output */ + MASA_DECODER_EXT_OUT_META_HANDLE inMeta1, /* i : Input metadata 1 */ + IVAS_REND_AudioConfigType inType1, /* i : Type of input 1 */ + Word32 inEne1_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i/o: TF-energy of input 1. after merge, contains the energy of the merged signal */ + Word16 *inEne1_e, + MASA_DECODER_EXT_OUT_META_HANDLE inMeta2, /* i : Input metadata 2 */ + IVAS_REND_AudioConfigType inType2, /* i : Type of input 2 */ + Word32 inEne2_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS], /* i : TF-energy of input 2 */ + Word16 *inEne2_e /* i : TF-energy of input 2 */ +); +#endif + void copy_masa_descriptive_meta( MASA_DECRIPTIVE_META *outMeta, /* o : metadata to be written */ MASA_DECRIPTIVE_META *inMeta /* i : input metadata */ ); +#ifndef IVAS_FLOAT_FIXED ivas_error masaPrerendOpen( MASA_PREREND_HANDLE *hMasaPrerendPtr, /* o : handle to the opened prerenderer */ int16_t numTransports, /* i : number of transport channels */ int32_t input_Fs /* i : signal sampling rate */ ); +#else +ivas_error masaPrerendOpen( + MASA_PREREND_HANDLE *hMasaPrerendPtr, /* o : handle to the opened prerenderer */ + Word16 numTransports, /* i : number of transport channels */ + Word32 input_Fs /* i : signal sampling rate */ +); +#endif void masaPrerendClose( MASA_PREREND_HANDLE *hMasaPrerendPtr /* i/o: prerenderer handle to be closed */ ); diff --git a/lib_rend/ivas_rotation.c b/lib_rend/ivas_rotation.c index c9843bafd36ab60da885a85cdc07d74d00af075e..20043875f6568be29b7582521dbadddf92d6aac4 100644 --- a/lib_rend/ivas_rotation.c +++ b/lib_rend/ivas_rotation.c @@ -1900,7 +1900,7 @@ ivas_error ivas_combined_orientation_open( ( *hCombinedOrientationData )->subframe_idx = 0; move16(); - tmp = BASOP_Util_Divide3232_Scale( fs, MAX_PARAM__SPATIAL_SUB_FRAMES_PER_SEC, &tmp_e ); + tmp = BASOP_Util_Divide3232_Scale( fs, MAX_PARAM_SPATIAL_SUB_FRAMES_PER_SEC, &tmp_e ); ( *hCombinedOrientationData )->subframe_size = shr( tmp, sub( 15, tmp_e ) ); // ( *hCombinedOrientationData )->subframe_size = (int16_t) ( fs / ( FRAMES_PER_SEC * MAX_PARAM_SPATIAL_SUBFRAMES ) ); ( *hCombinedOrientationData )->cur_subframe_samples_rendered = 0; diff --git a/lib_rend/ivas_stat_rend.h b/lib_rend/ivas_stat_rend.h index f961f6dfc947c4d0df94f46fabdbfb5ba1a4c86f..731afcdd0a193f66ae1f0542e37140c0c60b7d47 100644 --- a/lib_rend/ivas_stat_rend.h +++ b/lib_rend/ivas_stat_rend.h @@ -2358,12 +2358,18 @@ typedef struct ivas_omasa_ana_data_structure HANDLE_CLDFB_FILTER_BANK cldfbAnaEnc[MAX_NUM_OBJECTS]; /* DirAC parameter estimation */ + +#ifndef IVAS_FLOAT_FIXED float **direction_vector_m[DIRAC_NUM_DIMS]; /* Average direction vector */ +#endif + int16_t band_grouping[MASA_FREQUENCY_BANDS + 1]; int16_t block_grouping[5]; /* diffuseness */ int16_t index_buffer_intensity; + +#ifndef IVAS_FLOAT_FIXED float *buffer_intensity_real[DIRAC_NUM_DIMS][DIRAC_NO_COL_AVG_DIFF]; float buffer_energy[DIRAC_NO_COL_AVG_DIFF * MASA_FREQUENCY_BANDS]; @@ -2372,13 +2378,35 @@ typedef struct ivas_omasa_ana_data_structure float interpolator[L_FRAME48k]; float prev_object_dm_gains[MAX_NUM_OBJECTS][MASA_MAX_TRANSPORT_CHANNELS]; +#endif MASA_DECODER_EXT_OUT_META_HANDLE hMasaOut; SPHERICAL_GRID_DATA *sph_grid16; +#ifndef IVAS_FLOAT_FIXED float ism_azimuth[MAX_NUM_OBJECTS]; float ism_elevation[MAX_NUM_OBJECTS]; +#endif float energy[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; +#ifdef IVAS_FLOAT_FIXED + Word32 **direction_vector_m_fx[DIRAC_NUM_DIMS]; /* Average direction vector */ + Word16 direction_vector_m_q; /* Average direction vector */ + Word32 ism_azimuth_fx[MAX_NUM_OBJECTS]; + Word32 ism_elevation_fx[MAX_NUM_OBJECTS]; + + Word32 energy_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word16 energy_q; + Word16 energy_e[MAX_PARAM_SPATIAL_SUBFRAMES]; + Word16 interpolator_fx[L_FRAME48k]; + Word32 prev_object_dm_gains_fx[MAX_NUM_OBJECTS][MASA_MAX_TRANSPORT_CHANNELS]; + + Word32 *buffer_intensity_real_fx[DIRAC_NUM_DIMS][DIRAC_NO_COL_AVG_DIFF]; + Word32 buffer_energy_fx[DIRAC_NO_COL_AVG_DIFF * MASA_FREQUENCY_BANDS]; + Word16 buffer_intensity_real_q[DIRAC_NO_COL_AVG_DIFF]; + Word32 buffer_energy_q[DIRAC_NO_COL_AVG_DIFF]; + Word16 chnlToFoaMtx_fx[FOA_CHANNELS][MCMASA_MAX_ANA_CHANS]; // Q15 + +#endif } OMASA_ANA_DATA, *OMASA_ANA_HANDLE; @@ -2419,7 +2447,10 @@ typedef struct ivas_dirac_ana_data_structure SPHERICAL_GRID_DATA *sph_grid16; float energy[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; +#ifdef IVAS_FLOAT_FIXED Word32 energy_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word16 energy_e[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; +#endif } DIRAC_ANA_DATA, *DIRAC_ANA_HANDLE; #else @@ -2462,6 +2493,10 @@ typedef struct ivas_masa_prerend_data_structure SPHERICAL_GRID_DATA *sph_grid16; float energy[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; +#ifdef IVAS_FLOAT_FIXED + Word32 energy_fx[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word16 energy_e[MAX_PARAM_SPATIAL_SUBFRAMES]; +#endif } MASA_PREREND_DATA, *MASA_PREREND_HANDLE; diff --git a/lib_rend/lib_rend.c b/lib_rend/lib_rend.c index dbb301be66b553d59f813f465ba962f9d3d04917..a1f9b99544880932fddf7e79d73fcd5e68e01e56 100644 --- a/lib_rend/lib_rend.c +++ b/lib_rend/lib_rend.c @@ -193,13 +193,13 @@ typedef struct { Word16 numLfeChannels; bool pan_lfe; - //float lfeInputGain; + // float lfeInputGain; Word32 lfeInputGain_fx; - //float lfeOutputAzimuth; + // float lfeOutputAzimuth; Word16 lfeOutputAzimuth_fx; - //float lfeOutputElevation; + // float lfeOutputElevation; Word16 lfeOutputElevation_fx; - //IVAS_REND_LfePanMtx lfePanMtx; + // IVAS_REND_LfePanMtx lfePanMtx; IVAS_REND_LfePanMtx_fx lfePanMtx_fx; } lfe_routing; #else @@ -269,7 +269,7 @@ typedef struct typedef struct { input_base base; - //pan_matrix hoaDecMtx; + // pan_matrix hoaDecMtx; pan_matrix_fx hoaDecMtx_fx; CREND_WRAPPER_HANDLE crendWrapper; rotation_gains rot_gains_prev; @@ -296,6 +296,9 @@ typedef struct input_base base; MASA_METADATA_FRAME masaMetadata; bool metadataHasBeenFed; +#ifdef IVAS_FLOAT_FIXED + Word32 *bufferData_fx; +#endif // IVAS_FLOAT_FIXED float *bufferData; MASA_EXT_REND_HANDLE hMasaExtRend; MASA_PREREND_HANDLE hMasaPrerend; @@ -822,7 +825,7 @@ IVAS_REND_AudioConfigType getAudioConfigType( } #else IVAS_REND_AudioConfigType getAudioConfigType( - const AUDIO_CONFIG config) + const AUDIO_CONFIG config ) { IVAS_REND_AudioConfigType type; @@ -1072,12 +1075,12 @@ static ivas_error initLimiter( return error; } // The below code has to be deleted once whole conversion is completed - (*phLimiter)->gain = 1.0f; - (*phLimiter)->release_heuristic = 0.f; - (*phLimiter)->attack_constant = powf( 0.01f, 1.0f / ( IVAS_LIMITER_ATTACK_SECONDS * sampleRate ) ); + ( *phLimiter )->gain = 1.0f; + ( *phLimiter )->release_heuristic = 0.f; + ( *phLimiter )->attack_constant = powf( 0.01f, 1.0f / ( IVAS_LIMITER_ATTACK_SECONDS * sampleRate ) ); for ( Word32 i = 0; i < numChannels; ++i ) { - (*phLimiter)->channel_ptrs[i] = NULL; + ( *phLimiter )->channel_ptrs[i] = NULL; } // Till this line. @@ -1301,7 +1304,7 @@ static ivas_error getAmbisonicsOrder_fx( AUDIO_CONFIG config, Word16 *order ) { - SWITCH ( config ) + SWITCH( config ) { case IVAS_AUDIO_CONFIG_FOA: *order = 1; @@ -1596,14 +1599,11 @@ static ivas_error initEfap( const LSSETUP_CUSTOM_STRUCT *pCustomLsOut ) { ivas_error error; - const float *azimuths; - const float *elevations; - /*To be replaced with pointers*/ - Word32 azimuths_fx[MAX_OUTPUT_CHANNELS]; - Word32 elevations_fx[MAX_OUTPUT_CHANNELS]; + const Word32 *azimuths; + const Word32 *elevations; Word16 numNonLfeChannels; - IF ( outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR || outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB ) + IF( outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR || outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB ) { pEfapWrapper->speakerConfig = IVAS_AUDIO_CONFIG_7_1_4; } @@ -1614,51 +1614,42 @@ static ivas_error initEfap( pEfapWrapper->pCustomLsSetup = pCustomLsOut; /* If re-initializing, free existing EFAP handle. */ - IF ( pEfapWrapper->hEfap != NULL ) + IF( pEfapWrapper->hEfap != NULL ) { efap_free_data( &pEfapWrapper->hEfap ); } /* Only initialize EFAP handle if output config is channel-based */ - IF ( getAudioConfigType( pEfapWrapper->speakerConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) + IF( getAudioConfigType( pEfapWrapper->speakerConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) { pEfapWrapper->hEfap = NULL; return IVAS_ERR_OK; } - IF ( outConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) + IF( outConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) { - /*float2fix block: to be removed*/ - floatToFixed_arrL( (float *) pCustomLsOut->ls_azimuth, (Word32 *) pCustomLsOut->ls_azimuth_fx, Q22, pCustomLsOut->num_spk ); - floatToFixed_arrL( (float *) pCustomLsOut->ls_elevation, (Word32 *) pCustomLsOut->ls_elevation_fx, Q22, pCustomLsOut->num_spk ); - /*float2fix block end*/ - if ( ( error = efap_init_data_fx( &pEfapWrapper->hEfap, pCustomLsOut->ls_azimuth_fx, pCustomLsOut->ls_elevation_fx, pCustomLsOut->num_spk, EFAP_MODE_EFAP ) ) != IVAS_ERR_OK ) + IF ( ( error = efap_init_data_fx( &pEfapWrapper->hEfap, pCustomLsOut->ls_azimuth_fx, pCustomLsOut->ls_elevation_fx, pCustomLsOut->num_spk, EFAP_MODE_EFAP ) ) != IVAS_ERR_OK ) { return error; } } ELSE { - IF ( ( error = getSpeakerAzimuths( pEfapWrapper->speakerConfig, &azimuths ) ) != IVAS_ERR_OK ) + IF( ( error = getSpeakerAzimuths_fx( pEfapWrapper->speakerConfig, &azimuths ) ) != IVAS_ERR_OK ) { return error; } - IF ( ( error = getSpeakerElevations( pEfapWrapper->speakerConfig, &elevations ) ) != IVAS_ERR_OK ) + IF( ( error = getSpeakerElevations_fx( pEfapWrapper->speakerConfig, &elevations ) ) != IVAS_ERR_OK ) { return error; } - IF ( ( error = getNumNonLfeChannelsInSpeakerLayout( pEfapWrapper->speakerConfig, &numNonLfeChannels ) ) != IVAS_ERR_OK ) + IF( ( error = getNumNonLfeChannelsInSpeakerLayout( pEfapWrapper->speakerConfig, &numNonLfeChannels ) ) != IVAS_ERR_OK ) { return error; } - - /*float2fix block: to be removed*/ - floatToFixed_arrL( (float *) azimuths, azimuths_fx, Q22, numNonLfeChannels ); - floatToFixed_arrL( (float *) elevations, elevations_fx, Q22, numNonLfeChannels ); - /*float2fix block end*/ - IF ( ( error = efap_init_data_fx( &pEfapWrapper->hEfap, azimuths_fx, elevations_fx, numNonLfeChannels, EFAP_MODE_EFAP ) ) != IVAS_ERR_OK ) + IF( ( error = efap_init_data_fx( &pEfapWrapper->hEfap, azimuths, elevations, numNonLfeChannels, EFAP_MODE_EFAP ) ) != IVAS_ERR_OK ) { return error; } @@ -1667,71 +1658,71 @@ static ivas_error initEfap( return IVAS_ERR_OK; } #else -static ivas_error initEfap( - EFAP_WRAPPER *pEfapWrapper, - AUDIO_CONFIG outConfig, - const LSSETUP_CUSTOM_STRUCT *pCustomLsOut ) -{ - ivas_error error; - const float *azimuths; - const float *elevations; - int16_t numNonLfeChannels; + static ivas_error initEfap( + EFAP_WRAPPER * pEfapWrapper, + AUDIO_CONFIG outConfig, + const LSSETUP_CUSTOM_STRUCT *pCustomLsOut ) + { + ivas_error error; + const float *azimuths; + const float *elevations; + int16_t numNonLfeChannels; - if ( outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR || outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB ) - { - pEfapWrapper->speakerConfig = IVAS_AUDIO_CONFIG_7_1_4; - } - else - { - pEfapWrapper->speakerConfig = outConfig; - } - pEfapWrapper->pCustomLsSetup = pCustomLsOut; + if ( outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR || outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB ) + { + pEfapWrapper->speakerConfig = IVAS_AUDIO_CONFIG_7_1_4; + } + else + { + pEfapWrapper->speakerConfig = outConfig; + } + pEfapWrapper->pCustomLsSetup = pCustomLsOut; - /* If re-initializing, free existing EFAP handle. */ - if ( pEfapWrapper->hEfap != NULL ) - { - efap_free_data( &pEfapWrapper->hEfap ); - } + /* If re-initializing, free existing EFAP handle. */ + if ( pEfapWrapper->hEfap != NULL ) + { + efap_free_data( &pEfapWrapper->hEfap ); + } - /* Only initialize EFAP handle if output config is channel-based */ - if ( getAudioConfigType( pEfapWrapper->speakerConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) - { - pEfapWrapper->hEfap = NULL; - return IVAS_ERR_OK; - } + /* Only initialize EFAP handle if output config is channel-based */ + if ( getAudioConfigType( pEfapWrapper->speakerConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) + { + pEfapWrapper->hEfap = NULL; + return IVAS_ERR_OK; + } - if ( outConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) - { - if ( ( error = efap_init_data( &pEfapWrapper->hEfap, pCustomLsOut->ls_azimuth, pCustomLsOut->ls_elevation, pCustomLsOut->num_spk, EFAP_MODE_EFAP ) ) != IVAS_ERR_OK ) - { - return error; - } - } - else - { - if ( ( error = getSpeakerAzimuths( pEfapWrapper->speakerConfig, &azimuths ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( outConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) + { + if ( ( error = efap_init_data( &pEfapWrapper->hEfap, pCustomLsOut->ls_azimuth, pCustomLsOut->ls_elevation, pCustomLsOut->num_spk, EFAP_MODE_EFAP ) ) != IVAS_ERR_OK ) + { + return error; + } + } + else + { + if ( ( error = getSpeakerAzimuths( pEfapWrapper->speakerConfig, &azimuths ) ) != IVAS_ERR_OK ) + { + return error; + } - if ( ( error = getSpeakerElevations( pEfapWrapper->speakerConfig, &elevations ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = getSpeakerElevations( pEfapWrapper->speakerConfig, &elevations ) ) != IVAS_ERR_OK ) + { + return error; + } - if ( ( error = getNumNonLfeChannelsInSpeakerLayout( pEfapWrapper->speakerConfig, &numNonLfeChannels ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = getNumNonLfeChannelsInSpeakerLayout( pEfapWrapper->speakerConfig, &numNonLfeChannels ) ) != IVAS_ERR_OK ) + { + return error; + } - if ( ( error = efap_init_data( &pEfapWrapper->hEfap, azimuths, elevations, numNonLfeChannels, EFAP_MODE_EFAP ) ) != IVAS_ERR_OK ) - { - return error; - } - } + if ( ( error = efap_init_data( &pEfapWrapper->hEfap, azimuths, elevations, numNonLfeChannels, EFAP_MODE_EFAP ) ) != IVAS_ERR_OK ) + { + return error; + } + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED @@ -1803,67 +1794,67 @@ static ivas_error getEfapGains_fx( return IVAS_ERR_OK; } #else -static ivas_error getEfapGains( - EFAP_WRAPPER efapWrapper, - const float azi, - const float ele, - pan_vector panGains ) -{ - pan_vector tmpPanGains; /* tmp pan gain buffer without LFE channels */ - float *readPtr; - int16_t i; - int16_t lfeCount; - int16_t numChannels; - ivas_error error; - - /* EFAP returns an array of gains only for non-LFE speakers */ - efap_determine_gains( efapWrapper.hEfap, tmpPanGains, azi, ele, EFAP_MODE_EFAP ); + static ivas_error getEfapGains( + EFAP_WRAPPER efapWrapper, + const float azi, + const float ele, + pan_vector panGains ) + { + pan_vector tmpPanGains; /* tmp pan gain buffer without LFE channels */ + float *readPtr; + int16_t i; + int16_t lfeCount; + int16_t numChannels; + ivas_error error; - /* Now copy to buffer that includes LFE channels */ - if ( efapWrapper.speakerConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) - { - numChannels = efapWrapper.pCustomLsSetup->num_spk + efapWrapper.pCustomLsSetup->num_lfe; - readPtr = tmpPanGains; + /* EFAP returns an array of gains only for non-LFE speakers */ + efap_determine_gains( efapWrapper.hEfap, tmpPanGains, azi, ele, EFAP_MODE_EFAP ); - for ( i = 0, lfeCount = 0; i < numChannels; ++i ) - { - if ( lfeCount < efapWrapper.pCustomLsSetup->num_lfe && i == efapWrapper.pCustomLsSetup->lfe_idx[lfeCount] ) + /* Now copy to buffer that includes LFE channels */ + if ( efapWrapper.speakerConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) { - panGains[i] = 0.0f; - ++lfeCount; + numChannels = efapWrapper.pCustomLsSetup->num_spk + efapWrapper.pCustomLsSetup->num_lfe; + readPtr = tmpPanGains; + + for ( i = 0, lfeCount = 0; i < numChannels; ++i ) + { + if ( lfeCount < efapWrapper.pCustomLsSetup->num_lfe && i == efapWrapper.pCustomLsSetup->lfe_idx[lfeCount] ) + { + panGains[i] = 0.0f; + ++lfeCount; + } + else + { + panGains[i] = *readPtr; + ++readPtr; + } + } } else { - panGains[i] = *readPtr; - ++readPtr; - } - } - } - else - { - if ( ( error = getAudioConfigNumChannels( efapWrapper.speakerConfig, &numChannels ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = getAudioConfigNumChannels( efapWrapper.speakerConfig, &numChannels ) ) != IVAS_ERR_OK ) + { + return error; + } - readPtr = tmpPanGains; + readPtr = tmpPanGains; - for ( i = 0; i < numChannels; ++i ) - { - if ( i == LFE_CHANNEL ) - { - panGains[i] = 0.0f; - } - else - { - panGains[i] = *readPtr; - ++readPtr; + for ( i = 0; i < numChannels; ++i ) + { + if ( i == LFE_CHANNEL ) + { + panGains[i] = 0.0f; + } + else + { + panGains[i] = *readPtr; + ++readPtr; + } + } } - } - } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED @@ -1909,43 +1900,43 @@ static ivas_error initHeadRotation_fx( return IVAS_ERR_OK; } #else -static ivas_error initHeadRotation( - IVAS_REND_HANDLE hIvasRend ) -{ - int16_t i, crossfade_len; - float tmp; - ivas_error error; + static ivas_error initHeadRotation( + IVAS_REND_HANDLE hIvasRend ) + { + int16_t i, crossfade_len; + float tmp; + ivas_error error; - /* Head rotation is enabled by default */ - hIvasRend->headRotData.headRotEnabled = 1; + /* Head rotation is enabled by default */ + hIvasRend->headRotData.headRotEnabled = 1; - /* Initialize 5ms crossfade */ - crossfade_len = L_FRAME48k / MAX_PARAM_SPATIAL_SUBFRAMES; - tmp = 1.f / ( crossfade_len - 1 ); - for ( i = 0; i < crossfade_len; i++ ) - { - hIvasRend->headRotData.crossfade[i] = i * tmp; - } + /* Initialize 5ms crossfade */ + crossfade_len = L_FRAME48k / MAX_PARAM_SPATIAL_SUBFRAMES; + tmp = 1.f / ( crossfade_len - 1 ); + for ( i = 0; i < crossfade_len; i++ ) + { + hIvasRend->headRotData.crossfade[i] = i * tmp; + } - /* Initialize with unit quaternions */ - for ( i = 0; i < hIvasRend->num_subframes; ++i ) - { - hIvasRend->headRotData.headPositions[i] = quaternionInit(); - } + /* Initialize with unit quaternions */ + for ( i = 0; i < hIvasRend->num_subframes; ++i ) + { + hIvasRend->headRotData.headPositions[i] = quaternionInit(); + } - if ( ( hIvasRend->headRotData.hOrientationTracker = (ivas_orient_trk_state_t *) malloc( sizeof( ivas_orient_trk_state_t ) ) ) == NULL ) - { - return IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for Orientation tracking" ); - } + if ( ( hIvasRend->headRotData.hOrientationTracker = (ivas_orient_trk_state_t *) malloc( sizeof( ivas_orient_trk_state_t ) ) ) == NULL ) + { + return IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for Orientation tracking" ); + } - if ( ( error = ivas_orient_trk_Init( hIvasRend->headRotData.hOrientationTracker ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = ivas_orient_trk_Init( hIvasRend->headRotData.hOrientationTracker ) ) != IVAS_ERR_OK ) + { + return error; + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif @@ -1962,16 +1953,16 @@ static void closeHeadRotation( return; } #else -static void closeHeadRotation( - IVAS_REND_HANDLE hIvasRend ) -{ - if ( ( hIvasRend != NULL ) && ( hIvasRend->headRotData.hOrientationTracker != NULL ) ) - { - free( hIvasRend->headRotData.hOrientationTracker ); - } + static void closeHeadRotation( + IVAS_REND_HANDLE hIvasRend ) + { + if ( ( hIvasRend != NULL ) && ( hIvasRend->headRotData.hOrientationTracker != NULL ) ) + { + free( hIvasRend->headRotData.hOrientationTracker ); + } - return; -} + return; + } #endif @@ -2147,17 +2138,17 @@ static TDREND_WRAPPER defaultTdRendWrapper( return w; } #else -static TDREND_WRAPPER defaultTdRendWrapper( - void ) -{ - TDREND_WRAPPER w; + static TDREND_WRAPPER defaultTdRendWrapper( + void ) + { + TDREND_WRAPPER w; - w.binaural_latency_ns = 0; - w.hBinRendererTd = NULL; - w.hHrtfTD = NULL; + w.binaural_latency_ns = 0; + w.hBinRendererTd = NULL; + w.hHrtfTD = NULL; - return w; -} + return w; + } #endif @@ -2178,19 +2169,19 @@ static bool isIoConfigPairSupported( return true; } #else -static bool isIoConfigPairSupported( - const AUDIO_CONFIG inConfig, - const AUDIO_CONFIG outConfig ) -{ - /* Rendering mono or stereo to binaural is not supported */ - if ( ( inConfig == IVAS_AUDIO_CONFIG_MONO || inConfig == IVAS_AUDIO_CONFIG_STEREO ) && getAudioConfigType( outConfig ) == IVAS_REND_AUDIO_CONFIG_TYPE_BINAURAL ) - { - return false; - } + static bool isIoConfigPairSupported( + const AUDIO_CONFIG inConfig, + const AUDIO_CONFIG outConfig ) + { + /* Rendering mono or stereo to binaural is not supported */ + if ( ( inConfig == IVAS_AUDIO_CONFIG_MONO || inConfig == IVAS_AUDIO_CONFIG_STEREO ) && getAudioConfigType( outConfig ) == IVAS_REND_AUDIO_CONFIG_TYPE_BINAURAL ) + { + return false; + } - /* If not returned so far, config pair is supported */ - return true; -} + /* If not returned so far, config pair is supported */ + return true; + } #endif @@ -2205,7 +2196,7 @@ static ivas_error initIsmMasaRendering( #ifdef IVAS_FLOAT_FIXED ivas_td_binaural_close_fx( &inputIsm->tdRendWrapper.hBinRendererTd ); #else - ivas_td_binaural_close( &inputIsm->tdRendWrapper.hBinRendererTd ); + ivas_td_binaural_close( &inputIsm->tdRendWrapper.hBinRendererTd ); #endif // IVAS_FLOAT_FIXED inputIsm->tdRendWrapper.hHrtfTD = NULL; } @@ -2322,15 +2313,16 @@ static ivas_error setRendInputActiveIsm( if ( outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB ) { #ifdef IVAS_FLOAT_FIXED - if ( ( error = ivas_reverb_open_fx( &( inputIsm->hReverb ), outConfig, NULL,inputIsm->tdRendWrapper.hBinRendererTd->HrFiltSet_p->lr_energy_and_iac_fx, hRendCfg, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) + + if ( ( error = ivas_reverb_open_fx( &( inputIsm->hReverb ), outConfig, NULL, inputIsm->tdRendWrapper.hBinRendererTd->HrFiltSet_p->lr_energy_and_iac_fx, hRendCfg, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) { return error; } #else - if ( ( error = ivas_reverb_open( &( inputIsm->hReverb ), outConfig, NULL, inputIsm->tdRendWrapper.hBinRendererTd->HrFiltSet_p->lr_energy_and_iac, hRendCfg, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = ivas_reverb_open( &( inputIsm->hReverb ), outConfig, NULL, inputIsm->tdRendWrapper.hBinRendererTd->HrFiltSet_p->lr_energy_and_iac, hRendCfg, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) + { + return error; + } #endif // IVAS_FLOAT_FIXED } } @@ -2359,7 +2351,7 @@ static void clearInputIsm( #ifdef IVAS_FLOAT_FIXED ivas_td_binaural_close_fx( &inputIsm->tdRendWrapper.hBinRendererTd ); #else - ivas_td_binaural_close( &inputIsm->tdRendWrapper.hBinRendererTd ); + ivas_td_binaural_close( &inputIsm->tdRendWrapper.hBinRendererTd ); #endif inputIsm->tdRendWrapper.hHrtfTD = NULL; } @@ -2405,29 +2397,29 @@ static void copyLsConversionMatrixToPanMatrix_fx( } #else -static void copyLsConversionMatrixToPanMatrix( - const LS_CONVERSION_MATRIX *lsConvMatrix, - pan_matrix panMatrix ) -{ - int16_t i; - int16_t inCh, outCh; - int16_t numNonZeroGains; - int16_t numColumns; + static void copyLsConversionMatrixToPanMatrix( + const LS_CONVERSION_MATRIX *lsConvMatrix, + pan_matrix panMatrix ) + { + int16_t i; + int16_t inCh, outCh; + int16_t numNonZeroGains; + int16_t numColumns; - /* Index 0 is special and describes the following values */ - numNonZeroGains = lsConvMatrix[0].index; - numColumns = (int16_t) lsConvMatrix[0].value; + /* Index 0 is special and describes the following values */ + numNonZeroGains = lsConvMatrix[0].index; + numColumns = (int16_t) lsConvMatrix[0].value; - for ( i = 1; i < numNonZeroGains + 1; ++i ) - { - inCh = lsConvMatrix[i].index / numColumns; - outCh = lsConvMatrix[i].index % numColumns; + for ( i = 1; i < numNonZeroGains + 1; ++i ) + { + inCh = lsConvMatrix[i].index / numColumns; + outCh = lsConvMatrix[i].index % numColumns; - panMatrix[inCh][outCh] = lsConvMatrix[i].value; - } + panMatrix[inCh][outCh] = lsConvMatrix[i].value; + } - return; -} + return; + } #endif static void setZeroPanMatrix( pan_matrix panMatrix ) @@ -2471,19 +2463,19 @@ static void fillIdentityPanMatrix_fx( return; } #else -/* Note: this only sets non-zero elements, call setZeroPanMatrix() to init first. */ -static void fillIdentityPanMatrix( - pan_matrix panMatrix ) -{ - int16_t i; + /* Note: this only sets non-zero elements, call setZeroPanMatrix() to init first. */ + static void fillIdentityPanMatrix( + pan_matrix panMatrix ) + { + int16_t i; - for ( i = 0; i < min( MAX_INPUT_CHANNELS, MAX_OUTPUT_CHANNELS ); ++i ) - { - panMatrix[i][i] = 1.0f; - } + for ( i = 0; i < min( MAX_INPUT_CHANNELS, MAX_OUTPUT_CHANNELS ); ++i ) + { + panMatrix[i][i] = 1.0f; + } - return; -} + return; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error initMcPanGainsWithIdentMatrix( @@ -2494,13 +2486,13 @@ static ivas_error initMcPanGainsWithIdentMatrix( return IVAS_ERR_OK; } #else -static ivas_error initMcPanGainsWithIdentMatrix( - input_mc *inputMc ) -{ - fillIdentityPanMatrix( inputMc->panGains ); + static ivas_error initMcPanGainsWithIdentMatrix( + input_mc * inputMc ) + { + fillIdentityPanMatrix( inputMc->panGains ); - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED @@ -2542,39 +2534,39 @@ static ivas_error initMcPanGainsWithConversionMapping_fx( } #else -static ivas_error initMcPanGainsWithConversionMapping( - input_mc *inputMc, - const AUDIO_CONFIG outConfig ) -{ - AUDIO_CONFIG ivasConfigIn, ivasConfigOut; - int16_t i; + static ivas_error initMcPanGainsWithConversionMapping( + input_mc * inputMc, + const AUDIO_CONFIG outConfig ) + { + AUDIO_CONFIG ivasConfigIn, ivasConfigOut; + int16_t i; - ivasConfigIn = inputMc->base.inConfig; - ivasConfigOut = outConfig; + ivasConfigIn = inputMc->base.inConfig; + ivasConfigOut = outConfig; - /* Find conversion mapping for current I/O config pair. - * Stay with default panning matrix if conversion_matrix is NULL */ - for ( i = 0; i < LS_SETUP_CONVERSION_NUM_MAPPINGS; ++i ) - { - if ( ls_conversion_mapping[i].input_config == ivasConfigIn && ls_conversion_mapping[i].output_config == ivasConfigOut ) - { - /* Mapping found with valid matrix - copy */ - if ( ls_conversion_mapping[i].conversion_matrix != NULL ) - { - copyLsConversionMatrixToPanMatrix( ls_conversion_mapping[i].conversion_matrix, inputMc->panGains ); - } - /* Mapping found with NULL matrix - use identity matrix */ - else + /* Find conversion mapping for current I/O config pair. + * Stay with default panning matrix if conversion_matrix is NULL */ + for ( i = 0; i < LS_SETUP_CONVERSION_NUM_MAPPINGS; ++i ) { - fillIdentityPanMatrix( inputMc->panGains ); + if ( ls_conversion_mapping[i].input_config == ivasConfigIn && ls_conversion_mapping[i].output_config == ivasConfigOut ) + { + /* Mapping found with valid matrix - copy */ + if ( ls_conversion_mapping[i].conversion_matrix != NULL ) + { + copyLsConversionMatrixToPanMatrix( ls_conversion_mapping[i].conversion_matrix, inputMc->panGains ); + } + /* Mapping found with NULL matrix - use identity matrix */ + else + { + fillIdentityPanMatrix( inputMc->panGains ); + } + + return IVAS_ERR_OK; + } } - return IVAS_ERR_OK; + return IVAS_ERROR( IVAS_ERR_INTERNAL_FATAL, "Missing multichannel conversion mapping" ); } - } - - return IVAS_ERROR( IVAS_ERR_INTERNAL_FATAL, "Missing multichannel conversion mapping" ); -} #endif #ifdef IVAS_FLOAT_FIXED static ivas_error initMcPanGainsWithEfap_fx( @@ -2653,71 +2645,71 @@ static ivas_error initMcPanGainsWithEfap_fx( return IVAS_ERR_OK; } #else -static ivas_error initMcPanGainsWithEfap( - input_mc *inputMc, - const AUDIO_CONFIG outConfig ) -{ - int16_t i; - int16_t numNonLfeInChannels; - int16_t inLfeChIdx, outChIdx; - const float *spkAzi, *spkEle; - ivas_error error; - - if ( inputMc->base.inConfig != IVAS_AUDIO_CONFIG_LS_CUSTOM ) - { - if ( ( error = getNumNonLfeChannelsInSpeakerLayout( inputMc->base.inConfig, &numNonLfeInChannels ) ) != IVAS_ERR_OK ) + static ivas_error initMcPanGainsWithEfap( + input_mc * inputMc, + const AUDIO_CONFIG outConfig ) { - return error; - } + int16_t i; + int16_t numNonLfeInChannels; + int16_t inLfeChIdx, outChIdx; + const float *spkAzi, *spkEle; + ivas_error error; - if ( ( error = getSpeakerAzimuths( inputMc->base.inConfig, &spkAzi ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( inputMc->base.inConfig != IVAS_AUDIO_CONFIG_LS_CUSTOM ) + { + if ( ( error = getNumNonLfeChannelsInSpeakerLayout( inputMc->base.inConfig, &numNonLfeInChannels ) ) != IVAS_ERR_OK ) + { + return error; + } - if ( ( error = getSpeakerElevations( inputMc->base.inConfig, &spkEle ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = getSpeakerAzimuths( inputMc->base.inConfig, &spkAzi ) ) != IVAS_ERR_OK ) + { + return error; + } - inLfeChIdx = LFE_CHANNEL; - } - else - { - numNonLfeInChannels = inputMc->customLsInput.num_spk; - spkAzi = inputMc->customLsInput.ls_azimuth; - spkEle = inputMc->customLsInput.ls_elevation; - inLfeChIdx = -1; - if ( inputMc->customLsInput.num_lfe > 0 ) - { - inLfeChIdx = inputMc->customLsInput.lfe_idx[0]; - } - } + if ( ( error = getSpeakerElevations( inputMc->base.inConfig, &spkEle ) ) != IVAS_ERR_OK ) + { + return error; + } - for ( i = 0, outChIdx = 0; i < numNonLfeInChannels; ++i, ++outChIdx ) - { - if ( i == inLfeChIdx ) - { - ++outChIdx; - } + inLfeChIdx = LFE_CHANNEL; + } + else + { + numNonLfeInChannels = inputMc->customLsInput.num_spk; + spkAzi = inputMc->customLsInput.ls_azimuth; + spkEle = inputMc->customLsInput.ls_elevation; + inLfeChIdx = -1; + if ( inputMc->customLsInput.num_lfe > 0 ) + { + inLfeChIdx = inputMc->customLsInput.lfe_idx[0]; + } + } - if ( ( error = getEfapGains( *inputMc->base.ctx.pEfapOutWrapper, spkAzi[i], spkEle[i], inputMc->panGains[outChIdx] ) ) != IVAS_ERR_OK ) - { - return error; - } - } + for ( i = 0, outChIdx = 0; i < numNonLfeInChannels; ++i, ++outChIdx ) + { + if ( i == inLfeChIdx ) + { + ++outChIdx; + } - if ( outConfig != IVAS_AUDIO_CONFIG_LS_CUSTOM && inLfeChIdx >= 0 ) - { - inputMc->panGains[inLfeChIdx][LFE_CHANNEL] = 1; - } - else if ( inputMc->base.ctx.pCustomLsOut->num_lfe > 0 && inLfeChIdx >= 0 ) - { - inputMc->panGains[inLfeChIdx][inputMc->base.ctx.pCustomLsOut->lfe_idx[0]] = 1; - } + if ( ( error = getEfapGains( *inputMc->base.ctx.pEfapOutWrapper, spkAzi[i], spkEle[i], inputMc->panGains[outChIdx] ) ) != IVAS_ERR_OK ) + { + return error; + } + } - return IVAS_ERR_OK; -} + if ( outConfig != IVAS_AUDIO_CONFIG_LS_CUSTOM && inLfeChIdx >= 0 ) + { + inputMc->panGains[inLfeChIdx][LFE_CHANNEL] = 1; + } + else if ( inputMc->base.ctx.pCustomLsOut->num_lfe > 0 && inLfeChIdx >= 0 ) + { + inputMc->panGains[inLfeChIdx][inputMc->base.ctx.pCustomLsOut->lfe_idx[0]] = 1; + } + + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error getRendInputNumChannels( @@ -2749,34 +2741,34 @@ static ivas_error getRendInputNumChannels( return IVAS_ERR_OK; } #else -static ivas_error getRendInputNumChannels( - const void *rendInput, - int16_t *numInChannels ) -{ - /* Using a void pointer for this function to be reusable for any input type (input_ism, input_mc, input_sba). - Assumptions: - input_base is always the first member in the input struct */ + static ivas_error getRendInputNumChannels( + const void *rendInput, + int16_t *numInChannels ) + { + /* Using a void pointer for this function to be reusable for any input type (input_ism, input_mc, input_sba). + Assumptions: - input_base is always the first member in the input struct */ - ivas_error error; - const input_base *pInputBase; - const input_mc *pInputMc; + ivas_error error; + const input_base *pInputBase; + const input_mc *pInputMc; - pInputBase = (const input_base *) rendInput; + pInputBase = (const input_base *) rendInput; - if ( pInputBase->inConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) - { - pInputMc = (const input_mc *) rendInput; - *numInChannels = pInputMc->customLsInput.num_spk + pInputMc->customLsInput.num_lfe; - } - else - { - if ( ( error = getAudioConfigNumChannels( pInputBase->inConfig, numInChannels ) ) != IVAS_ERR_OK ) - { - return error; - } - } + if ( pInputBase->inConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) + { + pInputMc = (const input_mc *) rendInput; + *numInChannels = pInputMc->customLsInput.num_spk + pInputMc->customLsInput.num_lfe; + } + else + { + if ( ( error = getAudioConfigNumChannels( pInputBase->inConfig, numInChannels ) ) != IVAS_ERR_OK ) + { + return error; + } + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error initMcPanGainsWithMonoOut_fx( @@ -3054,55 +3046,55 @@ static bool configsAreEqual( return configA == configB; } #else -static bool configsAreEqual( - const AUDIO_CONFIG configA, - const LSSETUP_CUSTOM_STRUCT customLsA, - const AUDIO_CONFIG configB, - const LSSETUP_CUSTOM_STRUCT customLsB ) -{ - int16_t i; - - /* Both input and output are custom LS - compare structs */ - if ( configA == IVAS_AUDIO_CONFIG_LS_CUSTOM && configB == IVAS_AUDIO_CONFIG_LS_CUSTOM ) - { - if ( customLsA.num_spk != customLsB.num_spk ) + static bool configsAreEqual( + const AUDIO_CONFIG configA, + const LSSETUP_CUSTOM_STRUCT customLsA, + const AUDIO_CONFIG configB, + const LSSETUP_CUSTOM_STRUCT customLsB ) { - return false; - } + int16_t i; - if ( customLsA.num_lfe != customLsB.num_lfe ) - { - return false; - } + /* Both input and output are custom LS - compare structs */ + if ( configA == IVAS_AUDIO_CONFIG_LS_CUSTOM && configB == IVAS_AUDIO_CONFIG_LS_CUSTOM ) + { + if ( customLsA.num_spk != customLsB.num_spk ) + { + return false; + } - if ( customLsA.is_planar_setup != customLsB.is_planar_setup ) - { - return false; - } + if ( customLsA.num_lfe != customLsB.num_lfe ) + { + return false; + } - for ( i = 0; i < customLsA.num_spk; ++i ) - { - /* Compare to nearest degree (hence the int16_t cast) */ - if ( (int16_t) customLsA.ls_azimuth[i] != (int16_t) customLsB.ls_azimuth[i] || - (int16_t) customLsA.ls_elevation[i] != (int16_t) customLsB.ls_elevation[i] ) - { - return false; - } - } - for ( i = 0; i < customLsA.num_lfe; ++i ) - { - if ( customLsA.lfe_idx[i] != customLsB.lfe_idx[i] ) - { - return false; - } - } + if ( customLsA.is_planar_setup != customLsB.is_planar_setup ) + { + return false; + } - return true; - } + for ( i = 0; i < customLsA.num_spk; ++i ) + { + /* Compare to nearest degree (hence the int16_t cast) */ + if ( (int16_t) customLsA.ls_azimuth[i] != (int16_t) customLsB.ls_azimuth[i] || + (int16_t) customLsA.ls_elevation[i] != (int16_t) customLsB.ls_elevation[i] ) + { + return false; + } + } + for ( i = 0; i < customLsA.num_lfe; ++i ) + { + if ( customLsA.lfe_idx[i] != customLsB.lfe_idx[i] ) + { + return false; + } + } - /* Otherwise it's enough to compare config enums */ - return configA == configB; -} + return true; + } + + /* Otherwise it's enough to compare config enums */ + return configA == configB; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error updateLfePanGainsForMcOut( @@ -3148,48 +3140,48 @@ static ivas_error updateLfePanGainsForMcOut( return error; } #else -static ivas_error updateLfePanGainsForMcOut( - input_mc *inputMc, - const AUDIO_CONFIG outConfig ) -{ - int16_t i, numLfeIn, numOutChannels; - ivas_error error; - error = IVAS_ERR_OK; + static ivas_error updateLfePanGainsForMcOut( + input_mc * inputMc, + const AUDIO_CONFIG outConfig ) + { + int16_t i, numLfeIn, numOutChannels; + ivas_error error; + error = IVAS_ERR_OK; - /* If panning is not required, simply return */ - if ( !inputMc->lfeRouting.pan_lfe ) - { - return error; - } + /* If panning is not required, simply return */ + if ( !inputMc->lfeRouting.pan_lfe ) + { + return error; + } - numLfeIn = getNumLfeChannels( inputMc ); + numLfeIn = getNumLfeChannels( inputMc ); - if ( outConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) - { - numOutChannels = inputMc->base.ctx.pCustomLsOut->num_spk + inputMc->base.ctx.pCustomLsOut->num_lfe; - } - else - { - if ( ( error = getAudioConfigNumChannels( outConfig, &numOutChannels ) ) != IVAS_ERR_OK ) - { - return error; - } - } + if ( outConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) + { + numOutChannels = inputMc->base.ctx.pCustomLsOut->num_spk + inputMc->base.ctx.pCustomLsOut->num_lfe; + } + else + { + if ( ( error = getAudioConfigNumChannels( outConfig, &numOutChannels ) ) != IVAS_ERR_OK ) + { + return error; + } + } - for ( i = 0; i < numLfeIn; i++ ) - { - /* panning gains */ - if ( ( error = getEfapGains( *inputMc->base.ctx.pEfapOutWrapper, inputMc->lfeRouting.lfeOutputAzimuth, inputMc->lfeRouting.lfeOutputElevation, inputMc->lfeRouting.lfePanMtx[i] ) ) != IVAS_ERR_OK ) - { - return error; - } + for ( i = 0; i < numLfeIn; i++ ) + { + /* panning gains */ + if ( ( error = getEfapGains( *inputMc->base.ctx.pEfapOutWrapper, inputMc->lfeRouting.lfeOutputAzimuth, inputMc->lfeRouting.lfeOutputElevation, inputMc->lfeRouting.lfePanMtx[i] ) ) != IVAS_ERR_OK ) + { + return error; + } - /* linear input gain */ - v_multc( inputMc->lfeRouting.lfePanMtx[i], inputMc->lfeRouting.lfeInputGain, inputMc->lfeRouting.lfePanMtx[i], numOutChannels ); - } + /* linear input gain */ + v_multc( inputMc->lfeRouting.lfePanMtx[i], inputMc->lfeRouting.lfeInputGain, inputMc->lfeRouting.lfePanMtx[i], numOutChannels ); + } - return error; -} + return error; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error updateLfePanGainsForAmbiOut( @@ -3202,19 +3194,19 @@ static ivas_error updateLfePanGainsForAmbiOut( error = IVAS_ERR_OK; /* If panning is not required, simply return */ - IF ( !inputMc->lfeRouting.pan_lfe ) + IF( !inputMc->lfeRouting.pan_lfe ) { return error; } - IF ( ( error = getAmbisonicsOrder_fx( outConfig, &outAmbiOrder ) ) != IVAS_ERR_OK ) + IF( ( error = getAmbisonicsOrder_fx( outConfig, &outAmbiOrder ) ) != IVAS_ERR_OK ) { return error; } numLfeIn = getNumLfeChannels( inputMc ); move16(); - FOR ( i = 0; i < numLfeIn; i++ ) + FOR( i = 0; i < numLfeIn; i++ ) { /* panning gains */ ivas_dirac_dec_get_response_fixed( inputMc->lfeRouting.lfeOutputAzimuth_fx, inputMc->lfeRouting.lfeOutputElevation_fx, inputMc->lfeRouting.lfePanMtx_fx[i], outAmbiOrder ); @@ -3226,39 +3218,39 @@ static ivas_error updateLfePanGainsForAmbiOut( return error; } #else -static ivas_error updateLfePanGainsForAmbiOut( - input_mc *inputMc, - const AUDIO_CONFIG outConfig ) -{ - int16_t i; - int16_t numLfeIn, outAmbiOrder; - ivas_error error; - error = IVAS_ERR_OK; + static ivas_error updateLfePanGainsForAmbiOut( + input_mc * inputMc, + const AUDIO_CONFIG outConfig ) + { + int16_t i; + int16_t numLfeIn, outAmbiOrder; + ivas_error error; + error = IVAS_ERR_OK; - /* If panning is not required, simply return */ - if ( !inputMc->lfeRouting.pan_lfe ) - { - return error; - } + /* If panning is not required, simply return */ + if ( !inputMc->lfeRouting.pan_lfe ) + { + return error; + } - if ( ( error = getAmbisonicsOrder( outConfig, &outAmbiOrder ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = getAmbisonicsOrder( outConfig, &outAmbiOrder ) ) != IVAS_ERR_OK ) + { + return error; + } - numLfeIn = getNumLfeChannels( inputMc ); + numLfeIn = getNumLfeChannels( inputMc ); - for ( i = 0; i < numLfeIn; i++ ) - { - /* panning gains */ - ivas_dirac_dec_get_response( (int16_t) inputMc->lfeRouting.lfeOutputAzimuth, (int16_t) inputMc->lfeRouting.lfeOutputElevation, inputMc->lfeRouting.lfePanMtx[i], outAmbiOrder ); + for ( i = 0; i < numLfeIn; i++ ) + { + /* panning gains */ + ivas_dirac_dec_get_response( (int16_t) inputMc->lfeRouting.lfeOutputAzimuth, (int16_t) inputMc->lfeRouting.lfeOutputElevation, inputMc->lfeRouting.lfePanMtx[i], outAmbiOrder ); - /* linear input gain */ - v_multc( inputMc->lfeRouting.lfePanMtx[i], inputMc->lfeRouting.lfeInputGain, inputMc->lfeRouting.lfePanMtx[i], IVAS_MAX_OUTPUT_CHANNELS ); - } + /* linear input gain */ + v_multc( inputMc->lfeRouting.lfePanMtx[i], inputMc->lfeRouting.lfeInputGain, inputMc->lfeRouting.lfePanMtx[i], IVAS_MAX_OUTPUT_CHANNELS ); + } - return error; -} + return error; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error updateMcPanGainsForMcOut( @@ -3328,67 +3320,67 @@ static ivas_error updateMcPanGainsForMcOut( return error; } #else -static ivas_error updateMcPanGainsForMcOut( - input_mc *inputMc, - const AUDIO_CONFIG outConfig ) -{ - ivas_error error; + static ivas_error updateMcPanGainsForMcOut( + input_mc * inputMc, + const AUDIO_CONFIG outConfig ) + { + ivas_error error; - /* "if" conditions below realize the following mapping: + /* "if" conditions below realize the following mapping: - If in == out, use identity matrix, otherwise follow the table: - +-----------+-------------+---------------+-----------+--------------------+ - | in\out | MONO | STEREO | custom LS | other | - +-----------+-------------+---------------+-----------+--------------------+ - | MONO | mono out | EFAP | EFAP | EFAP | - | custom LS | mono out | EFAP | EFAP | EFAP | - | other | mono lookup | stereo lookup | EFAP | conversion mapping | - +-----------+-------------+---------------+-----------+--------------------+ - */ + If in == out, use identity matrix, otherwise follow the table: + +-----------+-------------+---------------+-----------+--------------------+ + | in\out | MONO | STEREO | custom LS | other | + +-----------+-------------+---------------+-----------+--------------------+ + | MONO | mono out | EFAP | EFAP | EFAP | + | custom LS | mono out | EFAP | EFAP | EFAP | + | other | mono lookup | stereo lookup | EFAP | conversion mapping | + +-----------+-------------+---------------+-----------+--------------------+ + */ - if ( configsAreEqual( inputMc->base.inConfig, inputMc->customLsInput, outConfig, *inputMc->base.ctx.pCustomLsOut ) ) - { - error = initMcPanGainsWithIdentMatrix( inputMc ); - } - else if ( outConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM || - inputMc->base.inConfig == IVAS_AUDIO_CONFIG_MONO || - inputMc->base.inConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) - { - if ( ( inputMc->base.inConfig == IVAS_AUDIO_CONFIG_MONO ) && ( inputMc->nonDiegeticPan ) ) - { - inputMc->panGains[0][0] = ( inputMc->nonDiegeticPanGain + 1.f ) * 0.5f; - inputMc->panGains[0][1] = 1.f - inputMc->panGains[0][0]; - error = IVAS_ERR_OK; - } - else - { - error = initMcPanGainsWithEfap( inputMc, outConfig ); - } - } - else if ( outConfig == IVAS_AUDIO_CONFIG_MONO ) - { - error = initMcPanGainsWithMonoOut( inputMc ); - } - else if ( outConfig == IVAS_AUDIO_CONFIG_STEREO ) - { - error = initMcPanGainsWithStereoLookup( inputMc ); - } - else /* default */ - { - error = initMcPanGainsWithConversionMapping( inputMc, outConfig ); - } + if ( configsAreEqual( inputMc->base.inConfig, inputMc->customLsInput, outConfig, *inputMc->base.ctx.pCustomLsOut ) ) + { + error = initMcPanGainsWithIdentMatrix( inputMc ); + } + else if ( outConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM || + inputMc->base.inConfig == IVAS_AUDIO_CONFIG_MONO || + inputMc->base.inConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) + { + if ( ( inputMc->base.inConfig == IVAS_AUDIO_CONFIG_MONO ) && ( inputMc->nonDiegeticPan ) ) + { + inputMc->panGains[0][0] = ( inputMc->nonDiegeticPanGain + 1.f ) * 0.5f; + inputMc->panGains[0][1] = 1.f - inputMc->panGains[0][0]; + error = IVAS_ERR_OK; + } + else + { + error = initMcPanGainsWithEfap( inputMc, outConfig ); + } + } + else if ( outConfig == IVAS_AUDIO_CONFIG_MONO ) + { + error = initMcPanGainsWithMonoOut( inputMc ); + } + else if ( outConfig == IVAS_AUDIO_CONFIG_STEREO ) + { + error = initMcPanGainsWithStereoLookup( inputMc ); + } + else /* default */ + { + error = initMcPanGainsWithConversionMapping( inputMc, outConfig ); + } - /* check for errors from above block */ - if ( error != IVAS_ERR_OK ) - { - return error; - } + /* check for errors from above block */ + if ( error != IVAS_ERR_OK ) + { + return error; + } - /* update LFE panning */ - error = updateLfePanGainsForMcOut( inputMc, outConfig ); + /* update LFE panning */ + error = updateLfePanGainsForMcOut( inputMc, outConfig ); - return error; -} + return error; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error updateMcPanGainsForAmbiOut( @@ -3484,75 +3476,75 @@ static ivas_error updateMcPanGainsForAmbiOut( return IVAS_ERR_OK; } #else -static ivas_error updateMcPanGainsForAmbiOut( - input_mc *inputMc, - const AUDIO_CONFIG outConfig ) -{ - int16_t ch_in, ch_out, lfeIdx; - int16_t numNonLfeInChannels, outAmbiOrder; - const float *spkAzi, *spkEle; - ivas_error error; - - if ( ( error = getAmbisonicsOrder( outConfig, &outAmbiOrder ) ) != IVAS_ERR_OK ) - { - return error; - } - - if ( inputMc->base.inConfig != IVAS_AUDIO_CONFIG_LS_CUSTOM ) - { - if ( ( error = getNumNonLfeChannelsInSpeakerLayout( inputMc->base.inConfig, &numNonLfeInChannels ) ) != IVAS_ERR_OK ) - { - return error; - } - - if ( ( error = getSpeakerAzimuths( inputMc->base.inConfig, &spkAzi ) ) != IVAS_ERR_OK ) + static ivas_error updateMcPanGainsForAmbiOut( + input_mc * inputMc, + const AUDIO_CONFIG outConfig ) { - return error; - } - - if ( ( error = getSpeakerElevations( inputMc->base.inConfig, &spkEle ) ) != IVAS_ERR_OK ) - { - return error; - } + int16_t ch_in, ch_out, lfeIdx; + int16_t numNonLfeInChannels, outAmbiOrder; + const float *spkAzi, *spkEle; + ivas_error error; - for ( ch_in = 0, ch_out = 0; ch_in < numNonLfeInChannels; ++ch_in, ++ch_out ) - { - if ( ch_in == LFE_CHANNEL ) + if ( ( error = getAmbisonicsOrder( outConfig, &outAmbiOrder ) ) != IVAS_ERR_OK ) { - ++ch_out; + return error; } - ivas_dirac_dec_get_response( (int16_t) spkAzi[ch_in], (int16_t) spkEle[ch_in], inputMc->panGains[ch_out], outAmbiOrder ); - } - } - else - { - numNonLfeInChannels = inputMc->customLsInput.num_spk; - spkAzi = inputMc->customLsInput.ls_azimuth; - spkEle = inputMc->customLsInput.ls_elevation; - for ( ch_in = 0, ch_out = 0; ch_in < numNonLfeInChannels; ++ch_in, ++ch_out ) - { - for ( lfeIdx = 0; lfeIdx < inputMc->customLsInput.num_lfe; ++lfeIdx ) + if ( inputMc->base.inConfig != IVAS_AUDIO_CONFIG_LS_CUSTOM ) { - if ( inputMc->customLsInput.lfe_idx[lfeIdx] == ch_in ) + if ( ( error = getNumNonLfeChannelsInSpeakerLayout( inputMc->base.inConfig, &numNonLfeInChannels ) ) != IVAS_ERR_OK ) { - ++ch_out; - break; + return error; + } + + if ( ( error = getSpeakerAzimuths( inputMc->base.inConfig, &spkAzi ) ) != IVAS_ERR_OK ) + { + return error; + } + + if ( ( error = getSpeakerElevations( inputMc->base.inConfig, &spkEle ) ) != IVAS_ERR_OK ) + { + return error; + } + + for ( ch_in = 0, ch_out = 0; ch_in < numNonLfeInChannels; ++ch_in, ++ch_out ) + { + if ( ch_in == LFE_CHANNEL ) + { + ++ch_out; + } + ivas_dirac_dec_get_response( (int16_t) spkAzi[ch_in], (int16_t) spkEle[ch_in], inputMc->panGains[ch_out], outAmbiOrder ); } } + else + { + numNonLfeInChannels = inputMc->customLsInput.num_spk; + spkAzi = inputMc->customLsInput.ls_azimuth; + spkEle = inputMc->customLsInput.ls_elevation; - ivas_dirac_dec_get_response( (int16_t) spkAzi[ch_in], (int16_t) spkEle[ch_in], inputMc->panGains[ch_out], outAmbiOrder ); - } - } + for ( ch_in = 0, ch_out = 0; ch_in < numNonLfeInChannels; ++ch_in, ++ch_out ) + { + for ( lfeIdx = 0; lfeIdx < inputMc->customLsInput.num_lfe; ++lfeIdx ) + { + if ( inputMc->customLsInput.lfe_idx[lfeIdx] == ch_in ) + { + ++ch_out; + break; + } + } - /* update LFE panning */ - if ( ( error = updateLfePanGainsForAmbiOut( inputMc, outConfig ) ) != IVAS_ERR_OK ) - { - return error; - } + ivas_dirac_dec_get_response( (int16_t) spkAzi[ch_in], (int16_t) spkEle[ch_in], inputMc->panGains[ch_out], outAmbiOrder ); + } + } - return IVAS_ERR_OK; -} + /* update LFE panning */ + if ( ( error = updateLfePanGainsForAmbiOut( inputMc, outConfig ) ) != IVAS_ERR_OK ) + { + return error; + } + + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error updateMcPanGains( @@ -3616,66 +3608,66 @@ static ivas_error updateMcPanGains( return IVAS_ERR_OK; } #else -static ivas_error updateMcPanGains( - input_mc *inputMc, - const AUDIO_CONFIG outConfig ) -{ - int16_t i; - ivas_error error; + static ivas_error updateMcPanGains( + input_mc * inputMc, + const AUDIO_CONFIG outConfig ) + { + int16_t i; + ivas_error error; - /* Reset to all zeros - some functions below only write non-zero elements. */ - setZeroPanMatrix( inputMc->panGains ); + /* Reset to all zeros - some functions below only write non-zero elements. */ + setZeroPanMatrix( inputMc->panGains ); - error = IVAS_ERR_OK; - switch ( getAudioConfigType( outConfig ) ) - { - case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: - error = updateMcPanGainsForMcOut( inputMc, outConfig ); - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: - error = updateMcPanGainsForAmbiOut( inputMc, outConfig ); - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_BINAURAL: - switch ( outConfig ) + error = IVAS_ERR_OK; + switch ( getAudioConfigType( outConfig ) ) { - case IVAS_AUDIO_CONFIG_BINAURAL: - break; /* Do nothing */ - case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR: - case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB: - /* Prepare rendering to intermediate format */ - error = updateMcPanGainsForMcOut( inputMc, IVAS_AUDIO_CONFIG_7_1_4 ); + case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: + error = updateMcPanGainsForMcOut( inputMc, outConfig ); + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: + error = updateMcPanGainsForAmbiOut( inputMc, outConfig ); + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_BINAURAL: + switch ( outConfig ) + { + case IVAS_AUDIO_CONFIG_BINAURAL: + break; /* Do nothing */ + case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR: + case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB: + /* Prepare rendering to intermediate format */ + error = updateMcPanGainsForMcOut( inputMc, IVAS_AUDIO_CONFIG_7_1_4 ); + break; + default: + return IVAS_ERR_INVALID_OUTPUT_FORMAT; + } break; + case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: + break; /* Do nothing */ default: return IVAS_ERR_INVALID_OUTPUT_FORMAT; } - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: - break; /* Do nothing */ - default: - return IVAS_ERR_INVALID_OUTPUT_FORMAT; - } - /* Check error here to keep switch statement more compact */ - if ( error != IVAS_ERR_OK ) - { - return error; - } + /* Check error here to keep switch statement more compact */ + if ( error != IVAS_ERR_OK ) + { + return error; + } - /* Copy LFE routing to pan gains array */ - if ( inputMc->base.inConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) - { - for ( i = 0; i < inputMc->customLsInput.num_lfe; ++i ) - { - mvr2r( inputMc->lfeRouting.lfePanMtx[i], inputMc->panGains[inputMc->customLsInput.lfe_idx[i]], IVAS_MAX_OUTPUT_CHANNELS ); - } - } - else - { - /* For code simplicity, always copy LFE gains. If config has no LFE, gains will be zero anyway. */ - mvr2r( inputMc->lfeRouting.lfePanMtx[0], inputMc->panGains[LFE_CHANNEL], IVAS_MAX_OUTPUT_CHANNELS ); - } + /* Copy LFE routing to pan gains array */ + if ( inputMc->base.inConfig == IVAS_AUDIO_CONFIG_LS_CUSTOM ) + { + for ( i = 0; i < inputMc->customLsInput.num_lfe; ++i ) + { + mvr2r( inputMc->lfeRouting.lfePanMtx[i], inputMc->panGains[inputMc->customLsInput.lfe_idx[i]], IVAS_MAX_OUTPUT_CHANNELS ); + } + } + else + { + /* For code simplicity, always copy LFE gains. If config has no LFE, gains will be zero anyway. */ + mvr2r( inputMc->lfeRouting.lfePanMtx[0], inputMc->panGains[LFE_CHANNEL], IVAS_MAX_OUTPUT_CHANNELS ); + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif static ivas_error initMcBinauralRendering( @@ -3712,7 +3704,7 @@ static ivas_error initMcBinauralRendering( #ifdef IVAS_FLOAT_FIXED ivas_td_binaural_close_fx( &inputMc->tdRendWrapper.hBinRendererTd ); #else - ivas_td_binaural_close( &inputMc->tdRendWrapper.hBinRendererTd ); + ivas_td_binaural_close( &inputMc->tdRendWrapper.hBinRendererTd ); #endif inputMc->tdRendWrapper.hHrtfTD = NULL; } @@ -3783,25 +3775,26 @@ static ivas_error initMcBinauralRendering( if ( outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB && inputMc->hReverb == NULL ) { #ifdef IVAS_FLOAT_FIXED - if ( ( error = ivas_reverb_open_fx( &( inputMc->hReverb ), outConfig, NULL,inputMc->tdRendWrapper.hBinRendererTd->HrFiltSet_p->lr_energy_and_iac_fx, hRendCfg, outSampleRate ) ) != IVAS_ERR_OK ) + + if ( ( error = ivas_reverb_open_fx( &( inputMc->hReverb ), outConfig, NULL, inputMc->tdRendWrapper.hBinRendererTd->HrFiltSet_p->lr_energy_and_iac_fx, hRendCfg, outSampleRate ) ) != IVAS_ERR_OK ) { return error; } #if 1 /*Fixed to float conversions */ - FOR( Word16 k = 0; k < add( extract_l( L_shr(inputMc->hReverb->fft_size, 1 ) ), 1 ); k++ ) + FOR( Word16 k = 0; k < add( extract_l( L_shr( inputMc->hReverb->fft_size, 1 ) ), 1 ); k++ ) { - (inputMc->hReverb)->fft_filter_correl_0.fft_spectrum[k] = (float) (inputMc->hReverb)->fft_filter_correl_0.fft_spectrum_fx[k] / ONE_IN_Q31; - (inputMc->hReverb)->fft_filter_color_0.fft_spectrum[k] = (float) (inputMc->hReverb)->fft_filter_color_0.fft_spectrum_fx[k] / ONE_IN_Q31; - (inputMc->hReverb)->fft_filter_correl_1.fft_spectrum[k] = (float) (inputMc->hReverb)->fft_filter_correl_1.fft_spectrum_fx[k] / ONE_IN_Q31; - (inputMc->hReverb)->fft_filter_color_1.fft_spectrum[k] = (float) (inputMc->hReverb)->fft_filter_color_1.fft_spectrum_fx[k] / ONE_IN_Q31; + ( inputMc->hReverb )->fft_filter_correl_0.fft_spectrum[k] = (float) ( inputMc->hReverb )->fft_filter_correl_0.fft_spectrum_fx[k] / ONE_IN_Q31; + ( inputMc->hReverb )->fft_filter_color_0.fft_spectrum[k] = (float) ( inputMc->hReverb )->fft_filter_color_0.fft_spectrum_fx[k] / ONE_IN_Q31; + ( inputMc->hReverb )->fft_filter_correl_1.fft_spectrum[k] = (float) ( inputMc->hReverb )->fft_filter_correl_1.fft_spectrum_fx[k] / ONE_IN_Q31; + ( inputMc->hReverb )->fft_filter_color_1.fft_spectrum[k] = (float) ( inputMc->hReverb )->fft_filter_color_1.fft_spectrum_fx[k] / ONE_IN_Q31; } #endif #else - if ( ( error = ivas_reverb_open( &( inputMc->hReverb ), outConfig, NULL, inputMc->tdRendWrapper.hBinRendererTd->HrFiltSet_p->lr_energy_and_iac, hRendCfg, outSampleRate ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = ivas_reverb_open( &( inputMc->hReverb ), outConfig, NULL, inputMc->tdRendWrapper.hBinRendererTd->HrFiltSet_p->lr_energy_and_iac, hRendCfg, outSampleRate ) ) != IVAS_ERR_OK ) + { + return error; + } #endif } } @@ -3848,7 +3841,7 @@ static ivas_error initMcMasaRendering( #ifdef IVAS_FLOAT_FIXED ivas_td_binaural_close_fx( &inputMc->tdRendWrapper.hBinRendererTd ); #else - ivas_td_binaural_close( &inputMc->tdRendWrapper.hBinRendererTd ); + ivas_td_binaural_close( &inputMc->tdRendWrapper.hBinRendererTd ); #endif inputMc->tdRendWrapper.hHrtfTD = NULL; } @@ -3870,15 +3863,15 @@ static ivas_error initMcMasaRendering( #if 1 /*Fixed to float conversion for ivas_mcmasa_ana_open (to be removed later)*/ MCMASA_ANA_HANDLE hMcMasa = inputMc->hMcMasa; Word16 i, j; - fixedToFloat_arrL( hMcMasa->ls_azimuth_fx, hMcMasa->ls_azimuth, Q22, MCMASA_MAX_ANA_CHANS); - FOR ( i = 0; i < MCMASA_MAX_ANA_CHANS; i++ ) + fixedToFloat_arrL( hMcMasa->ls_azimuth_fx, hMcMasa->ls_azimuth, Q22, MCMASA_MAX_ANA_CHANS ); + FOR( i = 0; i < MCMASA_MAX_ANA_CHANS; i++ ) { - FOR ( j = 0; j < FOA_CHANNELS; j++ ) + FOR( j = 0; j < FOA_CHANNELS; j++ ) { hMcMasa->chnlToFoaMtx[j][i] = fixedToFloat( hMcMasa->chnlToFoaMtx_fx[j][i], Q31 ); } } - FOR( i = 0; i < (inSampleRate/FRAMES_PER_SEC); i++ ) + FOR( i = 0; i < ( inSampleRate / FRAMES_PER_SEC ); i++ ) { hMcMasa->interpolator[i] = fixedToFloat( hMcMasa->interpolator_fx[i], Q15 ); } @@ -3951,83 +3944,83 @@ static lfe_routing defaultLfeRouting( return routing; } #else -static lfe_routing defaultLfeRouting( + static lfe_routing defaultLfeRouting( + const AUDIO_CONFIG inConfig, + const LSSETUP_CUSTOM_STRUCT customLsIn, + const AUDIO_CONFIG outConfig, + const LSSETUP_CUSTOM_STRUCT customLsOut ) + { + int16_t i; + lfe_routing routing; + + /* Set all output gains to zero, then route each input LFE consecutively to the next available output LFE. */ + + for ( i = 0; i < RENDERER_MAX_INPUT_LFE_CHANNELS; ++i ) + { + set_zero( routing.lfePanMtx[i], IVAS_MAX_OUTPUT_CHANNELS ); + } + + routing.pan_lfe = false; + routing.lfeInputGain = 1.0f; + + switch ( inConfig ) + { + case IVAS_AUDIO_CONFIG_5_1: + case IVAS_AUDIO_CONFIG_5_1_2: + case IVAS_AUDIO_CONFIG_5_1_4: + case IVAS_AUDIO_CONFIG_7_1: + case IVAS_AUDIO_CONFIG_7_1_4: + routing.numLfeChannels = 1; + break; + case IVAS_AUDIO_CONFIG_LS_CUSTOM: + routing.numLfeChannels = customLsIn.num_lfe; + break; + default: + routing.numLfeChannels = 0; + } + + switch ( outConfig ) + { + case IVAS_AUDIO_CONFIG_5_1: + case IVAS_AUDIO_CONFIG_5_1_2: + case IVAS_AUDIO_CONFIG_5_1_4: + case IVAS_AUDIO_CONFIG_7_1: + case IVAS_AUDIO_CONFIG_7_1_4: + routing.lfePanMtx[0][LFE_CHANNEL] = 1.0f; + break; + case IVAS_AUDIO_CONFIG_LS_CUSTOM: + for ( i = 0; i < routing.numLfeChannels && i < customLsOut.num_lfe; ++i ) + { + routing.lfePanMtx[i][customLsOut.lfe_idx[i]] = 1.0f; + } + break; + default: + /* Do nothing */ + break; + } + + return routing; + } +#endif +#ifdef IVAS_FLOAT_FIXED +static ivas_error setRendInputActiveMc( + void *input, const AUDIO_CONFIG inConfig, - const LSSETUP_CUSTOM_STRUCT customLsIn, - const AUDIO_CONFIG outConfig, - const LSSETUP_CUSTOM_STRUCT customLsOut ) + const IVAS_REND_InputId id, + RENDER_CONFIG_DATA *hRendCfg ) { - int16_t i; - lfe_routing routing; + ivas_error error; + rendering_context rendCtx; + AUDIO_CONFIG outConfig; + input_mc *inputMc; - /* Set all output gains to zero, then route each input LFE consecutively to the next available output LFE. */ + inputMc = (input_mc *) input; + rendCtx = inputMc->base.ctx; + outConfig = *rendCtx.pOutConfig; - for ( i = 0; i < RENDERER_MAX_INPUT_LFE_CHANNELS; ++i ) + if ( !isIoConfigPairSupported( inConfig, outConfig ) ) { - set_zero( routing.lfePanMtx[i], IVAS_MAX_OUTPUT_CHANNELS ); - } - - routing.pan_lfe = false; - routing.lfeInputGain = 1.0f; - - switch ( inConfig ) - { - case IVAS_AUDIO_CONFIG_5_1: - case IVAS_AUDIO_CONFIG_5_1_2: - case IVAS_AUDIO_CONFIG_5_1_4: - case IVAS_AUDIO_CONFIG_7_1: - case IVAS_AUDIO_CONFIG_7_1_4: - routing.numLfeChannels = 1; - break; - case IVAS_AUDIO_CONFIG_LS_CUSTOM: - routing.numLfeChannels = customLsIn.num_lfe; - break; - default: - routing.numLfeChannels = 0; - } - - switch ( outConfig ) - { - case IVAS_AUDIO_CONFIG_5_1: - case IVAS_AUDIO_CONFIG_5_1_2: - case IVAS_AUDIO_CONFIG_5_1_4: - case IVAS_AUDIO_CONFIG_7_1: - case IVAS_AUDIO_CONFIG_7_1_4: - routing.lfePanMtx[0][LFE_CHANNEL] = 1.0f; - break; - case IVAS_AUDIO_CONFIG_LS_CUSTOM: - for ( i = 0; i < routing.numLfeChannels && i < customLsOut.num_lfe; ++i ) - { - routing.lfePanMtx[i][customLsOut.lfe_idx[i]] = 1.0f; - } - break; - default: - /* Do nothing */ - break; - } - - return routing; -} -#endif -#ifdef IVAS_FLOAT_FIXED -static ivas_error setRendInputActiveMc( - void *input, - const AUDIO_CONFIG inConfig, - const IVAS_REND_InputId id, - RENDER_CONFIG_DATA *hRendCfg ) -{ - ivas_error error; - rendering_context rendCtx; - AUDIO_CONFIG outConfig; - input_mc *inputMc; - - inputMc = (input_mc *) input; - rendCtx = inputMc->base.ctx; - outConfig = *rendCtx.pOutConfig; - - if ( !isIoConfigPairSupported( inConfig, outConfig ) ) - { - return IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED; + return IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED; } if ( ( error = allocateMcLfeDelayBuffer( &inputMc->lfeDelayBuffer, MAX_BIN_DELAY_SAMPLES ) ) != IVAS_ERR_OK ) @@ -4089,72 +4082,72 @@ static ivas_error setRendInputActiveMc( return IVAS_ERR_OK; } #else -static ivas_error setRendInputActiveMc( - void *input, - const AUDIO_CONFIG inConfig, - const IVAS_REND_InputId id, - RENDER_CONFIG_DATA *hRendCfg ) -{ - ivas_error error; - rendering_context rendCtx; - AUDIO_CONFIG outConfig; - input_mc *inputMc; + static ivas_error setRendInputActiveMc( + void *input, + const AUDIO_CONFIG inConfig, + const IVAS_REND_InputId id, + RENDER_CONFIG_DATA *hRendCfg ) + { + ivas_error error; + rendering_context rendCtx; + AUDIO_CONFIG outConfig; + input_mc *inputMc; - inputMc = (input_mc *) input; - rendCtx = inputMc->base.ctx; - outConfig = *rendCtx.pOutConfig; + inputMc = (input_mc *) input; + rendCtx = inputMc->base.ctx; + outConfig = *rendCtx.pOutConfig; - if ( !isIoConfigPairSupported( inConfig, outConfig ) ) - { - return IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED; - } + if ( !isIoConfigPairSupported( inConfig, outConfig ) ) + { + return IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED; + } - if ( ( error = allocateMcLfeDelayBuffer( &inputMc->lfeDelayBuffer, MAX_BIN_DELAY_SAMPLES ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = allocateMcLfeDelayBuffer( &inputMc->lfeDelayBuffer, MAX_BIN_DELAY_SAMPLES ) ) != IVAS_ERR_OK ) + { + return error; + } - if ( ( error = allocateInputBaseBufferData( &inputMc->bufferData, MAX_BUFFER_LENGTH ) ) != IVAS_ERR_OK ) - { - return error; - } - initRendInputBase( &inputMc->base, inConfig, id, rendCtx, inputMc->bufferData, MAX_BUFFER_LENGTH ); + if ( ( error = allocateInputBaseBufferData( &inputMc->bufferData, MAX_BUFFER_LENGTH ) ) != IVAS_ERR_OK ) + { + return error; + } + initRendInputBase( &inputMc->base, inConfig, id, rendCtx, inputMc->bufferData, MAX_BUFFER_LENGTH ); - setZeroPanMatrix( inputMc->panGains ); - inputMc->customLsInput = defaultCustomLs(); - inputMc->tdRendWrapper = defaultTdRendWrapper(); - inputMc->crendWrapper = NULL; - inputMc->hReverb = NULL; - inputMc->hMcMasa = NULL; + setZeroPanMatrix( inputMc->panGains ); + inputMc->customLsInput = defaultCustomLs(); + inputMc->tdRendWrapper = defaultTdRendWrapper(); + inputMc->crendWrapper = NULL; + inputMc->hReverb = NULL; + inputMc->hMcMasa = NULL; - initRotGains( inputMc->rot_gains_prev ); - inputMc->lfeRouting = defaultLfeRouting( inConfig, inputMc->customLsInput, outConfig, *inputMc->base.ctx.pCustomLsOut ); - set_zero( inputMc->lfeDelayBuffer, MAX_BIN_DELAY_SAMPLES ); - inputMc->binauralDelaySmp = 0; + initRotGains( inputMc->rot_gains_prev ); + inputMc->lfeRouting = defaultLfeRouting( inConfig, inputMc->customLsInput, outConfig, *inputMc->base.ctx.pCustomLsOut ); + set_zero( inputMc->lfeDelayBuffer, MAX_BIN_DELAY_SAMPLES ); + inputMc->binauralDelaySmp = 0; - if ( outConfig == IVAS_AUDIO_CONFIG_BINAURAL || outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR || outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB ) - { - if ( ( error = initMcBinauralRendering( inputMc, inConfig, outConfig, hRendCfg, FALSE ) ) != IVAS_ERR_OK ) - { - return error; - } - } + if ( outConfig == IVAS_AUDIO_CONFIG_BINAURAL || outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR || outConfig == IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB ) + { + if ( ( error = initMcBinauralRendering( inputMc, inConfig, outConfig, hRendCfg, FALSE ) ) != IVAS_ERR_OK ) + { + return error; + } + } - if ( outConfig == IVAS_AUDIO_CONFIG_MASA1 || outConfig == IVAS_AUDIO_CONFIG_MASA2 ) - { - if ( ( error = initMcMasaRendering( inputMc, inConfig, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) - { - return error; - } - } + if ( outConfig == IVAS_AUDIO_CONFIG_MASA1 || outConfig == IVAS_AUDIO_CONFIG_MASA2 ) + { + if ( ( error = initMcMasaRendering( inputMc, inConfig, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) + { + return error; + } + } - if ( ( error = updateMcPanGains( inputMc, outConfig ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = updateMcPanGains( inputMc, outConfig ) ) != IVAS_ERR_OK ) + { + return error; + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED static void clearInputMc( @@ -4197,38 +4190,38 @@ static void clearInputMc( return; } #else -static void clearInputMc( - input_mc *inputMc ) -{ - rendering_context rendCtx; + static void clearInputMc( + input_mc * inputMc ) + { + rendering_context rendCtx; - rendCtx = inputMc->base.ctx; + rendCtx = inputMc->base.ctx; - freeMcLfeDelayBuffer( &inputMc->lfeDelayBuffer ); - freeInputBaseBufferData( &inputMc->bufferData ); - initRendInputBase( &inputMc->base, IVAS_AUDIO_CONFIG_INVALID, 0, rendCtx, NULL, 0 ); + freeMcLfeDelayBuffer( &inputMc->lfeDelayBuffer ); + freeInputBaseBufferData( &inputMc->bufferData ); + initRendInputBase( &inputMc->base, IVAS_AUDIO_CONFIG_INVALID, 0, rendCtx, NULL, 0 ); - /* Free input's internal handles */ - if ( inputMc->efapInWrapper.hEfap != NULL ) - { - efap_free_data( &inputMc->efapInWrapper.hEfap ); - } + /* Free input's internal handles */ + if ( inputMc->efapInWrapper.hEfap != NULL ) + { + efap_free_data( &inputMc->efapInWrapper.hEfap ); + } - ivas_rend_closeCrend( &inputMc->crendWrapper ); + ivas_rend_closeCrend( &inputMc->crendWrapper ); - ivas_reverb_close( &inputMc->hReverb ); + ivas_reverb_close( &inputMc->hReverb ); - if ( inputMc->tdRendWrapper.hBinRendererTd != NULL ) - { - ivas_td_binaural_close( &inputMc->tdRendWrapper.hBinRendererTd ); - inputMc->tdRendWrapper.hHrtfTD = NULL; - } + if ( inputMc->tdRendWrapper.hBinRendererTd != NULL ) + { + ivas_td_binaural_close( &inputMc->tdRendWrapper.hBinRendererTd ); + inputMc->tdRendWrapper.hHrtfTD = NULL; + } - ivas_mcmasa_ana_close( &( inputMc->hMcMasa ) ); + ivas_mcmasa_ana_close( &( inputMc->hMcMasa ) ); - return; -} + return; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error initSbaPanGainsForMcOut( @@ -4247,13 +4240,13 @@ static ivas_error initSbaPanGainsForMcOut( return error; } - IF ( getAudioConfigType( outConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) + IF( getAudioConfigType( outConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) { assert( !"Invalid configuration" ); return IVAS_ERR_WRONG_PARAMS; } - SWITCH ( outConfig ) + SWITCH( outConfig ) { case IVAS_AUDIO_CONFIG_MONO: hOutSetup.ls_azimuth = ls_azimuth_CICP1; @@ -4272,8 +4265,8 @@ static ivas_error initSbaPanGainsForMcOut( ivas_output_init( &hOutSetup, outConfig ); BREAK; case IVAS_AUDIO_CONFIG_LS_CUSTOM: - //ivas_ls_custom_setup( &hOutSetup, (LSSETUP_CUSTOM_STRUCT *)outSetupCustom ); - ivas_ls_custom_setup_fx( &hOutSetup, (LSSETUP_CUSTOM_STRUCT *)outSetupCustom ); + // ivas_ls_custom_setup( &hOutSetup, (LSSETUP_CUSTOM_STRUCT *)outSetupCustom ); + ivas_ls_custom_setup_fx( &hOutSetup, (LSSETUP_CUSTOM_STRUCT *) outSetupCustom ); BREAK; default: assert( !"Invalid speaker config" ); @@ -4282,17 +4275,17 @@ static ivas_error initSbaPanGainsForMcOut( /* obtain and copy over HOA decoding matrix */ tmpDecMtx = NULL; - IF ( ( error = ivas_sba_get_hoa_dec_matrix_fx( hOutSetup, &tmpDecMtx, ambiOrderIn ) ) != IVAS_ERR_OK ) + IF( ( error = ivas_sba_get_hoa_dec_matrix_fx( hOutSetup, &tmpDecMtx, ambiOrderIn ) ) != IVAS_ERR_OK ) { return error; } readPtr = &tmpDecMtx[0]; - FOR ( chOutIdx = 0; chOutIdx < hOutSetup.nchan_out_woLFE + hOutSetup.num_lfe; ++chOutIdx ) + FOR( chOutIdx = 0; chOutIdx < hOutSetup.nchan_out_woLFE + hOutSetup.num_lfe; ++chOutIdx ) { - FOR ( chInIdx = 0; chInIdx < SBA_NHARM_HOA3; ++chInIdx ) + FOR( chInIdx = 0; chInIdx < SBA_NHARM_HOA3; ++chInIdx ) { - IF ( hOutSetup.num_lfe > 0 && chOutIdx == hOutSetup.index_lfe[0] ) + IF( hOutSetup.num_lfe > 0 && chOutIdx == hOutSetup.index_lfe[0] ) { continue; /* nothing to be rendered to LFE */ } @@ -4304,75 +4297,75 @@ static ivas_error initSbaPanGainsForMcOut( return IVAS_ERR_OK; } #else -static ivas_error initSbaPanGainsForMcOut( - input_sba *inputSba, - const AUDIO_CONFIG outConfig, - const LSSETUP_CUSTOM_STRUCT *outSetupCustom ) -{ - int16_t ambiOrderIn; - int16_t chInIdx, chOutIdx; - float *tmpDecMtx, *readPtr; - IVAS_OUTPUT_SETUP hOutSetup; - ivas_error error; + static ivas_error initSbaPanGainsForMcOut( + input_sba * inputSba, + const AUDIO_CONFIG outConfig, + const LSSETUP_CUSTOM_STRUCT *outSetupCustom ) + { + int16_t ambiOrderIn; + int16_t chInIdx, chOutIdx; + float *tmpDecMtx, *readPtr; + IVAS_OUTPUT_SETUP hOutSetup; + ivas_error error; - if ( ( error = getAmbisonicsOrder( inputSba->base.inConfig, &ambiOrderIn ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = getAmbisonicsOrder( inputSba->base.inConfig, &ambiOrderIn ) ) != IVAS_ERR_OK ) + { + return error; + } - if ( getAudioConfigType( outConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) - { - assert( !"Invalid configuration" ); - return IVAS_ERR_WRONG_PARAMS; - } + if ( getAudioConfigType( outConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) + { + assert( !"Invalid configuration" ); + return IVAS_ERR_WRONG_PARAMS; + } - switch ( outConfig ) - { - case IVAS_AUDIO_CONFIG_MONO: - hOutSetup.ls_azimuth = ls_azimuth_CICP1; - hOutSetup.ls_elevation = ls_elevation_CICP1; - ivas_output_init( &hOutSetup, outConfig ); - break; - case IVAS_AUDIO_CONFIG_STEREO: - case IVAS_AUDIO_CONFIG_5_1: - case IVAS_AUDIO_CONFIG_7_1: - case IVAS_AUDIO_CONFIG_5_1_2: - case IVAS_AUDIO_CONFIG_5_1_4: - case IVAS_AUDIO_CONFIG_7_1_4: - ivas_output_init( &hOutSetup, outConfig ); - break; - case IVAS_AUDIO_CONFIG_LS_CUSTOM: - ivas_ls_custom_setup( &hOutSetup, outSetupCustom ); - break; - default: - assert( !"Invalid speaker config" ); - return IVAS_ERR_WRONG_PARAMS; - } + switch ( outConfig ) + { + case IVAS_AUDIO_CONFIG_MONO: + hOutSetup.ls_azimuth = ls_azimuth_CICP1; + hOutSetup.ls_elevation = ls_elevation_CICP1; + ivas_output_init( &hOutSetup, outConfig ); + break; + case IVAS_AUDIO_CONFIG_STEREO: + case IVAS_AUDIO_CONFIG_5_1: + case IVAS_AUDIO_CONFIG_7_1: + case IVAS_AUDIO_CONFIG_5_1_2: + case IVAS_AUDIO_CONFIG_5_1_4: + case IVAS_AUDIO_CONFIG_7_1_4: + ivas_output_init( &hOutSetup, outConfig ); + break; + case IVAS_AUDIO_CONFIG_LS_CUSTOM: + ivas_ls_custom_setup( &hOutSetup, outSetupCustom ); + break; + default: + assert( !"Invalid speaker config" ); + return IVAS_ERR_WRONG_PARAMS; + } - /* obtain and copy over HOA decoding matrix */ - tmpDecMtx = NULL; - if ( ( error = ivas_sba_get_hoa_dec_matrix( hOutSetup, &tmpDecMtx, ambiOrderIn ) ) != IVAS_ERR_OK ) - { - return error; - } + /* obtain and copy over HOA decoding matrix */ + tmpDecMtx = NULL; + if ( ( error = ivas_sba_get_hoa_dec_matrix( hOutSetup, &tmpDecMtx, ambiOrderIn ) ) != IVAS_ERR_OK ) + { + return error; + } - readPtr = &tmpDecMtx[0]; - for ( chOutIdx = 0; chOutIdx < hOutSetup.nchan_out_woLFE + hOutSetup.num_lfe; ++chOutIdx ) - { - for ( chInIdx = 0; chInIdx < SBA_NHARM_HOA3; ++chInIdx ) - { - if ( hOutSetup.num_lfe > 0 && chOutIdx == hOutSetup.index_lfe[0] ) + readPtr = &tmpDecMtx[0]; + for ( chOutIdx = 0; chOutIdx < hOutSetup.nchan_out_woLFE + hOutSetup.num_lfe; ++chOutIdx ) { - continue; /* nothing to be rendered to LFE */ + for ( chInIdx = 0; chInIdx < SBA_NHARM_HOA3; ++chInIdx ) + { + if ( hOutSetup.num_lfe > 0 && chOutIdx == hOutSetup.index_lfe[0] ) + { + continue; /* nothing to be rendered to LFE */ + } + inputSba->hoaDecMtx[chInIdx][chOutIdx] = *readPtr++; + } } - inputSba->hoaDecMtx[chInIdx][chOutIdx] = *readPtr++; - } - } - free( tmpDecMtx ); + free( tmpDecMtx ); - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED @@ -4394,23 +4387,23 @@ static ivas_error initSbaPanGainsForSbaOut( return error; } #else -static ivas_error initSbaPanGainsForSbaOut( - input_sba *inputSba, - const AUDIO_CONFIG outConfig ) -{ - ivas_error error; - error = IVAS_ERR_OK; + static ivas_error initSbaPanGainsForSbaOut( + input_sba * inputSba, + const AUDIO_CONFIG outConfig ) + { + ivas_error error; + error = IVAS_ERR_OK; - if ( getAudioConfigType( outConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS ) - { - assert( !"Invalid configuration" ); - return IVAS_ERR_WRONG_PARAMS; - } + if ( getAudioConfigType( outConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS ) + { + assert( !"Invalid configuration" ); + return IVAS_ERR_WRONG_PARAMS; + } - fillIdentityPanMatrix( inputSba->hoaDecMtx ); + fillIdentityPanMatrix( inputSba->hoaDecMtx ); - return error; -} + return error; + } #endif #ifdef IVAS_FLOAT_FIXED static ivas_error updateSbaPanGains( @@ -4423,13 +4416,13 @@ static ivas_error updateSbaPanGains( rendering_context rendCtx; /* Reset to all zeros - some functions below only write non-zero elements. */ - //setZeroPanMatrix( inputSba->hoaDecMtx ); + // setZeroPanMatrix( inputSba->hoaDecMtx ); setZeroPanMatrix_fx( inputSba->hoaDecMtx_fx ); inConfig = inputSba->base.inConfig; rendCtx = inputSba->base.ctx; - SWITCH ( getAudioConfigType( outConfig ) ) + SWITCH( getAudioConfigType( outConfig ) ) { case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: error = initSbaPanGainsForMcOut( inputSba, outConfig, inputSba->base.ctx.pCustomLsOut ); @@ -4438,25 +4431,25 @@ static ivas_error updateSbaPanGains( error = initSbaPanGainsForSbaOut( inputSba, outConfig ); BREAK; case IVAS_REND_AUDIO_CONFIG_TYPE_BINAURAL: - SWITCH ( outConfig ) + SWITCH( outConfig ) { case IVAS_AUDIO_CONFIG_BINAURAL: { - IF ( ( error = ivas_rend_openCrend( &inputSba->crendWrapper, inConfig, outConfig, hRendCfg, NULL, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) + IF( ( error = ivas_rend_openCrend( &inputSba->crendWrapper, inConfig, outConfig, hRendCfg, NULL, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) { return error; } } - BREAK; + BREAK; case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR: case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB: - IF ( ( error = initSbaPanGainsForMcOut( inputSba, IVAS_AUDIO_CONFIG_7_1_4, NULL ) ) != IVAS_ERR_OK ) + IF( ( error = initSbaPanGainsForMcOut( inputSba, IVAS_AUDIO_CONFIG_7_1_4, NULL ) ) != IVAS_ERR_OK ) { return error; } - IF ( ( error = ivas_rend_openCrend( &inputSba->crendWrapper, IVAS_AUDIO_CONFIG_7_1_4, outConfig, hRendCfg, NULL, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) + IF( ( error = ivas_rend_openCrend( &inputSba->crendWrapper, IVAS_AUDIO_CONFIG_7_1_4, outConfig, hRendCfg, NULL, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) { return error; } @@ -4473,7 +4466,7 @@ static ivas_error updateSbaPanGains( } /* Check error here to keep switch statement more compact */ - IF ( error != IVAS_ERR_OK ) + IF( error != IVAS_ERR_OK ) { return error; } @@ -4481,72 +4474,72 @@ static ivas_error updateSbaPanGains( return IVAS_ERR_OK; } #else -static ivas_error updateSbaPanGains( - input_sba *inputSba, - const AUDIO_CONFIG outConfig, - RENDER_CONFIG_DATA *hRendCfg ) -{ - ivas_error error; - AUDIO_CONFIG inConfig; - rendering_context rendCtx; + static ivas_error updateSbaPanGains( + input_sba * inputSba, + const AUDIO_CONFIG outConfig, + RENDER_CONFIG_DATA *hRendCfg ) + { + ivas_error error; + AUDIO_CONFIG inConfig; + rendering_context rendCtx; - /* Reset to all zeros - some functions below only write non-zero elements. */ - setZeroPanMatrix( inputSba->hoaDecMtx ); + /* Reset to all zeros - some functions below only write non-zero elements. */ + setZeroPanMatrix( inputSba->hoaDecMtx ); - inConfig = inputSba->base.inConfig; - rendCtx = inputSba->base.ctx; + inConfig = inputSba->base.inConfig; + rendCtx = inputSba->base.ctx; - switch ( getAudioConfigType( outConfig ) ) - { - case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: - error = initSbaPanGainsForMcOut( inputSba, outConfig, inputSba->base.ctx.pCustomLsOut ); - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: - error = initSbaPanGainsForSbaOut( inputSba, outConfig ); - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_BINAURAL: - switch ( outConfig ) + switch ( getAudioConfigType( outConfig ) ) { - case IVAS_AUDIO_CONFIG_BINAURAL: - { - if ( ( error = ivas_rend_openCrend( &inputSba->crendWrapper, inConfig, outConfig, hRendCfg, NULL, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) - - { - return error; - } - } - break; - case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR: - case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB: - if ( ( error = initSbaPanGainsForMcOut( inputSba, IVAS_AUDIO_CONFIG_7_1_4, NULL ) ) != IVAS_ERR_OK ) + case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: + error = initSbaPanGainsForMcOut( inputSba, outConfig, inputSba->base.ctx.pCustomLsOut ); + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: + error = initSbaPanGainsForSbaOut( inputSba, outConfig ); + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_BINAURAL: + switch ( outConfig ) { - return error; - } + case IVAS_AUDIO_CONFIG_BINAURAL: + { + if ( ( error = ivas_rend_openCrend( &inputSba->crendWrapper, inConfig, outConfig, hRendCfg, NULL, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) - if ( ( error = ivas_rend_openCrend( &inputSba->crendWrapper, IVAS_AUDIO_CONFIG_7_1_4, outConfig, hRendCfg, NULL, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) - { - return error; + { + return error; + } + } + break; + case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR: + case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB: + if ( ( error = initSbaPanGainsForMcOut( inputSba, IVAS_AUDIO_CONFIG_7_1_4, NULL ) ) != IVAS_ERR_OK ) + { + return error; + } + + if ( ( error = ivas_rend_openCrend( &inputSba->crendWrapper, IVAS_AUDIO_CONFIG_7_1_4, outConfig, hRendCfg, NULL, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) + { + return error; + } + break; + default: + return IVAS_ERR_INVALID_OUTPUT_FORMAT; } break; + case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: + error = IVAS_ERR_OK; + break; /* Do nothing */ default: return IVAS_ERR_INVALID_OUTPUT_FORMAT; } - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: - error = IVAS_ERR_OK; - break; /* Do nothing */ - default: - return IVAS_ERR_INVALID_OUTPUT_FORMAT; - } - /* Check error here to keep switch statement more compact */ - if ( error != IVAS_ERR_OK ) - { - return error; - } + /* Check error here to keep switch statement more compact */ + if ( error != IVAS_ERR_OK ) + { + return error; + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif @@ -4559,75 +4552,22 @@ static ivas_error initSbaMasaRendering( ivas_rend_closeCrend( &inputSba->crendWrapper ); #ifdef IVAS_FLOAT_FIXED - IF ( ( error = ivas_dirac_ana_open_fx( &inputSba->hDirAC, inSampleRate ) ) != IVAS_ERR_OK ) + IF( ( error = ivas_dirac_ana_open_fx( &inputSba->hDirAC, inSampleRate ) ) != IVAS_ERR_OK ) { return error; } #else - if ( ( error = ivas_dirac_ana_open( &inputSba->hDirAC, inSampleRate ) ) != IVAS_ERR_OK ) - { - return error; - } -#endif - - return IVAS_ERR_OK; -} - - -#ifdef IVAS_FLOAT_FIXED -static ivas_error setRendInputActiveSba( - void *input, - const AUDIO_CONFIG inConfig, - const IVAS_REND_InputId id, - RENDER_CONFIG_DATA *hRendCfg ) -{ - ivas_error error; - rendering_context rendCtx; - AUDIO_CONFIG outConfig; - input_sba *inputSba; - - inputSba = (input_sba *) input; - rendCtx = inputSba->base.ctx; - outConfig = *rendCtx.pOutConfig; - - IF ( !isIoConfigPairSupported( inConfig, outConfig ) ) - { - return IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED; - } - - if ( ( error = allocateInputBaseBufferData( &inputSba->bufferData, MAX_BUFFER_LENGTH ) ) != IVAS_ERR_OK ) - { - return error; - } - IF ( ( error = allocateInputBaseBufferData_fx( &inputSba->bufferData_fx, MAX_BUFFER_LENGTH ) ) != IVAS_ERR_OK ) - { - return error; - } - initRendInputBase( &inputSba->base, inConfig, id, rendCtx, inputSba->bufferData, MAX_BUFFER_LENGTH ); - initRendInputBase_fx( &inputSba->base, inConfig, id, rendCtx, inputSba->bufferData_fx, MAX_BUFFER_LENGTH ); - - setZeroPanMatrix_fx( inputSba->hoaDecMtx_fx ); - - inputSba->crendWrapper = NULL; - inputSba->hDirAC = NULL; - initRotGains_fx( inputSba->rot_gains_prev_fx ); - - IF ( outConfig == IVAS_AUDIO_CONFIG_MASA1 || outConfig == IVAS_AUDIO_CONFIG_MASA2 ) - { - IF ( ( error = initSbaMasaRendering( inputSba, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) - { - return error; - } - } - - IF ( ( error = updateSbaPanGains( inputSba, outConfig, hRendCfg ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = ivas_dirac_ana_open( &inputSba->hDirAC, inSampleRate ) ) != IVAS_ERR_OK ) + { + return error; + } +#endif - return error; + return IVAS_ERR_OK; } -#else + + +#ifdef IVAS_FLOAT_FIXED static ivas_error setRendInputActiveSba( void *input, const AUDIO_CONFIG inConfig, @@ -4643,7 +4583,7 @@ static ivas_error setRendInputActiveSba( rendCtx = inputSba->base.ctx; outConfig = *rendCtx.pOutConfig; - if ( !isIoConfigPairSupported( inConfig, outConfig ) ) + IF( !isIoConfigPairSupported( inConfig, outConfig ) ) { return IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED; } @@ -4652,30 +4592,83 @@ static ivas_error setRendInputActiveSba( { return error; } - + IF( ( error = allocateInputBaseBufferData_fx( &inputSba->bufferData_fx, MAX_BUFFER_LENGTH ) ) != IVAS_ERR_OK ) + { + return error; + } initRendInputBase( &inputSba->base, inConfig, id, rendCtx, inputSba->bufferData, MAX_BUFFER_LENGTH ); + initRendInputBase_fx( &inputSba->base, inConfig, id, rendCtx, inputSba->bufferData_fx, MAX_BUFFER_LENGTH ); - setZeroPanMatrix( inputSba->hoaDecMtx ); + setZeroPanMatrix_fx( inputSba->hoaDecMtx_fx ); inputSba->crendWrapper = NULL; inputSba->hDirAC = NULL; - initRotGains( inputSba->rot_gains_prev ); + initRotGains_fx( inputSba->rot_gains_prev_fx ); - if ( outConfig == IVAS_AUDIO_CONFIG_MASA1 || outConfig == IVAS_AUDIO_CONFIG_MASA2 ) + IF( outConfig == IVAS_AUDIO_CONFIG_MASA1 || outConfig == IVAS_AUDIO_CONFIG_MASA2 ) { - if ( ( error = initSbaMasaRendering( inputSba, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) + IF( ( error = initSbaMasaRendering( inputSba, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) { return error; } } - if ( ( error = updateSbaPanGains( inputSba, outConfig, hRendCfg ) ) != IVAS_ERR_OK ) + IF( ( error = updateSbaPanGains( inputSba, outConfig, hRendCfg ) ) != IVAS_ERR_OK ) { return error; } return error; } +#else + static ivas_error setRendInputActiveSba( + void *input, + const AUDIO_CONFIG inConfig, + const IVAS_REND_InputId id, + RENDER_CONFIG_DATA *hRendCfg ) + { + ivas_error error; + rendering_context rendCtx; + AUDIO_CONFIG outConfig; + input_sba *inputSba; + + inputSba = (input_sba *) input; + rendCtx = inputSba->base.ctx; + outConfig = *rendCtx.pOutConfig; + + if ( !isIoConfigPairSupported( inConfig, outConfig ) ) + { + return IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED; + } + + if ( ( error = allocateInputBaseBufferData( &inputSba->bufferData, MAX_BUFFER_LENGTH ) ) != IVAS_ERR_OK ) + { + return error; + } + + initRendInputBase( &inputSba->base, inConfig, id, rendCtx, inputSba->bufferData, MAX_BUFFER_LENGTH ); + + setZeroPanMatrix( inputSba->hoaDecMtx ); + + inputSba->crendWrapper = NULL; + inputSba->hDirAC = NULL; + initRotGains( inputSba->rot_gains_prev ); + + if ( outConfig == IVAS_AUDIO_CONFIG_MASA1 || outConfig == IVAS_AUDIO_CONFIG_MASA2 ) + { + if ( ( error = initSbaMasaRendering( inputSba, *rendCtx.pOutSampleRate ) ) != IVAS_ERR_OK ) + { + return error; + } + } + + if ( ( error = updateSbaPanGains( inputSba, outConfig, hRendCfg ) ) != IVAS_ERR_OK ) + { + return error; + } + + return error; + } #endif #ifdef IVAS_FLOAT_FIXED static void clearInputSba( @@ -4699,26 +4692,27 @@ static void clearInputSba( return; } #else -static void clearInputSba( - input_sba *inputSba ) -{ - rendering_context rendCtx; + static void clearInputSba( + input_sba * inputSba ) + { + rendering_context rendCtx; - rendCtx = inputSba->base.ctx; + rendCtx = inputSba->base.ctx; - freeInputBaseBufferData( &inputSba->bufferData ); + freeInputBaseBufferData( &inputSba->bufferData ); - initRendInputBase( &inputSba->base, IVAS_AUDIO_CONFIG_INVALID, 0, rendCtx, NULL, 0 ); + initRendInputBase( &inputSba->base, IVAS_AUDIO_CONFIG_INVALID, 0, rendCtx, NULL, 0 ); - /* Free input's internal handles */ - ivas_rend_closeCrend( &inputSba->crendWrapper ); + /* Free input's internal handles */ + ivas_rend_closeCrend( &inputSba->crendWrapper ); - ivas_dirac_ana_close( &( inputSba->hDirAC ) ); + ivas_dirac_ana_close( &( inputSba->hDirAC ) ); - return; -} + return; + } #endif +#ifndef IVAS_FLOAT_FIXED static ivas_error setRendInputActiveMasa( void *input, const AUDIO_CONFIG inConfig, @@ -4773,6 +4767,85 @@ static ivas_error setRendInputActiveMasa( return IVAS_ERR_OK; } +#else +static ivas_error setRendInputActiveMasa( + void *input, + const AUDIO_CONFIG inConfig, + const IVAS_REND_InputId id, + RENDER_CONFIG_DATA *hRendCfg ) /* Todo: This is not used at all within MASA. Support might be better to do after refactoring. */ +{ + ivas_error error; + rendering_context rendCtx; + AUDIO_CONFIG outConfig; + input_masa *inputMasa; + Word16 numInChannels; + + inputMasa = (input_masa *) input; + rendCtx = inputMasa->base.ctx; + outConfig = *rendCtx.pOutConfig; + (void) hRendCfg; /* Suppress warning */ + + IF ( !isIoConfigPairSupported( inConfig, outConfig ) ) + { + return IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED; + } + + IF ( ( error = allocateInputBaseBufferData_fx( &inputMasa->bufferData_fx, MAX_BUFFER_LENGTH ) ) != IVAS_ERR_OK ) + { + return error; + } +#if 1/*To be removed later:(contains malloc for inputMasa->bufferData)*/ + IF ( ( error = allocateInputBaseBufferData( &inputMasa->bufferData, MAX_BUFFER_LENGTH ) ) != IVAS_ERR_OK ) + { + return error; + } +#endif + initRendInputBase_fx( &inputMasa->base, inConfig, id, rendCtx, inputMasa->bufferData_fx, MAX_BUFFER_LENGTH ); + + IF ( ( error = getAudioConfigNumChannels( inConfig, &numInChannels ) ) != IVAS_ERR_OK ) + { + return error; + } + + IF ( getAudioConfigType( outConfig ) == IVAS_REND_AUDIO_CONFIG_TYPE_MASA ) + { + inputMasa->metadataHasBeenFed = false; + IF ( ( error = masaPrerendOpen( &inputMasa->hMasaPrerend, EQ_16(inputMasa->base.inConfig , IVAS_AUDIO_CONFIG_MASA1) ? 1 : 2, *( inputMasa->base.ctx.pOutSampleRate ) ) ) != IVAS_ERR_OK ) + { + return error; + } + } + ELSE + { + IF ( ( error = initMasaExtRenderer( inputMasa, outConfig ) ) != IVAS_ERR_OK ) + { + return error; + } + inputMasa->metadataHasBeenFed = false; + } + +#if 1 /*TODO: To be removed later(fixed to float)*/ + IF( inputMasa->hMasaExtRend ) + { + DIRAC_REND_HANDLE hDirACRend = inputMasa->hMasaExtRend->hDirACRend; + IF ( hDirACRend ) + { + FOR( int i = 0; i < hDirACRend->num_outputs_dir; i++ ) + { + hDirACRend->diffuse_response_function[i] = fix16_to_float( hDirACRend->diffuse_response_function_fx[i], Q15 ); + } + IF( hDirACRend->hoa_encoder_fx ) + fixedToFloat_arrL( hDirACRend->hoa_encoder_fx, hDirACRend->hoa_encoder, Q29, hDirACRend->hoa_encoder_len ); + } + IF ( inputMasa->hMasaExtRend->hDiracDecBin ) + fixedToFloat_arrL( inputMasa->hMasaExtRend->hDiracDecBin->earlyPartEneCorrection_fx, inputMasa->hMasaExtRend->hDiracDecBin->earlyPartEneCorrection, (Word16) Q28 /*1.0f Q28*/, (Word16) CLDFB_NO_CHANNELS_MAX ); + } + inputMasa->base.inputBuffer.data = inputMasa->bufferData; + fixedToFloat_arrL( inputMasa->base.inputBuffer.data_fx, inputMasa->base.inputBuffer.data, 0, MAX_BUFFER_LENGTH ); /*fixed to float only for set zero(that's why q0)*/ +#endif + return IVAS_ERR_OK; +} +#endif // IVAS_FLOAT_FIXED static void clearInputMasa( input_masa *inputMasa ) @@ -4865,48 +4938,11 @@ ivas_error IVAS_REND_Open( { return error; } -#ifdef IVAS_FLOAT_FIXED - for ( i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++ ) - { - hIvasRend->hExternalOrientationData->Quaternions[i].w = fixedToFloat_32( hIvasRend->hExternalOrientationData->Quaternions[i].w_fx, hIvasRend->hExternalOrientationData->Quaternions[i].q_fact ); - hIvasRend->hExternalOrientationData->Quaternions[i].x = fixedToFloat_32( hIvasRend->hExternalOrientationData->Quaternions[i].x_fx, hIvasRend->hExternalOrientationData->Quaternions[i].q_fact ); - hIvasRend->hExternalOrientationData->Quaternions[i].y = fixedToFloat_32( hIvasRend->hExternalOrientationData->Quaternions[i].y_fx, hIvasRend->hExternalOrientationData->Quaternions[i].q_fact ); - hIvasRend->hExternalOrientationData->Quaternions[i].z = fixedToFloat_32( hIvasRend->hExternalOrientationData->Quaternions[i].z_fx, hIvasRend->hExternalOrientationData->Quaternions[i].q_fact ); - } - -#endif /* Initilize combined orientation data */ if ( ( error = ivas_combined_orientation_open( &( hIvasRend->hCombinedOrientationData ), outputSampleRate, num_subframes ) ) != IVAS_ERR_OK ) { return error; } -#ifdef IVAS_FLOAT_FIXED - for ( i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++ ) - { - hIvasRend->hCombinedOrientationData->Quaternions[i].w = fixedToFloat_32( hIvasRend->hCombinedOrientationData->Quaternions[i].w_fx, hIvasRend->hCombinedOrientationData->Quaternions[i].q_fact ); - hIvasRend->hCombinedOrientationData->Quaternions[i].x = fixedToFloat_32( hIvasRend->hCombinedOrientationData->Quaternions[i].x_fx, hIvasRend->hCombinedOrientationData->Quaternions[i].q_fact ); - hIvasRend->hCombinedOrientationData->Quaternions[i].y = fixedToFloat_32( hIvasRend->hCombinedOrientationData->Quaternions[i].y_fx, hIvasRend->hCombinedOrientationData->Quaternions[i].q_fact ); - hIvasRend->hCombinedOrientationData->Quaternions[i].z = fixedToFloat_32( hIvasRend->hCombinedOrientationData->Quaternions[i].z_fx, hIvasRend->hCombinedOrientationData->Quaternions[i].q_fact ); - - hIvasRend->hCombinedOrientationData->listenerPos[i].x = fixedToFloat_32( hIvasRend->hCombinedOrientationData->listenerPos[i].x_fx, hIvasRend->hCombinedOrientationData->listenerPos[i].q_fact ); - hIvasRend->hCombinedOrientationData->listenerPos[i].y = fixedToFloat_32( hIvasRend->hCombinedOrientationData->listenerPos[i].y_fx, hIvasRend->hCombinedOrientationData->listenerPos[i].q_fact ); - hIvasRend->hCombinedOrientationData->listenerPos[i].z = fixedToFloat_32( hIvasRend->hCombinedOrientationData->listenerPos[i].z_fx, hIvasRend->hCombinedOrientationData->listenerPos[i].q_fact ); - for ( Word16 j = 0; j < 3; j++ ) - { - for ( Word16 k = 0; k < 3; k++ ) - { - hIvasRend->hCombinedOrientationData->Rmat[i][j][k] = (float) fixedToFloat_32( hIvasRend->hCombinedOrientationData->Rmat_fx[i][j][k], 30 ); - } - } - } - for ( Word16 j = 0; j < 3; j++ ) - { - for ( Word16 k = 0; k < 3; k++ ) - { - hIvasRend->hCombinedOrientationData->Rmat_prev[j][k] = (float) fixedToFloat_32( hIvasRend->hCombinedOrientationData->Rmat_prev_fx[j][k], 30 ); - } - } -#endif /* Initialize EFAP */ if ( ( error = initEfap( &hIvasRend->efapOutWrapper, outConfig, &hIvasRend->customLsOut ) ) != IVAS_ERR_OK ) { @@ -4943,7 +4979,7 @@ ivas_error IVAS_REND_Open( hIvasRend->inputsMc[i].nonDiegeticPan = nonDiegeticPan; hIvasRend->inputsMc[i].nonDiegeticPanGain = nonDiegeticPanGain; Word32 temp = ( abs( (Word32) nonDiegeticPanGain ) ); - hIvasRend->inputsMc[i].nonDiegeticPanGain_fx = ( temp == 1 ) ? ( ( nonDiegeticPanGain < 0 ) ? L_negate( ONE_IN_Q31 ) : ONE_IN_Q31 ) :(Word32) (nonDiegeticPanGain * ( ONE_IN_Q31 )); + hIvasRend->inputsMc[i].nonDiegeticPanGain_fx = ( temp == 1 ) ? ( ( nonDiegeticPanGain < 0 ) ? L_negate( ONE_IN_Q31 ) : ONE_IN_Q31 ) : (Word32) ( nonDiegeticPanGain * ( ONE_IN_Q31 ) ); hIvasRend->inputsMc[i].hMcMasa = NULL; } @@ -4971,143 +5007,143 @@ ivas_error IVAS_REND_Open( return IVAS_ERR_OK; } #else -/*------------------------------------------------------------------------- - * IVAS_REND_Open() - * - * - *------------------------------------------------------------------------*/ - -ivas_error IVAS_REND_Open( - IVAS_REND_HANDLE *phIvasRend, - const int32_t outputSampleRate, - const AUDIO_CONFIG outConfig, - const int16_t nonDiegeticPan, - const float nonDiegeticPanGain, - const int16_t num_subframes ) -{ - int16_t i; - IVAS_REND_HANDLE hIvasRend; - ivas_error error; - int16_t numOutChannels; - - /* Validate function arguments */ - if ( phIvasRend == NULL ) - { - return IVAS_ERR_UNEXPECTED_NULL_POINTER; - } - - if ( ( error = validateOutputAudioConfig( outConfig ) ) != IVAS_ERR_OK ) - { - return error; - } + /*------------------------------------------------------------------------- + * IVAS_REND_Open() + * + * + *------------------------------------------------------------------------*/ - if ( ( error = validateOutputSampleRate( outputSampleRate, outConfig ) ) != IVAS_ERR_OK ) - { - return error; - } + ivas_error IVAS_REND_Open( + IVAS_REND_HANDLE * phIvasRend, + const int32_t outputSampleRate, + const AUDIO_CONFIG outConfig, + const int16_t nonDiegeticPan, + const float nonDiegeticPanGain, + const int16_t num_subframes ) + { + int16_t i; + IVAS_REND_HANDLE hIvasRend; + ivas_error error; + int16_t numOutChannels; - *phIvasRend = (IVAS_REND_HANDLE) malloc( sizeof( struct IVAS_REND ) ); - if ( *phIvasRend == NULL ) - { - return IVAS_ERR_FAILED_ALLOC; - } + /* Validate function arguments */ + if ( phIvasRend == NULL ) + { + return IVAS_ERR_UNEXPECTED_NULL_POINTER; + } - hIvasRend = *phIvasRend; - hIvasRend->sampleRateOut = outputSampleRate; - hIvasRend->outputConfig = outConfig; - hIvasRend->customLsOut = defaultCustomLs(); - hIvasRend->hLimiter = NULL; - hIvasRend->efapOutWrapper.hEfap = NULL; - hIvasRend->efapOutWrapper.pCustomLsSetup = NULL; - hIvasRend->num_subframes = num_subframes; + if ( ( error = validateOutputAudioConfig( outConfig ) ) != IVAS_ERR_OK ) + { + return error; + } - /* Initialize limiter */ - if ( ( error = IVAS_REND_NumOutChannels( hIvasRend, &numOutChannels ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = validateOutputSampleRate( outputSampleRate, outConfig ) ) != IVAS_ERR_OK ) + { + return error; + } - if ( ( error = initLimiter( &hIvasRend->hLimiter, numOutChannels, outputSampleRate ) ) != IVAS_ERR_OK ) - { - return error; - } + *phIvasRend = (IVAS_REND_HANDLE) malloc( sizeof( struct IVAS_REND ) ); + if ( *phIvasRend == NULL ) + { + return IVAS_ERR_FAILED_ALLOC; + } - /* Initialize headrotation data */ - if ( ( error = initHeadRotation( hIvasRend ) ) != IVAS_ERR_OK ) - { - return error; - } + hIvasRend = *phIvasRend; + hIvasRend->sampleRateOut = outputSampleRate; + hIvasRend->outputConfig = outConfig; + hIvasRend->customLsOut = defaultCustomLs(); + hIvasRend->hLimiter = NULL; + hIvasRend->efapOutWrapper.hEfap = NULL; + hIvasRend->efapOutWrapper.pCustomLsSetup = NULL; + hIvasRend->num_subframes = num_subframes; - /* Initialize external orientation data */ - if ( ( error = ivas_external_orientation_open( &( hIvasRend->hExternalOrientationData ), num_subframes ) ) != IVAS_ERR_OK ) - { - return error; - } + /* Initialize limiter */ + if ( ( error = IVAS_REND_NumOutChannels( hIvasRend, &numOutChannels ) ) != IVAS_ERR_OK ) + { + return error; + } - /* Initilize combined orientation data */ - if ( ( error = ivas_combined_orientation_open( &( hIvasRend->hCombinedOrientationData ), outputSampleRate, num_subframes ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = initLimiter( &hIvasRend->hLimiter, numOutChannels, outputSampleRate ) ) != IVAS_ERR_OK ) + { + return error; + } - /* Initialize EFAP */ - if ( ( error = initEfap( &hIvasRend->efapOutWrapper, outConfig, &hIvasRend->customLsOut ) ) != IVAS_ERR_OK ) - { - return error; - } + /* Initialize headrotation data */ + if ( ( error = initHeadRotation( hIvasRend ) ) != IVAS_ERR_OK ) + { + return error; + } - /* Initialize inputs */ + /* Initialize external orientation data */ + if ( ( error = ivas_external_orientation_open( &( hIvasRend->hExternalOrientationData ), num_subframes ) ) != IVAS_ERR_OK ) + { + return error; + } - for ( i = 0; i < RENDERER_MAX_ISM_INPUTS; ++i ) - { - initRendInputBase( &hIvasRend->inputsIsm[i].base, IVAS_AUDIO_CONFIG_INVALID, 0, getRendCtx( hIvasRend ), NULL, 0 ); + /* Initilize combined orientation data */ + if ( ( error = ivas_combined_orientation_open( &( hIvasRend->hCombinedOrientationData ), outputSampleRate, num_subframes ) ) != IVAS_ERR_OK ) + { + return error; + } - hIvasRend->inputsIsm[i].crendWrapper = NULL; - hIvasRend->inputsIsm[i].hReverb = NULL; - hIvasRend->inputsIsm[i].tdRendWrapper.hBinRendererTd = NULL; - hIvasRend->inputsIsm[i].bufferData = NULL; - hIvasRend->inputsIsm[i].nonDiegeticPan = nonDiegeticPan; - hIvasRend->inputsIsm[i].nonDiegeticPanGain = nonDiegeticPanGain; - hIvasRend->inputsIsm[i].hOMasa = NULL; - } + /* Initialize EFAP */ + if ( ( error = initEfap( &hIvasRend->efapOutWrapper, outConfig, &hIvasRend->customLsOut ) ) != IVAS_ERR_OK ) + { + return error; + } - for ( i = 0; i < RENDERER_MAX_MC_INPUTS; ++i ) - { - initRendInputBase( &hIvasRend->inputsMc[i].base, IVAS_AUDIO_CONFIG_INVALID, 0, getRendCtx( hIvasRend ), NULL, 0 ); + /* Initialize inputs */ - hIvasRend->inputsMc[i].efapInWrapper.hEfap = NULL; - hIvasRend->inputsMc[i].crendWrapper = NULL; - hIvasRend->inputsMc[i].hReverb = NULL; - hIvasRend->inputsMc[i].tdRendWrapper.hBinRendererTd = NULL; - hIvasRend->inputsMc[i].bufferData = NULL; - hIvasRend->inputsMc[i].lfeDelayBuffer = NULL; - hIvasRend->inputsMc[i].nonDiegeticPan = nonDiegeticPan; - hIvasRend->inputsMc[i].nonDiegeticPanGain = nonDiegeticPanGain; - hIvasRend->inputsMc[i].hMcMasa = NULL; - } + for ( i = 0; i < RENDERER_MAX_ISM_INPUTS; ++i ) + { + initRendInputBase( &hIvasRend->inputsIsm[i].base, IVAS_AUDIO_CONFIG_INVALID, 0, getRendCtx( hIvasRend ), NULL, 0 ); - for ( i = 0; i < RENDERER_MAX_SBA_INPUTS; ++i ) - { - initRendInputBase( &hIvasRend->inputsSba[i].base, IVAS_AUDIO_CONFIG_INVALID, 0, getRendCtx( hIvasRend ), NULL, 0 ); + hIvasRend->inputsIsm[i].crendWrapper = NULL; + hIvasRend->inputsIsm[i].hReverb = NULL; + hIvasRend->inputsIsm[i].tdRendWrapper.hBinRendererTd = NULL; + hIvasRend->inputsIsm[i].bufferData = NULL; + hIvasRend->inputsIsm[i].nonDiegeticPan = nonDiegeticPan; + hIvasRend->inputsIsm[i].nonDiegeticPanGain = nonDiegeticPanGain; + hIvasRend->inputsIsm[i].hOMasa = NULL; + } - hIvasRend->inputsSba[i].crendWrapper = NULL; - hIvasRend->inputsSba[i].bufferData = NULL; - hIvasRend->inputsSba[i].hDirAC = NULL; - } + for ( i = 0; i < RENDERER_MAX_MC_INPUTS; ++i ) + { + initRendInputBase( &hIvasRend->inputsMc[i].base, IVAS_AUDIO_CONFIG_INVALID, 0, getRendCtx( hIvasRend ), NULL, 0 ); - for ( i = 0; i < RENDERER_MAX_MASA_INPUTS; ++i ) - { - initRendInputBase( &hIvasRend->inputsMasa[i].base, IVAS_AUDIO_CONFIG_INVALID, 0, getRendCtx( hIvasRend ), NULL, 0 ); + hIvasRend->inputsMc[i].efapInWrapper.hEfap = NULL; + hIvasRend->inputsMc[i].crendWrapper = NULL; + hIvasRend->inputsMc[i].hReverb = NULL; + hIvasRend->inputsMc[i].tdRendWrapper.hBinRendererTd = NULL; + hIvasRend->inputsMc[i].bufferData = NULL; + hIvasRend->inputsMc[i].lfeDelayBuffer = NULL; + hIvasRend->inputsMc[i].nonDiegeticPan = nonDiegeticPan; + hIvasRend->inputsMc[i].nonDiegeticPanGain = nonDiegeticPanGain; + hIvasRend->inputsMc[i].hMcMasa = NULL; + } - hIvasRend->inputsMasa[i].metadataHasBeenFed = false; - hIvasRend->inputsMasa[i].bufferData = NULL; - hIvasRend->inputsMasa[i].hMasaPrerend = NULL; - hIvasRend->inputsMasa[i].hMasaExtRend = NULL; - } + for ( i = 0; i < RENDERER_MAX_SBA_INPUTS; ++i ) + { + initRendInputBase( &hIvasRend->inputsSba[i].base, IVAS_AUDIO_CONFIG_INVALID, 0, getRendCtx( hIvasRend ), NULL, 0 ); + + hIvasRend->inputsSba[i].crendWrapper = NULL; + hIvasRend->inputsSba[i].bufferData = NULL; + hIvasRend->inputsSba[i].hDirAC = NULL; + } + for ( i = 0; i < RENDERER_MAX_MASA_INPUTS; ++i ) + { + initRendInputBase( &hIvasRend->inputsMasa[i].base, IVAS_AUDIO_CONFIG_INVALID, 0, getRendCtx( hIvasRend ), NULL, 0 ); - return IVAS_ERR_OK; -} + hIvasRend->inputsMasa[i].metadataHasBeenFed = false; + hIvasRend->inputsMasa[i].bufferData = NULL; + hIvasRend->inputsMasa[i].hMasaPrerend = NULL; + hIvasRend->inputsMasa[i].hMasaExtRend = NULL; + } + + + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED static LSSETUP_CUSTOM_STRUCT makeCustomLsSetup( @@ -5142,32 +5178,32 @@ static LSSETUP_CUSTOM_STRUCT makeCustomLsSetup( return customLs; } #else -static LSSETUP_CUSTOM_STRUCT makeCustomLsSetup( - const IVAS_CUSTOM_LS_DATA rendCustomLsLayout ) -{ - int16_t i; - LSSETUP_CUSTOM_STRUCT customLs; + static LSSETUP_CUSTOM_STRUCT makeCustomLsSetup( + const IVAS_CUSTOM_LS_DATA rendCustomLsLayout ) + { + int16_t i; + LSSETUP_CUSTOM_STRUCT customLs; - /* Copy layout description */ - customLs.num_spk = rendCustomLsLayout.num_spk; - mvr2r( rendCustomLsLayout.azimuth, customLs.ls_azimuth, rendCustomLsLayout.num_spk ); - mvr2r( rendCustomLsLayout.elevation, customLs.ls_elevation, rendCustomLsLayout.num_spk ); + /* Copy layout description */ + customLs.num_spk = rendCustomLsLayout.num_spk; + mvr2r( rendCustomLsLayout.azimuth, customLs.ls_azimuth, rendCustomLsLayout.num_spk ); + mvr2r( rendCustomLsLayout.elevation, customLs.ls_elevation, rendCustomLsLayout.num_spk ); - customLs.is_planar_setup = 1; - for ( i = 0; i < rendCustomLsLayout.num_spk; ++i ) - { - if ( fabsf( rendCustomLsLayout.elevation[i] ) > EPSILON ) - { - customLs.is_planar_setup = 0; - break; - } - } + customLs.is_planar_setup = 1; + for ( i = 0; i < rendCustomLsLayout.num_spk; ++i ) + { + if ( fabsf( rendCustomLsLayout.elevation[i] ) > EPSILON ) + { + customLs.is_planar_setup = 0; + break; + } + } - customLs.num_lfe = rendCustomLsLayout.num_lfe; - mvs2s( rendCustomLsLayout.lfe_idx, customLs.lfe_idx, rendCustomLsLayout.num_lfe ); + customLs.num_lfe = rendCustomLsLayout.num_lfe; + mvs2s( rendCustomLsLayout.lfe_idx, customLs.lfe_idx, rendCustomLsLayout.num_lfe ); - return customLs; -} + return customLs; + } #endif @@ -5202,34 +5238,34 @@ static ivas_error validateCustomLsLayout_fx( return IVAS_ERR_OK; } #else -static ivas_error validateCustomLsLayout( - const IVAS_CUSTOM_LS_DATA layout ) -{ - int16_t i; + static ivas_error validateCustomLsLayout( + const IVAS_CUSTOM_LS_DATA layout ) + { + int16_t i; - /* Negative number of speakers or LFEs makes no sense */ - if ( layout.num_spk < 0 || layout.num_lfe < 0 ) - { - return IVAS_ERR_INVALID_CUSTOM_LS_LAYOUT; - } + /* Negative number of speakers or LFEs makes no sense */ + if ( layout.num_spk < 0 || layout.num_lfe < 0 ) + { + return IVAS_ERR_INVALID_CUSTOM_LS_LAYOUT; + } - /* There must be at least one speaker or LFE in the layout */ - if ( layout.num_spk + layout.num_lfe <= 0 ) - { - return IVAS_ERR_INVALID_CUSTOM_LS_LAYOUT; - } + /* There must be at least one speaker or LFE in the layout */ + if ( layout.num_spk + layout.num_lfe <= 0 ) + { + return IVAS_ERR_INVALID_CUSTOM_LS_LAYOUT; + } - /* LFE indices must be positive */ - for ( i = 0; i < layout.num_lfe; ++i ) - { - if ( layout.lfe_idx[i] < 0 ) - { - return IVAS_ERR_INVALID_CUSTOM_LS_LAYOUT; - } - } + /* LFE indices must be positive */ + for ( i = 0; i < layout.num_lfe; ++i ) + { + if ( layout.lfe_idx[i] < 0 ) + { + return IVAS_ERR_INVALID_CUSTOM_LS_LAYOUT; + } + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif @@ -5266,10 +5302,10 @@ ivas_error IVAS_REND_ConfigureCustomOutputLoudspeakerLayout( return error; } #else - if ( ( error = validateCustomLsLayout( layout ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = validateCustomLsLayout( layout ) ) != IVAS_ERR_OK ) + { + return error; + } #endif hIvasRend->customLsOut = makeCustomLsSetup( layout ); @@ -5367,40 +5403,40 @@ ivas_error IVAS_REND_NumOutChannels( return IVAS_ERR_OK; } #else -/*-------------------------------------------------------------------* - * IVAS_REND_NumOutChannels() - * - * - *-------------------------------------------------------------------*/ + /*-------------------------------------------------------------------* + * IVAS_REND_NumOutChannels() + * + * + *-------------------------------------------------------------------*/ -ivas_error IVAS_REND_NumOutChannels( - IVAS_REND_CONST_HANDLE hIvasRend, - int16_t *numOutChannels ) -{ - ivas_error error; + ivas_error IVAS_REND_NumOutChannels( + IVAS_REND_CONST_HANDLE hIvasRend, + int16_t * numOutChannels ) + { + ivas_error error; - /* Validate function arguments */ - if ( hIvasRend == NULL || numOutChannels == NULL ) - { - return IVAS_ERR_UNEXPECTED_NULL_POINTER; - } + /* Validate function arguments */ + if ( hIvasRend == NULL || numOutChannels == NULL ) + { + return IVAS_ERR_UNEXPECTED_NULL_POINTER; + } - /* Handle special cases where additional info is needed from the renderer, otherwise use getAudioConfigNumChannels() */ - switch ( hIvasRend->outputConfig ) - { - case IVAS_AUDIO_CONFIG_LS_CUSTOM: - *numOutChannels = hIvasRend->customLsOut.num_spk + hIvasRend->customLsOut.num_lfe; - break; - default: - if ( ( error = getAudioConfigNumChannels( hIvasRend->outputConfig, numOutChannels ) ) != IVAS_ERR_OK ) + /* Handle special cases where additional info is needed from the renderer, otherwise use getAudioConfigNumChannels() */ + switch ( hIvasRend->outputConfig ) { - return error; + case IVAS_AUDIO_CONFIG_LS_CUSTOM: + *numOutChannels = hIvasRend->customLsOut.num_spk + hIvasRend->customLsOut.num_lfe; + break; + default: + if ( ( error = getAudioConfigNumChannels( hIvasRend->outputConfig, numOutChannels ) ) != IVAS_ERR_OK ) + { + return error; + } + break; } - break; - } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif @@ -5415,15 +5451,15 @@ static IVAS_REND_InputId makeInputId( return (IVAS_REND_InputId) UL_or( UL_lshl( ( (UWord32) getAudioConfigType( config ) ), 8 ), L_add( inputIndex, 1 ) ); } #else -static IVAS_REND_InputId makeInputId( - AUDIO_CONFIG config, - const int32_t inputIndex ) -{ - /* Put config type in second byte (from LSB), put index + 1 in first byte - * - * Index is incremented here so that a valid ID can never be 0. */ - return (IVAS_REND_InputId) ( ( ( (uint32_t) getAudioConfigType( config ) ) << 8 ) | ( inputIndex + 1 ) ); -} + static IVAS_REND_InputId makeInputId( + AUDIO_CONFIG config, + const int32_t inputIndex ) + { + /* Put config type in second byte (from LSB), put index + 1 in first byte + * + * Index is incremented here so that a valid ID can never be 0. */ + return (IVAS_REND_InputId) ( ( ( (uint32_t) getAudioConfigType( config ) ) << 8 ) | ( inputIndex + 1 ) ); + } #endif @@ -5493,69 +5529,69 @@ static ivas_error getInputById( return IVAS_ERR_OK; } #else -static ivas_error getInputById( - IVAS_REND_HANDLE hIvasRend, - IVAS_REND_InputId inputId, - void **ppInput ) -{ - int32_t inputIndex; - IVAS_REND_AudioConfigType configType; - input_base *pInputBase; + static ivas_error getInputById( + IVAS_REND_HANDLE hIvasRend, + IVAS_REND_InputId inputId, + void **ppInput ) + { + int32_t inputIndex; + IVAS_REND_AudioConfigType configType; + input_base *pInputBase; - /* Reverse makeInputId() */ - inputIndex = ( inputId & 0xFF ) - 1; - configType = ( inputId & 0xFF00 ) >> 8; + /* Reverse makeInputId() */ + inputIndex = ( inputId & 0xFF ) - 1; + configType = ( inputId & 0xFF00 ) >> 8; - /* Validate values derived from input ID */ - if ( inputIndex < 0 ) - { - return IVAS_ERR_INVALID_INPUT_ID; - } - switch ( configType ) - { - case IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED: - if ( inputIndex > RENDERER_MAX_ISM_INPUTS ) - { - return IVAS_ERR_INVALID_INPUT_ID; - } - pInputBase = &hIvasRend->inputsIsm[inputIndex].base; - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: - if ( inputIndex > RENDERER_MAX_MC_INPUTS ) + /* Validate values derived from input ID */ + if ( inputIndex < 0 ) { return IVAS_ERR_INVALID_INPUT_ID; } - pInputBase = &hIvasRend->inputsMc[inputIndex].base; - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: - if ( inputIndex > RENDERER_MAX_SBA_INPUTS ) + switch ( configType ) { - return IVAS_ERR_INVALID_INPUT_ID; + case IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED: + if ( inputIndex > RENDERER_MAX_ISM_INPUTS ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + pInputBase = &hIvasRend->inputsIsm[inputIndex].base; + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: + if ( inputIndex > RENDERER_MAX_MC_INPUTS ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + pInputBase = &hIvasRend->inputsMc[inputIndex].base; + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: + if ( inputIndex > RENDERER_MAX_SBA_INPUTS ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + pInputBase = &hIvasRend->inputsSba[inputIndex].base; + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: + if ( inputIndex > RENDERER_MAX_MASA_INPUTS ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + pInputBase = &hIvasRend->inputsMasa[inputIndex].base; + break; + default: + return IVAS_ERR_INVALID_INPUT_ID; } - pInputBase = &hIvasRend->inputsSba[inputIndex].base; - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: - if ( inputIndex > RENDERER_MAX_MASA_INPUTS ) + + /* Ensure input ID matches and that input is active */ + if ( pInputBase->id != inputId || pInputBase->inConfig == IVAS_AUDIO_CONFIG_INVALID ) { return IVAS_ERR_INVALID_INPUT_ID; } - pInputBase = &hIvasRend->inputsMasa[inputIndex].base; - break; - default: - return IVAS_ERR_INVALID_INPUT_ID; - } - - /* Ensure input ID matches and that input is active */ - if ( pInputBase->id != inputId || pInputBase->inConfig == IVAS_AUDIO_CONFIG_INVALID ) - { - return IVAS_ERR_INVALID_INPUT_ID; - } - /* Validation done, set value via output parameter */ - *ppInput = pInputBase; + /* Validation done, set value via output parameter */ + *ppInput = pInputBase; - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif @@ -5588,97 +5624,33 @@ static ivas_error getConstInputById( pInputBase = &hIvasRend->inputsIsm[inputIndex].base; BREAK; case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: - IF( GT_32( inputIndex, RENDERER_MAX_MC_INPUTS ) ) - { - return IVAS_ERR_INVALID_INPUT_ID; - } - pInputBase = &hIvasRend->inputsMc[inputIndex].base; - BREAK; - case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: - IF( GT_32( inputIndex, RENDERER_MAX_SBA_INPUTS ) ) - { - return IVAS_ERR_INVALID_INPUT_ID; - } - pInputBase = &hIvasRend->inputsSba[inputIndex].base; - BREAK; - case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: - IF( GT_32( inputIndex, RENDERER_MAX_MASA_INPUTS ) ) - { - return IVAS_ERR_INVALID_INPUT_ID; - } - pInputBase = &hIvasRend->inputsMasa[inputIndex].base; - BREAK; - default: - return IVAS_ERR_INVALID_INPUT_ID; - } - - /* Ensure input ID matches and that input is active */ - test(); - IF( NE_32( pInputBase->id, inputId ) || EQ_32( pInputBase->inConfig, IVAS_AUDIO_CONFIG_INVALID ) ) - { - return IVAS_ERR_INVALID_INPUT_ID; - } - - /* Validation done, set value via output parameter */ - *ppInput = pInputBase; - - return IVAS_ERR_OK; -} -#else -static ivas_error getConstInputById( - IVAS_REND_CONST_HANDLE hIvasRend, - const IVAS_REND_InputId inputId, - const void **ppInput ) -{ - int32_t inputIndex; - IVAS_REND_AudioConfigType configType; - const input_base *pInputBase; - - /* Reverse makeInputId() */ - inputIndex = ( inputId & 0xFF ) - 1; - configType = ( inputId & 0xFF00 ) >> 8; - - /* Validate values derived from input ID */ - if ( inputIndex < 0 ) - { - return IVAS_ERR_INVALID_INPUT_ID; - } - switch ( configType ) - { - case IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED: - if ( inputIndex > RENDERER_MAX_ISM_INPUTS ) - { - return IVAS_ERR_INVALID_INPUT_ID; - } - pInputBase = &hIvasRend->inputsIsm[inputIndex].base; - break; - case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: - if ( inputIndex > RENDERER_MAX_MC_INPUTS ) + IF( GT_32( inputIndex, RENDERER_MAX_MC_INPUTS ) ) { return IVAS_ERR_INVALID_INPUT_ID; } pInputBase = &hIvasRend->inputsMc[inputIndex].base; - break; + BREAK; case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: - if ( inputIndex > RENDERER_MAX_SBA_INPUTS ) + IF( GT_32( inputIndex, RENDERER_MAX_SBA_INPUTS ) ) { return IVAS_ERR_INVALID_INPUT_ID; } pInputBase = &hIvasRend->inputsSba[inputIndex].base; - break; + BREAK; case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: - if ( inputIndex > RENDERER_MAX_MASA_INPUTS ) + IF( GT_32( inputIndex, RENDERER_MAX_MASA_INPUTS ) ) { return IVAS_ERR_INVALID_INPUT_ID; } pInputBase = &hIvasRend->inputsMasa[inputIndex].base; - break; + BREAK; default: return IVAS_ERR_INVALID_INPUT_ID; } /* Ensure input ID matches and that input is active */ - if ( pInputBase->id != inputId || pInputBase->inConfig == IVAS_AUDIO_CONFIG_INVALID ) + test(); + IF( NE_32( pInputBase->id, inputId ) || EQ_32( pInputBase->inConfig, IVAS_AUDIO_CONFIG_INVALID ) ) { return IVAS_ERR_INVALID_INPUT_ID; } @@ -5688,6 +5660,70 @@ static ivas_error getConstInputById( return IVAS_ERR_OK; } +#else + static ivas_error getConstInputById( + IVAS_REND_CONST_HANDLE hIvasRend, + const IVAS_REND_InputId inputId, + const void **ppInput ) + { + int32_t inputIndex; + IVAS_REND_AudioConfigType configType; + const input_base *pInputBase; + + /* Reverse makeInputId() */ + inputIndex = ( inputId & 0xFF ) - 1; + configType = ( inputId & 0xFF00 ) >> 8; + + /* Validate values derived from input ID */ + if ( inputIndex < 0 ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + switch ( configType ) + { + case IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED: + if ( inputIndex > RENDERER_MAX_ISM_INPUTS ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + pInputBase = &hIvasRend->inputsIsm[inputIndex].base; + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: + if ( inputIndex > RENDERER_MAX_MC_INPUTS ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + pInputBase = &hIvasRend->inputsMc[inputIndex].base; + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: + if ( inputIndex > RENDERER_MAX_SBA_INPUTS ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + pInputBase = &hIvasRend->inputsSba[inputIndex].base; + break; + case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: + if ( inputIndex > RENDERER_MAX_MASA_INPUTS ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + pInputBase = &hIvasRend->inputsMasa[inputIndex].base; + break; + default: + return IVAS_ERR_INVALID_INPUT_ID; + } + + /* Ensure input ID matches and that input is active */ + if ( pInputBase->id != inputId || pInputBase->inConfig == IVAS_AUDIO_CONFIG_INVALID ) + { + return IVAS_ERR_INVALID_INPUT_ID; + } + + /* Validation done, set value via output parameter */ + *ppInput = pInputBase; + + return IVAS_ERR_OK; + } #endif #ifndef IVAS_FLOAT_FIXED @@ -5732,46 +5768,46 @@ static ivas_error findFreeInputSlot( return IVAS_ERR_OK; } #else -static ivas_error findFreeInputSlot_fx( - const void *inputs, - const Word32 inputStructSize, - const Word32 maxInputs, - Word32 *inputIndex ) -{ - /* Using a void pointer and a separately provided size is a hack for this function - to be reusable for arrays of any input type (input_ism, input_mc, input_sba, input_masa). - Assumptions: - - input_base is always the first member in the input struct - - provided size is correct - */ + static ivas_error findFreeInputSlot_fx( + const void *inputs, + const Word32 inputStructSize, + const Word32 maxInputs, + Word32 *inputIndex ) + { + /* Using a void pointer and a separately provided size is a hack for this function + to be reusable for arrays of any input type (input_ism, input_mc, input_sba, input_masa). + Assumptions: + - input_base is always the first member in the input struct + - provided size is correct + */ - Word32 i; - bool canAddInput; - const UWord8 *pByte; - const input_base *pInputBase; + Word32 i; + bool canAddInput; + const UWord8 *pByte; + const input_base *pInputBase; - canAddInput = false; + canAddInput = false; - /* Find first unused input in array */ - FOR( ( i = 0, pByte = inputs ); i < maxInputs; ( ++i, pByte += inputStructSize ) ) - { - pInputBase = (const input_base *) pByte; + /* Find first unused input in array */ + FOR( ( i = 0, pByte = inputs ); i < maxInputs; ( ++i, pByte += inputStructSize ) ) + { + pInputBase = (const input_base *) pByte; - IF( EQ_32( pInputBase->inConfig, IVAS_AUDIO_CONFIG_INVALID ) ) - { - *inputIndex = i; - canAddInput = true; - BREAK; - } - } + IF( EQ_32( pInputBase->inConfig, IVAS_AUDIO_CONFIG_INVALID ) ) + { + *inputIndex = i; + canAddInput = true; + BREAK; + } + } - IF ( !canAddInput ) - { - return IVAS_ERR_TOO_MANY_INPUTS; - } + IF( !canAddInput ) + { + return IVAS_ERR_TOO_MANY_INPUTS; + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif @@ -5847,71 +5883,71 @@ ivas_error IVAS_REND_AddInput( return IVAS_ERR_OK; } #else -ivas_error IVAS_REND_AddInput_fx( - IVAS_REND_HANDLE hIvasRend, /* i/o: Renderer handle */ - const AUDIO_CONFIG inConfig, /* i : audio config for a new input */ - IVAS_REND_InputId *inputId /* o : ID of the new input */ -) -{ - ivas_error error; - Word32 maxNumInputsOfType; - void *inputsArray; - Word32 inputStructSize; - ivas_error ( *activateInput )( void *, AUDIO_CONFIG, IVAS_REND_InputId, RENDER_CONFIG_DATA * ); - Word32 inputIndex; + ivas_error IVAS_REND_AddInput_fx( + IVAS_REND_HANDLE hIvasRend, /* i/o: Renderer handle */ + const AUDIO_CONFIG inConfig, /* i : audio config for a new input */ + IVAS_REND_InputId *inputId /* o : ID of the new input */ + ) + { + ivas_error error; + Word32 maxNumInputsOfType; + void *inputsArray; + Word32 inputStructSize; + ivas_error ( *activateInput )( void *, AUDIO_CONFIG, IVAS_REND_InputId, RENDER_CONFIG_DATA * ); + Word32 inputIndex; - /* Validate function arguments */ - IF ( hIvasRend == NULL || inputId == NULL ) - { - return IVAS_ERR_UNEXPECTED_NULL_POINTER; - } + /* Validate function arguments */ + IF( hIvasRend == NULL || inputId == NULL ) + { + return IVAS_ERR_UNEXPECTED_NULL_POINTER; + } - SWITCH ( getAudioConfigType( inConfig ) ) - { - case IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED: - maxNumInputsOfType = RENDERER_MAX_ISM_INPUTS; - inputsArray = hIvasRend->inputsIsm; - inputStructSize = sizeof( *hIvasRend->inputsIsm ); - activateInput = setRendInputActiveIsm; - BREAK; - case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: - maxNumInputsOfType = RENDERER_MAX_MC_INPUTS; - inputsArray = hIvasRend->inputsMc; - inputStructSize = sizeof( *hIvasRend->inputsMc ); - activateInput = setRendInputActiveMc; - BREAK; - case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: - maxNumInputsOfType = RENDERER_MAX_SBA_INPUTS; - inputsArray = hIvasRend->inputsSba; - inputStructSize = sizeof( *hIvasRend->inputsSba ); - activateInput = setRendInputActiveSba; - BREAK; - case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: - maxNumInputsOfType = RENDERER_MAX_MASA_INPUTS; - inputsArray = hIvasRend->inputsMasa; - inputStructSize = sizeof( *hIvasRend->inputsMasa ); - activateInput = setRendInputActiveMasa; - BREAK; - default: - return IVAS_ERR_INVALID_INPUT_FORMAT; - } + SWITCH( getAudioConfigType( inConfig ) ) + { + case IVAS_REND_AUDIO_CONFIG_TYPE_OBJECT_BASED: + maxNumInputsOfType = RENDERER_MAX_ISM_INPUTS; + inputsArray = hIvasRend->inputsIsm; + inputStructSize = sizeof( *hIvasRend->inputsIsm ); + activateInput = setRendInputActiveIsm; + BREAK; + case IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED: + maxNumInputsOfType = RENDERER_MAX_MC_INPUTS; + inputsArray = hIvasRend->inputsMc; + inputStructSize = sizeof( *hIvasRend->inputsMc ); + activateInput = setRendInputActiveMc; + BREAK; + case IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS: + maxNumInputsOfType = RENDERER_MAX_SBA_INPUTS; + inputsArray = hIvasRend->inputsSba; + inputStructSize = sizeof( *hIvasRend->inputsSba ); + activateInput = setRendInputActiveSba; + BREAK; + case IVAS_REND_AUDIO_CONFIG_TYPE_MASA: + maxNumInputsOfType = RENDERER_MAX_MASA_INPUTS; + inputsArray = hIvasRend->inputsMasa; + inputStructSize = sizeof( *hIvasRend->inputsMasa ); + activateInput = setRendInputActiveMasa; + BREAK; + default: + return IVAS_ERR_INVALID_INPUT_FORMAT; + } - /* Find first free input in array corresponding to input type */ - IF ( ( error = findFreeInputSlot_fx( inputsArray, inputStructSize, maxNumInputsOfType, &inputIndex ) ) != IVAS_ERR_OK ) - { - return error; - } + /* Find first free input in array corresponding to input type */ + IF( ( error = findFreeInputSlot_fx( inputsArray, inputStructSize, maxNumInputsOfType, &inputIndex ) ) != IVAS_ERR_OK ) + { + return error; + } - *inputId = makeInputId( inConfig, inputIndex ); + *inputId = makeInputId( inConfig, inputIndex ); - IF ( ( error = activateInput( (uint8_t *) inputsArray + inputStructSize * inputIndex, inConfig, *inputId, hIvasRend->hRendererConfig ) ) != IVAS_ERR_OK ) - { - return error; - } + IF( ( error = activateInput( (uint8_t *) inputsArray + inputStructSize * inputIndex, inConfig, *inputId, hIvasRend->hRendererConfig ) ) != IVAS_ERR_OK ) + { + return error; + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif @@ -5943,10 +5979,10 @@ ivas_error IVAS_REND_ConfigureCustomInputLoudspeakerLayout( return error; } #else - if ( ( error = validateCustomLsLayout( layout ) ) != IVAS_ERR_OK ) - { - return error; - } + if ( ( error = validateCustomLsLayout( layout ) ) != IVAS_ERR_OK ) + { + return error; + } #endif if ( ( error = getInputById( hIvasRend, inputId, (void **) &inputMc ) ) != IVAS_ERR_OK ) @@ -6020,30 +6056,30 @@ ivas_error IVAS_REND_SetInputGain( return IVAS_ERR_OK; } #else -ivas_error IVAS_REND_SetInputGain_fx( - IVAS_REND_HANDLE hIvasRend, /* i/o: Renderer handle */ - const IVAS_REND_InputId inputId, /* i : ID of the input */ - const Word32 gain /* i : linear gain (not in dB) */ -) -{ - input_base *inputBase; - ivas_error error; + ivas_error IVAS_REND_SetInputGain_fx( + IVAS_REND_HANDLE hIvasRend, /* i/o: Renderer handle */ + const IVAS_REND_InputId inputId, /* i : ID of the input */ + const Word32 gain /* i : linear gain (not in dB) */ + ) + { + input_base *inputBase; + ivas_error error; - /* Validate function arguments */ - IF ( hIvasRend == NULL ) - { - return IVAS_ERR_UNEXPECTED_NULL_POINTER; - } + /* Validate function arguments */ + IF( hIvasRend == NULL ) + { + return IVAS_ERR_UNEXPECTED_NULL_POINTER; + } - IF ( ( error = getInputById( hIvasRend, inputId, (void **) &inputBase ) ) != IVAS_ERR_OK ) - { - return error; - } + IF( ( error = getInputById( hIvasRend, inputId, (void **) &inputBase ) ) != IVAS_ERR_OK ) + { + return error; + } - inputBase->gain_fx = gain; + inputBase->gain_fx = gain; - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif /*-------------------------------------------------------------------* @@ -6095,48 +6131,48 @@ ivas_error IVAS_REND_SetInputLfeMtx( return IVAS_ERR_OK; } #else -ivas_error IVAS_REND_SetInputLfeMtx_fx( - IVAS_REND_HANDLE hIvasRend, /* i/o: Renderer handle */ - const IVAS_REND_InputId inputId, /* i : ID of the input */ - const IVAS_REND_LfePanMtx_fx *lfePanMtx /* i : LFE panning matrix */ -) -{ - Word16 i; - input_base *pInputBase; - input_mc *pInputMc; - ivas_error error; + ivas_error IVAS_REND_SetInputLfeMtx_fx( + IVAS_REND_HANDLE hIvasRend, /* i/o: Renderer handle */ + const IVAS_REND_InputId inputId, /* i : ID of the input */ + const IVAS_REND_LfePanMtx_fx *lfePanMtx /* i : LFE panning matrix */ + ) + { + Word16 i; + input_base *pInputBase; + input_mc *pInputMc; + ivas_error error; - /* Validate function arguments */ - IF ( hIvasRend == NULL ) - { - return IVAS_ERR_UNEXPECTED_NULL_POINTER; - } + /* Validate function arguments */ + IF( hIvasRend == NULL ) + { + return IVAS_ERR_UNEXPECTED_NULL_POINTER; + } - IF ( ( error = getInputById( hIvasRend, inputId, (void **) &pInputBase ) ) != IVAS_ERR_OK ) - { - return error; - } + IF( ( error = getInputById( hIvasRend, inputId, (void **) &pInputBase ) ) != IVAS_ERR_OK ) + { + return error; + } - IF ( getAudioConfigType( pInputBase->inConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) - { - /* Custom LFE panning matrix only makes sense with channel-based input */ - return IVAS_ERR_INVALID_INPUT_FORMAT; - } - pInputMc = (input_mc *) pInputBase; + IF( getAudioConfigType( pInputBase->inConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) + { + /* Custom LFE panning matrix only makes sense with channel-based input */ + return IVAS_ERR_INVALID_INPUT_FORMAT; + } + pInputMc = (input_mc *) pInputBase; - /* copy LFE panning matrix */ - FOR ( i = 0; i < RENDERER_MAX_INPUT_LFE_CHANNELS; i++ ) - { - Copy32( ( *lfePanMtx )[i], pInputMc->lfeRouting.lfePanMtx_fx[i], IVAS_MAX_OUTPUT_CHANNELS ); - } + /* copy LFE panning matrix */ + FOR( i = 0; i < RENDERER_MAX_INPUT_LFE_CHANNELS; i++ ) + { + Copy32( ( *lfePanMtx )[i], pInputMc->lfeRouting.lfePanMtx_fx[i], IVAS_MAX_OUTPUT_CHANNELS ); + } - IF ( ( error = updateMcPanGains( pInputMc, hIvasRend->outputConfig ) ) != IVAS_ERR_OK ) - { - return error; - } + IF( ( error = updateMcPanGains( pInputMc, hIvasRend->outputConfig ) ) != IVAS_ERR_OK ) + { + return error; + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif #ifdef IVAS_FLOAT_FIXED @@ -6149,52 +6185,9 @@ ivas_error IVAS_REND_SetInputLfeMtx_fx( ivas_error IVAS_REND_SetInputLfePos_fx( IVAS_REND_HANDLE hIvasRend, /* i/o: Renderer handle */ const IVAS_REND_InputId inputId, /* i : ID of the input */ - const Word32 inputGain, /* i : Input gain to be applied to the LFE channel(s) */ - const Word16 outputAzimuth, /* i : Output azimuth position */ - const Word16 outputElevation /* i : Output elevation position */ -) -{ - input_base *pInputBase; - input_mc *pInputMc; - ivas_error error; - - /* Validate function arguments */ - IF ( hIvasRend == NULL ) - { - return IVAS_ERR_UNEXPECTED_NULL_POINTER; - } - - IF ( ( error = getInputById( hIvasRend, inputId, (void **) &pInputBase ) ) != IVAS_ERR_OK ) - { - return error; - } - - IF ( getAudioConfigType( pInputBase->inConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) - { - /* Custom LFE routing only makes sense with channel-based input */ - return IVAS_ERR_INVALID_INPUT_FORMAT; - } - pInputMc = (input_mc *) pInputBase; - - pInputMc->lfeRouting.pan_lfe = true; - pInputMc->lfeRouting.lfeInputGain_fx = inputGain; // Q31 - pInputMc->lfeRouting.lfeOutputAzimuth_fx = (Word16) ( outputAzimuth ); // Q0 - pInputMc->lfeRouting.lfeOutputElevation_fx = (Word16) ( outputElevation ); // Q0 - - IF ( ( error = updateMcPanGains( pInputMc, hIvasRend->outputConfig ) ) != IVAS_ERR_OK ) - { - return error; - } - - return IVAS_ERR_OK; -} -#else -ivas_error IVAS_REND_SetInputLfePos( - IVAS_REND_HANDLE hIvasRend, /* i/o: Renderer handle */ - const IVAS_REND_InputId inputId, /* i : ID of the input */ - const float inputGain, /* i : Input gain to be applied to the LFE channel(s) */ - const float outputAzimuth, /* i : Output azimuth position */ - const float outputElevation /* i : Output elevation position */ + const Word32 inputGain, /* i : Input gain to be applied to the LFE channel(s) */ + const Word16 outputAzimuth, /* i : Output azimuth position */ + const Word16 outputElevation /* i : Output elevation position */ ) { input_base *pInputBase; @@ -6202,17 +6195,17 @@ ivas_error IVAS_REND_SetInputLfePos( ivas_error error; /* Validate function arguments */ - if ( hIvasRend == NULL ) + IF( hIvasRend == NULL ) { return IVAS_ERR_UNEXPECTED_NULL_POINTER; } - if ( ( error = getInputById( hIvasRend, inputId, (void **) &pInputBase ) ) != IVAS_ERR_OK ) + IF( ( error = getInputById( hIvasRend, inputId, (void **) &pInputBase ) ) != IVAS_ERR_OK ) { return error; } - if ( getAudioConfigType( pInputBase->inConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) + IF( getAudioConfigType( pInputBase->inConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) { /* Custom LFE routing only makes sense with channel-based input */ return IVAS_ERR_INVALID_INPUT_FORMAT; @@ -6220,17 +6213,60 @@ ivas_error IVAS_REND_SetInputLfePos( pInputMc = (input_mc *) pInputBase; pInputMc->lfeRouting.pan_lfe = true; - pInputMc->lfeRouting.lfeInputGain = inputGain; - pInputMc->lfeRouting.lfeOutputAzimuth = outputAzimuth; - pInputMc->lfeRouting.lfeOutputElevation = outputElevation; + pInputMc->lfeRouting.lfeInputGain_fx = inputGain; // Q31 + pInputMc->lfeRouting.lfeOutputAzimuth_fx = (Word16) ( outputAzimuth ); // Q0 + pInputMc->lfeRouting.lfeOutputElevation_fx = (Word16) ( outputElevation ); // Q0 - if ( ( error = updateMcPanGains( pInputMc, hIvasRend->outputConfig ) ) != IVAS_ERR_OK ) + IF( ( error = updateMcPanGains( pInputMc, hIvasRend->outputConfig ) ) != IVAS_ERR_OK ) { return error; } return IVAS_ERR_OK; } +#else + ivas_error IVAS_REND_SetInputLfePos( + IVAS_REND_HANDLE hIvasRend, /* i/o: Renderer handle */ + const IVAS_REND_InputId inputId, /* i : ID of the input */ + const float inputGain, /* i : Input gain to be applied to the LFE channel(s) */ + const float outputAzimuth, /* i : Output azimuth position */ + const float outputElevation /* i : Output elevation position */ + ) + { + input_base *pInputBase; + input_mc *pInputMc; + ivas_error error; + + /* Validate function arguments */ + if ( hIvasRend == NULL ) + { + return IVAS_ERR_UNEXPECTED_NULL_POINTER; + } + + if ( ( error = getInputById( hIvasRend, inputId, (void **) &pInputBase ) ) != IVAS_ERR_OK ) + { + return error; + } + + if ( getAudioConfigType( pInputBase->inConfig ) != IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) + { + /* Custom LFE routing only makes sense with channel-based input */ + return IVAS_ERR_INVALID_INPUT_FORMAT; + } + pInputMc = (input_mc *) pInputBase; + + pInputMc->lfeRouting.pan_lfe = true; + pInputMc->lfeRouting.lfeInputGain = inputGain; + pInputMc->lfeRouting.lfeOutputAzimuth = outputAzimuth; + pInputMc->lfeRouting.lfeOutputElevation = outputElevation; + + if ( ( error = updateMcPanGains( pInputMc, hIvasRend->outputConfig ) ) != IVAS_ERR_OK ) + { + return error; + } + + return IVAS_ERR_OK; + } #endif /*-------------------------------------------------------------------* @@ -6314,33 +6350,33 @@ ivas_error IVAS_REND_GetInputNumChannels( return IVAS_ERR_OK; } #else -ivas_error IVAS_REND_GetInputNumChannels( - IVAS_REND_CONST_HANDLE hIvasRend, /* i : Renderer handle */ - const IVAS_REND_InputId inputId, /* i : ID of the input */ - Word16 *numChannels /* o : number of channels of the input */ -) -{ - ivas_error error; - const input_base *pInput; + ivas_error IVAS_REND_GetInputNumChannels( + IVAS_REND_CONST_HANDLE hIvasRend, /* i : Renderer handle */ + const IVAS_REND_InputId inputId, /* i : ID of the input */ + Word16 *numChannels /* o : number of channels of the input */ + ) + { + ivas_error error; + const input_base *pInput; - /* Validate function arguments */ - IF ( hIvasRend == NULL || numChannels == NULL ) - { - return IVAS_ERR_UNEXPECTED_NULL_POINTER; - } + /* Validate function arguments */ + IF( hIvasRend == NULL || numChannels == NULL ) + { + return IVAS_ERR_UNEXPECTED_NULL_POINTER; + } - IF( ( error = getConstInputById( hIvasRend, inputId, (const void **) &pInput ) ) != IVAS_ERR_OK ) - { - return error; - } + IF( ( error = getConstInputById( hIvasRend, inputId, (const void **) &pInput ) ) != IVAS_ERR_OK ) + { + return error; + } - IF ( ( error = getRendInputNumChannels( pInput, numChannels ) ) != IVAS_ERR_OK ) - { - return error; - } + IF( ( error = getRendInputNumChannels( pInput, numChannels ) ) != IVAS_ERR_OK ) + { + return error; + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif /*-------------------------------------------------------------------* @@ -6367,23 +6403,23 @@ ivas_error IVAS_REND_GetNumAllObjects( return IVAS_ERR_OK; } #else -ivas_error IVAS_REND_GetNumAllObjects( - IVAS_REND_CONST_HANDLE hIvasRend, /* i : Renderer handle */ - Word16 *numChannels /* o : number of all objects */ -) -{ - IF ( hIvasRend == NULL || numChannels == NULL ) - { - return IVAS_ERR_UNEXPECTED_NULL_POINTER; - } + ivas_error IVAS_REND_GetNumAllObjects( + IVAS_REND_CONST_HANDLE hIvasRend, /* i : Renderer handle */ + Word16 * numChannels /* o : number of all objects */ + ) + { + IF( hIvasRend == NULL || numChannels == NULL ) + { + return IVAS_ERR_UNEXPECTED_NULL_POINTER; + } - IF( EQ_32( hIvasRend->outputConfig, IVAS_AUDIO_CONFIG_MASA1 ) || EQ_32( hIvasRend->outputConfig, IVAS_AUDIO_CONFIG_MASA2 ) ) - { - *numChannels = (Word16) hIvasRend->inputsIsm[0].total_num_objects; - } + IF( EQ_32( hIvasRend->outputConfig, IVAS_AUDIO_CONFIG_MASA1 ) || EQ_32( hIvasRend->outputConfig, IVAS_AUDIO_CONFIG_MASA2 ) ) + { + *numChannels = (Word16) hIvasRend->inputsIsm[0].total_num_objects; + } - return IVAS_ERR_OK; -} + return IVAS_ERR_OK; + } #endif /*-------------------------------------------------------------------* @@ -6462,70 +6498,68 @@ ivas_error IVAS_REND_GetDelay( return IVAS_ERR_OK; } #else -ivas_error IVAS_REND_GetDelay_fx( - IVAS_REND_CONST_HANDLE hIvasRend, /* i : Renderer state */ - Word16 *nSamples, /* o : Renderer delay in samples */ - Word32 *timeScale /* o : Time scale of the delay, equal to renderer output sampling rate */ -) -{ - /* TODO tmu : this function only returns the maximum delay across all inputs - * Ideally each input has its own delay buffer and everything is aligned (binaural and LFE filtering delays are nonuniform) - */ - Word16 i; - Word32 latency_ns; - Word32 max_latency_ns; + ivas_error IVAS_REND_GetDelay_fx( + IVAS_REND_CONST_HANDLE hIvasRend, /* i : Renderer state */ + Word16 * nSamples, /* o : Renderer delay in samples */ + Word32 * timeScale /* o : Time scale of the delay, equal to renderer output sampling rate */ + ) + { + /* TODO tmu : this function only returns the maximum delay across all inputs + * Ideally each input has its own delay buffer and everything is aligned (binaural and LFE filtering delays are nonuniform) + */ + Word16 i; + Word32 latency_ns; + Word32 max_latency_ns; - Word32 timescale_by_ns[7] = { 0, 17180, 34360, 0, 68719, 0, 103079 }; + Word32 timescale_by_ns[7] = { 0, 17180, 34360, 0, 68719, 0, 103079 }; - /* Validate function arguments */ - IF ( hIvasRend == NULL || nSamples == NULL || timeScale == NULL ) - { - return IVAS_ERR_UNEXPECTED_NULL_POINTER; - } + /* Validate function arguments */ + IF( hIvasRend == NULL || nSamples == NULL || timeScale == NULL ) + { + return IVAS_ERR_UNEXPECTED_NULL_POINTER; + } - *timeScale = hIvasRend->sampleRateOut; - assert( *timeScale == 8000 || *timeScale == 16000 || *timeScale == 32000 || *timeScale == 48000 ); - *nSamples = 0; - max_latency_ns = 0; + *timeScale = hIvasRend->sampleRateOut; + assert( *timeScale == 8000 || *timeScale == 16000 || *timeScale == 32000 || *timeScale == 48000 ); + *nSamples = 0; + max_latency_ns = 0; - /* Compute the maximum delay across all inputs */ - FOR ( i = 0; i < RENDERER_MAX_ISM_INPUTS; i++ ) - { - IF ( NE_32(hIvasRend->inputsIsm[i].base.inConfig, IVAS_AUDIO_CONFIG_INVALID )) - { - latency_ns = L_max( ( hIvasRend->inputsIsm[i].crendWrapper != NULL ) ? hIvasRend->inputsIsm[i].crendWrapper->binaural_latency_ns : 0, - hIvasRend->inputsIsm[i].tdRendWrapper.binaural_latency_ns ); - max_latency_ns = L_max( max_latency_ns, latency_ns ); - } - } + /* Compute the maximum delay across all inputs */ + FOR( i = 0; i < RENDERER_MAX_ISM_INPUTS; i++ ) + { + IF( NE_32( hIvasRend->inputsIsm[i].base.inConfig, IVAS_AUDIO_CONFIG_INVALID ) ) + { + latency_ns = L_max( ( hIvasRend->inputsIsm[i].crendWrapper != NULL ) ? hIvasRend->inputsIsm[i].crendWrapper->binaural_latency_ns : 0, + hIvasRend->inputsIsm[i].tdRendWrapper.binaural_latency_ns ); + max_latency_ns = L_max( max_latency_ns, latency_ns ); + } + } - FOR ( i = 0; i < RENDERER_MAX_MC_INPUTS; i++ ) - { - IF ( NE_32(hIvasRend->inputsMc[i].base.inConfig, IVAS_AUDIO_CONFIG_INVALID )) - { - latency_ns = L_max( ( hIvasRend->inputsMc[i].crendWrapper != NULL ) ? hIvasRend->inputsMc[i].crendWrapper->binaural_latency_ns : 0, - hIvasRend->inputsMc[i].tdRendWrapper.binaural_latency_ns ); - max_latency_ns = L_max( max_latency_ns, latency_ns ); - } - } + FOR( i = 0; i < RENDERER_MAX_MC_INPUTS; i++ ) + { + IF( NE_32( hIvasRend->inputsMc[i].base.inConfig, IVAS_AUDIO_CONFIG_INVALID ) ) + { + latency_ns = L_max( ( hIvasRend->inputsMc[i].crendWrapper != NULL ) ? hIvasRend->inputsMc[i].crendWrapper->binaural_latency_ns : 0, + hIvasRend->inputsMc[i].tdRendWrapper.binaural_latency_ns ); + max_latency_ns = L_max( max_latency_ns, latency_ns ); + } + } - FOR ( i = 0; i < RENDERER_MAX_SBA_INPUTS; i++ ) - { - IF ( NE_32(hIvasRend->inputsSba[i].base.inConfig, IVAS_AUDIO_CONFIG_INVALID )) - { + FOR( i = 0; i < RENDERER_MAX_SBA_INPUTS; i++ ) { - latency_ns = ( hIvasRend->inputsSba[i].crendWrapper != NULL ) ? hIvasRend->inputsSba[i].crendWrapper->binaural_latency_ns : 0; - max_latency_ns = L_max( max_latency_ns, latency_ns ); + IF( NE_32( hIvasRend->inputsSba[i].base.inConfig, IVAS_AUDIO_CONFIG_INVALID ) ) + { + { + latency_ns = ( hIvasRend->inputsSba[i].crendWrapper != NULL ) ? hIvasRend->inputsSba[i].crendWrapper->binaural_latency_ns : 0; + max_latency_ns = L_max( max_latency_ns, latency_ns ); + } + } } - } - } - FOR ( i = 0; i < RENDERER_MAX_MASA_INPUTS; i++ ) - { - IF ( NE_32(hIvasRend->inputsMasa[i].base.inConfig, IVAS_AUDIO_CONFIG_INVALID )) - { - latency_ns = (Word32) ( IVAS_FB_DEC_DELAY_NS ); + FOR( i = 0; i < RENDERER_MAX_MASA_INPUTS; i++ ){ + IF( NE_32( hIvasRend->inputsMasa[i].base.inConfig, IVAS_AUDIO_CONFIG_INVALID ) ){ + latency_ns = (Word32) ( IVAS_FB_DEC_DELAY_NS ); max_latency_ns = L_max( max_latency_ns, latency_ns ); } } @@ -6770,8 +6804,13 @@ ivas_error IVAS_REND_FeedInputObjectMetadataToOMasa( } /* Set position to OMasa struct */ +#ifdef IVAS_FLOAT_FIXED + hIvasRend->inputsIsm->hOMasa->ism_azimuth_fx[inputIndex] = floatToFixed(objectPosition.azimuth, Q22); + hIvasRend->inputsIsm->hOMasa->ism_elevation_fx[inputIndex] = floatToFixed(objectPosition.elevation, Q22); +#else hIvasRend->inputsIsm->hOMasa->ism_azimuth[inputIndex] = objectPosition.azimuth; hIvasRend->inputsIsm->hOMasa->ism_elevation[inputIndex] = objectPosition.elevation; +#endif return IVAS_ERR_OK; } @@ -6886,7 +6925,7 @@ ivas_error IVAS_REND_InitConfig( return error; } #ifdef IVAS_FLOAT_FIXED - IF ((error = ivas_render_config_init_from_rom_fx(&hIvasRend->hRendererConfig)) != IVAS_ERR_OK) + IF( ( error = ivas_render_config_init_from_rom_fx( &hIvasRend->hRendererConfig ) ) != IVAS_ERR_OK ) { return error; } @@ -7000,7 +7039,7 @@ int16_t IVAS_REND_GetRenderConfig( { RENDER_CONFIG_HANDLE hRCin; - IF ( hIvasRend == NULL || hIvasRend->hRendererConfig == NULL || hRCout == NULL ) + IF( hIvasRend == NULL || hIvasRend->hRendererConfig == NULL || hRCout == NULL ) { return IVAS_ERR_UNEXPECTED_NULL_POINTER; } @@ -7122,7 +7161,7 @@ ivas_error IVAS_REND_SetHeadRotation( rotQuat = headRot; } - IF ( ( error = ivas_orient_trk_Process_fx( hIvasRend->headRotData.hOrientationTracker, rotQuat, FRAMES_PER_SEC * MAX_PARAM_SPATIAL_SUBFRAMES, &hIvasRend->headRotData.headPositions[sf_idx] ) ) != IVAS_ERR_OK ) + IF( ( error = ivas_orient_trk_Process_fx( hIvasRend->headRotData.hOrientationTracker, rotQuat, FRAMES_PER_SEC * MAX_PARAM_SPATIAL_SUBFRAMES, &hIvasRend->headRotData.headPositions[sf_idx] ) ) != IVAS_ERR_OK ) { return error; } @@ -7237,17 +7276,7 @@ ivas_error IVAS_REND_SetReferenceRotation( #ifdef IVAS_FLOAT_FIXED - IVAS_QUATERNION refRot_fx; - refRot_fx.q_fact = Q29; - refRot_fx.w_fx = (Word32) float_to_fix( refRot.w, refRot_fx.q_fact); - refRot_fx.x_fx = (Word32) float_to_fix( refRot.x, refRot_fx.q_fact); - refRot_fx.y_fx = (Word32) float_to_fix( refRot.y, refRot_fx.q_fact); - refRot_fx.z_fx = (Word32) float_to_fix( refRot.z, refRot_fx.q_fact); - error = ivas_orient_trk_SetReferenceRotation_fx( hIvasRend->headRotData.hOrientationTracker, refRot_fx ); - hIvasRend->headRotData.hOrientationTracker->refRot.w = me2f( hIvasRend->headRotData.hOrientationTracker->refRot.w_fx, 31 - hIvasRend->headRotData.hOrientationTracker->refRot.q_fact); - hIvasRend->headRotData.hOrientationTracker->refRot.x = me2f( hIvasRend->headRotData.hOrientationTracker->refRot.x_fx, 31 - hIvasRend->headRotData.hOrientationTracker->refRot.q_fact); - hIvasRend->headRotData.hOrientationTracker->refRot.y = me2f( hIvasRend->headRotData.hOrientationTracker->refRot.y_fx, 31 - hIvasRend->headRotData.hOrientationTracker->refRot.q_fact); - hIvasRend->headRotData.hOrientationTracker->refRot.z = me2f( hIvasRend->headRotData.hOrientationTracker->refRot.z_fx, 31 - hIvasRend->headRotData.hOrientationTracker->refRot.q_fact); + error = ivas_orient_trk_SetReferenceRotation_fx( hIvasRend->headRotData.hOrientationTracker, refRot ); if ( error != IVAS_ERR_OK ) { @@ -7400,30 +7429,6 @@ ivas_error IVAS_REND_CombineHeadAndExternalOrientation( return IVAS_ERR_UNEXPECTED_NULL_POINTER; } ivas_error error_type = combine_external_and_head_orientations_rend( &hIvasRend->headRotData, hIvasRend->hExternalOrientationData, hIvasRend->hCombinedOrientationData ); -#ifdef IVAS_FLOAT_FIXED - for ( Word16 i = 0; i < hIvasRend->hCombinedOrientationData->num_subframes; i++ ) - { - hIvasRend->hCombinedOrientationData->Quaternions[i].w = fixedToFloat_32( hIvasRend->hCombinedOrientationData->Quaternions[i].w_fx, hIvasRend->hCombinedOrientationData->Quaternions[i].q_fact ); - hIvasRend->hCombinedOrientationData->Quaternions[i].x = fixedToFloat_32( hIvasRend->hCombinedOrientationData->Quaternions[i].x_fx, hIvasRend->hCombinedOrientationData->Quaternions[i].q_fact ); - hIvasRend->hCombinedOrientationData->Quaternions[i].y = fixedToFloat_32( hIvasRend->hCombinedOrientationData->Quaternions[i].y_fx, hIvasRend->hCombinedOrientationData->Quaternions[i].q_fact ); - hIvasRend->hCombinedOrientationData->Quaternions[i].z = fixedToFloat_32( hIvasRend->hCombinedOrientationData->Quaternions[i].z_fx, hIvasRend->hCombinedOrientationData->Quaternions[i].q_fact ); - - /*for ( j = 0; j < 3; j++ ) - { - for ( Word16 k = 0; k < 3; k++ ) - { - hCombinedOrientationData->Rmat_fx[i][j][k] = L_shl( hCombinedOrientationData->Rmat_fx[i][j][k], 30 - ( 2 * hCombinedOrientationData->Quaternions[i].q_fact - 32 ) ); - } - }*/ - for ( Word16 j = 0; j < 3; j++ ) - { - for ( Word16 k = 0; k < 3; k++ ) - { - hIvasRend->hCombinedOrientationData->Rmat[i][j][k] = (float) fixedToFloat_32( hIvasRend->hCombinedOrientationData->Rmat_fx[i][j][k], 30 ); - } - } - } -#endif return error_type; } @@ -8317,7 +8322,7 @@ static ivas_error renderIsmToBinauralRoom( { for ( j = 0; j < 3; j++ ) { - Rmat[i][j] = ( *hCombinedOrientationData )->Rmat[subframe_idx][i][j]; + Rmat[i][j] = fixedToFloat_32( ( *hCombinedOrientationData )->Rmat_fx[subframe_idx][i][j], 30 ); } } else @@ -8360,29 +8365,29 @@ static ivas_error renderIsmToBinauralRoom( /* set previous gains if this is the first frame */ /*float2fix to be removed*/ - Word32 azimuth_fx_tmp = floatToFixed(rotatedPosPrev.azimuth, Q22); - Word32 elevation_fx_tmp = floatToFixed(rotatedPosPrev.elevation, Q22); + Word32 azimuth_fx_tmp = floatToFixed( rotatedPosPrev.azimuth, Q22 ); + Word32 elevation_fx_tmp = floatToFixed( rotatedPosPrev.elevation, Q22 ); if ( ( error = getEfapGains_fx( *ismInput->base.ctx.pEfapOutWrapper, azimuth_fx_tmp, elevation_fx_tmp, ismInput->prev_pan_gains_fx ) ) != IVAS_ERR_OK ) { return error; } /* fix2float to be removed */ - fixedToFloat_arrL(ismInput->prev_pan_gains_fx, ismInput->prev_pan_gains, Q31, MAX_OUTPUT_CHANNELS); + fixedToFloat_arrL( ismInput->prev_pan_gains_fx, ismInput->prev_pan_gains, Q31, MAX_OUTPUT_CHANNELS ); /* compute gains only if position changed */ if ( position_changed ) { /*float2fix to be removed*/ - azimuth_fx_tmp = floatToFixed(rotatedPos.azimuth, Q22); - elevation_fx_tmp = floatToFixed(rotatedPos.elevation, Q22); + azimuth_fx_tmp = floatToFixed( rotatedPos.azimuth, Q22 ); + elevation_fx_tmp = floatToFixed( rotatedPos.elevation, Q22 ); if ( ( error = getEfapGains_fx( *ismInput->base.ctx.pEfapOutWrapper, - azimuth_fx_tmp, - elevation_fx_tmp, - currentPanGains_fx ) ) != IVAS_ERR_OK ) + azimuth_fx_tmp, + elevation_fx_tmp, + currentPanGains_fx ) ) != IVAS_ERR_OK ) { return error; } /* fix2float to be removed */ - fixedToFloat_arrL(currentPanGains_fx, currentPanGains, Q31, MAX_OUTPUT_CHANNELS); + fixedToFloat_arrL( currentPanGains_fx, currentPanGains, Q31, MAX_OUTPUT_CHANNELS ); } /* intermediate rendering to 7_1_4 */ @@ -8710,19 +8715,19 @@ static ivas_error renderIsmToMc( { // TODO tmu review when #215 is resolved /*float2fix to be removed*/ - Word32 azimuth_fx_tmp = (int16_t)floorf(ismInput->currentPos.azimuth + 0.5f); + Word32 azimuth_fx_tmp = (int16_t) floorf( ismInput->currentPos.azimuth + 0.5f ); azimuth_fx_tmp = azimuth_fx_tmp << 22; - Word32 elevation_fx_tmp = (int16_t)floorf(ismInput->currentPos.elevation + 0.5f); + Word32 elevation_fx_tmp = (int16_t) floorf( ismInput->currentPos.elevation + 0.5f ); elevation_fx_tmp = elevation_fx_tmp << 22; if ( ( error = getEfapGains_fx( *ismInput->base.ctx.pEfapOutWrapper, - azimuth_fx_tmp, - elevation_fx_tmp, - currentPanGains_fx ) ) != IVAS_ERR_OK ) + azimuth_fx_tmp, + elevation_fx_tmp, + currentPanGains_fx ) ) != IVAS_ERR_OK ) { return error; } /* fix2float to be removed */ - fixedToFloat_arrL(currentPanGains_fx, currentPanGains, Q31, MAX_OUTPUT_CHANNELS); + fixedToFloat_arrL( currentPanGains_fx, currentPanGains, Q31, MAX_OUTPUT_CHANNELS ); } /* set previous gains if this is the first frame */ @@ -8730,19 +8735,19 @@ static ivas_error renderIsmToMc( { // TODO tmu review when #215 is resolved /*float2fix to be removed*/ - Word32 azimuth_fx_tmp = (int16_t)floorf(ismInput->previousPos.azimuth + 0.5f); + Word32 azimuth_fx_tmp = (int16_t) floorf( ismInput->previousPos.azimuth + 0.5f ); azimuth_fx_tmp = azimuth_fx_tmp << 22; - Word32 elevation_fx_tmp = (int16_t)floorf(ismInput->previousPos.elevation + 0.5f); + Word32 elevation_fx_tmp = (int16_t) floorf( ismInput->previousPos.elevation + 0.5f ); elevation_fx_tmp = elevation_fx_tmp << 22; if ( ( error = getEfapGains_fx( *ismInput->base.ctx.pEfapOutWrapper, - azimuth_fx_tmp, - elevation_fx_tmp, - ismInput->prev_pan_gains_fx) ) != IVAS_ERR_OK ) + azimuth_fx_tmp, + elevation_fx_tmp, + ismInput->prev_pan_gains_fx ) ) != IVAS_ERR_OK ) { return error; } /* fix2float to be removed */ - fixedToFloat_arrL(ismInput->prev_pan_gains_fx, ismInput->prev_pan_gains, Q31, MAX_OUTPUT_CHANNELS); + fixedToFloat_arrL( ismInput->prev_pan_gains_fx, ismInput->prev_pan_gains, Q31, MAX_OUTPUT_CHANNELS ); } } @@ -8907,12 +8912,56 @@ static void renderIsmToMasa( IVAS_REND_AudioBuffer outAudio ) { float tmpRendBuffer[MAX_NUM_OBJECTS][L_FRAME48k]; +#ifdef IVAS_FLOAT_FIXED + Word32 tmpRendBuffer_fx[MAX_NUM_OBJECTS][L_FRAME48k]; + Word16 i, j; + Word16 q_fact; +#endif push_wmops( "renderIsmToMasa" ); copyBufferTo2dArray( ismInput->base.inputBuffer, tmpRendBuffer ); +#ifdef IVAS_FLOAT_FIXED + Word16 input_e[MAX_NUM_OBJECTS], max_e; + FOR(i = 0; i < MAX_NUM_OBJECTS; i++) + { + f2me_buf(tmpRendBuffer[i], tmpRendBuffer_fx[i], &input_e[i], L_FRAME48k); + } + + Word16 guard_bits = find_guarded_bits_fx(L_FRAME48k); + max_e = input_e[0]; + FOR (Word16 i = 1; i < MAX_NUM_OBJECTS; i++) + { + IF (max_e < input_e[0]) + max_e = input_e[i]; + } + + FOR(i = 0; i < MAX_NUM_OBJECTS; i++) + { + FOR (j = 0; j < L_FRAME48k; j++) + { + tmpRendBuffer_fx[i][j] = L_shr(tmpRendBuffer_fx[i][j], max_e - input_e[i] + guard_bits); + } + } + max_e += guard_bits; + q_fact = 31 - max_e; +#endif + +#ifdef IVAS_FLOAT_FIXED + ivas_omasa_ana_fx(ismInput->hOMasa, tmpRendBuffer, tmpRendBuffer_fx, &q_fact, ismInput->base.inputBuffer.config.numSamplesPerChannel, outAudio.config.numChannels, ismInput->base.inputBuffer.config.numChannels); + + FOR (Word16 block_m_idx = 0; block_m_idx < MAX_PARAM_SPATIAL_SUBFRAMES; block_m_idx++ ) { + FOR (Word16 band_m_idx = 0; band_m_idx < ismInput->hOMasa->nbands; band_m_idx++) { + ismInput->hOMasa->energy[block_m_idx][band_m_idx] = fixedToFloat(ismInput->hOMasa->energy_fx[block_m_idx][band_m_idx], ismInput->hOMasa->energy_q); + } + } + FOR(Word16 i = 0; i < ismInput->base.inputBuffer.config.numChannels; i++) { + fixedToFloat_arrL(tmpRendBuffer_fx[i], tmpRendBuffer[i], q_fact, L_FRAME48k ); + } +#else ivas_omasa_ana( ismInput->hOMasa, tmpRendBuffer, ismInput->base.inputBuffer.config.numSamplesPerChannel, outAudio.config.numChannels, ismInput->base.inputBuffer.config.numChannels ); +#endif accumulate2dArrayToBuffer( tmpRendBuffer, &outAudio ); @@ -8940,7 +8989,7 @@ static ivas_error renderInputIsm( ismInput->base.numNewSamplesPerChannel = 0; #ifdef IVAS_FLOAT_FIXED - ismInput->base.gain = fix_to_float(ismInput->base.gain_fx, 30); + ismInput->base.gain = fix_to_float( ismInput->base.gain_fx, 30 ); #endif // IVAS_FLOAT_FIXED /* Apply input gain to new audio */ @@ -9895,7 +9944,7 @@ static void renderMcToMasa( MCMASA_ANA_HANDLE hMcMasa = mcInput->hMcMasa; Word16 i, nchan_inp = mcInput->base.inputBuffer.config.numChannels; Word16 q_data = *( outAudio.pq_fact ); - FOR ( i = 0; i < nchan_inp - 1; i++ ) + FOR( i = 0; i < nchan_inp - 1; i++ ) { floatToFixed_arrL( hMcMasa->cldfbAnaEnc[i]->cldfb_state, hMcMasa->cldfbAnaEnc[i]->cldfb_state_fx, q_data, hMcMasa->cldfbAnaEnc[i]->p_filter_length - hMcMasa->cldfbAnaEnc[i]->no_channels ); } @@ -9908,33 +9957,33 @@ static void renderMcToMasa( ivas_mcmasa_ana_fx( mcInput->hMcMasa, tmpRendBuffer_fx, *( outAudio.pq_fact ), mcInput->base.inputBuffer.config.numSamplesPerChannel, outAudio.config.numChannels, mcInput->base.inputBuffer.config.numChannels ); #if 1 /*TODO: To be removed later(fixed to float)*/ /*From here : Cleanup changes for ivas_mcmasa_param_est_ana_fx*/ - FOR ( i = 0; i < nchan_inp - 1; i++ ) + FOR( i = 0; i < nchan_inp - 1; i++ ) { fixedToFloat_arrL( hMcMasa->cldfbAnaEnc[i]->cldfb_state_fx, hMcMasa->cldfbAnaEnc[i]->cldfb_state, q_data, hMcMasa->cldfbAnaEnc[i]->p_filter_length - hMcMasa->cldfbAnaEnc[i]->no_channels ); } - FOR ( int j = 0; j < MAX_PARAM_SPATIAL_SUBFRAMES; j++ ) + FOR( int j = 0; j < MAX_PARAM_SPATIAL_SUBFRAMES; j++ ) { - FOR ( int k = 0; k < MASA_FREQUENCY_BANDS; k++ ) + FOR( int k = 0; k < MASA_FREQUENCY_BANDS; k++ ) { - FOR ( i = 0; i < DIRAC_NUM_DIMS; i++ ) + FOR( i = 0; i < DIRAC_NUM_DIMS; i++ ) { hMcMasa->direction_vector_m[i][j][k] = me2f( hMcMasa->direction_vector_m_fx[i][j][k], hMcMasa->direction_vector_e[i][j][k] ); } hMcMasa->energy[j][k] = me2f( hMcMasa->energy_fx[j][k], hMcMasa->energy_e[j][k] ); } } - FOR ( i = 0; i < DIRAC_NO_COL_AVG_DIFF; i++ ) + FOR( i = 0; i < DIRAC_NO_COL_AVG_DIFF; i++ ) { - FOR ( int j = 0; j < DIRAC_NUM_DIMS; j++ ) + FOR( int j = 0; j < DIRAC_NUM_DIMS; j++ ) { - FOR ( int k = 0; k < MASA_FREQUENCY_BANDS; k++ ) - hMcMasa->buffer_intensity_real[j][i][k] = fixedToFloat( hMcMasa->buffer_intensity_real_fx[j][i][k], hMcMasa->buffer_intensity_real_q[i] ); + FOR( int k = 0; k < MASA_FREQUENCY_BANDS; k++ ) + hMcMasa->buffer_intensity_real[j][i][k] = fixedToFloat( hMcMasa->buffer_intensity_real_fx[j][i][k], hMcMasa->buffer_intensity_real_q[i] ); } - FOR ( int j = 0; j < MASA_FREQUENCY_BANDS; j++ ) + FOR( int j = 0; j < MASA_FREQUENCY_BANDS; j++ ) { hMcMasa->buffer_intensity_real_vert[i][j] = fixedToFloat( hMcMasa->buffer_intensity_real_vert_fx[i][j], hMcMasa->buffer_intensity_real_vert_q[i] ); } - FOR ( int j = 0; j < MASA_FREQUENCY_BANDS; j++ ) + FOR( int j = 0; j < MASA_FREQUENCY_BANDS; j++ ) { hMcMasa->buffer_energy[i * j + j] = fixedToFloat( hMcMasa->buffer_energy_fx[i * j + j], hMcMasa->buffer_energy_q[i] ); } @@ -11172,6 +11221,10 @@ ivas_error IVAS_REND_MergeMasaMetadata( MASA_DECODER_EXT_OUT_META_HANDLE inMeta2; float( *inEne1 )[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; float( *inEne2 )[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word32( *inEne1_fx )[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word32( *inEne2_fx )[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS]; + Word16 *inEne1_e; + Word16 *inEne2_e; if ( hIvasRend == NULL ) { @@ -11183,21 +11236,57 @@ ivas_error IVAS_REND_MergeMasaMetadata( { *hMasaExtOutMeta = hIvasRend->inputsIsm->hOMasa->hMasaOut; inEne1 = &( hIvasRend->inputsIsm->hOMasa->energy ); +#ifdef IVAS_FLOAT_FIXED + inEne1_fx = &(hIvasRend->inputsIsm->hOMasa->energy_fx); + inEne1_e = &(hIvasRend->inputsIsm->hOMasa->energy_e); + + + for (Word16 i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++) + { + f2me_buf(hIvasRend->inputsIsm->hOMasa->energy[i], hIvasRend->inputsIsm->hOMasa->energy_fx[i], &hIvasRend->inputsIsm->hOMasa->energy_e[i], MASA_FREQUENCY_BANDS); + } +#endif } else if ( inputType1 == IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) { *hMasaExtOutMeta = hIvasRend->inputsMc->hMcMasa->hMasaOut; inEne1 = &( hIvasRend->inputsMc->hMcMasa->energy ); +#ifdef IVAS_FLOAT_FIXED + inEne1_fx = &( hIvasRend->inputsMc->hMcMasa->energy_fx ); + inEne1_e = &(hIvasRend->inputsMc->hMcMasa->energy_e); + + for (Word16 i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++) + { + f2me_buf(hIvasRend->inputsMc->hMcMasa->energy[i], hIvasRend->inputsMc->hMcMasa->energy_fx[i], &hIvasRend->inputsMc->hMcMasa->energy_e[i], MASA_FREQUENCY_BANDS); + } +#endif } else if ( inputType1 == IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS ) { *hMasaExtOutMeta = hIvasRend->inputsSba->hDirAC->hMasaOut; inEne1 = &( hIvasRend->inputsSba->hDirAC->energy ); +#ifdef IVAS_FLOAT_FIXED + inEne1_fx = &(hIvasRend->inputsSba->hDirAC->energy_fx); + inEne1_e = &(hIvasRend->inputsSba->hDirAC->energy_e); + for (Word16 i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++) + { + f2me_buf(hIvasRend->inputsSba->hDirAC->energy[i], hIvasRend->inputsSba->hDirAC->energy_fx[i], &hIvasRend->inputsSba->hDirAC->energy_e[i], MASA_FREQUENCY_BANDS); + } + +#endif } else if ( inputType1 == IVAS_REND_AUDIO_CONFIG_TYPE_MASA ) { *hMasaExtOutMeta = hIvasRend->inputsMasa->hMasaPrerend->hMasaOut; inEne1 = &( hIvasRend->inputsMasa->hMasaPrerend->energy ); +#ifdef IVAS_FLOAT_FIXED + inEne1_fx = &( hIvasRend->inputsMasa->hMasaPrerend->energy_fx ); + inEne1_e = &(hIvasRend->inputsMasa->hMasaPrerend->energy_e); + for (Word16 i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++) + { + f2me_buf(hIvasRend->inputsMasa->hMasaPrerend->energy[i], hIvasRend->inputsMasa->hMasaPrerend->energy_fx[i], &hIvasRend->inputsMasa->hMasaPrerend->energy_e[i], MASA_FREQUENCY_BANDS); + } +#endif } else { @@ -11209,21 +11298,56 @@ ivas_error IVAS_REND_MergeMasaMetadata( { inMeta2 = hIvasRend->inputsIsm->hOMasa->hMasaOut; inEne2 = &( hIvasRend->inputsIsm->hOMasa->energy ); +#ifdef IVAS_FLOAT_FIXED + inEne2_fx = &(hIvasRend->inputsIsm->hOMasa->energy_fx); + inEne2_e = &(hIvasRend->inputsIsm->hOMasa->energy_e); + + for (Word16 i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++) + { + f2me_buf(hIvasRend->inputsIsm->hOMasa->energy[i], hIvasRend->inputsIsm->hOMasa->energy_fx[i], &hIvasRend->inputsIsm->hOMasa->energy_e[i], MASA_FREQUENCY_BANDS); + } + +#endif } else if ( inputType2 == IVAS_REND_AUDIO_CONFIG_TYPE_CHANNEL_BASED ) { inMeta2 = hIvasRend->inputsMc->hMcMasa->hMasaOut; inEne2 = &( hIvasRend->inputsMc->hMcMasa->energy ); +#ifdef IVAS_FLOAT_FIXED + inEne2_fx = &( hIvasRend->inputsMc->hMcMasa->energy_fx ); + inEne2_e = &(hIvasRend->inputsMc->hMcMasa->energy_e); + for (Word16 i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++) + { + f2me_buf(hIvasRend->inputsMc->hMcMasa->energy[i], hIvasRend->inputsMc->hMcMasa->energy_fx[i], &hIvasRend->inputsMc->hMcMasa->energy_e[i], MASA_FREQUENCY_BANDS); + } +#endif } else if ( inputType2 == IVAS_REND_AUDIO_CONFIG_TYPE_AMBISONICS ) { inMeta2 = hIvasRend->inputsSba->hDirAC->hMasaOut; inEne2 = &( hIvasRend->inputsSba->hDirAC->energy ); +#ifdef IVAS_FLOAT_FIXED + inEne2_fx = &( hIvasRend->inputsSba->hDirAC->energy_fx ); + inEne2_e = &(hIvasRend->inputsSba->hDirAC->energy_e); + for (Word16 i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++) + { + f2me_buf(hIvasRend->inputsSba->hDirAC->energy[i], hIvasRend->inputsSba->hDirAC->energy_fx[i], &hIvasRend->inputsSba->hDirAC->energy_e[i], MASA_FREQUENCY_BANDS); + } +#endif } else if ( inputType2 == IVAS_REND_AUDIO_CONFIG_TYPE_MASA ) { inMeta2 = hIvasRend->inputsMasa->hMasaPrerend->hMasaOut; inEne2 = &( hIvasRend->inputsMasa->hMasaPrerend->energy ); +#ifdef IVAS_FLOAT_FIXED + inEne2_fx = &( hIvasRend->inputsMasa->hMasaPrerend->energy_fx ); + inEne2_e = &(hIvasRend->inputsMasa->hMasaPrerend->energy_e); + for (Word16 i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++) + { + f2me_buf(hIvasRend->inputsMasa->hMasaPrerend->energy[i], hIvasRend->inputsMasa->hMasaPrerend->energy_fx[i], &hIvasRend->inputsMasa->hMasaPrerend->energy_e[i], MASA_FREQUENCY_BANDS); + } + +#endif } else { @@ -11231,8 +11355,19 @@ ivas_error IVAS_REND_MergeMasaMetadata( } /* Merge metadata */ +#ifdef IVAS_FLOAT_FIXED + ivas_prerend_merge_masa_metadata_fx( *hMasaExtOutMeta, *hMasaExtOutMeta, inputType1, *inEne1_fx, inEne1_e, inMeta2, inputType2, inEne2_fx, inEne2_e ); + + FOR(Word32 i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++) + { + me2f_buf((*inEne1_fx)[i], inEne1_e[i], (*inEne1)[i], MASA_FREQUENCY_BANDS); + } +#else ivas_prerend_merge_masa_metadata( *hMasaExtOutMeta, *hMasaExtOutMeta, inputType1, *inEne1, inMeta2, inputType2, *inEne2 ); ( *hMasaExtOutMeta )->descriptiveMeta.numberOfChannels = hIvasRend->outputConfig == IVAS_AUDIO_CONFIG_MASA1 ? 0u : 1u; +#endif + + (*hMasaExtOutMeta)->descriptiveMeta.numberOfChannels = hIvasRend->outputConfig == IVAS_AUDIO_CONFIG_MASA1 ? 0u : 1u; return IVAS_ERR_OK; } @@ -11320,70 +11455,72 @@ static ivas_error getSamplesInternal( Word16 numOutChannels; /* Validate function arguments */ test(); - IF ( hIvasRend == NULL || outAudio.data == NULL ) + IF( hIvasRend == NULL || outAudio.data == NULL ) { return IVAS_ERR_UNEXPECTED_NULL_POINTER; } test(); - IF ( LE_16(outAudio.config.numSamplesPerChannel , 0) || LT_16(MAX_BUFFER_LENGTH_PER_CHANNEL , outAudio.config.numSamplesPerChannel) ) + IF( LE_16( outAudio.config.numSamplesPerChannel, 0 ) || LT_16( MAX_BUFFER_LENGTH_PER_CHANNEL, outAudio.config.numSamplesPerChannel ) ) { return IVAS_ERR_INVALID_BUFFER_SIZE; } test(); - IF ( LE_16(outAudio.config.numChannels , 0) || LT_16(MAX_OUTPUT_CHANNELS , outAudio.config.numChannels) ) + IF( LE_16( outAudio.config.numChannels, 0 ) || LT_16( MAX_OUTPUT_CHANNELS, outAudio.config.numChannels ) ) { return IVAS_ERR_WRONG_NUM_CHANNELS; } - IF ( EQ_32(getAudioConfigType( hIvasRend->outputConfig ) , IVAS_REND_AUDIO_CONFIG_TYPE_BINAURAL) && - NE_32(outAudio.config.numSamplesPerChannel * 1000 , ( hIvasRend->num_subframes * BINAURAL_RENDERING_FRAME_SIZE_MS ) * hIvasRend->sampleRateOut) ) + IF( EQ_32( getAudioConfigType( hIvasRend->outputConfig ), IVAS_REND_AUDIO_CONFIG_TYPE_BINAURAL ) && + NE_32( outAudio.config.numSamplesPerChannel * 1000, ( hIvasRend->num_subframes * BINAURAL_RENDERING_FRAME_SIZE_MS ) * hIvasRend->sampleRateOut ) ) { return IVAS_ERROR( IVAS_ERR_INVALID_BUFFER_SIZE, "Binaural rendering requires specific frame size" ); } /* Check that there is allowed configuration for MASA format output */ - IF ( EQ_32(getAudioConfigType( hIvasRend->outputConfig ) , IVAS_REND_AUDIO_CONFIG_TYPE_MASA) ) + IF( EQ_32( getAudioConfigType( hIvasRend->outputConfig ), IVAS_REND_AUDIO_CONFIG_TYPE_MASA ) ) { Word16 i; - Word16 numMasaInputs = 0; move16(); - Word16 numOtherInputs = 0; move16(); + Word16 numMasaInputs = 0; + move16(); + Word16 numOtherInputs = 0; + move16(); - FOR ( i = 0; i < RENDERER_MAX_MASA_INPUTS; i++ ) + FOR( i = 0; i < RENDERER_MAX_MASA_INPUTS; i++ ) { - //numMasaInputs += hIvasRend->inputsMasa[i].base.inConfig == IVAS_AUDIO_CONFIG_INVALID ? 0 : 1; + // numMasaInputs += hIvasRend->inputsMasa[i].base.inConfig == IVAS_AUDIO_CONFIG_INVALID ? 0 : 1; numMasaInputs = EQ_32( L_add( numMasaInputs, hIvasRend->inputsMasa[i].base.inConfig ), IVAS_AUDIO_CONFIG_INVALID ) ? 0 : 1; } - FOR ( i = 0; i < RENDERER_MAX_MC_INPUTS; i++ ) + FOR( i = 0; i < RENDERER_MAX_MC_INPUTS; i++ ) { - //numOtherInputs += hIvasRend->inputsMc[i].base.inConfig == IVAS_AUDIO_CONFIG_INVALID ? 0 : 1; + // numOtherInputs += hIvasRend->inputsMc[i].base.inConfig == IVAS_AUDIO_CONFIG_INVALID ? 0 : 1; numOtherInputs = EQ_32( L_add( numOtherInputs, hIvasRend->inputsMc[i].base.inConfig ), IVAS_AUDIO_CONFIG_INVALID ) ? 0 : 1; } - FOR ( i = 0; i < RENDERER_MAX_SBA_INPUTS; i++ ) + FOR( i = 0; i < RENDERER_MAX_SBA_INPUTS; i++ ) { - //numOtherInputs += hIvasRend->inputsSba[i].base.inConfig == IVAS_AUDIO_CONFIG_INVALID ? 0 : 1; + // numOtherInputs += hIvasRend->inputsSba[i].base.inConfig == IVAS_AUDIO_CONFIG_INVALID ? 0 : 1; numOtherInputs = EQ_32( L_add( numOtherInputs, hIvasRend->inputsSba[i].base.inConfig ), IVAS_AUDIO_CONFIG_INVALID ) ? 0 : 1; } /* For ISM, we check only first as all ISMs are handled together via OMASA when merging to MASA. */ - //numOtherInputs += hIvasRend->inputsIsm[0].base.inConfig == IVAS_AUDIO_CONFIG_INVALID ? 0 : 1; + // numOtherInputs += hIvasRend->inputsIsm[0].base.inConfig == IVAS_AUDIO_CONFIG_INVALID ? 0 : 1; numOtherInputs = EQ_32( L_add( numOtherInputs, hIvasRend->inputsIsm[0].base.inConfig ), IVAS_AUDIO_CONFIG_INVALID ) ? 0 : 1; test(); - IF ( EQ_16(numMasaInputs , 0) || EQ_16(numOtherInputs , 0) ) + IF( EQ_16( numMasaInputs, 0 ) || EQ_16( numOtherInputs, 0 ) ) { return IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED; } } - IF ( NE_32(( error = IVAS_REND_NumOutChannels( hIvasRend, &numOutChannels ) ) , IVAS_ERR_OK) ) + IF( NE_32( ( error = IVAS_REND_NumOutChannels( hIvasRend, &numOutChannels ) ), IVAS_ERR_OK ) ) { return error; } - IF ( NE_16(numOutChannels , outAudio.config.numChannels) ) + IF( NE_16( numOutChannels, outAudio.config.numChannels ) ) { return IVAS_ERR_WRONG_NUM_CHANNELS; } @@ -11392,24 +11529,24 @@ static ivas_error getSamplesInternal( set_zero( outAudio.data, outAudio.config.numChannels * outAudio.config.numSamplesPerChannel ); set_val_Word32( outAudio.data_fx, 0, outAudio.config.numChannels * outAudio.config.numSamplesPerChannel ); - IF ( NE_32(( error = renderActiveInputsIsm( hIvasRend, outAudio ) ) , IVAS_ERR_OK) ) + IF( NE_32( ( error = renderActiveInputsIsm( hIvasRend, outAudio ) ), IVAS_ERR_OK ) ) { return error; } - IF ( NE_32(( error = renderActiveInputsMc( hIvasRend, outAudio ) ) , IVAS_ERR_OK) ) + IF( NE_32( ( error = renderActiveInputsMc( hIvasRend, outAudio ) ), IVAS_ERR_OK ) ) { return error; } - IF ( NE_32(( error = renderActiveInputsSba( hIvasRend, outAudio ) ) , IVAS_ERR_OK) ) + IF( NE_32( ( error = renderActiveInputsSba( hIvasRend, outAudio ) ), IVAS_ERR_OK ) ) { return error; } - IF ( NE_32(( error = renderActiveInputsMasa( hIvasRend, outAudio ) ) , IVAS_ERR_OK) ) + IF( NE_32( ( error = renderActiveInputsMasa( hIvasRend, outAudio ) ), IVAS_ERR_OK ) ) { return error; } - IF ( NE_32(hIvasRend->inputsSba[0].base.inConfig , IVAS_AUDIO_CONFIG_INVALID) ) + IF( NE_32( hIvasRend->inputsSba[0].base.inConfig, IVAS_AUDIO_CONFIG_INVALID ) ) { #ifndef DISABLE_LIMITER Word32 limiter_thresold = L_lshl( IVAS_LIMITER_THRESHOLD, *outAudio.pq_fact ); @@ -11419,7 +11556,7 @@ static ivas_error getSamplesInternal( ELSE { #ifndef DISABLE_LIMITER - limitRendererOutput( hIvasRend->hLimiter, outAudio.data, outAudio.config.numSamplesPerChannel, IVAS_LIMITER_THRESHOLD); + limitRendererOutput( hIvasRend->hLimiter, outAudio.data, outAudio.config.numSamplesPerChannel, IVAS_LIMITER_THRESHOLD ); *outAudio.pq_fact = 0; #endif } @@ -11622,12 +11759,12 @@ void IVAS_REND_Close( static ivas_error ivas_masa_ext_rend_dirac_rend_init( input_masa *inputMasa ) { - int16_t nchan_out_woLFE; - int16_t nchan_transport; - uint16_t i, j, k; - float ls_azimuth[MAX_OUTPUT_CHANNELS]; - float ls_elevation[MAX_OUTPUT_CHANNELS]; - int32_t output_Fs; + Word16 nchan_out_woLFE; + Word16 nchan_transport; + UWord16 i, j, k; + Word32 ls_azimuth_fx[MAX_OUTPUT_CHANNELS];/*Q22*/ + Word32 ls_elevation_fx[MAX_OUTPUT_CHANNELS];/*Q22*/ + Word32 output_Fs; ivas_error error; DIRAC_REND_HANDLE hDirACRend; SPAT_PARAM_REND_COMMON_DATA_HANDLE hSpatParamRendCom; @@ -11636,6 +11773,7 @@ static ivas_error ivas_masa_ext_rend_dirac_rend_init( hDirACRend = NULL; output_Fs = *( inputMasa->base.ctx.pOutSampleRate ); + move32(); hSpatParamRendCom = inputMasa->hMasaExtRend->hSpatParamRendCom; @@ -11643,12 +11781,12 @@ static ivas_error ivas_masa_ext_rend_dirac_rend_init( * prepare library opening *-----------------------------------------------------------------*/ - if ( ( hDirACRend = (DIRAC_REND_HANDLE) malloc( sizeof( DIRAC_REND_DATA ) ) ) == NULL ) + IF ( ( hDirACRend = (DIRAC_REND_HANDLE) malloc( sizeof( DIRAC_REND_DATA ) ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC renderer\n" ) ); } - nchan_transport = inputMasa->base.inConfig == IVAS_AUDIO_CONFIG_MASA2 ? 2 : 1; + nchan_transport = EQ_16(inputMasa->base.inConfig , IVAS_AUDIO_CONFIG_MASA2) ? 2 : 1; /*-----------------------------------------------------------------* * output setup: for parametric binaural renderer, use output setup, otherwise internal setup @@ -11656,100 +11794,112 @@ static ivas_error ivas_masa_ext_rend_dirac_rend_init( ivas_output_init( &hDirACRend->hOutSetup, *inputMasa->base.ctx.pOutConfig ); - if ( hDirACRend->hOutSetup.output_config == IVAS_AUDIO_CONFIG_LS_CUSTOM ) + IF ( EQ_16(hDirACRend->hOutSetup.output_config , IVAS_AUDIO_CONFIG_LS_CUSTOM) ) { /* Copy from ivas_ls_custom_setup */ hDirACRend->hOutSetup.nchan_out_woLFE = inputMasa->base.ctx.pCustomLsOut->num_spk; + move16(); +#if 1/*TODO: To be removed later(floating buffer init)*/ hDirACRend->hOutSetup.ls_azimuth = inputMasa->base.ctx.pCustomLsOut->ls_azimuth; hDirACRend->hOutSetup.ls_elevation = inputMasa->base.ctx.pCustomLsOut->ls_elevation; +#endif + hDirACRend->hOutSetup.ls_azimuth_fx = inputMasa->base.ctx.pCustomLsOut->ls_azimuth_fx; + hDirACRend->hOutSetup.ls_elevation_fx = inputMasa->base.ctx.pCustomLsOut->ls_elevation_fx; hDirACRend->hOutSetup.num_lfe = inputMasa->base.ctx.pCustomLsOut->num_lfe; hDirACRend->hOutSetup.index_lfe[0] = inputMasa->base.ctx.pCustomLsOut->lfe_idx[0]; hDirACRend->hOutSetup.is_loudspeaker_setup = TRUE; - hDirACRend->hOutSetup.is_planar_setup = (int8_t) inputMasa->base.ctx.pCustomLsOut->is_planar_setup; + hDirACRend->hOutSetup.is_planar_setup = (Word8) inputMasa->base.ctx.pCustomLsOut->is_planar_setup; + move16(); + move16(); + move16(); + move16(); } nchan_out_woLFE = hDirACRend->hOutSetup.nchan_out_woLFE; + move16(); - if ( hDirACRend->hOutSetup.ls_azimuth != NULL && hDirACRend->hOutSetup.ls_elevation != NULL ) + IF ( hDirACRend->hOutSetup.ls_azimuth != NULL && hDirACRend->hOutSetup.ls_elevation != NULL ) { - mvr2r( hDirACRend->hOutSetup.ls_azimuth, ls_azimuth, nchan_out_woLFE ); - mvr2r( hDirACRend->hOutSetup.ls_elevation, ls_elevation, nchan_out_woLFE ); + Copy32( hDirACRend->hOutSetup.ls_azimuth_fx, ls_azimuth_fx, nchan_out_woLFE ); + Copy32( hDirACRend->hOutSetup.ls_elevation_fx, ls_elevation_fx, nchan_out_woLFE ); } - if ( hDirACRend->hOutSetup.ambisonics_order == -1 ) + IF ( EQ_16(hDirACRend->hOutSetup.ambisonics_order , -1) ) { hDirACRend->hOutSetup.ambisonics_order = SBA_HOA3_ORDER; /* Order 3 is used by default in DirAC for SHD processing */ - if ( hDirACRend->hOutSetup.output_config == IVAS_AUDIO_CONFIG_MONO || hDirACRend->hOutSetup.output_config == IVAS_AUDIO_CONFIG_STEREO ) + move16(); + IF ( EQ_16(hDirACRend->hOutSetup.output_config , IVAS_AUDIO_CONFIG_MONO) || EQ_16(hDirACRend->hOutSetup.output_config , IVAS_AUDIO_CONFIG_STEREO) ) { hDirACRend->hOutSetup.ambisonics_order = SBA_FOA_ORDER; + move16(); } } - else if ( hDirACRend->hOutSetup.ambisonics_order >= SBA_FOA_ORDER ) + ELSE IF ( GE_16(hDirACRend->hOutSetup.ambisonics_order , SBA_FOA_ORDER) ) { - mvr2r( ls_azimuth_4d4, ls_azimuth, DIRAC_HOA_RENDERING_NUM_VIRT_DECORR_LS ); - mvr2r( ls_elevation_4d4, ls_elevation, DIRAC_HOA_RENDERING_NUM_VIRT_DECORR_LS ); + Copy32( ls_azimuth_4d4_fx, ls_azimuth_fx, DIRAC_HOA_RENDERING_NUM_VIRT_DECORR_LS ); + Copy32( ls_elevation_4d4_fx, ls_elevation_fx, DIRAC_HOA_RENDERING_NUM_VIRT_DECORR_LS ); } /*-----------------------------------------------------------------* * set input parameters *-----------------------------------------------------------------*/ - if ( hDirACRend->hOutSetup.output_config == IVAS_AUDIO_CONFIG_MONO ) + IF ( EQ_16(hDirACRend->hOutSetup.output_config , IVAS_AUDIO_CONFIG_MONO) ) { hDirACRend->synthesisConf = DIRAC_SYNTHESIS_MONO; hDirACRend->panningConf = DIRAC_PANNING_HOA3; nchan_out_woLFE = 1; + move16(); } - else if ( hDirACRend->hOutSetup.is_loudspeaker_setup ) + ELSE IF ( hDirACRend->hOutSetup.is_loudspeaker_setup ) { hDirACRend->synthesisConf = DIRAC_SYNTHESIS_PSD_LS; hDirACRend->panningConf = DIRAC_PANNING_VBAP; } - else if ( !hDirACRend->hOutSetup.is_loudspeaker_setup && nchan_transport > 1 ) + ELSE IF ( !hDirACRend->hOutSetup.is_loudspeaker_setup && GT_16(nchan_transport , 1) ) { hDirACRend->synthesisConf = DIRAC_SYNTHESIS_PSD_SHD; hDirACRend->panningConf = DIRAC_PANNING_HOA3; } - else + ELSE { hDirACRend->synthesisConf = DIRAC_SYNTHESIS_GAIN_SHD; hDirACRend->panningConf = DIRAC_PANNING_HOA3; } - if ( ( hDirACRend->frequency_axis = (float *) malloc( hSpatParamRendCom->num_freq_bands * sizeof( float ) ) ) == NULL ) +#if 1/*TODO: To be removed later(floating buffer malloc and init)*/ + IF ( ( hDirACRend->frequency_axis = (float *) malloc( hSpatParamRendCom->num_freq_bands * sizeof( float ) ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } set_f( hDirACRend->frequency_axis, 0.0f, hSpatParamRendCom->num_freq_bands ); -#ifdef IVAS_FLOAT_FIXED - hDirACRend->frequency_axis_fx = (Word16 *) malloc( hSpatParamRendCom->num_freq_bands * sizeof( Word16 ) ); - ivas_dirac_dec_get_frequency_axis_fx( hDirACRend->frequency_axis_fx, output_Fs, hSpatParamRendCom->num_freq_bands ); - - FOR( i = 0; i < hSpatParamRendCom->num_freq_bands; i++ ) +#endif + IF( ( hDirACRend->frequency_axis_fx = (Word16 *) malloc( hSpatParamRendCom->num_freq_bands * sizeof( Word16 ) ) ) == NULL ) { - hDirACRend->frequency_axis[i] = (float) hDirACRend->frequency_axis_fx[i]; + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } -#else - ivas_dirac_dec_get_frequency_axis( hDirACRend->frequency_axis, output_Fs, hSpatParamRendCom->num_freq_bands ); -#endif + set16_fx( hDirACRend->frequency_axis_fx, 0, hSpatParamRendCom->num_freq_bands ); + ivas_dirac_dec_get_frequency_axis_fx( hDirACRend->frequency_axis_fx, output_Fs, hSpatParamRendCom->num_freq_bands ); - if ( hDirACRend->panningConf == DIRAC_PANNING_HOA3 && nchan_transport == 2 ) + + IF ( EQ_16(hDirACRend->panningConf , DIRAC_PANNING_HOA3) && EQ_16(nchan_transport , 2) ) { - if ( ( hDirACRend->masa_stereo_type_detect = (MASA_STEREO_TYPE_DETECT *) malloc( sizeof( MASA_STEREO_TYPE_DETECT ) ) ) == NULL ) + IF ( ( hDirACRend->masa_stereo_type_detect = (MASA_STEREO_TYPE_DETECT *) malloc( sizeof( MASA_STEREO_TYPE_DETECT ) ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } - ivas_masa_init_stereotype_detection( hDirACRend->masa_stereo_type_detect ); + ivas_masa_init_stereotype_detection_fx( hDirACRend->masa_stereo_type_detect ); } - else + ELSE { hDirACRend->masa_stereo_type_detect = NULL; } hSpatParamRendCom->numIsmDirections = 0; + move16(); /*-----------------------------------------------------------------* * (re)configure sub-modules @@ -11757,65 +11907,74 @@ static ivas_error ivas_masa_ext_rend_dirac_rend_init( /* prototype signal computation */ /* allocate output setup related arrays */ - if ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_PSD_LS ) + IF ( EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_PSD_LS) ) { /* Directional and diffuses components in output LS format */ hDirACRend->num_outputs_diff = nchan_out_woLFE; hDirACRend->num_outputs_dir = nchan_out_woLFE; } - else if ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_GAIN_SHD ) + ELSE IF (EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_GAIN_SHD) ) { /* Directional and diffuses components in SHD */ /* Diffuseness components up to 1st order */ hDirACRend->num_outputs_diff = ( min( hDirACRend->hOutSetup.ambisonics_order, 1 ) + 1 ) * ( min( hDirACRend->hOutSetup.ambisonics_order, 1 ) + 1 ); hDirACRend->num_outputs_dir = ivas_sba_get_nchan( hDirACRend->hOutSetup.ambisonics_order, 0 ); } - else if ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_PSD_SHD ) + ELSE IF (EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_PSD_SHD) ) { hDirACRend->num_outputs_diff = DIRAC_HOA_RENDERING_NUM_VIRT_DECORR_LS; hDirACRend->num_outputs_dir = nchan_out_woLFE; } - else if ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_MONO ) + ELSE IF (EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_MONO) ) { hDirACRend->num_outputs_diff = 1; /* There is one output channel in mono */ hDirACRend->num_outputs_dir = 2; /* Two channels are pre-rendered for stereo type detection */ } - else + ELSE { assert( 0 && "DirAC: not existing synthesis methods!" ); } + move16(); + move16(); - if ( ( hDirACRend->proto_index_dir = (int16_t *) malloc( sizeof( int16_t ) * hDirACRend->num_outputs_dir ) ) == NULL ) + IF ( ( hDirACRend->proto_index_dir = (Word16 *) malloc( sizeof( Word16 ) * hDirACRend->num_outputs_dir ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } - if ( ( hDirACRend->proto_index_diff = (int16_t *) malloc( sizeof( int16_t ) * hDirACRend->num_outputs_diff ) ) == NULL ) + IF ( ( hDirACRend->proto_index_diff = (Word16 *) malloc( sizeof(Word16) * hDirACRend->num_outputs_diff ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } - set_s( hDirACRend->proto_index_dir, 0, hDirACRend->num_outputs_dir ); - set_s( hDirACRend->proto_index_diff, 0, hDirACRend->num_outputs_diff ); + set16_fx( hDirACRend->proto_index_dir, 0, hDirACRend->num_outputs_dir ); + set16_fx( hDirACRend->proto_index_diff, 0, hDirACRend->num_outputs_diff ); hDirACRend->sba_map_tc = sba_map_tc; - if ( nchan_transport == 1 ) + IF ( EQ_16(nchan_transport , 1) ) { hDirACRend->num_protos_ambi = 1; hDirACRend->num_protos_dir = 1; hDirACRend->num_protos_diff = 1; + move16(); + move16(); + move16(); } - else if ( nchan_transport == 2 ) + ELSE IF ( EQ_16(nchan_transport , 2) ) { - if ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_GAIN_SHD ) + IF ( EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_GAIN_SHD) ) { hDirACRend->num_protos_ambi = 2; hDirACRend->num_protos_diff = 1; hDirACRend->num_protos_dir = 2; hDirACRend->proto_index_dir[1] = 1; + move16(); + move16(); + move16(); + move16(); } - else if ( hDirACRend->hOutSetup.output_config == IVAS_AUDIO_CONFIG_MONO ) + ELSE IF (EQ_16(hDirACRend->hOutSetup.output_config , IVAS_AUDIO_CONFIG_MONO) ) { /* Following the foa rendering for code compatibility */ hDirACRend->num_protos_ambi = 2; @@ -11823,143 +11982,118 @@ static ivas_error ivas_masa_ext_rend_dirac_rend_init( hDirACRend->num_protos_diff = 3; hDirACRend->proto_index_dir[0] = 0; hDirACRend->proto_index_diff[0] = 0; + move16(); + move16(); + move16(); + move16(); + move16(); } - else + ELSE { hDirACRend->num_protos_ambi = 2; hDirACRend->num_protos_diff = 3; + move16(); + move16(); - for ( k = 0; k < hDirACRend->num_outputs_diff; k++ ) + FOR ( k = 0; k < hDirACRend->num_outputs_diff; k++ ) { - if ( ls_azimuth[k] > 0.0f ) + IF ( GT_32(ls_azimuth_fx[k] , 0) ) { hDirACRend->proto_index_diff[k] = 1; } - else if ( ls_azimuth[k] < 0.0f ) + ELSE IF ( LT_32(ls_azimuth_fx[k] , 0) ) { hDirACRend->proto_index_diff[k] = 2; } - else + ELSE { hDirACRend->proto_index_diff[k] = 0; } + move16(); } - if ( hDirACRend->hOutSetup.is_loudspeaker_setup ) + IF ( hDirACRend->hOutSetup.is_loudspeaker_setup ) { hDirACRend->num_protos_dir = 3; - mvs2s( hDirACRend->proto_index_diff, hDirACRend->proto_index_dir, nchan_out_woLFE ); + move16(); + Copy( hDirACRend->proto_index_diff, hDirACRend->proto_index_dir, nchan_out_woLFE ); } - else + ELSE { hDirACRend->num_protos_dir = 2; hDirACRend->proto_index_dir[1] = 1; + move16(); + move16(); } } } /* direct/diffuse responses */ -#ifdef IVAS_FLOAT_FIXED + IF( ( hDirACRend->diffuse_response_function_fx = (Word16 *) malloc( sizeof( Word16 ) * hDirACRend->num_outputs_dir ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } -#endif +#if 1/*TODO: To be removed later (Float buffer malloc)*/ if ( ( hDirACRend->diffuse_response_function = (float *) malloc( sizeof( float ) * hDirACRend->num_outputs_dir ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } +#endif - if ( ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_PSD_LS ) || ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_PSD_SHD ) || ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_MONO ) ) + IF ( EQ_16( hDirACRend->synthesisConf , DIRAC_SYNTHESIS_PSD_LS ) || EQ_16( hDirACRend->synthesisConf , DIRAC_SYNTHESIS_PSD_SHD ) || EQ_16( hDirACRend->synthesisConf , DIRAC_SYNTHESIS_MONO ) ) { -#ifdef IVAS_FLOAT_FIXED initDiffuseResponses_fx( hDirACRend->diffuse_response_function_fx, nchan_out_woLFE, hDirACRend->hOutSetup.output_config, hDirACRend->hOutSetup, hDirACRend->hOutSetup.ambisonics_order, MASA_FORMAT, &hDirACRend->num_ele_spk_no_diffuse_rendering, IVAS_AUDIO_CONFIG_INVALID ); - FOR( i = 0; i < hDirACRend->num_outputs_dir; i++ ) - { - hDirACRend->diffuse_response_function[i] = fix16_to_float( hDirACRend->diffuse_response_function_fx[i], Q15 ); - } -#else - initDiffuseResponses( hDirACRend->diffuse_response_function, nchan_out_woLFE, hDirACRend->hOutSetup.output_config, - hDirACRend->hOutSetup, hDirACRend->hOutSetup.ambisonics_order, MASA_FORMAT, &hDirACRend->num_ele_spk_no_diffuse_rendering, IVAS_AUDIO_CONFIG_INVALID ); -#endif } - else + ELSE { -#ifdef IVAS_FLOAT_FIXED initDiffuseResponses_fx( hDirACRend->diffuse_response_function_fx, hDirACRend->num_outputs_dir, IVAS_AUDIO_CONFIG_FOA, hDirACRend->hOutSetup, hDirACRend->hOutSetup.ambisonics_order, MASA_FORMAT, &hDirACRend->num_ele_spk_no_diffuse_rendering, IVAS_AUDIO_CONFIG_INVALID ); - FOR( i = 0; i < hDirACRend->num_outputs_dir; i++ ) - { - hDirACRend->diffuse_response_function[i] = fix16_to_float( hDirACRend->diffuse_response_function_fx[i], Q15 ); - } -#else - initDiffuseResponses( hDirACRend->diffuse_response_function, hDirACRend->num_outputs_dir, IVAS_AUDIO_CONFIG_FOA, - hDirACRend->hOutSetup, hDirACRend->hOutSetup.ambisonics_order, MASA_FORMAT, &hDirACRend->num_ele_spk_no_diffuse_rendering, IVAS_AUDIO_CONFIG_INVALID ); -#endif } +#if 1/*TODO: To be removed later(after dependecny on float buffer hoa_encoder is removed)*/ hDirACRend->hoa_encoder = NULL; -#ifdef IVAS_FLOAT_FIXED - hDirACRend->hoa_encoder_fx = NULL; #endif - if ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_PSD_SHD ) + hDirACRend->hoa_encoder_fx = NULL; + IF ( EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_PSD_SHD) ) { -#ifdef IVAS_FLOAT_FIXED IF ( ( hDirACRend->hoa_encoder_fx = (Word32 *) malloc( nchan_out_woLFE * hDirACRend->num_outputs_diff * sizeof( Word32 ) ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } set32_fx( hDirACRend->hoa_encoder_fx, 0, nchan_out_woLFE * hDirACRend->num_outputs_diff ); - hDirACRend->hoa_encoder_len = nchan_out_woLFE * hDirACRend->num_outputs_diff; -#endif + hDirACRend->hoa_encoder_len = imult1616(nchan_out_woLFE , hDirACRend->num_outputs_diff); +#if 1/*TODO: To be removed later(float buffer malloc and init)*/ if ( ( hDirACRend->hoa_encoder = (float *) malloc( nchan_out_woLFE * hDirACRend->num_outputs_diff * sizeof( float ) ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } set_f( hDirACRend->hoa_encoder, 0.0f, nchan_out_woLFE * hDirACRend->num_outputs_diff ); - compute_hoa_encoder_mtx( ls_azimuth, ls_elevation, hDirACRend->hoa_encoder, hDirACRend->num_outputs_diff, hDirACRend->hOutSetup.ambisonics_order ); +#endif + compute_hoa_encoder_mtx_fx( ls_azimuth_fx, ls_elevation_fx, hDirACRend->hoa_encoder_fx, hDirACRend->num_outputs_diff, hDirACRend->hOutSetup.ambisonics_order ); } /* VBAP */ inputMasa->hMasaExtRend->hVBAPdata = NULL; - if ( hDirACRend->panningConf == DIRAC_PANNING_VBAP ) + IF ( EQ_16(hDirACRend->panningConf , DIRAC_PANNING_VBAP) ) { -#ifdef IVAS_FLOAT_FIXED - Word32 ls_azimuth_fx[MAX_OUTPUT_CHANNELS]; - Word32 ls_elevation_fx[MAX_OUTPUT_CHANNELS]; - FOR( i = 0; i < MAX_OUTPUT_CHANNELS; i++ ) - { - ls_azimuth_fx[i] = (Word32) float_to_fix( ls_azimuth[i], Q22 ); - ls_elevation_fx[i] = (Word32) float_to_fix( ls_elevation[i], Q22 ); - } IF( ( error = vbap_init_data_fx( &( inputMasa->hMasaExtRend->hVBAPdata ), ls_azimuth_fx, ls_elevation_fx, nchan_out_woLFE, MASA_FORMAT ) ) != IVAS_ERR_OK ) { return error; } - FOR( i = 0; i < MAX_OUTPUT_CHANNELS; i++ ) - { - ls_azimuth[i] = (float) fix_to_float( ls_azimuth_fx[i], Q22 ); - ls_elevation[i] = (float) fix_to_float( ls_elevation_fx[i], Q22 ); - } -#else - if ( ( error = vbap_init_data( &( inputMasa->hMasaExtRend->hVBAPdata ), ls_azimuth, ls_elevation, nchan_out_woLFE, MASA_FORMAT ) ) != IVAS_ERR_OK ) - { - return error; - } -#endif } /* HOA panning/dec */ hDirACRend->hoa_decoder = NULL; - if ( hDirACRend->panningConf == DIRAC_PANNING_HOA3 ) + IF ( EQ_16(hDirACRend->panningConf , DIRAC_PANNING_HOA3) ) { - if ( hDirACRend->hOutSetup.is_loudspeaker_setup ) + IF ( hDirACRend->hOutSetup.is_loudspeaker_setup ) { - if ( ( error = ivas_sba_get_hoa_dec_matrix_fx( hDirACRend->hOutSetup, &inputMasa->hMasaExtRend->hoa_dec_mtx, hDirACRend->hOutSetup.ambisonics_order ) ) != IVAS_ERR_OK ) + IF ( ( error = ivas_sba_get_hoa_dec_matrix_fx( hDirACRend->hOutSetup, &inputMasa->hMasaExtRend->hoa_dec_mtx, hDirACRend->hOutSetup.ambisonics_order ) ) != IVAS_ERR_OK ) { return error; } @@ -11970,16 +12104,14 @@ static ivas_error ivas_masa_ext_rend_dirac_rend_init( /* decorrelation */ hDirACRend->proto_signal_decorr_on = 1; - if ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_MONO ) + IF ( EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_MONO) ) { hDirACRend->proto_signal_decorr_on = 0; } - if ( hDirACRend->proto_signal_decorr_on ) + IF ( hDirACRend->proto_signal_decorr_on ) { -#ifdef IVAS_FLOAT_FIXED - hDirACRend->frequency_axis[i] = (float)hDirACRend->frequency_axis_fx[i]; - if ( ( error = ivas_dirac_dec_decorr_open_fx( &( hDirACRend->h_freq_domain_decorr_ap_params ), + IF ( ( error = ivas_dirac_dec_decorr_open_fx( &( hDirACRend->h_freq_domain_decorr_ap_params ), &( hDirACRend->h_freq_domain_decorr_ap_state ), hSpatParamRendCom->num_freq_bands, hDirACRend->num_outputs_diff, @@ -11992,74 +12124,65 @@ static ivas_error ivas_masa_ext_rend_dirac_rend_init( return error; } -#else - - if ( ( error = ivas_dirac_dec_decorr_open( &( hDirACRend->h_freq_domain_decorr_ap_params ), - &( hDirACRend->h_freq_domain_decorr_ap_state ), - hSpatParamRendCom->num_freq_bands, - hDirACRend->num_outputs_diff, - hDirACRend->num_protos_diff, - hDirACRend->synthesisConf, - hDirACRend->frequency_axis, - nchan_transport, - output_Fs ) ) != IVAS_ERR_OK ) - { - return error; - } -#endif } /* output synthesis */ -#ifdef IVAS_FLOAT_FIXED - if ( ( ivas_dirac_dec_output_synthesis_open_fx( hSpatParamRendCom, hDirACRend, RENDERER_DIRAC, nchan_transport, output_Fs, 0 ) ) != IVAS_ERR_OK ) + IF ( ( ivas_dirac_dec_output_synthesis_open_fx( hSpatParamRendCom, hDirACRend, RENDERER_DIRAC, nchan_transport, output_Fs, 0 ) ) != IVAS_ERR_OK ) { return error; } -#else - if ( ( ivas_dirac_dec_output_synthesis_open( hSpatParamRendCom, hDirACRend, RENDERER_DIRAC, nchan_transport, output_Fs, 0 ) ) != IVAS_ERR_OK ) - { - return error; - } -#endif hDirACRend->h_output_synthesis_psd_params.use_onset_filters = hDirACRend->proto_signal_decorr_on; + move16(); - if ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_PSD_SHD || hDirACRend->synthesisConf == DIRAC_SYNTHESIS_GAIN_SHD ) + IF ( EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_PSD_SHD) || EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_GAIN_SHD) ) { hDirACRend->h_output_synthesis_psd_params.use_onset_filters = 0; + move16(); } /*-----------------------------------------------------------------* * memory allocation *-----------------------------------------------------------------*/ - if ( hDirACRend->synthesisConf == DIRAC_SYNTHESIS_GAIN_SHD ) + IF ( EQ_16(hDirACRend->synthesisConf , DIRAC_SYNTHESIS_GAIN_SHD) ) { hDirACRend->proto_frame_f = NULL; } - else + ELSE { - if ( ( hDirACRend->proto_frame_f = (float *) malloc( sizeof( float ) * 2 * hDirACRend->num_protos_diff * hSpatParamRendCom->num_freq_bands ) ) == NULL ) +#if 1/*TODO: To be removed later(after dependency on proto_frame_f is completely removed)*/ + IF ( ( hDirACRend->proto_frame_f = (float *) malloc( sizeof( float ) * 2 * hDirACRend->num_protos_diff * hSpatParamRendCom->num_freq_bands ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); + } +#endif + IF( ( hDirACRend->proto_frame_f_fx = (Word32 *) malloc( sizeof(Word32) * 2 * hDirACRend->num_protos_diff * hSpatParamRendCom->num_freq_bands ) ) == NULL ) { return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC\n" ) ); } } +#if 1/*TODO :To be removed later(after dependecy on buffer_energyis completely removed)*/ hDirACRend->buffer_energy = NULL; +#endif - for ( i = 0; i < DIRAC_NUM_DIMS; i++ ) + FOR ( i = 0; i < DIRAC_NUM_DIMS; i++ ) { - for ( j = 0; j < DIRAC_NO_COL_AVG_DIFF; j++ ) + FOR ( j = 0; j < DIRAC_NO_COL_AVG_DIFF; j++ ) { +#if 1 /*TODO :To be removed later(after dependecy on buffer_energyis completely removed)*/ hDirACRend->buffer_intensity_real[i][j] = NULL; +#endif + hDirACRend->buffer_intensity_real_fx[i][j] = NULL; } } /* output synthesis */ - ivas_dirac_dec_output_synthesis_init( hSpatParamRendCom, hDirACRend, nchan_out_woLFE, 0 ); + ivas_dirac_dec_output_synthesis_init_fx( hSpatParamRendCom, hDirACRend, nchan_out_woLFE, 0 ); /* Allocate stack memory */ - if ( ( error = ivas_dirac_alloc_mem( hDirACRend, RENDERER_DIRAC, hSpatParamRendCom->num_freq_bands, &( hDirACRend->stack_mem ), 0 ) ) != IVAS_ERR_OK ) + IF ( ( error = ivas_dirac_alloc_mem( hDirACRend, RENDERER_DIRAC, hSpatParamRendCom->num_freq_bands, &( hDirACRend->stack_mem ), 0 ) ) != IVAS_ERR_OK ) { return error; } @@ -12407,42 +12530,199 @@ static ivas_error ivas_masa_ext_rend_dirac_rend_init( hDirACRend->buffer_energy = NULL; - for ( i = 0; i < DIRAC_NUM_DIMS; i++ ) + for ( i = 0; i < DIRAC_NUM_DIMS; i++ ) + { + for ( j = 0; j < DIRAC_NO_COL_AVG_DIFF; j++ ) + { + hDirACRend->buffer_intensity_real[i][j] = NULL; + } + } + + /* output synthesis */ + ivas_dirac_dec_output_synthesis_init( hSpatParamRendCom, hDirACRend, nchan_out_woLFE, 0 ); + + /* Allocate stack memory */ + if ( ( error = ivas_dirac_alloc_mem( hDirACRend, RENDERER_DIRAC, hSpatParamRendCom->num_freq_bands, &( hDirACRend->stack_mem ), 0 ) ) != IVAS_ERR_OK ) + { + return error; + } + + inputMasa->hMasaExtRend->hDirACRend = hDirACRend; + + return error; +} +#endif + +#ifndef IVAS_FLOAT_FIXED +static ivas_error ivas_masa_ext_rend_parambin_init( + input_masa *inputMasa /* i/o: MASA external renderer structure */ +) +{ + DIRAC_DEC_BIN_HANDLE hDiracDecBin; + HRTFS_PARAMBIN_HANDLE hHrtfParambin; + int16_t nBins; + int32_t output_Fs; + RENDERER_TYPE renderer_type; + int16_t j, k, bin; + float binCenterFreq, tmpFloat; + ivas_error error; + float frequency_axis[CLDFB_NO_CHANNELS_MAX]; + + error = IVAS_ERR_OK; + + hHrtfParambin = inputMasa->hMasaExtRend->hHrtfParambin; + + /* Set common variables and defaults */ + output_Fs = *( inputMasa->base.ctx.pOutSampleRate ); + nBins = inputMasa->hMasaExtRend->hSpatParamRendCom->num_freq_bands; + renderer_type = inputMasa->hMasaExtRend->renderer_type; + + hDiracDecBin = inputMasa->hMasaExtRend->hDiracDecBin; + + /* Init assumes that no reconfiguration is required in external renderer. Instead, free and rebuild whole rendering. */ + if ( ( hDiracDecBin = (DIRAC_DEC_BIN_HANDLE) malloc( sizeof( DIRAC_DEC_BIN_DATA ) ) ) == NULL ) + { + return IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC binaural handle " ); + } + + hDiracDecBin->hTdDecorr = NULL; + hDiracDecBin->hReverb = NULL; + hDiracDecBin->h_freq_domain_decorr_ap_params = NULL; + hDiracDecBin->h_freq_domain_decorr_ap_state = NULL; + hDiracDecBin->hDiffuseDist = NULL; /* Not used in external renderer */ + hDiracDecBin->useTdDecorr = 0; /* Always use frequency domain decorrelator in external renderer */ + + for ( j = 0; j < BINAURAL_CHANNELS; j++ ) + { + for ( k = 0; k < BINAURAL_CHANNELS + MAX_NUM_OBJECTS; k++ ) + { + set_zero( hDiracDecBin->processMtxRe[j][k], nBins ); + set_zero( hDiracDecBin->processMtxIm[j][k], nBins ); + } + + for ( k = 0; k < BINAURAL_CHANNELS; k++ ) + { + set_zero( hDiracDecBin->processMtxDecRe[j][k], nBins ); + set_zero( hDiracDecBin->processMtxDecIm[j][k], nBins ); + } + set_zero( hDiracDecBin->ChEnePrev[j], nBins ); + set_zero( hDiracDecBin->ChEneOutPrev[j], nBins ); + } + set_zero( hDiracDecBin->ChCrossRePrev, nBins ); + set_zero( hDiracDecBin->ChCrossImPrev, nBins ); + set_zero( hDiracDecBin->ChCrossReOutPrev, nBins ); + set_zero( hDiracDecBin->ChCrossImOutPrev, nBins ); + hDiracDecBin->renderStereoOutputInsteadOfBinaural = 0; + + for ( bin = 0; bin < nBins; bin++ ) + { + binCenterFreq = ( (float) bin + 0.5f ) / (float) nBins * ( (float) output_Fs / 2.0f ); + /* These formulas and values are from Christian Borss's publication for binaural diffuse field coherence */ + tmpFloat = max( 0.0f, 1.0f - binCenterFreq / 2700.0f ); + hDiracDecBin->diffuseFieldCoherence[bin] = tmpFloat * sinf( binCenterFreq * EVS_PI / 550.0f ) / ( binCenterFreq * EVS_PI / 550.0f ); + } + + /* No SPAR in external renderer so set directive diffuse field coherence tables to zero */ + set_zero( hDiracDecBin->diffuseFieldCoherenceX, BINAURAL_COHERENCE_DIFFERENCE_BINS ); + set_zero( hDiracDecBin->diffuseFieldCoherenceY, BINAURAL_COHERENCE_DIFFERENCE_BINS ); + set_zero( hDiracDecBin->diffuseFieldCoherenceZ, BINAURAL_COHERENCE_DIFFERENCE_BINS ); + + if ( renderer_type == RENDERER_BINAURAL_PARAMETRIC ) /* Indication of binaural rendering without room effect */ + { + set_f( hDiracDecBin->earlyPartEneCorrection, 1.0f, CLDFB_NO_CHANNELS_MAX ); + hDiracDecBin->hReverb = NULL; + } + else if ( renderer_type == RENDERER_BINAURAL_PARAMETRIC_ROOM ) /* Indication of binaural rendering with room effect */ + { + mvr2r( hHrtfParambin->parametricEarlyPartEneCorrection, hDiracDecBin->earlyPartEneCorrection, nBins ); + + if ( hDiracDecBin->hReverb == NULL ) + { + /* Todo Philips: Room acoustics should be passed here once the underlying part works. In this case, it probably should come from render context or somewhere else suitable. */ + if ( ( error = ivas_binaural_reverb_open_parambin( &hDiracDecBin->hReverb, nBins, CLDFB_NO_COL_MAX / MAX_PARAM_SPATIAL_SUBFRAMES, NULL, output_Fs, hHrtfParambin ) ) != IVAS_ERR_OK ) + { + return error; + } + } + } + else if ( renderer_type == RENDERER_STEREO_PARAMETRIC ) + { + set_f( hDiracDecBin->earlyPartEneCorrection, 1.0f, CLDFB_NO_CHANNELS_MAX ); + hDiracDecBin->hReverb = NULL; + hDiracDecBin->renderStereoOutputInsteadOfBinaural = 1; + } + else /* Not valid renderer type for this renderer */ + { + assert( false ); + } + + /* Always open frequency domain decorrelator */ +#ifdef IVAS_FLOAT_FIXED + Word16 frequency_axis_fx[CLDFB_NO_CHANNELS_MAX]; + ivas_dirac_dec_get_frequency_axis_fx( frequency_axis_fx, output_Fs, nBins ); + + for ( int i = 0; i < nBins; i++ ) { - for ( j = 0; j < DIRAC_NO_COL_AVG_DIFF; j++ ) - { - hDirACRend->buffer_intensity_real[i][j] = NULL; - } + frequency_axis[i] = (float) frequency_axis_fx[i]; } + if ( ( error = ivas_dirac_dec_decorr_open_fx( &( hDiracDecBin->h_freq_domain_decorr_ap_params ), + &( hDiracDecBin->h_freq_domain_decorr_ap_state ), + nBins, + BINAURAL_CHANNELS, + BINAURAL_CHANNELS, + DIRAC_SYNTHESIS_PSD_LS, + frequency_axis_fx, + BINAURAL_CHANNELS, + output_Fs ) ) != IVAS_ERR_OK ) + { + return error; + } +#else + ivas_dirac_dec_get_frequency_axis( frequency_axis, output_Fs, nBins ); - /* output synthesis */ - ivas_dirac_dec_output_synthesis_init( hSpatParamRendCom, hDirACRend, nchan_out_woLFE, 0 ); - - /* Allocate stack memory */ - if ( ( error = ivas_dirac_alloc_mem( hDirACRend, RENDERER_DIRAC, hSpatParamRendCom->num_freq_bands, &( hDirACRend->stack_mem ), 0 ) ) != IVAS_ERR_OK ) + if ( ( error = ivas_dirac_dec_decorr_open( &( hDiracDecBin->h_freq_domain_decorr_ap_params ), + &( hDiracDecBin->h_freq_domain_decorr_ap_state ), + nBins, + BINAURAL_CHANNELS, + BINAURAL_CHANNELS, + DIRAC_SYNTHESIS_PSD_LS, + frequency_axis, + BINAURAL_CHANNELS, + output_Fs ) ) != IVAS_ERR_OK ) { return error; } +#endif + /* External renderer uses constant regularization factor */ +#ifdef IVAS_FLOAT_FIXED + hDiracDecBin->reqularizationFactor_fx = 6554; + move16(); +#else + hDiracDecBin->reqularizationFactor = 0.4f; +#endif - inputMasa->hMasaExtRend->hDirACRend = hDirACRend; + inputMasa->hMasaExtRend->hDiracDecBin = hDiracDecBin; return error; } -#endif - +#else static ivas_error ivas_masa_ext_rend_parambin_init( input_masa *inputMasa /* i/o: MASA external renderer structure */ ) { DIRAC_DEC_BIN_HANDLE hDiracDecBin; HRTFS_PARAMBIN_HANDLE hHrtfParambin; - int16_t nBins; - int32_t output_Fs; + Word16 nBins; + Word32 output_Fs; RENDERER_TYPE renderer_type; - int16_t j, k, bin; - float binCenterFreq, tmpFloat; + Word16 j, k, bin; + Word32 binCenterFreq_fx; + Word16 tmpFloat_fx; ivas_error error; - float frequency_axis[CLDFB_NO_CHANNELS_MAX]; + Word16 frequency_axis_fx[CLDFB_NO_CHANNELS_MAX]; + Word16 tmp; + Word16 tmp_e; + Word16 tmp2; error = IVAS_ERR_OK; @@ -12451,12 +12731,14 @@ static ivas_error ivas_masa_ext_rend_parambin_init( /* Set common variables and defaults */ output_Fs = *( inputMasa->base.ctx.pOutSampleRate ); nBins = inputMasa->hMasaExtRend->hSpatParamRendCom->num_freq_bands; + move32(); + move16(); renderer_type = inputMasa->hMasaExtRend->renderer_type; hDiracDecBin = inputMasa->hMasaExtRend->hDiracDecBin; /* Init assumes that no reconfiguration is required in external renderer. Instead, free and rebuild whole rendering. */ - if ( ( hDiracDecBin = (DIRAC_DEC_BIN_HANDLE) malloc( sizeof( DIRAC_DEC_BIN_DATA ) ) ) == NULL ) + IF ( ( hDiracDecBin = (DIRAC_DEC_BIN_HANDLE) malloc( sizeof( DIRAC_DEC_BIN_DATA ) ) ) == NULL ) { return IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for DirAC binaural handle " ); } @@ -12467,81 +12749,107 @@ static ivas_error ivas_masa_ext_rend_parambin_init( hDiracDecBin->h_freq_domain_decorr_ap_state = NULL; hDiracDecBin->hDiffuseDist = NULL; /* Not used in external renderer */ hDiracDecBin->useTdDecorr = 0; /* Always use frequency domain decorrelator in external renderer */ + move16(); - for ( j = 0; j < BINAURAL_CHANNELS; j++ ) + FOR ( j = 0; j < BINAURAL_CHANNELS; j++ ) { - for ( k = 0; k < BINAURAL_CHANNELS + MAX_NUM_OBJECTS; k++ ) + FOR ( k = 0; k < BINAURAL_CHANNELS + MAX_NUM_OBJECTS; k++ ) { +#if 1/*To be removed later(floating buffer init)*/ set_zero( hDiracDecBin->processMtxRe[j][k], nBins ); set_zero( hDiracDecBin->processMtxIm[j][k], nBins ); +#endif + set16_fx( hDiracDecBin->processMtxRe_fx[j][k],0, nBins ); + set16_fx( hDiracDecBin->processMtxIm_fx[j][k],0, nBins ); } - for ( k = 0; k < BINAURAL_CHANNELS; k++ ) + FOR ( k = 0; k < BINAURAL_CHANNELS; k++ ) { +#if 1/*To be removed later(floating buffer init)*/ set_zero( hDiracDecBin->processMtxDecRe[j][k], nBins ); set_zero( hDiracDecBin->processMtxDecIm[j][k], nBins ); +#endif + set16_fx( hDiracDecBin->processMtxDecRe_fx[j][k],0, nBins ); + set16_fx( hDiracDecBin->processMtxDecIm_fx[j][k],0, nBins ); } +#if 1/*TODO:To be removed later(floating buffer init)*/ set_zero( hDiracDecBin->ChEnePrev[j], nBins ); set_zero( hDiracDecBin->ChEneOutPrev[j], nBins ); +#endif + set_zero_fx( hDiracDecBin->ChEnePrev_fx[j], nBins ); + set_zero_fx( hDiracDecBin->ChEneOutPrev_fx[j], nBins ); } +#if 1/*TODO:To be removed later(floating buffer init)*/ set_zero( hDiracDecBin->ChCrossRePrev, nBins ); set_zero( hDiracDecBin->ChCrossImPrev, nBins ); set_zero( hDiracDecBin->ChCrossReOutPrev, nBins ); set_zero( hDiracDecBin->ChCrossImOutPrev, nBins ); +#endif + set_zero_fx( hDiracDecBin->ChCrossRePrev_fx, nBins ); + set_zero_fx( hDiracDecBin->ChCrossImPrev_fx, nBins ); + set_zero_fx( hDiracDecBin->ChCrossReOutPrev_fx, nBins ); + set_zero_fx( hDiracDecBin->ChCrossImOutPrev_fx, nBins ); hDiracDecBin->renderStereoOutputInsteadOfBinaural = 0; - for ( bin = 0; bin < nBins; bin++ ) + FOR ( bin = 0; bin < nBins; bin++ ) { - binCenterFreq = ( (float) bin + 0.5f ) / (float) nBins * ( (float) output_Fs / 2.0f ); + binCenterFreq_fx = L_mult0(extract_l(L_shr(output_Fs,1)), div_s(add(shl(bin, 1), 1), shl(nBins, 1)))/*( (float) bin + 0.5f ) / (float) nBins * ( (float) output_Fs / 2.0f )*/;/*Q15*/ /* These formulas and values are from Christian Borss's publication for binaural diffuse field coherence */ - tmpFloat = max( 0.0f, 1.0f - binCenterFreq / 2700.0f ); - hDiracDecBin->diffuseFieldCoherence[bin] = tmpFloat * sinf( binCenterFreq * EVS_PI / 550.0f ) / ( binCenterFreq * EVS_PI / 550.0f ); + tmp = BASOP_Util_Divide3232_Scale( binCenterFreq_fx, 2700<diffuseFieldCoherence_fx[bin] = L_shl(L_mult0(divide3232(tmpFloat_fx, Mult_32_16(binCenterFreq_fx, 187/*2^15*pi/550*/)), getSineWord16R2(tmp2)), tmp_e);/*tmpFloat * sinf( binCenterFreq * EVS_PI / 550.0f ) / ( binCenterFreq * EVS_PI / 550.0f );*/ + hDiracDecBin->diffuseFieldCoherence[bin] = fixedToFloat( hDiracDecBin->diffuseFieldCoherence_fx[bin], Q30 ); } /* No SPAR in external renderer so set directive diffuse field coherence tables to zero */ +#if 1/*TODO: To be removed later(floating buffer init)*/ set_zero( hDiracDecBin->diffuseFieldCoherenceX, BINAURAL_COHERENCE_DIFFERENCE_BINS ); set_zero( hDiracDecBin->diffuseFieldCoherenceY, BINAURAL_COHERENCE_DIFFERENCE_BINS ); set_zero( hDiracDecBin->diffuseFieldCoherenceZ, BINAURAL_COHERENCE_DIFFERENCE_BINS ); +#endif + set_zero_fx( hDiracDecBin->diffuseFieldCoherenceX_fx, BINAURAL_COHERENCE_DIFFERENCE_BINS ); + set_zero_fx( hDiracDecBin->diffuseFieldCoherenceY_fx, BINAURAL_COHERENCE_DIFFERENCE_BINS ); + set_zero_fx( hDiracDecBin->diffuseFieldCoherenceZ_fx, BINAURAL_COHERENCE_DIFFERENCE_BINS ); - if ( renderer_type == RENDERER_BINAURAL_PARAMETRIC ) /* Indication of binaural rendering without room effect */ + IF ( EQ_16(renderer_type , RENDERER_BINAURAL_PARAMETRIC) ) /* Indication of binaural rendering without room effect */ { - set_f( hDiracDecBin->earlyPartEneCorrection, 1.0f, CLDFB_NO_CHANNELS_MAX ); + set32_fx( hDiracDecBin->earlyPartEneCorrection_fx, ONE_IN_Q28/*1.0f Q28*/, CLDFB_NO_CHANNELS_MAX ); hDiracDecBin->hReverb = NULL; } - else if ( renderer_type == RENDERER_BINAURAL_PARAMETRIC_ROOM ) /* Indication of binaural rendering with room effect */ + ELSE IF ( EQ_16(renderer_type , RENDERER_BINAURAL_PARAMETRIC_ROOM) ) /* Indication of binaural rendering with room effect */ { - mvr2r( hHrtfParambin->parametricEarlyPartEneCorrection, hDiracDecBin->earlyPartEneCorrection, nBins ); + Copy32( hHrtfParambin->parametricEarlyPartEneCorrection_fx, hDiracDecBin->earlyPartEneCorrection_fx, nBins ); - if ( hDiracDecBin->hReverb == NULL ) + IF ( hDiracDecBin->hReverb == NULL ) { /* Todo Philips: Room acoustics should be passed here once the underlying part works. In this case, it probably should come from render context or somewhere else suitable. */ - if ( ( error = ivas_binaural_reverb_open_parambin( &hDiracDecBin->hReverb, nBins, CLDFB_NO_COL_MAX / MAX_PARAM_SPATIAL_SUBFRAMES, NULL, output_Fs, hHrtfParambin ) ) != IVAS_ERR_OK ) + IF ( ( error = ivas_binaural_reverb_open_parambin( &hDiracDecBin->hReverb, nBins, CLDFB_NO_COL_MAX / MAX_PARAM_SPATIAL_SUBFRAMES, NULL, output_Fs, hHrtfParambin ) ) != IVAS_ERR_OK ) { return error; } } } - else if ( renderer_type == RENDERER_STEREO_PARAMETRIC ) + ELSE IF ( EQ_16(renderer_type , RENDERER_STEREO_PARAMETRIC) ) { - set_f( hDiracDecBin->earlyPartEneCorrection, 1.0f, CLDFB_NO_CHANNELS_MAX ); + set32_fx( hDiracDecBin->earlyPartEneCorrection_fx, ONE_IN_Q28 /*1.0f Q28*/, CLDFB_NO_CHANNELS_MAX ); hDiracDecBin->hReverb = NULL; hDiracDecBin->renderStereoOutputInsteadOfBinaural = 1; } - else /* Not valid renderer type for this renderer */ + ELSE /* Not valid renderer type for this renderer */ { assert( false ); } /* Always open frequency domain decorrelator */ -#ifdef IVAS_FLOAT_FIXED - Word16 frequency_axis_fx[CLDFB_NO_CHANNELS_MAX]; ivas_dirac_dec_get_frequency_axis_fx( frequency_axis_fx, output_Fs, nBins ); - for ( int i = 0; i < nBins; i++ ) - { - frequency_axis[i] = (float) frequency_axis_fx[i]; - } - if ( ( error = ivas_dirac_dec_decorr_open_fx( &( hDiracDecBin->h_freq_domain_decorr_ap_params ), + IF ( ( error = ivas_dirac_dec_decorr_open_fx( &( hDiracDecBin->h_freq_domain_decorr_ap_params ), &( hDiracDecBin->h_freq_domain_decorr_ap_state ), nBins, BINAURAL_CHANNELS, @@ -12553,35 +12861,17 @@ static ivas_error ivas_masa_ext_rend_parambin_init( { return error; } -#else - ivas_dirac_dec_get_frequency_axis( frequency_axis, output_Fs, nBins ); - - if ( ( error = ivas_dirac_dec_decorr_open( &( hDiracDecBin->h_freq_domain_decorr_ap_params ), - &( hDiracDecBin->h_freq_domain_decorr_ap_state ), - nBins, - BINAURAL_CHANNELS, - BINAURAL_CHANNELS, - DIRAC_SYNTHESIS_PSD_LS, - frequency_axis, - BINAURAL_CHANNELS, - output_Fs ) ) != IVAS_ERR_OK ) - { - return error; - } -#endif /* External renderer uses constant regularization factor */ -#ifdef IVAS_FLOAT_FIXED hDiracDecBin->reqularizationFactor_fx = 6554; move16(); -#else - hDiracDecBin->reqularizationFactor = 0.4f; -#endif inputMasa->hMasaExtRend->hDiracDecBin = hDiracDecBin; return error; } +#endif // IVAS_FLOAT_FIXED +#ifndef IVAS_FLOAT_FIXED static ivas_error initMasaExtRenderer( input_masa *inputMasa, const AUDIO_CONFIG outConfig ) @@ -12744,6 +13034,170 @@ static ivas_error initMasaExtRenderer( return IVAS_ERR_OK; } +#else +static ivas_error initMasaExtRenderer( + input_masa *inputMasa, + const AUDIO_CONFIG outConfig ) +{ + Word16 i; + ivas_error error; + MASA_EXT_REND_HANDLE hMasaExtRend; + + error = IVAS_ERR_OK; + + IF ( ( hMasaExtRend = (MASA_EXT_REND_HANDLE) malloc( sizeof( MASA_EXT_REND_DATA ) ) ) == NULL ) + { + return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for MASA external renderer structure\n" ) ); + } + + inputMasa->hMasaExtRend = hMasaExtRend; + + /* Default init */ + hMasaExtRend->renderer_type = RENDERER_DISABLE; + hMasaExtRend->hDirACRend = NULL; + hMasaExtRend->hSpatParamRendCom = NULL; + hMasaExtRend->hDiracDecBin = NULL; + hMasaExtRend->hReverb = NULL; + hMasaExtRend->hHrtfParambin = NULL; + hMasaExtRend->hVBAPdata = NULL; + hMasaExtRend->hoa_dec_mtx = NULL; + + IF ( ( error = getAudioConfigNumChannels( inputMasa->base.inConfig, &hMasaExtRend->nchan_input ) ) != IVAS_ERR_OK ) + { + return error; + } + + IF ( ( error = getAudioConfigNumChannels( outConfig, &hMasaExtRend->nchan_output ) ) != IVAS_ERR_OK ) + { + return error; + } + + SWITCH ( outConfig ) + { + case IVAS_AUDIO_CONFIG_MONO: + IF ( EQ_16(inputMasa->base.inConfig , IVAS_AUDIO_CONFIG_MASA2) ) + { + hMasaExtRend->renderer_type = RENDERER_DIRAC; + } + ELSE + { + /* 1TC MASA to mono does not need rendering. */ + hMasaExtRend->renderer_type = RENDERER_DISABLE; + } + BREAK; + + case IVAS_AUDIO_CONFIG_STEREO: + hMasaExtRend->renderer_type = RENDERER_STEREO_PARAMETRIC; + BREAK; + + case IVAS_AUDIO_CONFIG_5_1: + case IVAS_AUDIO_CONFIG_7_1: + case IVAS_AUDIO_CONFIG_5_1_2: + case IVAS_AUDIO_CONFIG_5_1_4: + case IVAS_AUDIO_CONFIG_7_1_4: + case IVAS_AUDIO_CONFIG_LS_CUSTOM: + case IVAS_AUDIO_CONFIG_FOA: + case IVAS_AUDIO_CONFIG_HOA2: + case IVAS_AUDIO_CONFIG_HOA3: + hMasaExtRend->renderer_type = RENDERER_DIRAC; + BREAK; + + case IVAS_AUDIO_CONFIG_BINAURAL: + hMasaExtRend->renderer_type = RENDERER_BINAURAL_PARAMETRIC; + BREAK; + + case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_IR: + case IVAS_AUDIO_CONFIG_BINAURAL_ROOM_REVERB: + hMasaExtRend->renderer_type = RENDERER_BINAURAL_PARAMETRIC_ROOM; + BREAK; + + default: + return ( IVAS_ERROR( IVAS_ERR_IO_CONFIG_PAIR_NOT_SUPPORTED, "Wrong output config for MASA input in external renderer\n" ) ); + } + + IF ( NE_16(hMasaExtRend->renderer_type , RENDERER_DISABLE) ) + { + Word16 subframe; + IF( ( error = ivas_spat_hSpatParamRendCom_config_fx( &hMasaExtRend->hSpatParamRendCom, DIRAC_OPEN, 0, MASA_FORMAT, MC_MODE_NONE, *( inputMasa->base.ctx.pOutSampleRate ), 0, 1 ) ) != IVAS_ERR_OK ) + { + return error; + } + /* Simple population of the metadata index map as no adaptation is present */ + set16_fx( hMasaExtRend->hSpatParamRendCom->render_to_md_map, 0, MAX_JBM_SUBFRAMES_5MS * JBM_CLDFB_SLOTS_IN_SUBFRAME ); + FOR ( subframe = 0; subframe < MAX_PARAM_SPATIAL_SUBFRAMES; subframe++ ) + { + hMasaExtRend->hSpatParamRendCom->render_to_md_map[subframe] = subframe; + move16(); + } + hMasaExtRend->hSpatParamRendCom->subframes_rendered = 0; + move16(); + } + + IF ( EQ_16(hMasaExtRend->renderer_type , RENDERER_DIRAC) ) + { + IF ( ( error = ivas_masa_ext_rend_dirac_rend_init( inputMasa ) ) != IVAS_ERR_OK ) + { + return error; + } + } + + IF ( EQ_16(hMasaExtRend->renderer_type , RENDERER_BINAURAL_PARAMETRIC) || EQ_16(hMasaExtRend->renderer_type , RENDERER_BINAURAL_PARAMETRIC_ROOM) || EQ_16(hMasaExtRend->renderer_type , RENDERER_STEREO_PARAMETRIC) ) + { + IF ( NE_16(hMasaExtRend->renderer_type , RENDERER_STEREO_PARAMETRIC) ) + { + IF ( ( error = ivas_dirac_dec_binaural_copy_hrtfs_fx( &inputMasa->hMasaExtRend->hHrtfParambin ) ) != IVAS_ERR_OK ) + { + return error; + } +#if 1/*TODO: To be removed later after dependency on floating buffers in hHrtfParambin is removed*/ + if ( ( error = ivas_dirac_dec_binaural_copy_hrtfs( &inputMasa->hMasaExtRend->hHrtfParambin ) ) != IVAS_ERR_OK ) + { + return error; + } +#endif // IVAS_FLOAT_FIXED + } + + IF ( ( error = ivas_masa_ext_rend_parambin_init( inputMasa ) ) != IVAS_ERR_OK ) + { + return error; + } + } + + /* Init CLDFB for analysis & synthesis if renderer is used. Otherwise, NULL. */ + FOR ( i = 0; i < MASA_MAX_TRANSPORT_CHANNELS; i++ ) + { + hMasaExtRend->cldfbAnaRend[i] = NULL; + } + + FOR ( i = 0; i < MAX_OUTPUT_CHANNELS; i++ ) + { + hMasaExtRend->cldfbSynRend[i] = NULL; + } + + IF ( hMasaExtRend->renderer_type != RENDERER_DISABLE ) + { + FOR ( i = 0; i < hMasaExtRend->nchan_input; i++ ) + { + IF ( ( error = openCldfb_ivas_fx( &( hMasaExtRend->cldfbAnaRend[i] ), CLDFB_ANALYSIS, *inputMasa->base.ctx.pOutSampleRate, CLDFB_PROTOTYPE_5_00MS ) ) != IVAS_ERR_OK ) + { + return error; + } + } + + FOR ( i = 0; i < hMasaExtRend->nchan_output; i++ ) + { + IF ( ( error = openCldfb_ivas_fx( &( hMasaExtRend->cldfbSynRend[i] ), CLDFB_SYNTHESIS, *inputMasa->base.ctx.pOutSampleRate, CLDFB_PROTOTYPE_5_00MS ) ) != IVAS_ERR_OK ) + { + return error; + } + } + } + + inputMasa->hMasaExtRend = hMasaExtRend; + + return IVAS_ERR_OK; +} +#endif // IVAS_FLOAT_FIXED static void freeMasaExtRenderer( MASA_EXT_REND_HANDLE *hMasaExtRendOut )