Commit 55c6a406 authored by Jonas Svedberg's avatar Jonas Svedberg
Browse files
Merge branch 'main' of https://forge.3gpp.org/rep/ivas-codec-pc/ivas-codec into 1179-usan-implicit-signed-integer-truncation-in-fec-hq-phase-ecu
parents 0687948a f25bce36
Loading
Loading
Loading
Loading
Loading
+4 −1
Original line number Diff line number Diff line
@@ -203,6 +203,9 @@ ivas_error pre_proc_front_ivas(
    const int16_t front_vad_dtx_flag,                           /* i  : front-VAD DTX flag to overwrite VAD decision*/
    const IVAS_FORMAT ivas_format,                              /* i  : IVAS format                                */
    const int16_t MCT_flag,                                     /* i  : hMCT handle allocated (1) or not (0)       */
#ifdef NONBE_1211_DTX_BR_SWITCHING
    const int32_t last_ivas_total_brate,                        /* i  : last IVAS total bitrate                    */
#endif
    const int32_t ivas_total_brate                              /* i  : IVAS total bitrate                         */
);

+3 −0
Original line number Diff line number Diff line
@@ -172,6 +172,9 @@

#define NONBE_FIX_1176_OSBA_REVERB_JBM_ASAN_ERROR       /* Ericsson: Issue 1176, fix in TDREND_firfilt for subframes shorter than the filter length */
#define NONBE_1240_FIX_CORE_SELECTION_ISM_SW            /* VA: issue 1240: Remove the forcing of the TCX core in ISM when switching from a high bitarte to a low one */
#define NONBE_1246_INF_COHERENCE_IN_HIGH_LEVEL_DTX      /* Ericsson: Issue 1246: High level input which triggers DTX can lead to numerical overflow in coherence calculation */
#define NONBE_1211_DTX_BR_SWITCHING                     /* VA: issue 1211: fix crash in MASA DTX bitrate switching */
#define NONBE_1217_INIT_OBJ_EDIT                        /* VA: issue 1217: do object editing only when objects metadata is available */

/* ##################### End NON-BE switches ########################### */

