LCOV - code coverage report
Current view: top level - lib_rend - ivas_omasa_ana.c (source / functions) Hit Total Coverage
Test: Coverage on main -- merged total coverage @ 9b04ec3cb36f5e8dc438cf854fa3e349998fa1e9 Lines: 191 198 96.5 %
Date: 2025-10-31 05:45:46 Functions: 7 7 100.0 %

          Line data    Source code
       1             : /******************************************************************************************************
       2             : 
       3             :    (C) 2022-2025 IVAS codec Public Collaboration with portions copyright Dolby International AB, Ericsson AB,
       4             :    Fraunhofer-Gesellschaft zur Foerderung der angewandten Forschung e.V., Huawei Technologies Co. LTD.,
       5             :    Koninklijke Philips N.V., Nippon Telegraph and Telephone Corporation, Nokia Technologies Oy, Orange,
       6             :    Panasonic Holdings Corporation, Qualcomm Technologies, Inc., VoiceAge Corporation, and other
       7             :    contributors to this repository. All Rights Reserved.
       8             : 
       9             :    This software is protected by copyright law and by international treaties.
      10             :    The IVAS codec Public Collaboration consisting of Dolby International AB, Ericsson AB,
      11             :    Fraunhofer-Gesellschaft zur Foerderung der angewandten Forschung e.V., Huawei Technologies Co. LTD.,
      12             :    Koninklijke Philips N.V., Nippon Telegraph and Telephone Corporation, Nokia Technologies Oy, Orange,
      13             :    Panasonic Holdings Corporation, Qualcomm Technologies, Inc., VoiceAge Corporation, and other
      14             :    contributors to this repository retain full ownership rights in their respective contributions in
      15             :    the software. This notice grants no license of any kind, including but not limited to patent
      16             :    license, nor is any license granted by implication, estoppel or otherwise.
      17             : 
      18             :    Contributors are required to enter into the IVAS codec Public Collaboration agreement before making
      19             :    contributions.
      20             : 
      21             :    This software is provided "AS IS", without any express or implied warranties. The software is in the
      22             :    development stage. It is intended exclusively for experts who have experience with such software and
      23             :    solely for the purpose of inspection. All implied warranties of non-infringement, merchantability
      24             :    and fitness for a particular purpose are hereby disclaimed and excluded.
      25             : 
      26             :    Any dispute, controversy or claim arising under or in relation to providing this software shall be
      27             :    submitted to and settled by the final, binding jurisdiction of the courts of Munich, Germany in
      28             :    accordance with the laws of the Federal Republic of Germany excluding its conflict of law rules and
      29             :    the United Nations Convention on Contracts on the International Sales of Goods.
      30             : 
      31             : *******************************************************************************************************/
      32             : 
      33             : #include "options.h"
      34             : #include <stdlib.h>
      35             : #include <math.h>
      36             : #include "ivas_cnst.h"
      37             : #include "ivas_prot_rend.h"
      38             : #include "ivas_prot.h"
      39             : #include "prot.h"
      40             : #include "ivas_stat_rend.h"
      41             : #include "ivas_rom_com.h"
      42             : #ifdef DEBUGGING
      43             : #include "debug.h"
      44             : #endif
      45             : #include "wmc_auto.h"
      46             : 
      47             : 
      48             : /*-------------------------------------------------------------------------
      49             :  * Local function prototypes
      50             :  *------------------------------------------------------------------------*/
      51             : 
      52             : 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 );
      53             : 
      54             : 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] );
      55             : 
      56             : 
      57             : /*--------------------------------------------------------------------------*
      58             :  * ivas_omasa_ana_open()
      59             :  *
      60             :  * Allocate and initialize OMASA handle
      61             :  *--------------------------------------------------------------------------*/
      62             : 
      63         163 : ivas_error ivas_omasa_ana_open(
      64             :     OMASA_ANA_HANDLE *hOMasaPtr, /* i/o: OMASA data handle pointer */
      65             :     int32_t input_Fs,            /* i  : Sampling frequency        */
      66             :     uint16_t total_num_objects   /* i  : Number of objects         */
      67             : )
      68             : {
      69             :     int16_t i, j;
      70             :     OMASA_ANA_HANDLE hOMasa;
      71             :     int16_t numAnalysisChannels;
      72             :     int16_t maxBin, input_frame;
      73             :     ivas_error error;
      74             : 
      75         163 :     error = IVAS_ERR_OK;
      76             : 
      77         163 :     if ( ( hOMasa = (OMASA_ANA_HANDLE) malloc( sizeof( OMASA_ANA_DATA ) ) ) == NULL )
      78             :     {
      79           0 :         return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for OMASA\n" ) );
      80             :     }
      81             : 
      82         163 :     numAnalysisChannels = (int16_t) total_num_objects;
      83             : 
      84             :     /* Determine the number of bands */
      85         163 :     hOMasa->nbands = MASA_FREQUENCY_BANDS;
      86             : 
      87             :     /* Determine band grouping */
      88         163 :     mvs2s( MASA_band_grouping_24, hOMasa->band_grouping, 24 + 1 );
      89             : 
      90         163 :     maxBin = (int16_t) ( input_Fs * INV_CLDFB_BANDWIDTH + 0.5f );
      91        3642 :     for ( i = 1; i < hOMasa->nbands + 1; i++ )
      92             :     {
      93        3642 :         if ( hOMasa->band_grouping[i] >= maxBin )
      94             :         {
      95         163 :             hOMasa->band_grouping[i] = maxBin;
      96         163 :             hOMasa->nbands = i;
      97         163 :             break;
      98             :         }
      99             :     }
     100             : 
     101             :     /* Determine block grouping */
     102         163 :     mvs2s( DirAC_block_grouping, hOMasa->block_grouping, MAX_PARAM_SPATIAL_SUBFRAMES + 1 );
     103             : 
     104             :     /* open/initialize CLDFB */
     105         163 :     hOMasa->num_Cldfb_instances = numAnalysisChannels;
     106         599 :     for ( i = 0; i < hOMasa->num_Cldfb_instances; i++ )
     107             :     {
     108         436 :         if ( ( error = openCldfb( &( hOMasa->cldfbAnaEnc[i] ), CLDFB_ANALYSIS, input_Fs, CLDFB_PROTOTYPE_5_00MS ) ) != IVAS_ERR_OK )
     109             :         {
     110           0 :             return error;
     111             :         }
     112             :     }
     113             : 
     114         379 :     for ( ; i < MAX_NUM_OBJECTS; i++ )
     115             :     {
     116         216 :         hOMasa->cldfbAnaEnc[i] = NULL;
     117             :     }
     118             : 
     119             :     /* intensity 3-dim */
     120         652 :     for ( i = 0; i < DIRAC_NUM_DIMS; i++ )
     121             :     {
     122         489 :         if ( ( hOMasa->direction_vector_m[i] = (float **) malloc( MAX_PARAM_SPATIAL_SUBFRAMES * sizeof( float * ) ) ) == NULL )
     123             :         {
     124           0 :             return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for OMASA data\n" ) );
     125             :         }
     126             : 
     127        2445 :         for ( j = 0; j < MAX_PARAM_SPATIAL_SUBFRAMES; j++ )
     128             :         {
     129        1956 :             if ( ( hOMasa->direction_vector_m[i][j] = (float *) malloc( MASA_FREQUENCY_BANDS * sizeof( float ) ) ) == NULL )
     130             :             {
     131           0 :                 return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for OMASA data\n" ) );
     132             :             }
     133        1956 :             set_zero( hOMasa->direction_vector_m[i][j], MASA_FREQUENCY_BANDS );
     134             :         }
     135             :     }
     136             : 
     137         652 :     for ( i = 0; i < DIRAC_NUM_DIMS; i++ )
     138             :     {
     139       16137 :         for ( j = 0; j < DIRAC_NO_COL_AVG_DIFF; j++ )
     140             :         {
     141       15648 :             if ( ( hOMasa->buffer_intensity_real[i][j] = (float *) malloc( MASA_FREQUENCY_BANDS * sizeof( float ) ) ) == NULL )
     142             :             {
     143           0 :                 return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for OMASA data\n" ) );
     144             :             }
     145       15648 :             set_zero( hOMasa->buffer_intensity_real[i][j], MASA_FREQUENCY_BANDS );
     146             :         }
     147             :     }
     148             : 
     149         163 :     set_zero( hOMasa->buffer_energy, DIRAC_NO_COL_AVG_DIFF * MASA_FREQUENCY_BANDS );
     150             : 
     151         815 :     for ( i = 0; i < MAX_NUM_OBJECTS; i++ )
     152             :     {
     153         652 :         set_f( hOMasa->prev_object_dm_gains[i], INV_SQRT_2, MASA_MAX_TRANSPORT_CHANNELS );
     154             :     }
     155             : 
     156         163 :     input_frame = (int16_t) ( input_Fs / FRAMES_PER_SEC );
     157      104803 :     for ( i = 0; i < input_frame; i++ )
     158             :     {
     159      104640 :         hOMasa->interpolator[i] = ( (float) i ) / ( (float) input_frame );
     160             :     }
     161             : 
     162         163 :     hOMasa->index_buffer_intensity = 0;
     163             : 
     164         163 :     if ( ( hOMasa->hMasaOut = (MASA_DECODER_EXT_OUT_META_HANDLE) malloc( sizeof( MASA_DECODER_EXT_OUT_META ) ) ) == NULL )
     165             :     {
     166           0 :         return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for MASA decoder\n" ) );
     167             :     }
     168             : 
     169         163 :     if ( ( hOMasa->sph_grid16 = (SPHERICAL_GRID_DATA *) malloc( sizeof( SPHERICAL_GRID_DATA ) ) ) == NULL )
     170             :     {
     171           0 :         return ( IVAS_ERROR( IVAS_ERR_FAILED_ALLOC, "Can not allocate memory for MASA decoder\n" ) );
     172             :     }
     173         163 :     generate_gridEq( hOMasa->sph_grid16 );
     174             : 
     175         815 :     for ( i = 0; i < MAX_PARAM_SPATIAL_SUBFRAMES; i++ )
     176             :     {
     177         652 :         set_zero( hOMasa->energy[i], MASA_FREQUENCY_BANDS );
     178             :     }
     179             : 
     180         163 :     set_zero( hOMasa->ism_azimuth, MAX_NUM_OBJECTS );
     181         163 :     set_zero( hOMasa->ism_elevation, MAX_NUM_OBJECTS );
     182             : 
     183         163 :     ( *hOMasaPtr ) = hOMasa;
     184             : 
     185         163 :     return error;
     186             : }
     187             : 
     188             : 
     189             : /*--------------------------------------------------------------------------*
     190             :  * ivas_omasa_ana_close()
     191             :  *
     192             :  * Close OMASA handle
     193             :  *--------------------------------------------------------------------------*/
     194             : 
     195       56716 : void ivas_omasa_ana_close(
     196             :     OMASA_ANA_HANDLE *hOMasa /* i/o: analysis OMASA handle */
     197             : )
     198             : {
     199             :     int16_t i, j;
     200             : 
     201       56716 :     if ( hOMasa == NULL || *hOMasa == NULL )
     202             :     {
     203       56553 :         return;
     204             :     }
     205             : 
     206         599 :     for ( i = 0; i < ( *hOMasa )->num_Cldfb_instances; i++ )
     207             :     {
     208         436 :         deleteCldfb( &( ( *hOMasa )->cldfbAnaEnc[i] ) );
     209             :     }
     210             : 
     211         652 :     for ( i = 0; i < DIRAC_NUM_DIMS; i++ )
     212             :     {
     213        2445 :         for ( j = 0; j < MAX_PARAM_SPATIAL_SUBFRAMES; j++ )
     214             :         {
     215        1956 :             free( ( *hOMasa )->direction_vector_m[i][j] );
     216        1956 :             ( *hOMasa )->direction_vector_m[i][j] = NULL;
     217             :         }
     218             : 
     219       16137 :         for ( j = 0; j < DIRAC_NO_COL_AVG_DIFF; j++ )
     220             :         {
     221       15648 :             free( ( *hOMasa )->buffer_intensity_real[i][j] );
     222       15648 :             ( *hOMasa )->buffer_intensity_real[i][j] = NULL;
     223             :         }
     224             : 
     225         489 :         free( ( *hOMasa )->direction_vector_m[i] );
     226         489 :         ( *hOMasa )->direction_vector_m[i] = NULL;
     227             :     }
     228             : 
     229         163 :     free( ( *hOMasa )->hMasaOut );
     230         163 :     ( *hOMasa )->hMasaOut = NULL;
     231         163 :     free( ( *hOMasa )->sph_grid16 );
     232         163 :     ( *hOMasa )->sph_grid16 = NULL;
     233             : 
     234         163 :     free( ( *hOMasa ) );
     235         163 :     ( *hOMasa ) = NULL;
     236             : 
     237         163 :     return;
     238             : }
     239             : 
     240             : 
     241             : /*--------------------------------------------------------------------------*
     242             :  * ivas_omasa_ana()
     243             :  *
     244             :  * OMASA analysis function
     245             :  *--------------------------------------------------------------------------*/
     246             : 
     247      304693 : void ivas_omasa_ana(
     248             :     OMASA_ANA_HANDLE hOMasa,       /* i/o: OMASA analysis handle                       */
     249             :     float data_in_f[][L_FRAME48k], /* i/o: Input / transport audio signals             */
     250             :     const int16_t input_frame,     /* i  : Input frame size                            */
     251             :     const int16_t nchan_transport, /* i  : Number of transport channels                */
     252             :     const int16_t nchan_ism        /* i  : Number of objects for parameter analysis    */
     253             : )
     254             : {
     255             :     float elevation_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS];
     256             :     float azimuth_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS];
     257             :     float energyRatio[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS];
     258             :     float spreadCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS];
     259             :     float surroundingCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS];
     260             : 
     261             :     /* Estimate MASA parameters from the objects */
     262      304693 :     ivas_omasa_param_est_ana( hOMasa, data_in_f, elevation_m_values, azimuth_m_values, energyRatio, spreadCoherence, surroundingCoherence, input_frame, nchan_ism );
     263             : 
     264             :     /* Add zeros to higher bands in case of lower sampling rates */
     265      304693 :     if ( hOMasa->nbands < MASA_FREQUENCY_BANDS )
     266             :     {
     267      203028 :         ivas_masa_zero_high_bands( hOMasa->nbands, elevation_m_values, azimuth_m_values, energyRatio, spreadCoherence, surroundingCoherence );
     268             :     }
     269             : 
     270             :     /* Create MASA metadata buffer from the estimated values */
     271      304693 :     ivas_create_masa_out_meta( hOMasa->hMasaOut, hOMasa->sph_grid16, nchan_transport, elevation_m_values, azimuth_m_values, energyRatio, spreadCoherence, surroundingCoherence );
     272             : 
     273             :     /* Downmix */
     274      304693 :     ivas_omasa_dmx( data_in_f, input_frame, nchan_transport, nchan_ism, hOMasa->ism_azimuth, hOMasa->ism_elevation, hOMasa->prev_object_dm_gains, hOMasa->interpolator );
     275             : 
     276      304693 :     return;
     277             : }
     278             : 
     279             : 
     280             : /*--------------------------------------------------------------------------*
     281             :  * Local functions
     282             :  *--------------------------------------------------------------------------*/
     283             : 
     284             : /* Estimate MASA parameters from the objects */
     285      304693 : static void ivas_omasa_param_est_ana(
     286             :     OMASA_ANA_HANDLE hOMasa,
     287             :     float data_f[][L_FRAME48k],
     288             :     float elevation_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS],
     289             :     float azimuth_m_values[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS],
     290             :     float energyRatio[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS],
     291             :     float spreadCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS],
     292             :     float surroundingCoherence[MAX_PARAM_SPATIAL_SUBFRAMES][MASA_FREQUENCY_BANDS],
     293             :     const int16_t input_frame,
     294             :     const int16_t nchan_ism )
     295             : {
     296             :     float reference_power[MASA_FREQUENCY_BANDS];
     297             :     int16_t ts, i, d, j;
     298             :     int16_t num_freq_bins, num_freq_bands, index;
     299             :     float dir_v[DIRAC_NUM_DIMS];
     300             :     int16_t l_ts;
     301             :     float Chnl_RealBuffer[MAX_NUM_OBJECTS][CLDFB_NO_CHANNELS_MAX];
     302             :     float Chnl_ImagBuffer[MAX_NUM_OBJECTS][CLDFB_NO_CHANNELS_MAX];
     303             :     float Foa_RealBuffer[FOA_CHANNELS][CLDFB_NO_CHANNELS_MAX];
     304             :     float Foa_ImagBuffer[FOA_CHANNELS][CLDFB_NO_CHANNELS_MAX];
     305             :     float intensity_real[DIRAC_NUM_DIMS][MASA_FREQUENCY_BANDS];
     306             :     float direction_vector[DIRAC_NUM_DIMS][MASA_FREQUENCY_BANDS];
     307             :     float diffuseness_vector[MASA_FREQUENCY_BANDS];
     308             :     float diffuseness_m[MASA_FREQUENCY_BANDS];
     309             : 
     310             :     int16_t band_m_idx, block_m_idx;
     311             :     float renormalization_factor_diff[MASA_FREQUENCY_BANDS];
     312             :     float norm_tmp;
     313             :     int16_t mrange[2];
     314             :     int16_t brange[2];
     315             : 
     316      304693 :     num_freq_bins = hOMasa->cldfbAnaEnc[0]->no_channels;
     317      304693 :     num_freq_bands = hOMasa->nbands;
     318      304693 :     l_ts = input_frame / CLDFB_NO_COL_MAX;
     319             : 
     320             : 
     321             :     /* Compute ISM to FOA matrices */
     322     1070729 :     for ( i = 0; i < nchan_ism; i++ )
     323             :     {
     324      766036 :         hOMasa->chnlToFoaMtx[0][i] = 1.0f;
     325      766036 :         hOMasa->chnlToFoaMtx[1][i] = sinf( ( hOMasa->ism_azimuth[i] / 180.0f * EVS_PI ) ) * cosf( ( hOMasa->ism_elevation[i] / 180.0f * EVS_PI ) );
     326      766036 :         hOMasa->chnlToFoaMtx[2][i] = sinf( ( hOMasa->ism_elevation[i] / 180.0f * EVS_PI ) );
     327      766036 :         hOMasa->chnlToFoaMtx[3][i] = cosf( ( hOMasa->ism_azimuth[i] / 180.0f * EVS_PI ) ) * cosf( ( hOMasa->ism_elevation[i] / 180.0f * EVS_PI ) );
     328             :     }
     329             : 
     330             :     /* do processing over all CLDFB time slots */
     331     1523465 :     for ( block_m_idx = 0; block_m_idx < MAX_PARAM_SPATIAL_SUBFRAMES; block_m_idx++ )
     332             :     {
     333     1218772 :         mrange[0] = hOMasa->block_grouping[block_m_idx];
     334     1218772 :         mrange[1] = hOMasa->block_grouping[block_m_idx + 1];
     335             : 
     336    28439020 :         for ( band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++ )
     337             :         {
     338    27220248 :             hOMasa->direction_vector_m[0][block_m_idx][band_m_idx] = 0.0f;
     339    27220248 :             hOMasa->direction_vector_m[1][block_m_idx][band_m_idx] = 0.0f;
     340    27220248 :             hOMasa->direction_vector_m[2][block_m_idx][band_m_idx] = 0.0f;
     341             :         }
     342             : 
     343             :         /* Need to initialize renormalization_factors, and variables to be normalized */
     344     1218772 :         set_zero( renormalization_factor_diff, hOMasa->nbands );
     345     1218772 :         set_zero( diffuseness_m, hOMasa->nbands );
     346     1218772 :         set_zero( hOMasa->energy[block_m_idx], MASA_FREQUENCY_BANDS );
     347             : 
     348     6093860 :         for ( ts = mrange[0]; ts < mrange[1]; ts++ )
     349             :         {
     350    17131664 :             for ( i = 0; i < nchan_ism; i++ )
     351             :             {
     352    12256576 :                 cldfbAnalysis_ts( &( data_f[i][l_ts * ts] ), Chnl_RealBuffer[i], Chnl_ImagBuffer[i], l_ts, hOMasa->cldfbAnaEnc[i] );
     353             :             }
     354             : 
     355             :             /* Compute channel-based energy for metadata processing */
     356   113756080 :             for ( band_m_idx = 0; band_m_idx < num_freq_bands; band_m_idx++ )
     357             :             {
     358   108880992 :                 brange[0] = hOMasa->band_grouping[band_m_idx];
     359   108880992 :                 brange[1] = hOMasa->band_grouping[band_m_idx + 1];
     360   303932832 :                 for ( j = brange[0]; j < brange[1]; j++ )
     361             :                 {
     362   685508160 :                     for ( i = 0; i < nchan_ism; i++ )
     363             :                     {
     364   490456320 :                         hOMasa->energy[block_m_idx][band_m_idx] += Chnl_RealBuffer[i][j] * Chnl_RealBuffer[i][j] + Chnl_ImagBuffer[i][j] * Chnl_ImagBuffer[i][j];
     365             :                     }
     366             :                 }
     367             :             }
     368             : 
     369             :             /* Compute FOA */
     370             :             /* W */
     371     4875088 :             mvr2r( Chnl_RealBuffer[0], Foa_RealBuffer[0], num_freq_bins );
     372     4875088 :             mvr2r( Chnl_ImagBuffer[0], Foa_ImagBuffer[0], num_freq_bins );
     373    12256576 :             for ( i = 1; i < nchan_ism; i++ )
     374             :             {
     375     7381488 :                 v_add( Chnl_RealBuffer[i], Foa_RealBuffer[0], Foa_RealBuffer[0], num_freq_bins );
     376     7381488 :                 v_add( Chnl_ImagBuffer[i], Foa_ImagBuffer[0], Foa_ImagBuffer[0], num_freq_bins );
     377             :             }
     378             : 
     379             :             /* Y */
     380     4875088 :             v_multc( Chnl_RealBuffer[0], hOMasa->chnlToFoaMtx[1][0], Foa_RealBuffer[1], num_freq_bins );
     381     4875088 :             v_multc( Chnl_ImagBuffer[0], hOMasa->chnlToFoaMtx[1][0], Foa_ImagBuffer[1], num_freq_bins );
     382    12256576 :             for ( i = 1; i < nchan_ism; i++ )
     383             :             {
     384     7381488 :                 v_multc_acc( Chnl_RealBuffer[i], hOMasa->chnlToFoaMtx[1][i], Foa_RealBuffer[1], num_freq_bins );
     385     7381488 :                 v_multc_acc( Chnl_ImagBuffer[i], hOMasa->chnlToFoaMtx[1][i], Foa_ImagBuffer[1], num_freq_bins );
     386             :             }
     387             : 
     388             :             /* Z */
     389     4875088 :             v_multc( Chnl_RealBuffer[0], hOMasa->chnlToFoaMtx[2][0], Foa_RealBuffer[2], num_freq_bins );
     390     4875088 :             v_multc( Chnl_ImagBuffer[0], hOMasa->chnlToFoaMtx[2][0], Foa_ImagBuffer[2], num_freq_bins );
     391    12256576 :             for ( i = 1; i < nchan_ism; i++ )
     392             :             {
     393     7381488 :                 v_multc_acc( Chnl_RealBuffer[i], hOMasa->chnlToFoaMtx[2][i], Foa_RealBuffer[2], num_freq_bins );
     394     7381488 :                 v_multc_acc( Chnl_ImagBuffer[i], hOMasa->chnlToFoaMtx[2][i], Foa_ImagBuffer[2], num_freq_bins );
     395             :             }
     396             : 
     397             :             /* X */
     398     4875088 :             v_multc( Chnl_RealBuffer[0], hOMasa->chnlToFoaMtx[3][0], Foa_RealBuffer[3], num_freq_bins );
     399     4875088 :             v_multc( Chnl_ImagBuffer[0], hOMasa->chnlToFoaMtx[3][0], Foa_ImagBuffer[3], num_freq_bins );
     400    12256576 :             for ( i = 1; i < nchan_ism; i++ )
     401             :             {
     402     7381488 :                 v_multc_acc( Chnl_RealBuffer[i], hOMasa->chnlToFoaMtx[3][i], Foa_RealBuffer[3], num_freq_bins );
     403     7381488 :                 v_multc_acc( Chnl_ImagBuffer[i], hOMasa->chnlToFoaMtx[3][i], Foa_ImagBuffer[3], num_freq_bins );
     404             :             }
     405             : 
     406             :             /* Direction estimation */
     407     4875088 :             computeIntensityVector_ana( hOMasa->band_grouping, Foa_RealBuffer, Foa_ImagBuffer, num_freq_bands, intensity_real );
     408     4875088 :             computeDirectionVectors( intensity_real[0], intensity_real[1], intensity_real[2], 0, num_freq_bands, direction_vector[0], direction_vector[1], direction_vector[2] );
     409             : 
     410             :             /* Power estimation for diffuseness */
     411     4875088 :             computeReferencePower_ana( hOMasa->band_grouping, Foa_RealBuffer, Foa_ImagBuffer, reference_power, num_freq_bands );
     412             : 
     413             :             /* Fill buffers of length "averaging_length" time slots for intensity and energy */
     414     4875088 :             hOMasa->index_buffer_intensity = ( hOMasa->index_buffer_intensity % DIRAC_NO_COL_AVG_DIFF ) + 1; /* averaging_length = 32 */
     415     4875088 :             index = hOMasa->index_buffer_intensity;
     416    19500352 :             for ( i = 0; i < DIRAC_NUM_DIMS; i++ )
     417             :             {
     418             :                 /* only real part needed */
     419    14625264 :                 mvr2r( intensity_real[i], &( hOMasa->buffer_intensity_real[i][index - 1][0] ), num_freq_bands );
     420             :             }
     421     4875088 :             mvr2r( reference_power, &( hOMasa->buffer_energy[( index - 1 ) * num_freq_bands] ), num_freq_bands );
     422             : 
     423     4875088 :             computeDiffuseness( hOMasa->buffer_intensity_real, hOMasa->buffer_energy, num_freq_bands, diffuseness_vector );
     424             : 
     425   113756080 :             for ( band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++ )
     426             :             {
     427   108880992 :                 norm_tmp = reference_power[band_m_idx] * ( 1 - diffuseness_vector[band_m_idx] );
     428             : 
     429   108880992 :                 hOMasa->direction_vector_m[0][block_m_idx][band_m_idx] += norm_tmp * direction_vector[0][band_m_idx];
     430   108880992 :                 hOMasa->direction_vector_m[1][block_m_idx][band_m_idx] += norm_tmp * direction_vector[1][band_m_idx];
     431   108880992 :                 hOMasa->direction_vector_m[2][block_m_idx][band_m_idx] += norm_tmp * direction_vector[2][band_m_idx];
     432             : 
     433   108880992 :                 diffuseness_m[band_m_idx] += reference_power[band_m_idx] * diffuseness_vector[band_m_idx];
     434   108880992 :                 renormalization_factor_diff[band_m_idx] += reference_power[band_m_idx];
     435             :             }
     436             :         }
     437             : 
     438    28439020 :         for ( band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++ )
     439             :         {
     440   108880992 :             for ( d = 0; d < DIRAC_NUM_DIMS; d++ )
     441             :             {
     442    81660744 :                 dir_v[d] = hOMasa->direction_vector_m[d][block_m_idx][band_m_idx];
     443             :             }
     444    27220248 :             ivas_qmetadata_direction_vector_to_azimuth_elevation( dir_v, &azimuth_m_values[block_m_idx][band_m_idx], &elevation_m_values[block_m_idx][band_m_idx] );
     445             :         }
     446             : 
     447             :         /* Determine energy ratios */
     448    28439020 :         for ( band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++ )
     449             :         {
     450    27220248 :             if ( renormalization_factor_diff[band_m_idx] > EPSILON )
     451             :             {
     452    23683962 :                 diffuseness_m[band_m_idx] /= renormalization_factor_diff[band_m_idx];
     453             :             }
     454             :             else
     455             :             {
     456     3536286 :                 diffuseness_m[band_m_idx] = 0.0f;
     457             :             }
     458             : 
     459    27220248 :             energyRatio[block_m_idx][band_m_idx] = 1.0f - diffuseness_m[band_m_idx];
     460             :         }
     461             : 
     462             :         /* Set coherences to zero, as this mode is used at lowest bit rates where the coherences are not transmitted */
     463    28439020 :         for ( band_m_idx = 0; band_m_idx < hOMasa->nbands; band_m_idx++ )
     464             :         {
     465    27220248 :             spreadCoherence[block_m_idx][band_m_idx] = 0.0f;
     466    27220248 :             surroundingCoherence[block_m_idx][band_m_idx] = 0.0f;
     467             :         }
     468             :     }
     469             : 
     470      304693 :     return;
     471             : }
     472             : 
     473             : 
     474             : /* Compute downmix */
     475      304693 : static void ivas_omasa_dmx(
     476             :     float data_in_f[][L_FRAME48k],
     477             :     const int16_t input_frame,
     478             :     const int16_t nchan_transport,
     479             :     const int16_t nchan_ism,
     480             :     const float ism_azimuth[MAX_NUM_OBJECTS],
     481             :     const float ism_elevation[MAX_NUM_OBJECTS],
     482             :     float prev_gains[][MASA_MAX_TRANSPORT_CHANNELS],
     483             :     const float interpolator[L_FRAME48k] )
     484             : {
     485             :     int16_t i, j, k;
     486             :     float azimuth, elevation;
     487             :     float gains[MASA_MAX_TRANSPORT_CHANNELS];
     488             :     float g1, g2;
     489             :     float data_out_f[MASA_MAX_TRANSPORT_CHANNELS][L_FRAME48k];
     490             : 
     491      761808 :     for ( i = 0; i < nchan_transport; i++ )
     492             :     {
     493      457115 :         set_zero( data_out_f[i], input_frame );
     494             :     }
     495             : 
     496     1070729 :     for ( i = 0; i < nchan_ism; i++ )
     497             :     {
     498      766036 :         if ( nchan_transport == 1 )
     499             :         {
     500      382716 :             v_add( data_out_f[0], data_in_f[i], data_out_f[0], input_frame );
     501             :         }
     502             :         else
     503             :         {
     504      383320 :             azimuth = ism_azimuth[i];
     505      383320 :             elevation = ism_elevation[i];
     506             : 
     507      383320 :             ivas_ism_get_stereo_gains( azimuth, elevation, &gains[0], &gains[1] );
     508             : 
     509             :             /* Downmix using the panning gains */
     510     1149960 :             for ( j = 0; j < nchan_transport; j++ )
     511             :             {
     512      766640 :                 if ( fabsf( gains[j] ) > 0.0 || fabsf( prev_gains[i][j] ) > 0.0f )
     513             :                 {
     514   424197860 :                     for ( k = 0; k < input_frame; k++ )
     515             :                     {
     516   423536640 :                         g1 = interpolator[k];
     517   423536640 :                         g2 = 1.0f - g1;
     518   423536640 :                         data_out_f[j][k] += ( g1 * gains[j] + g2 * prev_gains[i][j] ) * data_in_f[i][k];
     519             :                     }
     520             :                 }
     521      766640 :                 prev_gains[i][j] = gains[j];
     522             :             }
     523             :         }
     524             :     }
     525             : 
     526      761808 :     for ( i = 0; i < nchan_transport; i++ )
     527             :     {
     528      457115 :         mvr2r( data_out_f[i], data_in_f[i], input_frame );
     529             :     }
     530             : 
     531      304693 :     return;
     532             : }
     533             : 
     534             : 
     535             : /*--------------------------------------------------------------------------*
     536             :  * computeIntensityVector_ana()
     537             :  *
     538             :  *
     539             :  *--------------------------------------------------------------------------*/
     540             : 
     541     5012800 : void computeIntensityVector_ana(
     542             :     const int16_t *band_grouping,                                /* i  : Band grouping for estimation    */
     543             :     float Cldfb_RealBuffer[FOA_CHANNELS][CLDFB_NO_CHANNELS_MAX], /* i  : Real part of input signal       */
     544             :     float Cldfb_ImagBuffer[FOA_CHANNELS][CLDFB_NO_CHANNELS_MAX], /* i  : Imag part of input signal       */
     545             :     const int16_t num_frequency_bands,                           /* i  : Number of frequency bands       */
     546             :     float intensity_real[DIRAC_NUM_DIMS][MASA_FREQUENCY_BANDS]   /* o  : Intensity vector                */
     547             : )
     548             : {
     549             :     /* Reminder
     550             :      * X = a + ib; Y = c + id
     551             :      * X*Y = ac - bd + i(ad +bc)
     552             :      */
     553             :     int16_t i, j;
     554             :     float real, img;
     555             :     int16_t brange[2];
     556             : 
     557   116981440 :     for ( i = 0; i < num_frequency_bands; i++ )
     558             :     {
     559   111968640 :         brange[0] = band_grouping[i];
     560   111968640 :         brange[1] = band_grouping[i + 1];
     561             : 
     562   111968640 :         intensity_real[0][i] = 0;
     563   111968640 :         intensity_real[1][i] = 0;
     564   111968640 :         intensity_real[2][i] = 0;
     565             : 
     566   312673920 :         for ( j = brange[0]; j < brange[1]; j++ )
     567             :         {
     568   200705280 :             real = Cldfb_RealBuffer[0][j];
     569   200705280 :             img = Cldfb_ImagBuffer[0][j];
     570   200705280 :             intensity_real[0][i] += Cldfb_RealBuffer[3][j] * real + Cldfb_ImagBuffer[3][j] * img; /* Intensity is XYZ order, audio is WYZX order. */
     571   200705280 :             intensity_real[1][i] += Cldfb_RealBuffer[1][j] * real + Cldfb_ImagBuffer[1][j] * img;
     572   200705280 :             intensity_real[2][i] += Cldfb_RealBuffer[2][j] * real + Cldfb_ImagBuffer[2][j] * img;
     573             :         }
     574             :     }
     575             : 
     576     5012800 :     return;
     577             : }
     578             : 
     579             : 
     580             : /*--------------------------------------------------------------------------*
     581             :  * computeReferencePower_ana()
     582             :  *
     583             :  *
     584             :  *--------------------------------------------------------------------------*/
     585             : 
     586     4966896 : void computeReferencePower_ana(
     587             :     const int16_t *band_grouping,                                /* i  : Band grouping for estimation    */
     588             :     float Cldfb_RealBuffer[FOA_CHANNELS][CLDFB_NO_CHANNELS_MAX], /* i  : Real part of input signal       */
     589             :     float Cldfb_ImagBuffer[FOA_CHANNELS][CLDFB_NO_CHANNELS_MAX], /* i  : Imag part of input signal       */
     590             :     float *reference_power,                                      /* o  : Estimated power                 */
     591             :     const int16_t num_freq_bands                                 /* i  : Number of frequency bands       */
     592             : )
     593             : {
     594             :     int16_t brange[2];
     595             :     int16_t ch_idx, i, j;
     596             : 
     597   115906320 :     for ( i = 0; i < num_freq_bands; i++ )
     598             :     {
     599   110939424 :         brange[0] = band_grouping[i];
     600   110939424 :         brange[1] = band_grouping[i + 1];
     601   110939424 :         reference_power[i] = 0;
     602             : 
     603   554697120 :         for ( ch_idx = 0; ch_idx < FOA_CHANNELS; ch_idx++ )
     604             :         {
     605             :             /* abs()^2 */
     606  1239040896 :             for ( j = brange[0]; j < brange[1]; j++ )
     607             :             {
     608   795283200 :                 reference_power[i] += ( Cldfb_RealBuffer[ch_idx][j] * Cldfb_RealBuffer[ch_idx][j] ) + ( Cldfb_ImagBuffer[ch_idx][j] * Cldfb_ImagBuffer[ch_idx][j] );
     609             :             }
     610             :         }
     611             :     }
     612             : 
     613     4966896 :     v_multc( reference_power, 0.5f, reference_power, num_freq_bands );
     614             : 
     615     4966896 :     return;
     616             : }

Generated by: LCOV version 1.14