LCOV - code coverage report
Current view: top level - lib_dec - ivas_stereo_ica_dec_fx.c (source / functions) Hit Total Coverage
Test: Coverage on main -- dec/rend @ 633e3f2e309758d10805ef21e0436356fe719b7a Lines: 239 257 93.0 %
Date: 2025-08-23 01:22:27 Functions: 3 3 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 <assert.h>
      34             : #include <stdint.h>
      35             : #include "options.h"
      36             : #include <math.h>
      37             : #include "cnst.h"
      38             : #include "ivas_cnst.h"
      39             : #include "prot_fx.h"
      40             : #include "wmc_auto.h"
      41             : #include "rom_com.h"
      42             : #include "ivas_rom_com.h"
      43             : #include "ivas_prot_fx.h"
      44             : #include "basop32.h"
      45             : #include "ivas_stat_dec.h"
      46             : 
      47             : 
      48             : /*---------------------------------------------------------------
      49             :  *  stereo_tca_dec()
      50             :  *
      51             :  *     Stereo temporal channel adjustment/allocation processing module;
      52             :  *     upnmix, convert L/R to M/S.
      53             :  * ---------------------------------------------------------------*/
      54             : 
      55      149278 : void stereo_tca_dec_fx(
      56             :     CPE_DEC_HANDLE hCPE,            /* i/o: CPE decoder structure                                 */
      57             :     Word32 *synth_fx[CPE_CHANNELS], /* i/o: output synth                    qsynth*/
      58             :     const Word16 output_frame       /* i  : length of a frame per channel       Q0*/
      59             : )
      60             : {
      61             :     /* Buffers, input Left and right channels  @ input_Fs*/
      62      149278 :     Word32 bufChanL_fx[L_DEC_MEM_LEN_ICA + L_FRAME48k] = { 0 };
      63      149278 :     Word32 bufChanR_fx[L_DEC_MEM_LEN_ICA + L_FRAME48k] = { 0 };
      64             :     Word32 *ptrChanL_fx, *ptrChanR_fx;
      65             :     Word32 *target_fx;
      66             :     Word16 target_idx, prevNCShift, currentNCShift, l_shift_adapt;
      67             :     Word16 dsFactor, tempMax;
      68             :     Word32 *ref_fx;
      69             :     Word16 bothChannelShift;
      70             :     Word32 output_Fs;
      71             :     STEREO_TCA_DEC_HANDLE hStereoTCA;
      72             :     Word16 exp_ds;
      73             : 
      74      149278 :     hStereoTCA = hCPE->hStereoTCA;
      75             : 
      76      149278 :     output_Fs = hCPE->hCoreCoder[0]->output_Fs; /* Q0 */
      77      149278 :     move32();
      78             : 
      79      149278 :     test();
      80      149278 :     IF( EQ_16( hCPE->nchan_out, 1 ) )
      81             :     {
      82       30737 :         IF( hCPE->hStereoDftDmx )
      83             :         {
      84       23737 :             IF( EQ_16( hCPE->element_mode, IVAS_CPE_DFT ) )
      85             :             {
      86       22405 :                 hCPE->hStereoDftDmx->targetGain_fx = ONE_IN_Q29; /* Q29 */
      87       22405 :                 move32();
      88             :             }
      89             : 
      90             :             /* save the target gain for next frame */
      91       23737 :             hCPE->hStereoDftDmx->prevTargetGain_fx = hCPE->hStereoDftDmx->targetGain_fx; /* Q29 */
      92       23737 :             move32();
      93             :         }
      94             : 
      95       30737 :         return;
      96             :     }
      97      118541 :     ELSE IF( EQ_16( hCPE->element_mode, IVAS_CPE_MDCT ) && !hCPE->hStereoMdct->use_itd )
      98             :     {
      99       68779 :         return;
     100             :     }
     101             : 
     102             :     /* populate L/R memories into current buffers */
     103       49762 :     Copy32( hStereoTCA->memChanL_fx, bufChanL_fx, L_DEC_MEM_LEN_ICA ); /* memChan_q */
     104       49762 :     Copy32( hStereoTCA->memChanR_fx, bufChanR_fx, L_DEC_MEM_LEN_ICA ); /* memChan_q */
     105             : 
     106             :     /* pointers to the current frame */
     107       49762 :     ptrChanL_fx = bufChanL_fx + L_DEC_MEM_LEN_ICA; /* memChan_q */
     108       49762 :     ptrChanR_fx = bufChanR_fx + L_DEC_MEM_LEN_ICA; /* memChan_q */
     109             : 
     110             :     /* copy interleaved stereo data to two channels, e.g., L, R */
     111       49762 :     Copy32( synth_fx[0], ptrChanL_fx, output_frame ); /* qsynth */
     112       49762 :     Copy32( synth_fx[1], ptrChanR_fx, output_frame ); /* qsynth */
     113             : 
     114             :     /* back up the L/R target synth for next frame */
     115       49762 :     Copy32( bufChanL_fx + output_frame, hStereoTCA->memChanL_fx, L_DEC_MEM_LEN_ICA ); /* memChan_q */
     116       49762 :     Copy32( bufChanR_fx + output_frame, hStereoTCA->memChanR_fx, L_DEC_MEM_LEN_ICA ); /* memChan_q */
     117             : 
     118             :     /* TCA parameter de-quantize */
     119       49762 :     dsFactor = BASOP_Util_Divide3232_Scale( output_Fs, 8000, &exp_ds );
     120       49762 :     dsFactor = shr( dsFactor, sub( 15, exp_ds ) ); /* Q0 */
     121             : 
     122       49762 :     tempMax = NS2SA_FX2( output_Fs, L_NCSHIFT_NS );                                       /* Q0 */
     123       49762 :     hStereoTCA->corrLagStats = s_min( hStereoTCA->indx_ica_NCShift * dsFactor, tempMax ); /* Q0 */
     124             : 
     125       49762 :     bothChannelShift = 0;
     126       49762 :     move16();
     127       49762 :     test();
     128       49762 :     IF( EQ_16( hCPE->element_mode, IVAS_CPE_DFT ) || EQ_16( hCPE->element_mode, IVAS_CPE_MDCT ) )
     129             :     {
     130       47408 :         hStereoTCA->corrLagStats = 0;
     131       47408 :         move16();
     132       47408 :         hStereoTCA->refChanIndx = L_CH_INDX; /* Q0 */
     133       47408 :         move16();
     134       47408 :         hStereoTCA->targetGain_fx = ONE_IN_Q29; /* Q29 */
     135       47408 :         move16();
     136             : 
     137       47408 :         IF( EQ_16( hCPE->element_mode, IVAS_CPE_DFT ) )
     138             :         {
     139       37287 :             hStereoTCA->corrLagStats = extract_l( L_shr( L_abs( hCPE->hStereoDft->itd_fx[1] ), Q15 ) ); /* Q0 */
     140             : 
     141       37287 :             IF( hCPE->hStereoDft->itd_fx[1] >= 0 )
     142             :             {
     143       24145 :                 hStereoTCA->refChanIndx = ( L_CH_INDX ); /* Q0 */
     144             :             }
     145             :             ELSE
     146             :             {
     147       13142 :                 hStereoTCA->refChanIndx = ( R_CH_INDX ); /* Q0 */
     148             :             }
     149       37287 :             move16();
     150       37287 :             move16();
     151             :         }
     152       10121 :         ELSE IF( EQ_16( hCPE->element_mode, IVAS_CPE_MDCT ) )
     153             :         {
     154             :             Word32 itd;
     155             : 
     156       10121 :             itd = hCPE->hStereoMdct->itd_fx;
     157       10121 :             move32();
     158       10121 :             hStereoTCA->corrLagStats = extract_l( L_shr( L_abs( itd ), Q15 ) ); /* Q0 */
     159             : 
     160       10121 :             IF( GE_32( itd, 0 ) )
     161             :             {
     162        8193 :                 hStereoTCA->refChanIndx = ( L_CH_INDX ); /* Q0 */
     163             :             }
     164             :             ELSE
     165             :             {
     166        1928 :                 hStereoTCA->refChanIndx = ( R_CH_INDX ); /* Q0 */
     167             :             }
     168       10121 :             move16();
     169             :         }
     170             : 
     171       47408 :         test();
     172       47408 :         IF( NE_16( hStereoTCA->refChanIndx, hStereoTCA->prevRefChanIndx ) && ( hStereoTCA->corrLagStats != 0 ) )
     173             :         {
     174         375 :             bothChannelShift = 1;
     175         375 :             move16();
     176             :         }
     177             :     }
     178             : 
     179       49762 :     prevNCShift = abs_s( hStereoTCA->prevCorrLagStats ); /* Q0 */
     180       49762 :     currentNCShift = abs_s( hStereoTCA->corrLagStats );  /* Q0 */
     181             : 
     182       49762 :     test();
     183       49762 :     IF( EQ_16( hCPE->element_mode, IVAS_CPE_TD ) && EQ_16( hCPE->last_element_mode, IVAS_CPE_TD ) )
     184             :     {
     185        2319 :         test();
     186        2319 :         IF( EQ_16( hStereoTCA->corrLagStats, hStereoTCA->prevCorrLagStats ) && EQ_16( hStereoTCA->interp_dec_switch_to_zero_diff, 0 ) )
     187             :         {
     188        1166 :             hStereoTCA->interp_dec_switch_to_zero_diff = 1;
     189        1166 :             move16();
     190             :         }
     191             :         ELSE
     192             :         {
     193        1153 :             hStereoTCA->interp_dec_switch_to_zero_diff = 0;
     194        1153 :             move16();
     195             :         }
     196             : 
     197        2319 :         IF( currentNCShift != 0 )
     198             :         {
     199           4 :             currentNCShift = add( mult( 19660 /* 0.6 in Q15 */, prevNCShift ), mult( 13106 /* 0.4 in Q15 */, currentNCShift ) ); /* Q0 */
     200             :         }
     201             : 
     202        2319 :         prevNCShift = hStereoTCA->interp_dec_prevNCShift; /* Q0 */
     203        2319 :         move16();
     204        2319 :         hStereoTCA->interp_dec_prevNCShift = currentNCShift; /* Q0 */
     205        2319 :         move16();
     206             :     }
     207             :     ELSE
     208             :     {
     209       47443 :         hStereoTCA->interp_dec_prevNCShift = currentNCShift; /* Q0 */
     210       47443 :         move16();
     211       47443 :         hStereoTCA->interp_dec_switch_to_zero_diff = 0;
     212       47443 :         move16();
     213             :     }
     214             : 
     215       49762 :     ref_fx = ptrChanL_fx;    /* qsynth */
     216       49762 :     target_fx = ptrChanR_fx; /* qsynth */
     217       49762 :     target_idx = R_CH_INDX;
     218       49762 :     move16();
     219             :     /* identify target signal to adjust for shift variations */
     220       49762 :     test();
     221       49762 :     test();
     222       49762 :     IF( ( ( prevNCShift == 0 ) && EQ_16( hStereoTCA->refChanIndx, R_CH_INDX ) ) || EQ_16( hStereoTCA->prevRefChanIndx, R_CH_INDX ) )
     223             :     {
     224       15198 :         ref_fx = ptrChanR_fx;    /* qsynth */
     225       15198 :         target_fx = ptrChanL_fx; /* qsynth */
     226       15198 :         target_idx = L_CH_INDX;
     227       15198 :         move16();
     228             :     }
     229             : 
     230       49762 :     IF( EQ_16( bothChannelShift, 1 ) )
     231             :     {
     232         375 :         ref_fx = ptrChanL_fx;    /* qsynth */
     233         375 :         target_fx = ptrChanR_fx; /* qsynth */
     234         375 :         target_idx = R_CH_INDX;
     235         375 :         move16();
     236         375 :         IF( EQ_16( hStereoTCA->refChanIndx, R_CH_INDX ) )
     237             :         {
     238         300 :             ref_fx = ptrChanR_fx;    /* qsynth */
     239         300 :             target_fx = ptrChanL_fx; /* qsynth */
     240         300 :             target_idx = L_CH_INDX;
     241         300 :             move16();
     242             :         }
     243             :     }
     244             : 
     245             :     /* target signal adjustment for temporal shift variations */
     246       49762 :     test();
     247       49762 :     test();
     248       49762 :     test();
     249       49762 :     IF( NE_16( hStereoTCA->prevCorrLagStats, hStereoTCA->corrLagStats ) || bothChannelShift || ( EQ_16( hStereoTCA->interp_dec_switch_to_zero_diff, 1 ) && EQ_16( hCPE->element_mode, IVAS_CPE_TD ) ) )
     250             :     {
     251        3745 :         l_shift_adapt = L_SHIFT_ADAPT_16k;
     252        3745 :         move16();
     253        3745 :         IF( GT_32( output_Fs, 16000 ) )
     254             :         {
     255        2908 :             l_shift_adapt = L_SHIFT_ADAPT_MAX; /* Q0 */
     256        2908 :             move16();
     257             :         }
     258             : 
     259        3745 :         test();
     260        3745 :         IF( EQ_16( hCPE->element_mode, IVAS_CPE_TD ) && EQ_16( hCPE->last_element_mode, IVAS_CPE_DFT ) )
     261             :         {
     262          12 :             l_shift_adapt = shr( l_shift_adapt, 1 ); /* Q0 */
     263             :         }
     264             : 
     265        3745 :         test();
     266        3745 :         IF( LE_16( abs_s( sub( currentNCShift, prevNCShift ) ), N_MAX_SHIFT_CHANGE ) && EQ_16( bothChannelShift, 0 ) )
     267             :         {
     268        3101 :             adjustTargetSignal_fx( target_fx - currentNCShift, currentNCShift, prevNCShift, l_shift_adapt, 0 );
     269             :         }
     270             :         ELSE
     271             :         {
     272         644 :             IF( EQ_16( bothChannelShift, 1 ) )
     273             :             {
     274         375 :                 adjustTargetSignal_fx( ref_fx, 0, prevNCShift, l_shift_adapt, 1 );
     275         375 :                 adjustTargetSignal_fx( target_fx - currentNCShift, currentNCShift, 0, l_shift_adapt, 1 );
     276             :             }
     277             :             ELSE
     278             :             {
     279         269 :                 adjustTargetSignal_fx( target_fx - currentNCShift, currentNCShift, prevNCShift, l_shift_adapt, 1 );
     280             :             }
     281             :         }
     282             :     }
     283             : 
     284             :     /* temporal channel adjustment */
     285       49762 :     Copy32( target_fx - currentNCShift, synth_fx[target_idx], output_frame ); /* qsynth */
     286             : 
     287       49762 :     Copy32( ref_fx, synth_fx[!target_idx], output_frame ); /* qsynth */
     288             : 
     289             :     /* Scale the Right channel with the gain */
     290       49762 :     stereo_tca_scale_R_channel_fx( hCPE, synth_fx[1], output_frame );
     291             : 
     292             :     /*-----------------------------------------------------------------*
     293             :      * updates and memory backups
     294             :      *-----------------------------------------------------------------*/
     295             : 
     296             :     /* save the reference channel index for next frame */
     297       49762 :     hStereoTCA->prevRefChanIndx = hStereoTCA->refChanIndx; /* Q0 */
     298       49762 :     move16();
     299             : 
     300             :     /* save the corr lag stats for next frame */
     301       49762 :     hStereoTCA->prevCorrLagStats = hStereoTCA->corrLagStats; /* Q0 */
     302       49762 :     move16();
     303             : 
     304             :     /* save the target gain for next frame */
     305       49762 :     hStereoTCA->prevTargetGain_fx = hStereoTCA->targetGain_fx; /* qsynth */
     306       49762 :     move32();
     307       49762 :     return;
     308             : }
     309             : /*-------------------------------------------------------------------*
     310             :  * stereo_tca_scale_R_channel()
     311             :  *
     312             :  * Scale the Right channel with the gain
     313             :  *-------------------------------------------------------------------*/
     314             : 
     315             : #define MAX_TARGET_GAIN_Q29 1904890240
     316       51101 : void stereo_tca_scale_R_channel_fx(
     317             :     CPE_DEC_HANDLE hCPE,      /* i/o: CPE decoder structure                              */
     318             :     Word32 *output_fx,        /* i/o: output synthesis, R channel       q_out*/
     319             :     const Word16 output_frame /* i  : frame length                                         Q0*/
     320             : )
     321             : {
     322             :     STEREO_TCA_DEC_HANDLE hStereoTCA;
     323             :     Word16 j, l_ica_ovl, flat_old;
     324             :     Word16 i_fx;
     325       51101 :     Word32 tempF_fx, tempF1_fx, winSlope_fx = 0;
     326             :     Word32 output_Fs;
     327       51101 :     move16();
     328             : 
     329       51101 :     hStereoTCA = hCPE->hStereoTCA;
     330       51101 :     output_Fs = hCPE->hCoreCoder[0]->output_Fs; /* Q0 */
     331       51101 :     move32();
     332             : 
     333       51101 :     test();
     334       51101 :     IF( LE_32( hCPE->hCoreCoder[0]->core_brate, SID_2k40 ) && EQ_16( hCPE->nchan_out, 2 ) )
     335             :     {
     336        7284 :         return;
     337             :     }
     338             :     /* Scale the Right channel with the gain */
     339       43817 :     l_ica_ovl = NS2SA_FX2( output_Fs, STEREO_L_TCA_OVLP_NS ); /* Q0 */
     340       43817 :     move16();
     341             : 
     342       43817 :     test();
     343       43817 :     IF( EQ_16( hCPE->nchan_out, 1 ) )
     344             :     {
     345             :         /* in mono DMX, the scaling is done before synchro_synthesis() */
     346        1339 :         flat_old = NS2SA_FX2( output_Fs, ACELP_LOOK_NS + IVAS_DEC_DELAY_NS - DELAY_CLDFB_NS ); /* Q0 */
     347        1339 :         move16();
     348             : 
     349        1339 :         test();
     350        1339 :         IF( EQ_16( hCPE->last_element_mode, IVAS_CPE_TD ) && EQ_16( hCPE->element_mode, IVAS_CPE_DFT ) )
     351             :         {
     352             :             Word64 local_value;
     353             :             // to be deleted next MR
     354             :             // hCPE->hStereoDftDmx->prevTargetGain *= 2.0f;
     355             :             // hCPE->hStereoDftDmx->prevTargetGain = min( hCPE->hStereoDftDmx->prevTargetGain, powf( 10, ( ( 1 << STEREO_BITS_TCA_GD ) - 1 ) * STEREO_TCA_GDSTEP + STEREO_TCA_GDMIN ) );
     356           7 :             local_value = W_shl( hCPE->hStereoDftDmx->prevTargetGain_fx, 1 );                          /* Q29 */
     357           7 :             hCPE->hStereoDftDmx->prevTargetGain_fx = (Word32) min( local_value, MAX_TARGET_GAIN_Q29 ); /* Q29 */
     358           7 :             hCPE->hStereoDftDmx->targetGain_fx = ONE_IN_Q29;                                           /* Q29 */
     359           7 :             move32();
     360             : 
     361           7 :             flat_old = NS2SA_FX2( output_Fs, IVAS_DEC_DELAY_NS ); /* Q0 */
     362           7 :             move16();
     363             :         }
     364             :     }
     365       42478 :     ELSE IF( EQ_16( hCPE->last_element_mode, IVAS_CPE_TD ) && EQ_16( hCPE->element_mode, IVAS_CPE_DFT ) )
     366             :     {
     367          13 :         flat_old = NS2SA_FX2( output_Fs, IVAS_DEC_DELAY_NS ); /* Q0 */
     368          13 :         move16();
     369             :     }
     370             :     ELSE
     371             :     {
     372       42465 :         flat_old = NS2SA_FX2( output_Fs, ACELP_LOOK_NS + IVAS_DEC_DELAY_NS ); /* Q0 */
     373       42465 :         move16();
     374             :     }
     375             : 
     376       43817 :     IF( EQ_16( hCPE->nchan_out, 1 ) )
     377             :     {
     378        1339 :         IF( EQ_32( hCPE->hStereoDftDmx->targetGain_fx, ONE_IN_Q29 ) )
     379             :         {
     380        1339 :             tempF1_fx = ONE_IN_Q27; /* Q27 */
     381        1339 :             move32();
     382             :         }
     383             :         ELSE
     384             :         {
     385           0 :             Word16 temp_a = (Word16) L_shr( hCPE->hStereoDftDmx->targetGain_fx, (Word16) 16 ); /* Q13 */
     386           0 :             Word16 temp_a_q = 2;
     387           0 :             move16();
     388           0 :             tempF1_fx = Inv16( temp_a, &temp_a_q );                                 /* Q13 */
     389           0 :             tempF1_fx = L_shl( tempF1_fx, sub( ( 31 - 4 ), sub( 15, temp_a_q ) ) ); /* Q27 */
     390             :         }
     391             : 
     392        1339 :         IF( EQ_32( hCPE->hStereoDftDmx->prevTargetGain_fx, ONE_IN_Q29 ) )
     393             :         {
     394        1332 :             tempF_fx = ONE_IN_Q27; /* Q27 */
     395        1332 :             move32();
     396             :         }
     397             :         ELSE
     398             :         {
     399           7 :             Word16 temp_b = (Word16) L_shr( hCPE->hStereoDftDmx->prevTargetGain_fx, 16 ); /* Q13 */
     400           7 :             Word16 temp_b_q = 2;
     401           7 :             move16();
     402           7 :             tempF_fx = Inv16( temp_b, &temp_b_q );                                /* Q13 */
     403           7 :             tempF_fx = L_shl( tempF_fx, sub( ( 31 - 4 ), sub( 15, temp_b_q ) ) ); /* Q27 */
     404             :         }
     405             :     }
     406             :     ELSE
     407             :     {
     408             : 
     409       42478 :         IF( EQ_32( hStereoTCA->targetGain_fx, ONE_IN_Q29 ) )
     410             :         {
     411       42478 :             tempF1_fx = ONE_IN_Q27; /* Q27 */
     412       42478 :             move32();
     413             :         }
     414             :         ELSE
     415             :         {
     416           0 :             Word16 temp_a = (Word16) L_shr( hStereoTCA->targetGain_fx, (Word16) 16 ); /* Q13 */
     417           0 :             Word16 temp_a_q = 2;
     418           0 :             move16();
     419           0 :             tempF1_fx = Inv16( temp_a, &temp_a_q );                                 /* Q13 */
     420           0 :             tempF1_fx = L_shl( tempF1_fx, sub( ( 31 - 4 ), sub( 15, temp_a_q ) ) ); /* Q27 */
     421             :         }
     422             : 
     423             : 
     424       42478 :         IF( EQ_32( hStereoTCA->prevTargetGain_fx, ONE_IN_Q29 ) )
     425             :         {
     426       42478 :             tempF_fx = ONE_IN_Q27; /* Q27 */
     427       42478 :             move32();
     428             :         }
     429             :         ELSE
     430             :         {
     431           0 :             Word16 temp_b = (Word16) L_shr( hStereoTCA->prevTargetGain_fx, (Word16) 16 ); /* Q13 */
     432           0 :             Word16 temp_b_q = 2;
     433           0 :             move16();
     434           0 :             tempF_fx = Inv16( temp_b, &temp_b_q );                                /* Q13 */
     435           0 :             tempF_fx = L_shl( tempF_fx, sub( ( 31 - 4 ), sub( 15, temp_b_q ) ) ); /* Q27 */
     436             :         }
     437             :     }
     438       43817 :     SWITCH( output_Fs )
     439             :     {
     440       14232 :         case 16000:
     441       14232 :             winSlope_fx = 26843546; // 0.0125 in Q31
     442       14232 :             move32();
     443       14232 :             BREAK;
     444       15645 :         case 32000:
     445       15645 :             winSlope_fx = 13421773; // 0.00625 in Q30
     446       15645 :             move32();
     447       15645 :             BREAK;
     448       13940 :         case 48000:
     449       13940 :             winSlope_fx = 8947849; // 0.00416 in Q30
     450       13940 :             move32();
     451       13940 :             BREAK;
     452             :     }
     453             : 
     454       43817 :     IF( EQ_32( tempF_fx, ONE_IN_Q27 ) )
     455             :     {
     456    16757362 :         FOR( i_fx = 0; i_fx < flat_old; i_fx++ )
     457             :         {
     458    16713552 :             output_fx[i_fx] = output_fx[i_fx]; /* q_out */
     459    16713552 :             move32();
     460             :         }
     461             :     }
     462             :     ELSE
     463             :     {
     464         839 :         FOR( i_fx = 0; i_fx < flat_old; i_fx++ )
     465             :         {
     466         832 :             output_fx[i_fx] = L_shl_sat( Mpy_32_32( output_fx[i_fx], tempF_fx ), 4 ); /* q_out */
     467         832 :             move32();
     468             :         }
     469             :     }
     470             : 
     471       43817 :     test();
     472       43817 :     IF( EQ_32( tempF1_fx, ONE_IN_Q27 ) && EQ_32( tempF_fx, ONE_IN_Q27 ) )
     473             :     {
     474     7029890 :         FOR( j = 0; i_fx < flat_old + l_ica_ovl; ( i_fx++, j++ ) )
     475             :         {
     476     6986080 :             Word32 slope_gain_decend = L_sub( ONE_IN_Q31, imult3216( winSlope_fx, j ) ); /* Q31 */
     477     6986080 :             Word32 slope_gain_ascend = imult3216( winSlope_fx, j );                      /* Q31 */
     478     6986080 :             Word32 left_res = Mpy_32_32( slope_gain_decend, output_fx[i_fx] );           /* q_out */
     479     6986080 :             Word32 right_res = Mpy_32_32( slope_gain_ascend, output_fx[i_fx] );          /* q_out */
     480     6986080 :             output_fx[i_fx] = L_add( left_res, right_res );                              /* q_out */
     481     6986080 :             move32();
     482             :         }
     483             :     }
     484             :     ELSE
     485             :     {
     486        1287 :         FOR( j = 0; i_fx < flat_old + l_ica_ovl; ( i_fx++, j++ ) )
     487             :         {
     488        1280 :             Word32 slope_gain_decend = L_sub( ONE_IN_Q31, imult3216( winSlope_fx, j ) );                                                       /* Q31 */
     489        1280 :             Word32 slope_gain_ascend = imult3216( winSlope_fx, j );                                                                            /* Q31 */
     490        1280 :             Word32 left_res = Mpy_32_32( slope_gain_decend, output_fx[i_fx] );                                                                 /* q_out */
     491        1280 :             Word32 right_res = Mpy_32_32( slope_gain_ascend, output_fx[i_fx] );                                                                /* q_out */
     492        1280 :             output_fx[i_fx] = L_add_sat( L_shl_sat( Mpy_32_32( tempF_fx, left_res ), 4 ), L_shl_sat( Mpy_32_32( right_res, tempF1_fx ), 4 ) ); /* q_out */
     493        1280 :             move32();
     494             :         }
     495             :     }
     496             : 
     497       43817 :     IF( EQ_32( tempF1_fx, ONE_IN_Q27 ) )
     498             :     {
     499     4291513 :         FOR( ; i_fx < output_frame; i_fx++ )
     500             :         {
     501     4247696 :             output_fx[i_fx] = output_fx[i_fx]; /* q_out */
     502     4247696 :             move32();
     503             :         }
     504             :     }
     505             :     ELSE
     506             :     {
     507           0 :         FOR( ; i_fx < output_frame; i_fx++ )
     508             :         {
     509           0 :             output_fx[i_fx] = L_shl_sat( Mpy_32_32( output_fx[i_fx], tempF1_fx ), 4 ); /* q_out */
     510           0 :             move32();
     511             :         }
     512             :     }
     513             : 
     514       43817 :     return;
     515             : }
     516             : 
     517             : /*-------------------------------------------------------------------*
     518             :  * stereo_tca_init_dec()
     519             :  *
     520             :  * Stereo temporal channel adjustment (TCA) decoder initialization
     521             :  *-------------------------------------------------------------------*/
     522             : 
     523             : 
     524         521 : void stereo_tca_init_dec_fx(
     525             :     STEREO_TCA_DEC_HANDLE hStereoTCA /* i/o: Stereo TCA handle */
     526             : )
     527             : {
     528         521 :     hStereoTCA->refChanIndx = L_CH_INDX;
     529         521 :     move16();
     530         521 :     hStereoTCA->prevRefChanIndx = L_CH_INDX;
     531         521 :     move16();
     532         521 :     hStereoTCA->indx_ica_NCShift = 0;
     533         521 :     move16();
     534         521 :     hStereoTCA->indx_ica_gD = 0;
     535         521 :     move16();
     536         521 :     hStereoTCA->targetGain_fx = ONE_IN_Q29; /* Q29 */
     537         521 :     move32();
     538         521 :     hStereoTCA->prevTargetGain_fx = ONE_IN_Q29; /* Q29 */
     539         521 :     move32();
     540             : 
     541         521 :     hStereoTCA->corrLagStats = 0;
     542         521 :     move16();
     543         521 :     hStereoTCA->prevCorrLagStats = 0;
     544         521 :     move16();
     545             : 
     546         521 :     hStereoTCA->interp_dec_prevNCShift = 0;
     547         521 :     move16();
     548         521 :     hStereoTCA->interp_dec_switch_to_zero_diff = 0;
     549         521 :     move16();
     550             : 
     551         521 :     set32_fx( hStereoTCA->memChanL_fx, 0, L_DEC_MEM_LEN_ICA );
     552         521 :     set32_fx( hStereoTCA->memChanR_fx, 0, L_DEC_MEM_LEN_ICA );
     553             : 
     554         521 :     return;
     555             : }

Generated by: LCOV version 1.14