+5 −2
Original line number Diff line number Diff line
@@ -3919,6 +3919,9 @@ void td_cng_enc_init(

void dtx(
    Encoder_State *st, /* i/o: encoder state structure                     */
#ifdef NONBE_1211_DTX_BR_SWITCHING
    const int32_t last_ivas_total_brate, /* i  : last IVAS total bitrate                */
#endif
    const int32_t ivas_total_brate, /* i  : IVAS total bitrate                          */
    const int16_t vad,              /* i  : VAD flag for DTX                            */
    const float speech[]            /* i  : Pointer to the speech frame                 */
+338 −0
Original line number Diff line number Diff line
@@ -1215,12 +1215,132 @@ ivas_error IVAS_DEC_GetEditableParameters(
)
{
    int16_t dirac_read_idx, obj;
#ifdef NONBE_1217_INIT_OBJ_EDIT
    Decoder_Struct *st_ivas;
    ISM_MODE ism_mode;
#endif

    if ( hIvasDec == NULL || hIvasDec->st_ivas == NULL || hIvasEditableParameters == NULL )
    {
        return IVAS_ERR_UNEXPECTED_NULL_POINTER;
    }

#ifdef NONBE_1217_INIT_OBJ_EDIT
    st_ivas = hIvasDec->st_ivas;
    ism_mode = st_ivas->ism_mode;

    if ( !( st_ivas->ivas_format == ISM_FORMAT ||
            st_ivas->ivas_format == SBA_ISM_FORMAT ||
            st_ivas->ivas_format == MASA_ISM_FORMAT ||
            ( st_ivas->ivas_format == MASA_FORMAT && st_ivas->nchan_ism > 0 ) ) )
    {
        return IVAS_ERROR( IVAS_ERR_OBJECTS_EDITING_NOT_SUPPORTED, "Object editing is not supported in this operation mode." );
    }

    hIvasEditableParameters->gain_bed = 1.0f;
    hIvasEditableParameters->num_obj = st_ivas->nchan_ism;
    if ( st_ivas->ivas_format == ISM_FORMAT || st_ivas->ivas_format == SBA_ISM_FORMAT )
    {
        if ( ism_mode == ISM_MODE_DISC || ism_mode == ISM_SBA_MODE_DISC )
        {
            for ( obj = 0; obj < hIvasEditableParameters->num_obj; obj++ )
            {
                hIvasEditableParameters->ism_metadata[obj].azimuth = st_ivas->hIsmMetaData[obj]->azimuth;
                hIvasEditableParameters->ism_metadata[obj].elevation = st_ivas->hIsmMetaData[obj]->elevation;
                hIvasEditableParameters->ism_metadata[obj].yaw = st_ivas->hIsmMetaData[obj]->yaw;
                hIvasEditableParameters->ism_metadata[obj].pitch = st_ivas->hIsmMetaData[obj]->pitch;
                hIvasEditableParameters->ism_metadata[obj].radius = st_ivas->hIsmMetaData[obj]->radius;
                hIvasEditableParameters->ism_metadata[obj].gain = st_ivas->hIsmMetaData[obj]->edited_gain;
                hIvasEditableParameters->ism_metadata[obj].non_diegetic_flag = st_ivas->hIsmMetaData[obj]->non_diegetic_flag;
            }

            if ( ism_mode == ISM_SBA_MODE_DISC )
            {
                hIvasEditableParameters->gain_bed = 1.0f;
            }
        }
        else if ( ism_mode == ISM_MODE_PARAM )
        {
            for ( obj = 0; obj < hIvasEditableParameters->num_obj; obj++ )
            {
                hIvasEditableParameters->ism_metadata[obj].azimuth = st_ivas->hParamIsmDec->azimuth_values[obj];
                hIvasEditableParameters->ism_metadata[obj].elevation = st_ivas->hParamIsmDec->elevation_values[obj];
                hIvasEditableParameters->ism_metadata[obj].yaw = 0.0f;
                hIvasEditableParameters->ism_metadata[obj].pitch = 0.0f;
                hIvasEditableParameters->ism_metadata[obj].radius = 0.0f;
                hIvasEditableParameters->ism_metadata[obj].gain = 1.0f;
                hIvasEditableParameters->ism_metadata[obj].non_diegetic_flag = 0;
            }
        }
        else if ( ism_mode == ISM_MODE_NONE )
        {
            hIvasEditableParameters->num_obj = 0;
        }
#ifdef DEBUGGING
        else
        {
            assert( 0 && "This should never happen!" );
        }
#endif
    }
    else if ( st_ivas->ivas_format == MASA_ISM_FORMAT || ( st_ivas->ivas_format == MASA_FORMAT && st_ivas->nchan_ism > 0 ) )
    {
        /* object editing possible only in two highest OMASA modes */
        if ( st_ivas->ism_mode == ISM_MASA_MODE_DISC )
        {
            for ( obj = 0; obj < hIvasEditableParameters->num_obj; obj++ )
            {
                hIvasEditableParameters->ism_metadata[obj].azimuth = st_ivas->hIsmMetaData[obj]->azimuth;
                hIvasEditableParameters->ism_metadata[obj].elevation = st_ivas->hIsmMetaData[obj]->elevation;
                hIvasEditableParameters->ism_metadata[obj].yaw = st_ivas->hIsmMetaData[obj]->yaw;
                hIvasEditableParameters->ism_metadata[obj].pitch = st_ivas->hIsmMetaData[obj]->pitch;
                hIvasEditableParameters->ism_metadata[obj].radius = st_ivas->hIsmMetaData[obj]->radius;

                /* reset the otherwise unused "gain" field for the object */
                hIvasDec->st_ivas->hIsmMetaData[obj]->edited_gain = 1.0f;
                hIvasEditableParameters->ism_metadata[obj].gain = st_ivas->hIsmMetaData[obj]->edited_gain;
                hIvasEditableParameters->ism_metadata[obj].non_diegetic_flag = st_ivas->hIsmMetaData[obj]->non_diegetic_flag;
            }
        }
        else if ( ism_mode == ISM_MASA_MODE_PARAM_ONE_OBJ )
        {
            /* Handle MONO output */
            if ( st_ivas->renderer_type != RENDERER_MONO_DOWNMIX )
            {
                dirac_read_idx = st_ivas->hSpatParamRendCom->render_to_md_map[st_ivas->hSpatParamRendCom->subframes_rendered];
            }
            else
            {
                dirac_read_idx = 0;
            }

            for ( obj = 0; obj < hIvasEditableParameters->num_obj; obj++ )
            {
                hIvasEditableParameters->ism_metadata[obj].azimuth = st_ivas->hMasaIsmData->azimuth_ism[obj][dirac_read_idx];
                hIvasEditableParameters->ism_metadata[obj].elevation = st_ivas->hMasaIsmData->elevation_ism[obj][dirac_read_idx];

                hIvasEditableParameters->ism_metadata[obj].yaw = st_ivas->hIsmMetaData[obj]->yaw;
                hIvasEditableParameters->ism_metadata[obj].pitch = st_ivas->hIsmMetaData[obj]->pitch;
                hIvasEditableParameters->ism_metadata[obj].radius = st_ivas->hIsmMetaData[obj]->radius;

                /* reset the otherwise unused "gain" field for the object */
                hIvasDec->st_ivas->hIsmMetaData[obj]->edited_gain = 1.0f;
                hIvasEditableParameters->ism_metadata[obj].gain = st_ivas->hIsmMetaData[obj]->edited_gain;
                hIvasEditableParameters->ism_metadata[obj].non_diegetic_flag = st_ivas->hIsmMetaData[obj]->non_diegetic_flag;
            }
        }
        else if ( ism_mode == ISM_MASA_MODE_MASA_ONE_OBJ || ism_mode == ISM_MODE_NONE )
        {
            hIvasEditableParameters->num_obj = 0;
        }
#ifdef DEBUGGING
        else
        {
            assert( 0 && "This should never happen!" );
        }
#endif
    }
#else
    if ( !( hIvasDec->st_ivas->ivas_format == ISM_FORMAT ||
            hIvasDec->st_ivas->ivas_format == SBA_ISM_FORMAT ||
            hIvasDec->st_ivas->ivas_format == MASA_ISM_FORMAT ||
@@ -1327,6 +1447,7 @@ ivas_error IVAS_DEC_GetEditableParameters(
            }
        }
    }
#endif

    return IVAS_ERR_OK;
}
@@ -1344,12 +1465,228 @@ ivas_error IVAS_DEC_SetEditableParameters(
)
{
    int16_t dirac_read_idx, obj;
#ifdef NONBE_1217_INIT_OBJ_EDIT
    Decoder_Struct *st_ivas;
    ISM_MODE ism_mode;

    if ( hIvasDec == NULL || hIvasDec->st_ivas == NULL )
    {
        return IVAS_ERR_UNEXPECTED_NULL_POINTER;
    }

    st_ivas = hIvasDec->st_ivas;
    ism_mode = st_ivas->ism_mode;

    if ( !( st_ivas->ivas_format == ISM_FORMAT ||
            st_ivas->ivas_format == SBA_ISM_FORMAT ||
            st_ivas->ivas_format == MASA_ISM_FORMAT ||
            ( st_ivas->ivas_format == MASA_FORMAT && st_ivas->nchan_ism > 0 ) ) )
    {
        return IVAS_ERROR( IVAS_ERR_OBJECTS_EDITING_NOT_SUPPORTED, "Object editing no supported in this operation mode." );
    }

    if ( hIvasDec == NULL || hIvasDec->st_ivas == NULL )
    {
        return IVAS_ERR_UNEXPECTED_NULL_POINTER;
    }

#ifdef DEBUGGING
    assert( hIvasEditableParameters.num_obj == st_ivas->nchan_ism );
#endif

    if ( st_ivas->ivas_format == ISM_FORMAT || st_ivas->ivas_format == SBA_ISM_FORMAT )
    {
        if ( ism_mode == ISM_MODE_DISC || ism_mode == ISM_SBA_MODE_DISC )
        {
            for ( obj = 0; obj < hIvasEditableParameters.num_obj; obj++ )
            {
                st_ivas->hIsmMetaData[obj]->edited_azimuth = hIvasEditableParameters.ism_metadata[obj].azimuth;
                st_ivas->hIsmMetaData[obj]->edited_elevation = hIvasEditableParameters.ism_metadata[obj].elevation;
                st_ivas->hIsmMetaData[obj]->edited_radius = hIvasEditableParameters.ism_metadata[obj].radius;

                st_ivas->hIsmMetaData[obj]->edited_gain = hIvasEditableParameters.ism_metadata[obj].gain;

                st_ivas->hIsmMetaData[obj]->edited_yaw = hIvasEditableParameters.ism_metadata[obj].yaw;
                st_ivas->hIsmMetaData[obj]->edited_pitch = hIvasEditableParameters.ism_metadata[obj].pitch;

                st_ivas->hIsmMetaData[obj]->non_diegetic_flag = hIvasEditableParameters.ism_metadata[obj].non_diegetic_flag;
            }

            if ( ism_mode == ISM_SBA_MODE_DISC )
            {
                st_ivas->hSbaIsmData->gain_bed = hIvasEditableParameters.gain_bed;
            }
        }
        else if ( ism_mode == ISM_MODE_PARAM )
        {
            for ( obj = 0; obj < hIvasEditableParameters.num_obj; obj++ )
            {
                st_ivas->hParamIsmDec->edited_azimuth_values[obj] = hIvasEditableParameters.ism_metadata[obj].azimuth;
                st_ivas->hParamIsmDec->edited_elevation_values[obj] = hIvasEditableParameters.ism_metadata[obj].elevation;
                st_ivas->hMasaIsmData->gain_ism_edited[obj] = hIvasEditableParameters.ism_metadata[obj].gain;

                /* Detect direction editing in Param-ISM mode */
                if ( fabsf( st_ivas->hParamIsmDec->azimuth_values[obj] - hIvasEditableParameters.ism_metadata[obj].azimuth ) > OMASA_AZI_EDIT_THR ||
                     fabsf( st_ivas->hParamIsmDec->elevation_values[obj] - hIvasEditableParameters.ism_metadata[obj].elevation ) > OMASA_ELE_EDIT_THR )
                {
                    st_ivas->hMasaIsmData->ism_dir_is_edited[obj] = 1u;
                }
                else
                {
                    st_ivas->hMasaIsmData->ism_dir_is_edited[obj] = 0u;
                }

                /* Detect gain editing in Param-ISM mode */
                if ( fabsf( 1.0f - hIvasEditableParameters.ism_metadata[obj].gain ) > OMASA_GAIN_EDIT_THR )
                {
                    st_ivas->hMasaIsmData->ism_gain_is_edited[obj] = 1u;
                }
                else
                {
                    st_ivas->hMasaIsmData->ism_gain_is_edited[obj] = 0u;
                }
            }

            /* MASA is not present with the ISM format */
            st_ivas->hMasaIsmData->masa_gain_is_edited = 0u;
        }
        else if ( ism_mode == ISM_MODE_NONE )
        {
            if ( hIvasEditableParameters.num_obj != 0 )
            {
                return IVAS_ERR_OBJECTS_EDITING_NOT_SUPPORTED;
            }
        }
#ifdef DEBUGGING
        else
        {
            assert( 0 && "This should never happen!" );
        }
#endif
    }
    else if ( st_ivas->ivas_format == MASA_ISM_FORMAT && ( ism_mode == ISM_MASA_MODE_PARAM_ONE_OBJ || ism_mode == ISM_MASA_MODE_DISC ) )
    {
        int16_t id_th;
        float threshold_azi, threshold_ele;

        for ( obj = 0; obj < hIvasEditableParameters.num_obj; obj++ )
        {
            if ( st_ivas->hMasaIsmData != NULL )
            {
                /* copy relevant fields also to OMASA structs, but only if the value has been changed. original values are in st_ivas->hIsmMetaData */
                /* first, need to convert float values to ints used internally */
                int16_t new_azi, new_ele;
                if ( hIvasEditableParameters.ism_metadata[obj].azimuth > 0.0f )
                {
                    new_azi = (int16_t) ( hIvasEditableParameters.ism_metadata[obj].azimuth + 0.5f );
                }
                else
                {
                    new_azi = (int16_t) ( hIvasEditableParameters.ism_metadata[obj].azimuth - 0.5f );
                }

                if ( hIvasEditableParameters.ism_metadata[obj].elevation > 0.0f )
                {
                    new_ele = (int16_t) ( hIvasEditableParameters.ism_metadata[obj].elevation + 0.5f );
                }
                else
                {
                    new_ele = (int16_t) ( hIvasEditableParameters.ism_metadata[obj].elevation - 0.5f );
                }

                if ( ism_mode == ISM_MASA_MODE_PARAM_ONE_OBJ )
                {
                    /* Handle MONO output */
                    if ( st_ivas->renderer_type != RENDERER_MONO_DOWNMIX )
                    {
                        dirac_read_idx = st_ivas->hSpatParamRendCom->render_to_md_map[st_ivas->hSpatParamRendCom->subframes_rendered];
                    }
                    else
                    {
                        dirac_read_idx = 0;
                    }

                    /* determine thresholds for detecting object metadata edit for direction based on quantization resolution of the spatial direction parameters.
                     * these depend from the number of bits used to transmit the directions,
                     * which in turn depends from the object priority and importance:
                     * importance -> priority -> number of bits -> elevation resolution -> elevation ring index -> azimuth resolution.
                     * leading to elevation_resolution -> elevation threshold and azimuth resolution -> azimuth threshold */
                    id_th = (int16_t) ( fabsf( (float) st_ivas->hMasaIsmData->elevation_ism[obj][dirac_read_idx] ) / delta_theta_masa[st_ivas->hMasaIsmData->bits_ism[obj] - 3] + 0.5f );
                    threshold_azi = 360.0f / (float) no_phi_masa[st_ivas->hMasaIsmData->bits_ism[obj] - 1][id_th];
                    threshold_ele = delta_theta_masa[st_ivas->hMasaIsmData->bits_ism[obj] - 3];

                    if ( ( (float) abs( new_azi - st_ivas->hMasaIsmData->azimuth_ism[obj][dirac_read_idx] ) > threshold_azi ) ||
                         ( (float) abs( new_ele - st_ivas->hMasaIsmData->elevation_ism[obj][dirac_read_idx] ) > threshold_ele ) )
                    {
                        /* at least one of the threshold is exceeded, so use new direction value and set editing detection flag */
                        st_ivas->hMasaIsmData->azimuth_ism_edited[obj] = new_azi;
                        st_ivas->hMasaIsmData->elevation_ism_edited[obj] = new_ele;

                        st_ivas->hMasaIsmData->ism_dir_is_edited[obj] = 1u;
                    }
                    else
                    {
                        st_ivas->hMasaIsmData->ism_dir_is_edited[obj] = 0u;
                    }
                }
                else
                {
                    /* detect editing in ISM_MASA_MODE_DISC. optionally, add quantization-resolution -based thresholds */
                    if ( fabsf( st_ivas->hIsmMetaData[obj]->azimuth - hIvasEditableParameters.ism_metadata[obj].azimuth ) > OMASA_AZI_EDIT_THR ||
                         fabsf( st_ivas->hIsmMetaData[obj]->elevation - hIvasEditableParameters.ism_metadata[obj].elevation ) > OMASA_ELE_EDIT_THR )
                    {
                        st_ivas->hMasaIsmData->azimuth_ism_edited[obj] = new_azi;
                        st_ivas->hMasaIsmData->elevation_ism_edited[obj] = new_ele;

                        st_ivas->hMasaIsmData->ism_dir_is_edited[obj] = 1u;
                    }
                    else
                    {
                        st_ivas->hMasaIsmData->ism_dir_is_edited[obj] = 0u;
                    }
                }

                /* compare pre-edit gain and the edited one to detect editing */
                if ( fabsf( st_ivas->hIsmMetaData[obj]->edited_gain - hIvasEditableParameters.ism_metadata[obj].gain ) > OMASA_GAIN_EDIT_THR )
                {
                    st_ivas->hMasaIsmData->ism_gain_is_edited[obj] = 1u;
                    st_ivas->hMasaIsmData->gain_ism_edited[obj] = hIvasEditableParameters.ism_metadata[obj].gain;
                }
                else
                {
                    st_ivas->hMasaIsmData->ism_gain_is_edited[obj] = 0u;
                }
            }

            /* Copy edited values to hIsmMetaData struct */
            if ( st_ivas->hIsmMetaData[obj] != NULL )
            {
                st_ivas->hIsmMetaData[obj]->azimuth = hIvasEditableParameters.ism_metadata[obj].azimuth;
                st_ivas->hIsmMetaData[obj]->elevation = hIvasEditableParameters.ism_metadata[obj].elevation;
                st_ivas->hIsmMetaData[obj]->yaw = hIvasEditableParameters.ism_metadata[obj].yaw;
                st_ivas->hIsmMetaData[obj]->pitch = hIvasEditableParameters.ism_metadata[obj].pitch;
                st_ivas->hIsmMetaData[obj]->radius = hIvasEditableParameters.ism_metadata[obj].radius;
                st_ivas->hIsmMetaData[obj]->edited_gain = hIvasEditableParameters.ism_metadata[obj].gain;
                st_ivas->hIsmMetaData[obj]->non_diegetic_flag = hIvasEditableParameters.ism_metadata[obj].non_diegetic_flag;
            }
        }

        if ( fabsf( hIvasEditableParameters.gain_bed - 1.0f ) > OMASA_GAIN_EDIT_THR )
        {
            st_ivas->hMasaIsmData->gain_masa_edited = hIvasEditableParameters.gain_bed;
            st_ivas->hMasaIsmData->masa_gain_is_edited = 1u;
        }
        else
        {
            st_ivas->hMasaIsmData->masa_gain_is_edited = 0u;
        }
    }
#else
    if ( hIvasDec == NULL || hIvasDec->st_ivas == NULL )
    {
        return IVAS_ERR_UNEXPECTED_NULL_POINTER;
    }

    if ( !( hIvasDec->st_ivas->ivas_format == ISM_FORMAT ||
            hIvasDec->st_ivas->ivas_format == SBA_ISM_FORMAT ||
            hIvasDec->st_ivas->ivas_format == MASA_ISM_FORMAT ||
@@ -1552,6 +1889,7 @@ ivas_error IVAS_DEC_SetEditableParameters(
            hIvasDec->st_ivas->hMasaIsmData->masa_gain_is_edited = 0u;
        }
    }
#endif

    return IVAS_ERR_OK;
}
+6 −0
Original line number Diff line number Diff line
@@ -310,7 +310,13 @@ void amr_wb_enc(
    {
        st->fd_cng_reset_flag = 0;
    }

#ifdef NONBE_1211_DTX_BR_SWITCHING
    dtx( st, -1, -1, vad_flag_dtx, inp );
#else
    dtx( st, -1, vad_flag_dtx, inp );
#endif

    /*----------------------------------------------------------------*
     * Noise energy down-ward update and total noise energy estimation
     * Long-term energies and relative frame energy updates
Loading