LCOV - code coverage report
Current view: top level - lib_enc - cod_tcx.c (source / functions) Hit Total Coverage
Test: Coverage on main -- short test vectors @ ce3afad1c76ae62bc18a70c8b764ccf68a4a905a Lines: 755 769 98.2 %
Date: 2025-10-16 04:54:04 Functions: 13 13 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             : /*====================================================================================
      34             :     EVS Codec 3GPP TS26.443 Nov 04, 2021. Version 12.14.0 / 13.10.0 / 14.6.0 / 15.4.0 / 16.3.0
      35             :   ====================================================================================*/
      36             : 
      37             : #include <assert.h>
      38             : #include <stdint.h>
      39             : #include "options.h"
      40             : #include <math.h>
      41             : #include "cnst.h"
      42             : #include "prot.h"
      43             : #include "wmc_auto.h"
      44             : #include "ivas_prot.h"
      45             : #include "ivas_rom_com.h"
      46             : #ifdef DEBUGGING
      47             : #include <string.h>
      48             : #endif
      49             : #ifdef DEBUG_PLOT
      50             : #include "deb_out.h"
      51             : #endif
      52             : 
      53             : /*-------------------------------------------------------------------*
      54             :  * HBAutocorrelation()
      55             :  *
      56             :  *
      57             :  *-------------------------------------------------------------------*/
      58             : 
      59      208547 : void HBAutocorrelation(
      60             :     TCX_CONFIG_HANDLE hTcxCfg,        /* i  : configuration of TCX              */
      61             :     const int16_t left_overlap_mode,  /* i  : overlap mode of left window half  */
      62             :     const int16_t right_overlap_mode, /* i  : overlap mode of right window half */
      63             :     float speech[],                   /* i  : synthesis                         */
      64             :     int16_t L_frame,                  /* i  : frame length                      */
      65             :     float *r                          /* o  : autocorrelations vector           */
      66             : )
      67             : {
      68             :     int16_t i, j, left_overlap, right_overlap;
      69             :     float s;
      70             :     float xn_buf[L_MDCT_OVLP_MAX + L_FRAME_PLUS + L_MDCT_OVLP_MAX];
      71             : 
      72             :     /*-----------------------------------------------------------*
      73             :      * Windowing                                                 *
      74             :      *-----------------------------------------------------------*/
      75             : 
      76      208547 :     WindowSignal( hTcxCfg, hTcxCfg->tcx_offset, left_overlap_mode, right_overlap_mode, &left_overlap, &right_overlap, speech, &L_frame, xn_buf, 1, 0 );
      77             : 
      78             :     /*-----------------------------------------------------------*
      79             :      * Autocorrelation                                           *
      80             :      *-----------------------------------------------------------*/
      81             : 
      82     3753846 :     for ( i = 0; i <= M; i++ )
      83             :     {
      84     3545299 :         s = 0.0;
      85             : 
      86  2911660907 :         for ( j = 0; j < L_frame + ( left_overlap + right_overlap ) / 2 - i; j++ )
      87             :         {
      88  2908115608 :             s += xn_buf[j] * xn_buf[j + i];
      89             :         }
      90     3545299 :         r[i] = s;
      91             :     }
      92             : 
      93      208547 :     if ( r[0] < 100.0 )
      94             :     {
      95        6126 :         r[0] = 100.0;
      96             :     }
      97             : 
      98      208547 :     return;
      99             : }
     100             : 
     101             : 
     102             : /*-------------------------------------------------------------------*
     103             :  * TNSAnalysisStereo()
     104             :  *
     105             :  *
     106             :  *-------------------------------------------------------------------*/
     107             : 
     108             : #define SIMILAR_TNS_THRESHOLD        ( 0.04f )
     109             : #define TNS_GAIN_THRESHOLD_FOR_WHITE ( 3.0f )
     110             : 
     111     2139650 : void TNSAnalysisStereo(
     112             :     Encoder_State **sts,                        /* i  : encoder state handle                    */
     113             :     float *mdst_spectrum[CPE_CHANNELS][NB_DIV], /* o  : MDST spectrum                           */
     114             :     const int16_t bWhitenedDomain,              /* i  : whitened domain flag                    */
     115             :     int16_t tnsSize[CPE_CHANNELS][NB_DIV],      /* i  : number of tns parameters put into prm   */
     116             :     int16_t tnsBits[CPE_CHANNELS][NB_DIV],      /* i  : number of tns bits in the frame         */
     117             :     int16_t param_core[][NB_DIV * NPRM_DIV],    /* o  : TNS parameters                          */
     118             :     const int16_t mct_on                        /* i  : flag mct block (1) or stereo (0)          */
     119             : )
     120             : {
     121             :     int16_t ch, k, L_spec, L_frame, nSubframes, iFilter;
     122             :     float *spectrum;
     123     2139650 :     Encoder_State *st = NULL;
     124     2139650 :     TCX_ENC_HANDLE hTcxEnc = NULL;
     125             :     int16_t individual_decision[NB_DIV];
     126     2139650 :     float maxPredictionGain = 0.f, meanPredictionGain;
     127             : 
     128     2139650 :     individual_decision[0] = 0;
     129     2139650 :     individual_decision[1] = 0;
     130     2139650 :     L_spec = -1;
     131     2139650 :     L_frame = -1;
     132             : 
     133             :     /* TNS filter analysis, loop over channels */
     134     6418950 :     for ( ch = 0; ch < CPE_CHANNELS; ch++ )
     135             :     {
     136     4279300 :         st = sts[ch];
     137     4279300 :         if ( st->mct_chan_mode == MCT_CHAN_MODE_IGNORE )
     138             :         {
     139      498045 :             continue;
     140             :         }
     141             : 
     142     3781255 :         hTcxEnc = st->hTcxEnc;
     143             : 
     144     3781255 :         nSubframes = ( hTcxEnc->tcxMode == TCX_20 ) ? 1 : NB_DIV;
     145             : 
     146     7689246 :         for ( k = 0; k < nSubframes; k++ )
     147             :         {
     148             :             /* reset tns on whitened domain flag */
     149     3907991 :             if ( !bWhitenedDomain )
     150             :             {
     151     2017529 :                 hTcxEnc->bTnsOnWhithenedSpectra[k] = 0;
     152     2017529 :                 hTcxEnc->fUseTns[k] = 0;
     153             :             }
     154             : 
     155     3907991 :             if ( st->hTcxCfg->fIsTNSAllowed && ( !bWhitenedDomain || hTcxEnc->bTnsOnWhithenedSpectra[k] ) )
     156             :             {
     157             : 
     158     3777090 :                 spectrum = hTcxEnc->spectrum[k];
     159     3777090 :                 L_frame = hTcxEnc->L_frameTCX;
     160     3777090 :                 st->hTcxCfg->pCurrentTnsConfig = &st->hTcxCfg->tnsConfig[hTcxEnc->transform_type[k] == TCX_20][( k == 0 ) && ( st->last_core == ACELP_CORE )];
     161     3777090 :                 L_spec = st->hTcxCfg->pCurrentTnsConfig->iFilterBorders[0];
     162             : 
     163             :                 /*-----------------------------------------------------------*
     164             :                  * Temporal Noise Shaping analysis                           *
     165             :                  *-----------------------------------------------------------*/
     166             : 
     167     3777090 :                 if ( hTcxEnc->transform_type[k] == TCX_5 )
     168             :                 {
     169             :                     /* rearrange LF sub-window lines prior to TNS analysis & filtering */
     170       64148 :                     tcx5TnsGrouping( L_frame >> 2, L_spec >> 1, spectrum );
     171             :                 }
     172             : 
     173             :                 /* WMOPS: All initializations are either for safety or static (tables) and thus not to be counted */
     174     3777090 :                 ResetTnsData( &hTcxEnc->tnsData[k] );
     175     3777090 :                 if ( st->hTcxCfg->pCurrentTnsConfig->maxOrder <= 0 )
     176             :                 {
     177           0 :                     break;
     178             :                 }
     179             : 
     180     3777090 :                 CalculateTnsFilt( st->hTcxCfg->pCurrentTnsConfig, spectrum, &hTcxEnc->tnsData[k], NULL );
     181             :             }
     182             :         }
     183             :     }
     184             : 
     185     2139650 :     if ( !mct_on )
     186             :     {
     187             :         /* TNS decision */
     188             :         /* if framing differs between channels, keep the filter decision per channel */
     189      370354 :         if ( ( sts[0]->hTcxEnc->transform_type[0] != sts[1]->hTcxEnc->transform_type[0] &&
     190        5068 :                sts[0]->hTcxEnc->transform_type[1] != sts[1]->hTcxEnc->transform_type[1] ) ||
     191      365292 :              sts[0]->hTcxCfg->fIsTNSAllowed != sts[1]->hTcxCfg->fIsTNSAllowed )
     192             :         {
     193        5062 :             individual_decision[0] = individual_decision[1] = 1;
     194             :         }
     195      365292 :         else if ( bWhitenedDomain )
     196             :         {
     197      182646 :             nSubframes = ( sts[0]->hTcxEnc->tcxMode == TCX_20 ) ? 1 : NB_DIV;
     198      369979 :             for ( k = 0; k < nSubframes; k++ )
     199             :             {
     200      187333 :                 if ( sts[0]->hTcxEnc->bTnsOnWhithenedSpectra[k] != sts[1]->hTcxEnc->bTnsOnWhithenedSpectra[k] )
     201             :                 {
     202        2626 :                     individual_decision[k] = 1;
     203             :                 }
     204             :             }
     205             :         }
     206             : 
     207             :         /* framing equal, check for similar filters, if very similar (also indicator for and M signal),
     208             :          * use at least the same decision, maybe use the same filter
     209             :          */
     210             :         {
     211             :             int16_t isTCX10;
     212      370354 :             isTCX10 = ( sts[0]->hTcxEnc->tcxMode == TCX_20 ) ? 0 : 1;
     213             : 
     214      370354 :             nSubframes = ( sts[0]->hTcxEnc->tcxMode == TCX_20 ) ? 1 : NB_DIV;
     215             : 
     216      752524 :             for ( k = 0; k < nSubframes; k++ )
     217             :             {
     218      382170 :                 if ( sts[0]->hTcxCfg->fIsTNSAllowed && individual_decision[k] != 1 && ( !bWhitenedDomain || sts[0]->hTcxEnc->bTnsOnWhithenedSpectra[k] ) )
     219             :                 {
     220      359313 :                     float maxPredGain = -1.0f;
     221      359313 :                     sts[0]->hTcxCfg->pCurrentTnsConfig = &sts[0]->hTcxCfg->tnsConfig[sts[0]->hTcxEnc->transform_type[k] == TCX_20][( k == 0 ) && ( sts[0]->last_core == ACELP_CORE )];
     222      359313 :                     sts[1]->hTcxCfg->pCurrentTnsConfig = &sts[1]->hTcxCfg->tnsConfig[sts[1]->hTcxEnc->transform_type[k] == TCX_20][( k == 0 ) && ( sts[1]->last_core == ACELP_CORE )];
     223             : 
     224             : #ifdef DEBUGGING
     225             :                     assert( sts[0]->hTcxCfg->pCurrentTnsConfig->nMaxFilters == sts[1]->hTcxCfg->pCurrentTnsConfig->nMaxFilters );
     226             : #endif
     227     1035166 :                     for ( iFilter = sts[0]->hTcxCfg->pCurrentTnsConfig->nMaxFilters - 1; iFilter >= 0; iFilter-- )
     228             :                     {
     229             :                         STnsFilter *pFilter[2];
     230             :                         struct TnsParameters const *pTnsParameters[2];
     231      675853 :                         pFilter[0] = sts[0]->hTcxEnc->tnsData[k].filter + iFilter;
     232      675853 :                         pTnsParameters[0] = sts[0]->hTcxCfg->pCurrentTnsConfig->pTnsParameters + iFilter;
     233      675853 :                         pFilter[1] = sts[1]->hTcxEnc->tnsData[k].filter + iFilter;
     234      675853 :                         pTnsParameters[1] = sts[1]->hTcxCfg->pCurrentTnsConfig->pTnsParameters + iFilter;
     235             : 
     236             : #ifdef DEBUGGING
     237             :                         assert( pTnsParameters[0]->startLineFrequency == pTnsParameters[1]->startLineFrequency );
     238             :                         assert( pTnsParameters[0]->nSubdivisions == pTnsParameters[1]->nSubdivisions );
     239             : #endif
     240             :                         /* if prediction gain and avgSqrCoef are both close we are pretty sure the filters are quite similar, use the avg of
     241             :                          * both filters for the decision
     242             :                          */
     243      675853 :                         meanPredictionGain = ( pFilter[0]->predictionGain + pFilter[1]->predictionGain ) * 0.5f;
     244      675853 :                         maxPredictionGain = max( maxPredictionGain, meanPredictionGain );
     245             : 
     246      675853 :                         if ( ( pFilter[0]->predictionGain > pTnsParameters[0]->minPredictionGain ) && ( sts[0]->element_brate < IVAS_80k ) &&
     247       19132 :                              ( pFilter[1]->predictionGain > pTnsParameters[1]->minPredictionGain ) && ( sts[0]->hTcxEnc->tnsData[k].nFilters == sts[1]->hTcxEnc->tnsData[k].nFilters ) )
     248             :                         {
     249       12287 :                             pFilter[0]->predictionGain = pFilter[1]->predictionGain = meanPredictionGain; /* more TNS filter sync at 48kbps */
     250             :                         }
     251      675853 :                         if ( ( fabs( pFilter[0]->predictionGain - pFilter[1]->predictionGain ) < SIMILAR_TNS_THRESHOLD * meanPredictionGain ) &&
     252      455525 :                              ( sts[0]->hTcxEnc->tnsData[k].nFilters == sts[1]->hTcxEnc->tnsData[k].nFilters ) )
     253      455525 :                         {
     254      455525 :                             float maxAvgSqrCoef = max( pFilter[0]->avgSqrCoef, pFilter[1]->avgSqrCoef );
     255      455525 :                             float meanLtpGain = ( sts[0]->hTcxEnc->tcxltp_gain + sts[1]->hTcxEnc->tcxltp_gain ) * 0.5f;
     256      455525 :                             maxPredGain = max( maxPredGain, meanPredictionGain );
     257      455525 :                             if ( ( meanPredictionGain > pTnsParameters[0]->minPredictionGain ) || ( maxAvgSqrCoef > pTnsParameters[0]->minAvgSqrCoef ) )
     258             :                             {
     259       20214 :                                 if ( sts[0]->hTcxEnc->tnsData[k].nFilters > 0 || sts[1]->hTcxEnc->tnsData[k].nFilters > 0 || isTCX10 || meanLtpGain < 0.6f )
     260             :                                 {
     261       19520 :                                     ++sts[0]->hTcxEnc->tnsData[k].nFilters;
     262       19520 :                                     pFilter[0]->filterType = TNS_FILTER_ON;
     263       19520 :                                     ++sts[1]->hTcxEnc->tnsData[k].nFilters;
     264       19520 :                                     pFilter[1]->filterType = TNS_FILTER_ON;
     265             :                                 }
     266             :                                 else
     267             :                                 {
     268         694 :                                     const float maxEnergyChange = ( GetTCXMaxenergyChange( sts[0]->hTranDet, isTCX10, NSUBBLOCKS, 3 ) + GetTCXMaxenergyChange( sts[1]->hTranDet, isTCX10, NSUBBLOCKS, 3 ) ) * 0.5f;
     269             : 
     270         694 :                                     if ( maxEnergyChange >= pTnsParameters[0]->minEnergyChange )
     271             :                                     {
     272         684 :                                         ++sts[0]->hTcxEnc->tnsData[k].nFilters;
     273         684 :                                         pFilter[0]->filterType = TNS_FILTER_ON;
     274         684 :                                         ++sts[1]->hTcxEnc->tnsData[k].nFilters;
     275         684 :                                         pFilter[1]->filterType = TNS_FILTER_ON;
     276             :                                     }
     277             :                                     else
     278             :                                     {
     279          10 :                                         pFilter[0]->filterType = TNS_FILTER_OFF;
     280          10 :                                         pFilter[1]->filterType = TNS_FILTER_OFF;
     281             :                                     }
     282             :                                 }
     283             :                             }
     284      435311 :                             else if ( sts[0]->hTcxEnc->tnsData[k].nFilters > 0 && sts[1]->hTcxEnc->tnsData[k].nFilters > 0 ) /* If a previous filter is turned on */
     285             :                             {
     286        1700 :                                 pFilter[0]->filterType = TNS_FILTER_ON_ZERO;
     287        1700 :                                 pFilter[1]->filterType = TNS_FILTER_ON_ZERO;
     288        1700 :                                 ++sts[0]->hTcxEnc->tnsData[k].nFilters;
     289        1700 :                                 ++sts[1]->hTcxEnc->tnsData[k].nFilters;
     290             :                             }
     291      433611 :                             else if ( sts[0]->hTcxEnc->tnsData[k].nFilters != sts[1]->hTcxEnc->tnsData[k].nFilters ) /* sanity check */
     292             :                             {
     293           0 :                                 assert( 0 );
     294             :                             }
     295             :                             else
     296             :                             {
     297      433611 :                                 pFilter[0]->filterType = TNS_FILTER_OFF;
     298      433611 :                                 pFilter[1]->filterType = TNS_FILTER_OFF;
     299             :                             }
     300      455525 :                             if ( ( pFilter[0]->filterType == TNS_FILTER_ON ) && ( pFilter[1]->filterType == TNS_FILTER_ON ) && ( sts[0]->element_brate < IVAS_80k ) )
     301             :                             {
     302       14883 :                                 int16_t tmpIntValue = 0;
     303             :                                 int16_t tmpCoeff[TNS_MAX_FILTER_ORDER];
     304       14883 :                                 int16_t i, maxOrder = max( pFilter[0]->order, pFilter[1]->order );
     305             : 
     306       14883 :                                 set_s( tmpCoeff, 0, TNS_MAX_FILTER_ORDER );
     307      117052 :                                 for ( i = 0; i < maxOrder; i++ )
     308             :                                 {
     309      102169 :                                     tmpIntValue = (int16_t) max( tmpIntValue, abs( pFilter[0]->coefIndex[i] - pFilter[1]->coefIndex[i] ) );
     310             :                                 }
     311       14883 :                                 if ( tmpIntValue == 1 ) /* the TNS coefficients are sufficiently similar to equalize the two filters */
     312             :                                 {
     313       44736 :                                     for ( i = maxOrder - 1; i >= 0; i-- )
     314             :                                     {
     315       38974 :                                         tmpCoeff[i] = ( abs( pFilter[0]->coefIndex[i] ) < abs( pFilter[1]->coefIndex[i] ) ? pFilter[0]->coefIndex[i] : pFilter[1]->coefIndex[i] );
     316       38974 :                                         if ( ( tmpIntValue > 0 ) && ( tmpCoeff[i] == 0 ) )
     317             :                                         {
     318        8028 :                                             maxOrder--;
     319             :                                         }
     320             :                                         else
     321             :                                         {
     322       30946 :                                             tmpIntValue = 0;
     323             :                                         }
     324             :                                     }
     325             :                                     /* make sure that maxOrder is non zero and not all coefficients are zero (could happen in rare cases) */
     326        5762 :                                     if ( maxOrder > 0 )
     327             :                                     {
     328       51858 :                                         for ( i = TNS_MAX_FILTER_ORDER - 1; i >= 0; i-- )
     329             :                                         {
     330       46096 :                                             pFilter[0]->coefIndex[i] = pFilter[1]->coefIndex[i] = tmpCoeff[i];
     331             :                                         }
     332             : 
     333        5762 :                                         pFilter[0]->order = pFilter[1]->order = maxOrder;
     334             :                                     }
     335             :                                     else
     336             :                                     {
     337           0 :                                         pFilter[0]->filterType = TNS_FILTER_OFF;
     338           0 :                                         pFilter[1]->filterType = TNS_FILTER_OFF;
     339           0 :                                         sts[0]->hTcxEnc->tnsData[k].nFilters = 0;
     340           0 :                                         sts[1]->hTcxEnc->tnsData[k].nFilters = 0;
     341             :                                     }
     342             :                                 }
     343             :                             }
     344             :                         }
     345             :                         else
     346             :                         {
     347      220328 :                             individual_decision[k] = 1;
     348             :                         }
     349             :                     }
     350             : 
     351      359313 :                     if ( individual_decision[k] == 0 )
     352             :                     {
     353      183615 :                         sts[0]->hTcxEnc->fUseTns[k] = ( sts[0]->hTcxEnc->tnsData[k].nFilters > 0 ) ? 1 : 0;
     354      183615 :                         sts[1]->hTcxEnc->fUseTns[k] = ( sts[1]->hTcxEnc->tnsData[k].nFilters > 0 ) ? 1 : 0;
     355             :                     }
     356             :                     else
     357             :                     {
     358      175698 :                         sts[0]->hTcxEnc->tnsData[k].nFilters = 0;
     359      175698 :                         sts[1]->hTcxEnc->tnsData[k].nFilters = 0;
     360      175698 :                         sts[0]->hTcxEnc->fUseTns[k] = 0;
     361      175698 :                         sts[1]->hTcxEnc->fUseTns[k] = 0;
     362      513226 :                         for ( iFilter = sts[0]->hTcxCfg->pCurrentTnsConfig->nMaxFilters - 1; iFilter >= 0; iFilter-- )
     363             :                         {
     364      337528 :                             sts[0]->hTcxEnc->tnsData[k].filter[iFilter].filterType = TNS_FILTER_OFF;
     365      337528 :                             sts[1]->hTcxEnc->tnsData[k].filter[iFilter].filterType = TNS_FILTER_OFF;
     366             :                         }
     367             :                     }
     368             : 
     369      359313 :                     if ( !bWhitenedDomain && individual_decision[k] == 0 && maxPredGain < TNS_GAIN_THRESHOLD_FOR_WHITE && sts[0]->hTcxEnc->transform_type[k] != TCX_5 )
     370             :                     {
     371       87232 :                         sts[0]->hTcxEnc->bTnsOnWhithenedSpectra[k] = 1;
     372       87232 :                         sts[1]->hTcxEnc->bTnsOnWhithenedSpectra[k] = 1;
     373       87232 :                         sts[0]->hTcxEnc->tnsData[k].nFilters = 0;
     374       87232 :                         sts[1]->hTcxEnc->tnsData[k].nFilters = 0;
     375       87232 :                         sts[0]->hTcxEnc->fUseTns[k] = 0;
     376       87232 :                         sts[1]->hTcxEnc->fUseTns[k] = 0;
     377      247585 :                         for ( iFilter = sts[0]->hTcxCfg->pCurrentTnsConfig->nMaxFilters - 1; iFilter >= 0; iFilter-- )
     378             :                         {
     379      160353 :                             ClearTnsFilterCoefficients( sts[0]->hTcxEnc->tnsData[k].filter + iFilter );
     380      160353 :                             ClearTnsFilterCoefficients( sts[1]->hTcxEnc->tnsData[k].filter + iFilter );
     381             :                         }
     382             :                     }
     383      359313 :                     maxPredictionGain = max( maxPredictionGain, maxPredGain );
     384             :                 }
     385             :             }
     386             :         }
     387             :     }
     388             : 
     389             :     /* individual decision for each channel */
     390     6418950 :     for ( ch = 0; ch < CPE_CHANNELS; ch++ )
     391             :     {
     392     4279300 :         if ( sts[ch]->mct_chan_mode == MCT_CHAN_MODE_IGNORE )
     393             :         {
     394      498045 :             continue;
     395             :         }
     396             : 
     397             :         int16_t isTCX10;
     398     3781255 :         isTCX10 = ( sts[ch]->hTcxEnc->tcxMode == TCX_20 ) ? 0 : 1;
     399             : 
     400     3781255 :         nSubframes = ( sts[ch]->hTcxEnc->tcxMode == TCX_20 ) ? 1 : NB_DIV;
     401             : 
     402     7689246 :         for ( k = 0; k < nSubframes; k++ )
     403             :         {
     404     3907991 :             if ( sts[ch]->hTcxCfg->fIsTNSAllowed && ( individual_decision[k] || mct_on ) &&
     405     1684852 :                  ( !bWhitenedDomain || sts[ch]->hTcxEnc->bTnsOnWhithenedSpectra[k] ) )
     406             :             {
     407     3409860 :                 float maxPredGain = -1.0f;
     408             : 
     409     3409860 :                 sts[ch]->hTcxCfg->pCurrentTnsConfig = &sts[ch]->hTcxCfg->tnsConfig[sts[ch]->hTcxEnc->transform_type[k] == TCX_20][( k == 0 ) && ( sts[ch]->last_core == ACELP_CORE )];
     410             : 
     411    10000720 :                 for ( iFilter = sts[ch]->hTcxCfg->pCurrentTnsConfig->nMaxFilters - 1; iFilter >= 0; iFilter-- )
     412             :                 {
     413             :                     STnsFilter *pFilter;
     414             :                     const struct TnsParameters *pTnsParameters;
     415     6590860 :                     pFilter = sts[ch]->hTcxEnc->tnsData[k].filter + iFilter;
     416     6590860 :                     pTnsParameters = sts[ch]->hTcxCfg->pCurrentTnsConfig->pTnsParameters + iFilter;
     417     6590860 :                     maxPredGain = max( maxPredGain, pFilter->predictionGain );
     418             : 
     419     6590860 :                     if ( ( pFilter->predictionGain > pTnsParameters->minPredictionGain ) || ( pFilter->avgSqrCoef > pTnsParameters->minAvgSqrCoef ) )
     420             :                     {
     421      413855 :                         if ( sts[ch]->hTcxEnc->tnsData[k].nFilters > 0 || isTCX10 || sts[ch]->hTcxEnc->tcxltp_gain < 0.6f )
     422             :                         {
     423      375770 :                             ++sts[ch]->hTcxEnc->tnsData[k].nFilters;
     424      375770 :                             pFilter->filterType = TNS_FILTER_ON;
     425             :                         }
     426             :                         else
     427             :                         {
     428       38085 :                             const float maxEnergyChange = GetTCXMaxenergyChange( sts[ch]->hTranDet, isTCX10, NSUBBLOCKS, 3 );
     429             : 
     430       38085 :                             if ( maxEnergyChange >= pTnsParameters->minEnergyChange )
     431             :                             {
     432       35018 :                                 ++sts[ch]->hTcxEnc->tnsData[k].nFilters;
     433       35018 :                                 pFilter->filterType = TNS_FILTER_ON;
     434             :                             }
     435             :                             else
     436             :                             {
     437        3067 :                                 pFilter->filterType = TNS_FILTER_OFF;
     438             :                             }
     439             :                         }
     440             :                     }
     441     6177005 :                     else if ( sts[ch]->hTcxEnc->tnsData[k].nFilters > 0 ) /* If a previous filter is turned on */
     442             :                     {
     443       38483 :                         pFilter->filterType = TNS_FILTER_ON_ZERO;
     444       38483 :                         ++sts[ch]->hTcxEnc->tnsData[k].nFilters;
     445             :                     }
     446             :                     else
     447             :                     {
     448     6138522 :                         pFilter->filterType = TNS_FILTER_OFF;
     449             :                     }
     450             :                 }
     451             : 
     452     3409860 :                 sts[ch]->hTcxEnc->fUseTns[k] = ( sts[ch]->hTcxEnc->tnsData[k].nFilters > 0 ) ? 1 : 0;
     453             : 
     454     3409860 :                 if ( !bWhitenedDomain && maxPredGain < TNS_GAIN_THRESHOLD_FOR_WHITE && sts[ch]->hTcxEnc->transform_type[k] != TCX_5 )
     455             :                 {
     456     1710502 :                     sts[ch]->hTcxEnc->fUseTns[k] = 0;
     457     1710502 :                     sts[ch]->hTcxEnc->bTnsOnWhithenedSpectra[k] = 1;
     458     1710502 :                     sts[ch]->hTcxEnc->tnsData[k].nFilters = 0;
     459     5014417 :                     for ( iFilter = sts[ch]->hTcxCfg->pCurrentTnsConfig->nMaxFilters - 1; iFilter >= 0; iFilter-- )
     460             :                     {
     461     3303915 :                         ClearTnsFilterCoefficients( sts[ch]->hTcxEnc->tnsData[k].filter + iFilter );
     462     3303915 :                         sts[ch]->hTcxEnc->tnsData[k].filter[iFilter].filterType = TNS_FILTER_OFF;
     463             :                     }
     464             :                 }
     465     3409860 :                 maxPredictionGain = max( maxPredictionGain, maxPredGain );
     466             :             }
     467             :         }
     468             :     }
     469             : 
     470             : 
     471             :     /* we have the decision, set filter data accordingly */
     472     6418950 :     for ( ch = 0; ch < CPE_CHANNELS; ch++ )
     473             :     {
     474     4279300 :         if ( sts[ch]->mct_chan_mode == MCT_CHAN_MODE_IGNORE )
     475             :         {
     476      498045 :             continue;
     477             :         }
     478             : 
     479     3781255 :         nSubframes = ( sts[ch]->hTcxEnc->tcxMode == TCX_20 ) ? 1 : NB_DIV;
     480             : 
     481     7689246 :         for ( k = 0; k < nSubframes; k++ )
     482             :         {
     483     3907991 :             if ( sts[ch]->hTcxCfg->fIsTNSAllowed && ( !bWhitenedDomain || sts[ch]->hTcxEnc->bTnsOnWhithenedSpectra[k] ) )
     484             :             {
     485     3777090 :                 sts[ch]->hTcxCfg->pCurrentTnsConfig = &sts[ch]->hTcxCfg->tnsConfig[sts[ch]->hTcxEnc->transform_type[k] == TCX_20][( k == 0 ) && ( sts[ch]->last_core == ACELP_CORE )];
     486             : 
     487    11044600 :                 for ( iFilter = sts[ch]->hTcxCfg->pCurrentTnsConfig->nMaxFilters - 1; iFilter >= 0; iFilter-- )
     488             :                 {
     489             :                     STnsFilter *pFilter;
     490     7267510 :                     pFilter = sts[ch]->hTcxEnc->tnsData[k].filter + iFilter;
     491     7267510 :                     switch ( pFilter->filterType )
     492             :                     {
     493     6934215 :                         case TNS_FILTER_OFF:
     494     6934215 :                             ClearTnsFilterCoefficients( sts[ch]->hTcxEnc->tnsData[k].filter + iFilter );
     495     6934215 :                             break;
     496       30806 :                         case TNS_FILTER_ON_ZERO:
     497             :                             /* Since TNS filter of order 0 is not allowed we have to signal in the stream filter of order 1 with the 0th coefficient equal to 0 */
     498       30806 :                             ClearTnsFilterCoefficients( pFilter );
     499       30806 :                             pFilter->order = 1;
     500       30806 :                             break;
     501             :                     }
     502     7267510 :                 }
     503             :             }
     504             :         }
     505             :     }
     506             : 
     507             :     /* Apply filters, loop over channels */
     508     6418950 :     for ( ch = 0; ch < CPE_CHANNELS; ch++ )
     509             :     {
     510     4279300 :         st = sts[ch];
     511     4279300 :         if ( st->mct_chan_mode == MCT_CHAN_MODE_IGNORE )
     512             :         {
     513      498045 :             continue;
     514             :         }
     515             : 
     516     3781255 :         nSubframes = ( st->hTcxEnc->tcxMode == TCX_20 ) ? 1 : NB_DIV;
     517             : 
     518     7689246 :         for ( k = 0; k < nSubframes; k++ )
     519             :         {
     520     3907991 :             if ( bWhitenedDomain && ( ch > 0 ) && /* test for identical TNS filter data in both channels */
     521      858073 :                  sts[0]->hTcxCfg->fIsTNSAllowed && sts[0]->hTcxEnc->fUseTns[k] &&
     522      102742 :                  sts[1]->hTcxCfg->fIsTNSAllowed && sts[1]->hTcxEnc->fUseTns[k] )
     523             :             {
     524      166904 :                 int16_t equalFilterData = ( sts[0]->hTcxCfg->pCurrentTnsConfig->nMaxFilters == sts[1]->hTcxCfg->pCurrentTnsConfig->nMaxFilters &&
     525       55582 :                                             sts[0]->hTcxEnc->bTnsOnWhithenedSpectra[k] == sts[1]->hTcxEnc->bTnsOnWhithenedSpectra[k] &&
     526       49465 :                                             sts[0]->hTcxEnc->tnsData[k].nFilters == sts[1]->hTcxEnc->tnsData[k].nFilters )
     527             :                                               ? 1
     528      111243 :                                               : 0;
     529       55661 :                 if ( equalFilterData )
     530             :                 {
     531       90706 :                     for ( iFilter = st->hTcxCfg->pCurrentTnsConfig->nMaxFilters - 1; iFilter >= 0; iFilter-- )
     532             :                     {
     533       78146 :                         const int16_t *pDataCh0 = (const int16_t *) &sts[0]->hTcxEnc->tnsData[k].filter[iFilter];
     534       78146 :                         const int16_t *pDataCh1 = (const int16_t *) &sts[1]->hTcxEnc->tnsData[k].filter[iFilter];
     535       78146 :                         int16_t i = 2 + TNS_MAX_FILTER_ORDER; /* excl. informative float data. Portable? */
     536             : 
     537      660657 :                         while ( ( i >= 0 ) && ( pDataCh0[i] == pDataCh1[i] ) )
     538             :                         {
     539      582511 :                             i--;
     540             :                         }
     541       78146 :                         if ( i >= 0 )
     542             :                         {
     543       31329 :                             equalFilterData = 0;
     544       31329 :                             break;
     545             :                         }
     546             :                     }
     547       43889 :                     if ( equalFilterData )
     548             :                     {
     549       12560 :                         st->hTcxEnc->tnsData[k].nFilters *= -1; /* signals common TNS */
     550             :                     }
     551             :                 }
     552             :             }
     553     3907991 :             if ( st->hTcxCfg->fIsTNSAllowed && ( !bWhitenedDomain || st->hTcxEnc->bTnsOnWhithenedSpectra[k] ) )
     554             :             {
     555     3777090 :                 L_spec = st->hTcxCfg->pCurrentTnsConfig->iFilterBorders[0];
     556     3777090 :                 spectrum = st->hTcxEnc->spectrum[k];
     557             :                 /* If TNS should be used then get the residual after applying it inplace in the spectrum */
     558     3777090 :                 if ( st->hTcxEnc->fUseTns[k] )
     559             :                 {
     560      250549 :                     st->hTcxCfg->pCurrentTnsConfig = &st->hTcxCfg->tnsConfig[st->hTcxEnc->transform_type[k] == TCX_20][( k == 0 ) && ( st->last_core == ACELP_CORE )];
     561             : 
     562      250549 :                     ApplyTnsFilter( st->hTcxCfg->pCurrentTnsConfig, &st->hTcxEnc->tnsData[k], spectrum, 1 );
     563             :                 }
     564             : 
     565     3777090 :                 if ( st->hTcxEnc->transform_type[k] == TCX_5 )
     566             :                 {
     567       64148 :                     tcx5TnsUngrouping( L_frame >> 2, L_spec >> 1, st->hTcxEnc->spectrum[k], ENC );
     568             :                 }
     569             : 
     570     3777090 :                 st->hTcxEnc->tnsData[k].tnsOnWhitenedSpectra = st->hTcxEnc->bTnsOnWhithenedSpectra[k];
     571             : 
     572     3777090 :                 EncodeTnsData( st->hTcxCfg->pCurrentTnsConfig, &st->hTcxEnc->tnsData[k], param_core[ch] + k * NPRM_DIV + 1 + NOISE_FILL_RANGES + LTPSIZE, tnsSize[ch] + k, tnsBits[ch] + k );
     573             :             }
     574             : 
     575     3907991 :             if ( st->hTcxEnc->transform_type[k] == TCX_5 )
     576             :             {
     577      128296 :                 tcx5SpectrumInterleaving( st->hTcxCfg->tcx5SizeFB, st->hTcxEnc->spectrum[k] );
     578      128296 :                 tcx5SpectrumInterleaving( st->hTcxCfg->tcx5SizeFB, mdst_spectrum[ch][k] );
     579             :             }
     580             :         }
     581             :     }
     582             : 
     583     2139650 :     return;
     584             : }
     585             : 
     586             : 
     587             : /*-------------------------------------------------------------------*
     588             :  * TNSAnalysis()
     589             :  *
     590             :  *
     591             :  *-------------------------------------------------------------------*/
     592             : 
     593      471614 : void TNSAnalysis(
     594             :     TCX_CONFIG_HANDLE hTcxCfg,    /* i  : configuration of TCX                                                                    */
     595             :     const int16_t L_frame,        /* i  : frame length                                                                            */
     596             :     int16_t L_spec,               /* i  : length of the spectrum                                                                  */
     597             :     const int16_t transform_type, /* i  : transform type for the frame/subframe - TCX20 | TCX10 | TCX 5 (meaning 2 x TCX 5)       */
     598             :     const int16_t isAfterACELP,   /* i  : Flag indicating if the last frame was ACELP. For the second TCX subframe it should be 0 */
     599             :     float spectrum[],             /* i  : MDCT spectrum of the subframe                                                           */
     600             :     TRAN_DET_HANDLE hTranDet,     /* i  : handle transient detection                                                              */
     601             :     const float ltp_gain,         /* i  : ltp gain                                                                                */
     602             :     STnsData *pTnsData,           /* o  : TNS data                                                                                */
     603             :     int16_t *pfUseTns,            /* o  : Flag indicating if TNS is used                                                          */
     604             :     float *predictionGain         /* o  : TNS prediction gain                                                                     */
     605             : )
     606             : {
     607             :     float buff[8]; /* Buffer for the rearrangement of LF TCX5 */
     608             : 
     609             :     /* Init TNS */
     610      471614 :     *pfUseTns = 0;
     611             : 
     612      471614 :     if ( hTcxCfg->fIsTNSAllowed )
     613             :     {
     614      337459 :         hTcxCfg->pCurrentTnsConfig = &hTcxCfg->tnsConfig[transform_type == TCX_20][isAfterACELP];
     615      337459 :         L_spec = hTcxCfg->pCurrentTnsConfig->iFilterBorders[0];
     616             : 
     617             :         /*-----------------------------------------------------------*
     618             :          * Temporal Noise Shaping analysis                           *
     619             :          *-----------------------------------------------------------*/
     620             : 
     621      337459 :         if ( transform_type == TCX_5 )
     622             :         {
     623             :             /* rearrange LF sub-window lines prior to TNS analysis & filtering */
     624        3798 :             if ( L_spec < L_frame / 2 )
     625             :             {
     626        2756 :                 mvr2r( spectrum + 8, spectrum + 16, L_spec / 2 - 8 );
     627        2756 :                 mvr2r( spectrum + L_frame / 4, spectrum + 8, 8 );
     628        2756 :                 mvr2r( spectrum + L_frame / 4 + 8, spectrum + L_spec / 2 + 8, L_spec / 2 - 8 );
     629             :             }
     630             :             else
     631             :             {
     632        1042 :                 mvr2r( spectrum + L_frame / 4, buff, 8 );
     633        1042 :                 mvr2r( spectrum + 8, spectrum + 16, L_frame / 4 - 8 );
     634        1042 :                 mvr2r( buff, spectrum + 8, 8 );
     635             :             }
     636             :         }
     637             : 
     638      337459 :         *pfUseTns = DetectTnsFilt( hTcxCfg->pCurrentTnsConfig, spectrum, hTranDet, transform_type != TCX_20, ltp_gain, pTnsData, predictionGain );
     639             : 
     640             : 
     641             :         /* If TNS should be used then get the residual after applying it inplace in the spectrum */
     642      337459 :         if ( *pfUseTns )
     643             :         {
     644       33895 :             ApplyTnsFilter( hTcxCfg->pCurrentTnsConfig, pTnsData, spectrum, 1 );
     645             :         }
     646             : 
     647      337459 :         if ( transform_type == TCX_5 )
     648             :         {
     649             :             /* undo rearrangement of LF sub-window lines prior to TNS analysis */
     650        3798 :             if ( L_spec < L_frame / 2 )
     651             :             {
     652        2756 :                 mvr2r( spectrum + L_spec / 2 + 8, spectrum + L_frame / 4 + 8, L_spec / 2 - 8 );
     653        2756 :                 mvr2r( spectrum + 8, spectrum + L_frame / 4, 8 );
     654        2756 :                 mvr2r( spectrum + 16, spectrum + 8, L_spec / 2 - 8 );
     655        2756 :                 set_zero( spectrum + L_spec / 2, L_frame / 4 - L_spec / 2 );
     656        2756 :                 set_zero( spectrum + L_frame / 4 + L_spec / 2, L_frame / 4 - L_spec / 2 );
     657             :             }
     658             :             else
     659             :             {
     660        1042 :                 mvr2r( spectrum + 8, buff, 8 );
     661        1042 :                 mvr2r( spectrum + 16, spectrum + 8, L_frame / 4 - 8 );
     662        1042 :                 mvr2r( buff, spectrum + L_frame / 4, 8 );
     663             :             }
     664             :         }
     665             :     }
     666             : 
     667      471614 :     return;
     668             : }
     669             : 
     670             : 
     671             : /*-------------------------------------------------------------------*
     672             :  * ShapeSpectrum()
     673             :  *
     674             :  *
     675             :  *-------------------------------------------------------------------*/
     676             : 
     677     4004550 : void ShapeSpectrum(
     678             :     TCX_CONFIG_HANDLE hTcxCfg,  /* i  : configuration of TCX                */
     679             :     const float A[],            /* i  : quantized coefficients NxAz_q[M+1]  */
     680             :     float gainlpc[],            /* o  : MDCT gains for the previous frame   */
     681             :     const int16_t L_frame_glob, /* i  : frame length                        */
     682             :     int16_t L_spec,             /* i  : length of the spectrum              */
     683             :     float spectrum[],           /* i/o: MDCT spectrum                       */
     684             :     const int16_t fUseTns,      /* i  : Flag indicating if TNS is used      */
     685             :     Encoder_State *st,          /* i/o: encoder state structure             */
     686             :     float *scf                  /* i  : scale factors                       */
     687             : )
     688             : {
     689     4004550 :     TCX_ENC_HANDLE hTcxEnc = st->hTcxEnc;
     690             :     int16_t i, sf_width, L_frame, tcx_offset;
     691             :     float Ap[M + 2];
     692             :     float tmp, gamma1;
     693     4004550 :     float max_low_pre = 0.f, max_high_pre = 0.f;
     694             :     float sns_int_scf[FDNS_NPTS];
     695     4004550 :     int32_t total_brate = ( st->element_mode == IVAS_CPE_MDCT ? st->element_brate : st->total_brate );
     696             :     /*-----------------------------------------------------------*
     697             :      * Init                                                      *
     698             :      *-----------------------------------------------------------*/
     699             : 
     700             :     /* Init lengths */
     701     4004550 :     L_frame = L_frame_glob;
     702     4004550 :     tcx_offset = hTcxCfg->tcx_offset;
     703             : 
     704     4004550 :     gamma1 = st->gamma;
     705     4004550 :     if ( st->enableTcxLpc )
     706             :     {
     707       36218 :         gamma1 = 1.0f;
     708             :     }
     709             : 
     710     4004550 :     if ( st->element_mode != IVAS_CPE_MDCT ) /* in MDCT, this is already done outside the function */
     711             :     {
     712      472513 :         if ( st->last_core == ACELP_CORE )
     713             :         {
     714       17278 :             L_frame += tcx_offset;
     715       17278 :             L_spec += hTcxCfg->tcx_coded_lines >> 2;
     716       17278 :             if ( hTcxCfg->lfacNext < 0 )
     717             :             {
     718       17278 :                 L_frame -= hTcxCfg->lfacNext;
     719             :             }
     720             :         }
     721             :     }
     722             : 
     723     4004550 :     tcxGetNoiseFillingTilt( A, L_frame, ( total_brate >= ACELP_13k20 && !st->rf_mode ), &st->hTcxEnc->noiseTiltFactor );
     724             : 
     725             :     /* Calculate Spectrum Flatness Measure for the TCX Concealment */
     726     4004550 :     if ( st->enablePlcWaveadjust )
     727             :     {
     728        2500 :         hTcxCfg->SFM2 = SFM_Cal( spectrum, min( 200, L_frame ) );
     729             :     }
     730             : 
     731     4004550 :     if ( ( total_brate <= ACELP_13k20 && st->bwidth == SWB ) )
     732             :     {
     733       50334 :         max_low_pre = 0.f;
     734    13181598 :         for ( i = 0; i < L_frame; i++ )
     735             :         {
     736    13131264 :             tmp = fabsf( spectrum[i] );
     737    13131264 :             if ( tmp > max_low_pre )
     738             :             {
     739      260594 :                 max_low_pre = tmp;
     740             :             }
     741             :         }
     742             : 
     743       50334 :         max_high_pre = 0.f;
     744    19747230 :         for ( i = 0; i < L_spec - L_frame; i++ )
     745             :         {
     746    19696896 :             tmp = fabsf( spectrum[L_frame + i] );
     747    19696896 :             if ( tmp > max_high_pre )
     748             :             {
     749       19497 :                 max_high_pre = tmp;
     750             :             }
     751             :         }
     752             :     }
     753             : 
     754     4004550 :     if ( st->element_mode == IVAS_CPE_MDCT )
     755             :     {
     756     3532037 :         sns_interpolate_scalefactors( &sns_int_scf[0], scf, ENC );
     757     3532037 :         sns_shape_spectrum( spectrum, st->hTcxCfg->psychParamsCurrent, &sns_int_scf[0], L_frame );
     758     3532037 :         v_multc( spectrum + L_frame, sns_int_scf[hTcxCfg->psychParamsCurrent->nBands - 1], spectrum + L_frame, L_spec - L_frame );
     759             :     }
     760             :     else
     761             :     {
     762             :         /*-----------------------------------------------------------*
     763             :          * Pre-shaping in frequency domain using weighted LPC (Wz)   *
     764             :          *-----------------------------------------------------------*/
     765             : 
     766      472513 :         weight_a( A, Ap, gamma1, M );
     767             : 
     768      472513 :         lpc2mdct( Ap, M, gainlpc, FDNS_NPTS, 0 );
     769             : 
     770      472513 :         mdct_preShaping( spectrum, L_frame, gainlpc );
     771             : 
     772      472513 :         v_multc( spectrum + L_frame, 1.f / gainlpc[FDNS_NPTS - 1], spectrum + L_frame, L_spec - L_frame );
     773             :     }
     774             : 
     775             :     /* reduce the peaks in the IGF region, to make life of the core-coder easier... */
     776     4004550 :     if ( total_brate <= ACELP_13k20 && st->bwidth == SWB )
     777             :     {
     778             :         int16_t dist_low, dist_high;
     779             :         float max_fac;
     780             :         float max_low, max_low1, max_low2, max_high;
     781             : 
     782       50334 :         if ( hTcxEnc->tcx_lpc_shaped_ari )
     783             :         {
     784       22839 :             max_fac = 1.5f;
     785             :         }
     786             :         else
     787             :         {
     788       27495 :             max_fac = 3.f;
     789             :         }
     790             : 
     791       50334 :         sf_width = L_frame / 2;
     792             : 
     793       50334 :         max_low2 = 0.f;
     794       50334 :         dist_low = 0;
     795     6615966 :         for ( i = 0; i < sf_width; i++ )
     796             :         {
     797     6565632 :             tmp = fabsf( spectrum[L_frame - 1 - i] );
     798     6565632 :             if ( tmp > max_low2 )
     799             :             {
     800      303481 :                 max_low2 = tmp;
     801      303481 :                 dist_low = i;
     802             :             }
     803             :         }
     804             : 
     805       50334 :         max_low1 = 0.f;
     806     6615966 :         for ( i = 0; i < L_frame - sf_width; i++ )
     807             :         {
     808     6565632 :             tmp = fabsf( spectrum[L_frame - sf_width - 1 - i] );
     809     6565632 :             if ( tmp > max_low1 )
     810             :             {
     811      462909 :                 max_low1 = tmp;
     812             :             }
     813     6565632 :             if ( tmp > max_low2 )
     814             :             {
     815      861931 :                 dist_low = sf_width + i;
     816             :             }
     817             :         }
     818             : 
     819       50334 :         max_low = max( max_low1, max_low2 );
     820             : 
     821       50334 :         max_high = 0.f;
     822       50334 :         dist_high = 0;
     823    19747230 :         for ( i = 0; i < L_spec - L_frame; i++ )
     824             :         {
     825    19696896 :             tmp = fabsf( spectrum[L_frame + i] );
     826    19696896 :             if ( tmp > max_high )
     827             :             {
     828       19497 :                 max_high = tmp;
     829       19497 :                 dist_high = i;
     830             :             }
     831             :         }
     832             : 
     833       50334 :         if ( ( 4.f * dist_high * max_high > dist_low * max_low ) && ( 16.f * max_low_pre > max_high_pre ) && ( max_high > max_fac * max_low2 ) )
     834             :         {
     835        1142 :             tmp = max_fac * max_low2 / max_high;
     836        1142 :             v_multc( spectrum + L_frame, tmp, spectrum + L_frame, L_spec - L_frame );
     837             :         }
     838             :     }
     839             : 
     840     4004550 :     if ( st->element_mode != IVAS_CPE_MDCT && st->tcxonly && st->hTcxEnc->tcxltp && ( st->hTcxEnc->tcxltp_gain > 0.0f ) && !fUseTns )
     841             :     {
     842       28704 :         PsychAdaptLowFreqEmph( spectrum, gainlpc );
     843             :     }
     844             : 
     845     4004550 :     return;
     846             : }
     847             : 
     848             : 
     849             : /*-------------------------------------------------------------------*
     850             :  * GetTransWidth()
     851             :  *
     852             :  *
     853             :  *-------------------------------------------------------------------*/
     854             : 
     855     2628820 : static int16_t GetTransWidth(
     856             :     const int16_t tcxonly,
     857             :     const int16_t tcx10,
     858             :     const float tcxltp_gain,
     859             :     const int16_t hm_active )
     860             : {
     861     2628820 :     int16_t noiseTransWidth = MIN_NOISE_FILLING_HOLE;
     862             : 
     863     2628820 :     if ( tcxonly )
     864             :     {
     865     2116450 :         noiseTransWidth = HOLE_SIZE_FROM_LTP( max( tcxltp_gain, 0.3125f * hm_active ) );
     866             : 
     867     2116450 :         if ( tcx10 )
     868             :         {
     869      117294 :             noiseTransWidth = 3; /* minimum transition for noise filling in TCX-10 */
     870             :         }
     871             :     }
     872             : 
     873     2628820 :     return noiseTransWidth;
     874             : }
     875             : 
     876             : 
     877             : /*-----------------------------------------------------------*
     878             :  * EstimateTCXNoiseLevel()
     879             :  *
     880             :  * Estimate and quantize noise factor                        *
     881             :  *-----------------------------------------------------------*/
     882             : 
     883      472513 : static void EstimateTCXNoiseLevel(
     884             :     Encoder_State *st,                /* i  : encoder state handle                            */
     885             :     const float x_orig[],             /* i  : shaped MDCT spectrum                            */
     886             :     float spectrum[],                 /* i/o: quantized MDCT spectrum                         */
     887             :     const float gain_tcx,             /* i  : global gain                                     */
     888             :     const int16_t L_frame,            /* i  : frame length                                    */
     889             :     const int16_t noiseFillingBorder, /* i  : noise filling border                            */
     890             :     const int16_t hm_active,          /* i  : flag indicating if the harmonic model is active */
     891             :     float *fac_ns,                    /* o  : noise filling level                             */
     892             :     int16_t *fac_ns_q                 /* o  : quantized noise filling level                   */
     893             : )
     894             : {
     895             :     int16_t maxNfCalcBw, iStart, noiseTransWidth;
     896      472513 :     TCX_ENC_HANDLE hTcxEnc = st->hTcxEnc;
     897             : 
     898      472513 :     maxNfCalcBw = min( noiseFillingBorder, (int16_t) ( hTcxEnc->measuredBwRatio * (float) L_frame + 0.5f ) );
     899             : 
     900      472513 :     if ( st->total_brate >= HQ_96k )
     901             :     {
     902       49933 :         *fac_ns = 0.0f;
     903       49933 :         *fac_ns_q = 0;
     904             :     }
     905             :     else
     906             :     {
     907      422580 :         const int16_t minLevel = ( hTcxEnc->tcx_lpc_shaped_ari && st->element_mode > IVAS_SCE ? 0 : 1 );
     908      422580 :         iStart = L_frame / ( ( st->total_brate >= ACELP_13k20 && !st->rf_mode ) ? 6 : 8 ); /* noise filling start bin*/
     909      422580 :         noiseTransWidth = GetTransWidth( st->tcxonly, ( L_frame == st->L_frame >> 1 ), st->hTcxEnc->tcxltp_gain, ( st->hTcxCfg->ctx_hm && st->last_core != ACELP_CORE && hm_active ) );
     910      422580 :         tcx_noise_factor( x_orig, spectrum, iStart, maxNfCalcBw, noiseTransWidth, L_frame, gain_tcx, hTcxEnc->noiseTiltFactor, fac_ns, fac_ns_q, st->element_mode );
     911             : 
     912             :         /* hysteresis for very tonal passages (more stationary noise filling level) */
     913      422580 :         if ( *fac_ns_q == minLevel )
     914             :         {
     915       32657 :             hTcxEnc->noiseLevelMemory_cnt = (int16_t) min( INT16_MAX, 1 + abs( hTcxEnc->noiseLevelMemory_cnt ) ); /* update counter */
     916             :         }
     917             :         else
     918             :         {
     919      389923 :             if ( ( *fac_ns_q == minLevel + 1 ) && ( abs( hTcxEnc->noiseLevelMemory_cnt ) > 5 ) )
     920             :             {
     921        1075 :                 *fac_ns_q = minLevel; /* reduce noise filling level by one step */
     922        1075 :                 *fac_ns = minLevel * 0.75f / ( 1 << NBITS_NOISE_FILL_LEVEL );
     923             : 
     924             :                 /* signal that noise level is changed by inverting sign of level memory */
     925        1075 :                 hTcxEnc->noiseLevelMemory_cnt = ( hTcxEnc->noiseLevelMemory_cnt < 0 ) ? 5 : -1 - hTcxEnc->noiseLevelMemory_cnt;
     926             :             }
     927             :             else
     928             :             {
     929      388848 :                 hTcxEnc->noiseLevelMemory_cnt = 0; /* reset memory since level is too different */
     930             :             }
     931             :         }
     932             :     } /* bitrate */
     933             : 
     934      472513 :     return;
     935             : }
     936             : 
     937             : 
     938             : /*-----------------------------------------------------------*
     939             :  * EstimateStereoTCXNoiseLevel()
     940             :  *
     941             :  * Estimate and quantize stereo noise factors
     942             :  *-----------------------------------------------------------*/
     943             : 
     944     1069825 : void EstimateStereoTCXNoiseLevel(
     945             :     Encoder_State **sts,                     /* i  : state handle                                    */
     946             :     float *q_spectrum[CPE_CHANNELS][NB_DIV], /* i  : quantized MDCT spectrum                         */
     947             :     float gain_tcx[][NB_DIV],                /* i  : global gain                                     */
     948             :     int16_t L_frame[][NB_DIV],               /* i  : frame length                                    */
     949             :     int16_t noiseFillingBorder[][NB_DIV],    /* i  : noise filling border                            */
     950             :     int16_t hm_active[][NB_DIV],             /* i  : flag indicating if the harmonic model is active */
     951             :     const int16_t ignore_chan[],             /* i  : flag indicating whether the channel should be ignored */
     952             :     float fac_ns[][NB_DIV],                  /* o  : noise filling level                             */
     953             :     int16_t param_core[][NB_DIV * NPRM_DIV], /* o  : quantized noise filling level                   */
     954             :     const int16_t MCT_flag                   /* i  : hMCT handle allocated (1) or not (0)            */
     955             : )
     956             : {
     957             :     int16_t ch, n;
     958             :     int16_t nSubframes, maxNfCalcBw, iStart, noiseTransWidth;
     959             :     float smooth_gain;
     960             :     float combined_q_spectrum[N_MAX];
     961             :     int16_t *fac_ns_q;
     962             :     int32_t total_brate;
     963             : 
     964     3209475 :     for ( ch = 0; ch < CPE_CHANNELS; ch++ )
     965             :     {
     966     2139650 :         Encoder_State *st = sts[ch];
     967     2139650 :         TCX_ENC_HANDLE hTcxEnc = st->hTcxEnc;
     968             : 
     969     2139650 :         nSubframes = ( st->hTcxEnc->tcxMode == TCX_20 ) ? 1 : NB_DIV;
     970             : 
     971     2139650 :         if ( ignore_chan[ch] )
     972             :         {
     973      308673 :             continue;
     974             :         }
     975     1830977 :         total_brate = ( st->element_mode == IVAS_CPE_MDCT && !MCT_flag ) ? st->element_brate : st->total_brate;
     976             : 
     977     3725322 :         for ( n = 0; n < nSubframes; n++ )
     978             :         {
     979     1894345 :             fac_ns_q = param_core[ch] + n * NPRM_DIV + 1;
     980     1894345 :             maxNfCalcBw = min( noiseFillingBorder[ch][n], (int16_t) ( hTcxEnc->measuredBwRatio * (float) L_frame[ch][n] + 0.5f ) );
     981     1894345 :             if ( ( total_brate >= HQ_96k && ( st->element_mode <= IVAS_SCE || st->bwidth < SWB ) ) || total_brate > IVAS_192k )
     982             :             {
     983       89229 :                 fac_ns[ch][n] = 0.0f;
     984       89229 :                 *fac_ns_q = 0;
     985             :             }
     986             :             else
     987             :             {
     988     1805116 :                 iStart = L_frame[ch][n] / ( ( total_brate >= ACELP_13k20 && !st->rf_mode ) ? 6 : 8 ); /* noise filling start bin*/
     989             : 
     990     1805116 :                 if ( n == 0 )
     991             :                 {
     992     1751274 :                     mvr2r( hTcxEnc->ltpGainMemory, &hTcxEnc->ltpGainMemory[1], N_LTP_GAIN_MEMS - 1 );
     993     1751274 :                     hTcxEnc->ltpGainMemory[0] = st->hTcxEnc->tcxltp_gain;
     994             :                 }
     995             : 
     996     1805116 :                 smooth_gain = dotp( hTcxEnc->ltpGainMemory, nf_tw_smoothing_coeffs, N_LTP_GAIN_MEMS );
     997             : 
     998     1805116 :                 noiseTransWidth = GetTransWidth( st->tcxonly, ( L_frame[ch][n] == st->L_frame >> 1 ), smooth_gain, ( st->hTcxCfg->ctx_hm && st->last_core != ACELP_CORE && hm_active[ch][n] ) );
     999             : 
    1000     1805116 :                 mvr2r( q_spectrum[ch][n], combined_q_spectrum, L_frame[ch][n] );
    1001     1805116 :                 tcx_noise_factor( hTcxEnc->spectrum[n], combined_q_spectrum, iStart, maxNfCalcBw, noiseTransWidth, L_frame[ch][n], gain_tcx[ch][n], hTcxEnc->noiseTiltFactor, &fac_ns[ch][n], fac_ns_q, st->element_mode );
    1002             : 
    1003             :                 /* hysteresis for very tonal passages (more stationary noise filling level) */
    1004     1805116 :                 if ( *fac_ns_q == 1 )
    1005             :                 {
    1006      211268 :                     hTcxEnc->noiseLevelMemory_cnt = (int16_t) min( INT16_MAX, 1 + abs( hTcxEnc->noiseLevelMemory_cnt ) ); /* update counter */
    1007             :                 }
    1008             :                 else
    1009             :                 {
    1010     1593848 :                     if ( ( *fac_ns_q == 2 ) && ( abs( hTcxEnc->noiseLevelMemory_cnt ) > 5 ) )
    1011             :                     {
    1012       14062 :                         *fac_ns_q = 1; /* reduce noise filling level by one step */
    1013       14062 :                         fac_ns[ch][n] = 0.75f / ( 1 << NBITS_NOISE_FILL_LEVEL );
    1014             : 
    1015             :                         /* signal that noise level is changed by inverting sign of level memory */
    1016       14062 :                         hTcxEnc->noiseLevelMemory_cnt = ( hTcxEnc->noiseLevelMemory_cnt < 0 ) ? 5 : -1 - hTcxEnc->noiseLevelMemory_cnt;
    1017             :                     }
    1018             :                     else
    1019             :                     {
    1020     1579786 :                         hTcxEnc->noiseLevelMemory_cnt = 0; /* reset memory since level is too different */
    1021             :                     }
    1022             :                 }
    1023             :             } /* bitrate */
    1024             :         }
    1025             : #ifdef DEBUG_MODE_MDCT
    1026             :         dbgwrite( &smooth_gain, sizeof( float ), 1, 1, "./res/smooth_gain" );
    1027             :         dbgwrite( &st->hTcxEnc->tcxltp_gain, sizeof( float ), 1, 1, "./res/tcxltp_gain" );
    1028             :         dbgwrite( &noiseTransWidth, sizeof( int16_t ), 1, 1, "./res/noiseTrans" );
    1029             :         dbgwrite( &fac_ns[ch][0], sizeof( float ), 2, 1, "./res/fac_ns" );
    1030             : #endif
    1031             :     }
    1032             : 
    1033     1069825 :     return;
    1034             : }
    1035             : 
    1036             : 
    1037             : /*-----------------------------------------------------------*
    1038             :  * DecideTonalSideInfo()
    1039             :  *
    1040             :  *
    1041             :  *-----------------------------------------------------------*/
    1042             : 
    1043        2500 : static int16_t DecideTonalSideInfo(
    1044             :     const float spectrum[],
    1045             :     const int16_t L_frame_glob,
    1046             :     float SFM2 )
    1047             : {
    1048             :     float SFM, K, K2;
    1049             :     int16_t Tonal_SideInfo;
    1050             : 
    1051        2500 :     SFM = SFM_Cal( spectrum, min( 200, L_frame_glob ) );
    1052             : 
    1053        2500 :     if ( L_frame_glob <= 256 )
    1054             :     {
    1055         104 :         K = 0.4f;
    1056         104 :         K2 = 0.1f;
    1057             :     }
    1058        2396 :     else if ( L_frame_glob == 320 || L_frame_glob == 512 )
    1059             :     {
    1060        1324 :         K = 0.4f;
    1061        1324 :         K2 = 0.1f;
    1062             :     }
    1063             :     else /*FrameSize_Core == 640*/
    1064             :     {
    1065        1072 :         K = 0.35f;
    1066        1072 :         K2 = 0.04f;
    1067             :     }
    1068             : 
    1069             : 
    1070        2500 :     Tonal_SideInfo = 0;
    1071        2500 :     if ( SFM < K )
    1072             :     {
    1073        1056 :         Tonal_SideInfo = 1;
    1074             :     }
    1075             : 
    1076        2500 :     if ( SFM2 < K2 )
    1077             :     {
    1078           8 :         Tonal_SideInfo = 1;
    1079             :     }
    1080             : 
    1081        2500 :     return Tonal_SideInfo;
    1082             : }
    1083             : 
    1084             : /*-----------------------------------------------------------*
    1085             :  * QuantizeTCXSpectrum()
    1086             :  *
    1087             :  *
    1088             :  *-----------------------------------------------------------*/
    1089             : 
    1090     2366858 : void QuantizeTCXSpectrum(
    1091             :     Encoder_State *st,            /* i  : state handle                            */
    1092             :     const int16_t frame_cnt,      /* i  : frame counter in the super_frame        */
    1093             :     const float *x_orig,          /* i  : shaped MDCT spectrum                    */
    1094             :     const float *gainlpc,         /* i  : FDNS gains                              */
    1095             :     const Word16 *Aqind,          /* i  : frame-independent quantized coefficients (M+1) */
    1096             :     const int16_t tnsSize,        /* i  : number of tns parameters put into prm   */
    1097             :     const int16_t nb_bits,        /* i  : bit budget                              */
    1098             :     const int16_t vad_hover_flag, /* i  : VAD hangover flag */
    1099             :     int16_t *pL_frameTCX,         /* o  : full frame length                       */
    1100             :     int16_t *pL_frame,            /* o  : frame length                            */
    1101             :     int16_t *pL_spec,             /* o  : length of the coded spectrum            */
    1102             :     int16_t *ptcx_offset,         /* o  : folding point offset relative to the end of the previous frame */
    1103             :     int16_t *pnoiseFillingBorder, /* o  : noise filling border                    */
    1104             :     float spectrum[],             /* o  : quantized MDCT spectrum                 */
    1105             :     CONTEXT_HM_CONFIG *hm_cfg,    /* o  : Context-based harmonic model configuration */
    1106             :     int16_t *hm_active,           /* o  : flag indicating if the harmonic model is active */
    1107             :     float lf_deemph_fact[],       /* o  : low frequency deemphasis factors        */
    1108             :     int16_t *nf_seed,             /* o  : noise filling random seed               */
    1109             :     float *ener,                  /* o  : energy of the quantized spectrum        */
    1110             :     float *gain_tcx,              /* o  : global gain                             */
    1111             :     int16_t prm[]                 /* o  : tcx parameters                          */
    1112             : )
    1113             : {
    1114     2366858 :     TCX_ENC_HANDLE hTcxEnc = st->hTcxEnc;
    1115             :     int16_t i, L_frame, L_frameTCX, L_spec, tcx_offset;
    1116             :     int16_t noiseFillingBorder, LtpPitchLag, PeriodicityIndex;
    1117             :     float sqGain, gain_tcx_opt, RelativeScore;
    1118             :     int16_t lastnzCtxHm, lastnz;
    1119             :     int16_t stop;
    1120             :     int16_t nEncodedCtxHm, stopCtxHm, sqBitsCtxHm, Selector;
    1121             :     int16_t nEncoded, sqBits_noStop;
    1122             :     int16_t NumIndexBits, signaling_bits, sqTargetBits, sqBits, ctxHmBits, resQBits, resQTargetBits;
    1123             :     int16_t *prm_ltp, *prm_tns, *prm_hm, *prm_lastnz, *sqQ, *prm_target;
    1124             :     float att;
    1125             :     int32_t total_brate;
    1126             : 
    1127             :     /*-----------------------------------------------------------*
    1128             :      * Init                                                      *
    1129             :      *-----------------------------------------------------------*/
    1130             : 
    1131     2366858 :     sqGain = 1.0f;
    1132     2366858 :     resQTargetBits = 0;
    1133             : 
    1134     2366858 :     NumIndexBits = 0;
    1135     2366858 :     sqBits = 0;
    1136     2366858 :     ctxHmBits = 0;
    1137     2366858 :     resQBits = 0;
    1138     2366858 :     prm_ltp = &prm[1 + NOISE_FILL_RANGES];
    1139     2366858 :     prm_tns = prm_ltp + LTPSIZE;
    1140     2366858 :     prm_hm = prm_tns + tnsSize;
    1141     2366858 :     prm_lastnz = prm_hm + 2;
    1142     2366858 :     sqQ = prm_hm + NPRM_CTX_HM;
    1143             : 
    1144     2366858 :     total_brate = ( st->element_mode == IVAS_CPE_MDCT ) ? st->element_brate : st->total_brate;
    1145             : 
    1146             :     /*-----------------------------------------------------------*
    1147             :      * Init lengths                                              *
    1148             :      *-----------------------------------------------------------*/
    1149             : 
    1150     2366858 :     L_frame = st->L_frame;
    1151     2366858 :     L_frameTCX = hTcxEnc->L_frameTCX;
    1152     2366858 :     L_spec = st->hTcxCfg->tcx_coded_lines;
    1153     2366858 :     tcx_offset = st->hTcxCfg->tcx_offset;
    1154             : 
    1155     2366858 :     if ( st->core == TCX_10_CORE )
    1156             :     {
    1157      134020 :         L_frame /= 2;
    1158      134020 :         L_frameTCX /= 2;
    1159      134020 :         L_spec /= 2;
    1160             :     }
    1161     2232838 :     else if ( st->last_core == ACELP_CORE )
    1162             :     {
    1163       18755 :         st->hTcxCfg->last_aldo = 0;
    1164             : 
    1165       18755 :         L_frame += tcx_offset;
    1166       18755 :         L_frameTCX += st->hTcxCfg->tcx_offsetFB;
    1167       18755 :         L_spec += st->hTcxCfg->tcx_coded_lines >> 2;
    1168             : 
    1169       18755 :         if ( st->hTcxCfg->lfacNext < 0 )
    1170             :         {
    1171       18755 :             L_frame -= st->hTcxCfg->lfacNext;
    1172       18755 :             L_frameTCX -= st->hTcxCfg->lfacNextFB;
    1173       18755 :             tcx_offset = st->hTcxCfg->lfacNext;
    1174             :         }
    1175             :         else
    1176             :         {
    1177           0 :             tcx_offset = 0;
    1178             :         }
    1179       18755 :         hTcxEnc->noiseLevelMemory_cnt = 0;
    1180             :     }
    1181             : 
    1182     2366858 :     *pL_frameTCX = L_frameTCX;
    1183     2366858 :     *pL_frame = L_frame;
    1184     2366858 :     *pL_spec = L_spec;
    1185     2366858 :     *ptcx_offset = tcx_offset;
    1186             : 
    1187             :     /* target bitrate for SQ */
    1188     2366858 :     sqTargetBits = nb_bits - NBITS_TCX_GAIN - NBITS_NOISE_FILL_LEVEL;
    1189             : 
    1190     2366858 :     if ( st->enablePlcWaveadjust )
    1191             :     {
    1192        2500 :         st->Tonal_SideInfo = DecideTonalSideInfo( x_orig, ( st->core == TCX_20_CORE ) ? st->L_frame : st->L_frame / 2, st->hTcxCfg->SFM2 );
    1193             :     }
    1194             : 
    1195             :     /* Start with the pre-shaped spectrum*/
    1196     2366858 :     mvr2r( x_orig, spectrum, L_spec );
    1197             : 
    1198             :     /*-----------------------------------------------------------*
    1199             :      * Bandwidth Limitation                                      *
    1200             :      *-----------------------------------------------------------*/
    1201             : 
    1202     2366858 :     noiseFillingBorder = L_spec;
    1203     2366858 :     if ( st->igf )
    1204             :     {
    1205     1582196 :         noiseFillingBorder = st->hIGFEnc->infoStartLine;
    1206             :     }
    1207     2366858 :     *pnoiseFillingBorder = noiseFillingBorder;
    1208             : 
    1209     2366858 :     if ( st->igf )
    1210             :     {
    1211   243565672 :         for ( i = st->hIGFEnc->infoStopLine; i < max( L_frame, L_frameTCX ); i++ )
    1212             :         {
    1213   241983476 :             spectrum[i] = 0.0f;
    1214             :         }
    1215             :     }
    1216             :     else
    1217             :     {
    1218    16472926 :         for ( i = noiseFillingBorder; i < max( L_frame, L_frameTCX ); i++ )
    1219             :         {
    1220    15688264 :             spectrum[i] = 0.0f;
    1221             :         }
    1222             :     }
    1223             : 
    1224             :     /*-----------------------------------------------------------*
    1225             :      * Quantization                                              *
    1226             :      *-----------------------------------------------------------*/
    1227             : 
    1228     2366858 :     if ( !hTcxEnc->tcx_lpc_shaped_ari )
    1229             :     {
    1230             :         /* context based arithmetic coder */
    1231             : 
    1232             :         /* initialize signaling to default, i.e. context based AC is inactive */
    1233     2330640 :         prm_hm[0] = 0;
    1234     2330640 :         prm_hm[1] = -1;
    1235             : 
    1236             :         /* Fast estimation of the scalar quantizer step size */
    1237     2330640 :         if ( st->hTcxCfg->ctx_hm && st->last_core != ACELP_CORE )
    1238             :         {
    1239      343820 :             LtpPitchLag = ( ( !st->tcxonly ) && ( hTcxEnc->tcxltp_pitch_int < st->L_frame ) ? ( ( 2 * st->L_frame * st->pit_res_max ) << kLtpHmFractionalResolution ) / ( hTcxEnc->tcxltp_pitch_int * st->pit_res_max + hTcxEnc->tcxltp_pitch_fr ) : -1 );
    1240             : 
    1241      343820 :             ++ctxHmBits;    /* ContextHM flag */
    1242      343820 :             --sqTargetBits; /* ContextHM flag */
    1243             : 
    1244      343820 :             PeriodicityIndex = SearchPeriodicityIndex( spectrum, NULL, L_spec, sqTargetBits, LtpPitchLag, hTcxEnc->tcxltp ? hTcxEnc->tcxltp_gain : -1.0f, &RelativeScore );
    1245             : 
    1246      343820 :             NumIndexBits = CountIndexBits( L_spec >= 256, PeriodicityIndex );
    1247             : 
    1248      343820 :             if ( st->element_mode > EVS_MONO )
    1249             :             {
    1250      342016 :                 ConfigureContextHm( L_spec, sqTargetBits - NumIndexBits, PeriodicityIndex, LtpPitchLag, hm_cfg );
    1251             :             }
    1252             :             else
    1253             :             {
    1254        1804 :                 ConfigureContextHm( L_spec, sqTargetBits, PeriodicityIndex, LtpPitchLag, hm_cfg );
    1255             :             }
    1256             : 
    1257             :             /* Quantize original spectrum */
    1258      343820 :             sqGain = SQ_gain( spectrum, (int16_t) ( hTcxEnc->tcx_target_bits_fac * (float) sqTargetBits ), L_spec );
    1259             : 
    1260      343820 :             tcx_scalar_quantization( spectrum, sqQ, L_spec, sqGain, st->hTcxCfg->sq_rounding, hTcxEnc->memQuantZeros, st->tcxonly );
    1261             : 
    1262             :             /* Estimate original bitrate */
    1263      343820 :             stop = 0;
    1264      343820 :             if ( st->element_mode > EVS_MONO )
    1265             :             {
    1266      342016 :                 sqBits = RCcontextMapping_encode2_estimate_no_mem_s17_LCS( sqQ, L_spec, &lastnz, &nEncoded, sqTargetBits, &stop, 0, NULL );
    1267             :             }
    1268             :             else
    1269             :             {
    1270        1804 :                 sqBits = ACcontextMapping_encode2_estimate_no_mem_s17_LC( sqQ, L_spec, &lastnz, &nEncoded, sqTargetBits, &stop, NULL );
    1271             :             }
    1272             : 
    1273             :             /* Estimate context mapped bitrate */
    1274      343820 :             stopCtxHm = 0;
    1275             : 
    1276             :             /* Context Mapping */
    1277      343820 :             if ( st->element_mode > EVS_MONO )
    1278             :             {
    1279      342016 :                 sqBitsCtxHm = RCcontextMapping_encode2_estimate_no_mem_s17_LCS( sqQ, L_spec, &lastnzCtxHm, &nEncodedCtxHm, sqTargetBits - NumIndexBits, &stopCtxHm, 0, hm_cfg );
    1280             :             }
    1281             :             else
    1282             :             {
    1283        1804 :                 sqBitsCtxHm = ACcontextMapping_encode2_estimate_no_mem_s17_LC( sqQ, L_spec, &lastnzCtxHm, &nEncodedCtxHm, sqTargetBits - NumIndexBits, &stopCtxHm, hm_cfg );
    1284             :             }
    1285             : 
    1286             :             /* Decide whether or not to use context mapping */
    1287      343820 :             Selector = max( stop, sqBits ) - ( max( stopCtxHm, sqBitsCtxHm ) + NumIndexBits );
    1288             : 
    1289      343820 :             if ( Selector > 2 || ( abs( Selector ) <= 2 && kCtxHmOlRSThr < RelativeScore ) )
    1290             :             {
    1291             :                 /* CtxHm is likely better */
    1292       16343 :                 sqTargetBits -= NumIndexBits;
    1293       16343 :                 ctxHmBits += NumIndexBits;
    1294       16343 :                 prm_hm[0] = 1;
    1295       16343 :                 prm_hm[1] = PeriodicityIndex;
    1296       16343 :                 *prm_lastnz = lastnzCtxHm;
    1297       16343 :                 sqBits_noStop = sqBits = sqBitsCtxHm;
    1298       16343 :                 nEncoded = nEncodedCtxHm;
    1299       16343 :                 stop = stopCtxHm;
    1300             :             }
    1301             :             else
    1302             :             {
    1303             :                 /* Original is better or not much difference */
    1304      327477 :                 prm_hm[0] = 0;
    1305      327477 :                 prm_hm[1] = PeriodicityIndex;
    1306      327477 :                 *prm_lastnz = lastnz;
    1307      327477 :                 PeriodicityIndex = -1;
    1308             : 
    1309      327477 :                 sqBits_noStop = sqBits;
    1310             :             }
    1311             : 
    1312      343820 :             if ( stop != 0 )
    1313             :             {
    1314      128472 :                 sqBits = stop;
    1315             :             }
    1316             :         }
    1317             :         else
    1318             :         {
    1319             :             /* no context hm*/
    1320     1986820 :             PeriodicityIndex = -1;
    1321             : 
    1322     1986820 :             if ( st->element_mode == IVAS_CPE_MDCT )
    1323             :             {
    1324     1894345 :                 sqGain = SQ_gain_estimate( spectrum, (int16_t) ( hTcxEnc->tcx_target_bits_fac * (float) sqTargetBits ), L_spec );
    1325             :             }
    1326             :             else
    1327             :             {
    1328       92475 :                 sqGain = SQ_gain( spectrum, (int16_t) ( hTcxEnc->tcx_target_bits_fac * (float) sqTargetBits ), L_spec );
    1329             :             }
    1330             : 
    1331             :             /* Quantize spectrum */
    1332     1986820 :             tcx_scalar_quantization( spectrum, sqQ, L_spec, sqGain, st->hTcxCfg->sq_rounding, hTcxEnc->memQuantZeros, st->tcxonly );
    1333             : 
    1334             :             /* Estimate bitrate */
    1335     1986820 :             stop = 0;
    1336     1986820 :             if ( st->element_mode > EVS_MONO )
    1337             :             {
    1338     1985083 :                 sqBits_noStop = sqBits = RCcontextMapping_encode2_estimate_no_mem_s17_LCS( sqQ, L_spec, prm_lastnz, &nEncoded, sqTargetBits, &stop, 0, NULL );
    1339             :             }
    1340             :             else
    1341             :             {
    1342        1737 :                 sqBits_noStop = sqBits = ACcontextMapping_encode2_estimate_no_mem_s17_LC( sqQ, L_spec, prm_lastnz, &nEncoded, sqTargetBits, &stop, NULL );
    1343             :             }
    1344             : 
    1345     1986820 :             if ( stop != 0 )
    1346             :             {
    1347     1018668 :                 sqBits = stop;
    1348             :             }
    1349             :         } /* end of if (ctx_hm) */
    1350             : 
    1351             :         /* Adjust correction factor */
    1352     2330640 :         if ( ( L_spec & ( L_spec - 1 ) ) == 0 )
    1353             :         {
    1354             :             /* power-of-2 */
    1355           0 :             hTcxEnc->tcx_target_bits_fac *= (float) sqTargetBits / (float) ( sqBits + 1 );
    1356             :         }
    1357             :         else
    1358             :         {
    1359     2330640 :             hTcxEnc->tcx_target_bits_fac *= (float) sqTargetBits / (float) sqBits;
    1360             :         }
    1361             : 
    1362     2330640 :         if ( hTcxEnc->tcx_target_bits_fac > 1.25 )
    1363             :         {
    1364      233682 :             hTcxEnc->tcx_target_bits_fac = 1.25;
    1365             :         }
    1366     2330640 :         if ( hTcxEnc->tcx_target_bits_fac < 0.75 )
    1367             :         {
    1368      147677 :             hTcxEnc->tcx_target_bits_fac = 0.75;
    1369             :         }
    1370             : 
    1371             :         /* Refine quantizer step size with a rate-control-loop (optional) */
    1372     2330640 :         sqBits = tcx_scalar_quantization_rateloop( spectrum, sqQ, L_spec, &sqGain, st->hTcxCfg->sq_rounding, hTcxEnc->memQuantZeros, prm_lastnz, /* lastnz */ sqTargetBits, &nEncoded, &stop, sqBits_noStop, sqBits, st->hTcxCfg->tcxRateLoopOpt, st->tcxonly, PeriodicityIndex >= 0 ? hm_cfg : NULL, ( st->element_mode == IVAS_CPE_MDCT ? 2 : 4 ), st->element_mode );
    1373             : 
    1374     2330640 :         if ( ctxHmBits > 0 )
    1375             :         {
    1376             :             /* Mapping tool is enabled */
    1377             :             /* Truncate spectrum */
    1378      883507 :             for ( i = nEncoded; i < L_spec; i++ )
    1379             :             {
    1380      875288 :                 if ( st->element_mode > EVS_MONO )
    1381             :                 {
    1382      335601 :                     break;
    1383             :                 }
    1384             :                 else
    1385             :                 {
    1386      539687 :                     sqQ[i] = 0;
    1387             :                 }
    1388             :             }
    1389             : 
    1390      343820 :             if ( PeriodicityIndex >= 0 )
    1391             :             {
    1392             :                 /* Mapping is used */
    1393             :                 /* Estimate non-mapped bitrate */
    1394       16343 :                 stopCtxHm = 1;
    1395       16343 :                 if ( st->element_mode > EVS_MONO )
    1396             :                 {
    1397             :                     /* Fix: Use updated value for target bits (sqTargetBits + NumIndexBits) before computing non-mapped estimate */
    1398       16027 :                     sqBitsCtxHm = RCcontextMapping_encode2_estimate_no_mem_s17_LCS( sqQ, L_spec, &lastnz, &nEncodedCtxHm, sqTargetBits + NumIndexBits, &stopCtxHm, 0, NULL );
    1399             :                 }
    1400             :                 else
    1401             :                 {
    1402         316 :                     sqBitsCtxHm = ACcontextMapping_encode2_estimate_no_mem_s17_LC( sqQ, L_spec, &lastnz, &nEncodedCtxHm, sqTargetBits, &stopCtxHm, NULL );
    1403             :                 }
    1404             : 
    1405             :                 /* Decide whether or not to revert mapping */
    1406       16343 :                 Selector = sqBits - ( sqBitsCtxHm + NumIndexBits );
    1407             : 
    1408       16343 :                 if ( st->element_mode > EVS_MONO )
    1409             :                 {
    1410       16027 :                     if ( ( stopCtxHm == 0 && Selector > 0 ) || stop ) /* If overflow occured with mapped, select non-mapped */
    1411             :                     {
    1412             :                         /* Non-mapped is better */
    1413         682 :                         sqTargetBits += NumIndexBits;
    1414         682 :                         ctxHmBits -= NumIndexBits;
    1415         682 :                         prm_hm[0] = 0;
    1416         682 :                         *prm_lastnz = lastnz;
    1417         682 :                         PeriodicityIndex = -1;
    1418         682 :                         sqBits_noStop = sqBits = sqBitsCtxHm;
    1419         682 :                         nEncoded = nEncodedCtxHm;
    1420         682 :                         stop = stopCtxHm;
    1421             :                     }
    1422             :                 }
    1423             :                 else
    1424             :                 {
    1425         316 :                     if ( stopCtxHm == 0 && Selector > 0 )
    1426             :                     {
    1427             :                         /* Non-mapped is better */
    1428           2 :                         sqTargetBits += NumIndexBits;
    1429           2 :                         ctxHmBits -= NumIndexBits;
    1430           2 :                         prm_hm[0] = 0;
    1431           2 :                         *prm_lastnz = lastnz;
    1432           2 :                         PeriodicityIndex = -1;
    1433           2 :                         sqBits_noStop = sqBits = sqBitsCtxHm;
    1434           2 :                         nEncoded = nEncodedCtxHm;
    1435           2 :                         stop = stopCtxHm;
    1436             :                     }
    1437             :                 }
    1438             :             }
    1439             :             else
    1440             :             {
    1441             :                 /* Mapping is not used */
    1442      327477 :                 if ( st->element_mode > EVS_MONO )
    1443             :                 {
    1444             :                     /* Truncate Spectrum */
    1445   165791947 :                     for ( i = nEncoded; i < L_spec; i++ )
    1446             :                     {
    1447   165465958 :                         sqQ[i] = 0;
    1448             :                     }
    1449             :                 }
    1450             :                 /* Estimate mapped bitrate */
    1451      327477 :                 stopCtxHm = 1;
    1452      327477 :                 if ( st->element_mode > EVS_MONO )
    1453             :                 {
    1454      325989 :                     sqBitsCtxHm = RCcontextMapping_encode2_estimate_no_mem_s17_LCS( sqQ, L_spec, &lastnzCtxHm, &nEncodedCtxHm, sqTargetBits - NumIndexBits, &stopCtxHm, 0, hm_cfg );
    1455             :                 }
    1456             :                 else
    1457             :                 {
    1458        1488 :                     sqBitsCtxHm = ACcontextMapping_encode2_estimate_no_mem_s17_LC( sqQ, L_spec, &lastnzCtxHm, &nEncodedCtxHm, sqTargetBits - NumIndexBits, &stopCtxHm, hm_cfg );
    1459             :                 }
    1460             : 
    1461             :                 /* Decide whether or not to use mapping */
    1462      327477 :                 Selector = sqBits - ( sqBitsCtxHm + NumIndexBits );
    1463             : 
    1464      327477 :                 if ( stopCtxHm == 0 && Selector > 0 )
    1465             :                 {
    1466             :                     /* Mapped is better */
    1467        1460 :                     sqTargetBits -= NumIndexBits;
    1468        1460 :                     ctxHmBits += NumIndexBits;
    1469        1460 :                     prm_hm[0] = 1;
    1470        1460 :                     *prm_lastnz = lastnzCtxHm;
    1471        1460 :                     PeriodicityIndex = prm_hm[1];
    1472        1460 :                     sqBits_noStop = sqBits = sqBitsCtxHm;
    1473        1460 :                     nEncoded = nEncodedCtxHm;
    1474        1460 :                     stop = stopCtxHm;
    1475             :                 }
    1476             :             }
    1477             :         }
    1478             : 
    1479             :         /* Limit low sqGain for avoiding saturation of the gain quantizer*/
    1480     2330640 :         if ( st->hTcxCfg->tcxRateLoopOpt < 3 && sqGain < sqrt( (float) NORM_MDCT_FACTOR / (float) L_spec ) )
    1481             :         {
    1482       13755 :             sqGain = (float) sqrt( (float) NORM_MDCT_FACTOR / (float) L_spec );
    1483             : 
    1484       13755 :             tcx_scalar_quantization( spectrum, sqQ, L_spec, sqGain, st->hTcxCfg->sq_rounding, hTcxEnc->memQuantZeros, st->tcxonly );
    1485             : 
    1486       13755 :             stop = 1;
    1487       13755 :             if ( st->element_mode > EVS_MONO )
    1488             :             {
    1489             :                 /* Ensure non-mapped estimation is used for limiting low sqGain considering that this refinement occurs very rarely */
    1490       13743 :                 PeriodicityIndex = -1;
    1491       13743 :                 if ( prm_hm[0] == 1 )
    1492             :                 {
    1493           0 :                     prm_hm[0] = 0;
    1494           0 :                     sqTargetBits += NumIndexBits;
    1495           0 :                     ctxHmBits -= NumIndexBits;
    1496             :                 }
    1497       13743 :                 sqBits = RCcontextMapping_encode2_estimate_no_mem_s17_LCS( sqQ, L_spec, prm_lastnz, &nEncoded, sqTargetBits, &stop, 0, NULL );
    1498             :             }
    1499             :             else
    1500             :             {
    1501          12 :                 sqBits = ACcontextMapping_encode2_estimate_no_mem_s17_LC( sqQ, L_spec, prm_lastnz, &nEncoded, sqTargetBits, &stop, PeriodicityIndex >= 0 ? hm_cfg : NULL );
    1502             :             }
    1503             :         }
    1504             : 
    1505             :         /* Truncate spectrum (for CBR) */
    1506     2330640 :         if ( stop )
    1507             :         {
    1508   196976878 :             for ( i = nEncoded; i < L_spec; i++ )
    1509             :             {
    1510   196603786 :                 sqQ[i] = 0;
    1511             :             }
    1512             :         }
    1513             : 
    1514             :         /* Save quantized Values */
    1515     2330640 :         *nf_seed = 0;
    1516  1942431520 :         for ( i = 0; i < L_spec; i++ )
    1517             :         {
    1518  1940100880 :             spectrum[i] = (float) sqQ[i];
    1519             :             /* noise filling seed */
    1520  1940100880 :             *nf_seed += (int16_t) ( abs( sqQ[i] ) * i * 2 );
    1521             :         }
    1522             :     }
    1523             :     else
    1524             :     {
    1525             :         /* low rates: envelope based arithmetic coder */
    1526             : 
    1527       36218 :         AdaptLowFreqEmph( spectrum, NULL, 0.f, 1, gainlpc, L_frame );
    1528             : 
    1529       36218 :         prm_target = sqQ;
    1530       36218 :         sqQ = prm_target + 1;
    1531             : 
    1532       36218 :         LtpPitchLag = ( ( hTcxEnc->tcxltp_pitch_int < st->L_frame ) ? ( ( 2 * st->L_frame * st->pit_res_max ) << kLtpHmFractionalResolution ) / ( st->hTcxEnc->tcxltp_pitch_int * st->pit_res_max + hTcxEnc->tcxltp_pitch_fr ) : -1 );
    1533             : 
    1534       36218 :         tcx_arith_encode_envelope( spectrum, hm_cfg->indexBuffer, L_frame, L_spec, st, Aqind, sqTargetBits, sqQ, st->last_core != ACELP_CORE, prm_hm, /* HM parameter area */ LtpPitchLag, &sqBits, &signaling_bits, ( st->bwidth > WB ) ? 1 : 0 );
    1535             : 
    1536       36218 :         sqTargetBits -= signaling_bits;
    1537       36218 :         *prm_target = sqTargetBits;
    1538             : 
    1539             :         /* Noise filling seed */
    1540       36218 :         *nf_seed = 0;
    1541     7615382 :         for ( i = 0; i < noiseFillingBorder; ++i )
    1542             :         {
    1543     7579164 :             *nf_seed += (int16_t) ( abs( (int16_t) spectrum[i] ) * i * 2 );
    1544             :         }
    1545             :     }
    1546             : 
    1547     2366858 :     *hm_active = prm_hm[0];
    1548             : 
    1549             :     /*-----------------------------------------------------------*
    1550             :      * Compute optimal TCX gain.                                 *
    1551             :      *-----------------------------------------------------------*/
    1552             : 
    1553     2366858 :     if ( lf_deemph_fact != NULL )
    1554             :     {
    1555             :         /* initialize LF deemphasis factors in lf_deemph_fact */
    1556   379005833 :         for ( i = 0; i < L_spec; i++ )
    1557             :         {
    1558   378533320 :             lf_deemph_fact[i] = 1.0f;
    1559             :         }
    1560             :     }
    1561             : 
    1562     2366858 :     if ( !st->tcxonly )
    1563             :     {
    1564      263966 :         AdaptLowFreqDeemph( spectrum, hTcxEnc->tcx_lpc_shaped_ari, gainlpc, L_frame, lf_deemph_fact );
    1565             :     }
    1566             : 
    1567     2366858 :     assert( x_orig != spectrum );
    1568     2366858 :     gain_tcx_opt = get_gain( x_orig, spectrum, L_spec, ener );
    1569             : 
    1570     2366858 :     if ( gain_tcx_opt <= 0.0f )
    1571             :     {
    1572       59113 :         gain_tcx_opt = sqGain;
    1573             :     }
    1574     2366858 :     *gain_tcx = gain_tcx_opt;
    1575             : 
    1576     2366858 :     if ( st->element_mode == IVAS_CPE_DFT || st->element_mode == IVAS_CPE_TD )
    1577             :     {
    1578       30663 :         calculate_hangover_attenuation_gain( st, &att, vad_hover_flag );
    1579       30663 :         *gain_tcx *= att;
    1580             :     }
    1581             : 
    1582             :     /*-----------------------------------------------------------*
    1583             :      * Quantize TCX gain                                         *
    1584             :      *-----------------------------------------------------------*/
    1585             : 
    1586             :     /*  gain quantization here in case of VBR unvoiced coding; fixes problems of uninitialized global gain values */
    1587     2366858 :     if ( total_brate >= ACELP_13k20 && !st->rf_mode )
    1588             :     {
    1589     2311441 :         tcx_QuantizeGain( L_spec, gain_tcx, &prm[0] );
    1590             :     }
    1591             : 
    1592             :     /*-----------------------------------------------------------*
    1593             :      * Residual Quantization                                     *
    1594             :      *-----------------------------------------------------------*/
    1595             : 
    1596     2366858 :     if ( st->hTcxCfg->resq )
    1597             :     {
    1598      893936 :         resQTargetBits = sqTargetBits - sqBits;
    1599             : 
    1600      893936 :         if ( hTcxEnc->tcx_lpc_shaped_ari )
    1601             :         {
    1602             :             /* envelope based arithmetic coder */
    1603             :             int16_t *prm_resq;
    1604             : 
    1605       36218 :             prm_resq = sqQ + sqTargetBits - resQTargetBits;
    1606             : 
    1607       36218 :             resQBits = tcx_ari_res_Q_spec( x_orig, hm_cfg->indexBuffer, spectrum, L_spec, *gain_tcx, prm_resq, resQTargetBits, resQBits, st->hTcxCfg->sq_rounding, lf_deemph_fact );
    1608             : 
    1609             :             /* Transmit zeros when there bits remain after RESQ */
    1610       40953 :             for ( i = resQBits; i < resQTargetBits; ++i )
    1611             :             {
    1612        4735 :                 prm_resq[i] = 0;
    1613             :             }
    1614             :         }
    1615             :         else
    1616             :         {
    1617             :             /* context based arithmetic coder */
    1618      857718 :             resQBits = tcx_res_Q_gain( gain_tcx_opt, gain_tcx, sqQ + L_spec, resQTargetBits );
    1619             : 
    1620      857718 :             resQBits = tcx_res_Q_spec( x_orig, spectrum, L_spec, *gain_tcx, sqQ + L_spec, resQTargetBits, resQBits, st->hTcxCfg->sq_rounding, st->tcxonly ? NULL : lf_deemph_fact );
    1621             :         }
    1622             :     }
    1623             : 
    1624             :     /*-----------------------------------------------------------*
    1625             :      * ALFE tcx only bitrates                                    *
    1626             :      *-----------------------------------------------------------*/
    1627             : 
    1628     2366858 :     if ( st->element_mode != IVAS_CPE_MDCT )
    1629             :     {
    1630      472513 :         if ( st->tcxonly )
    1631             :         {
    1632      208547 :             if ( hTcxEnc->tcxltp && ( hTcxEnc->tcxltp_gain > 0.0f ) && !hTcxEnc->fUseTns[frame_cnt] )
    1633             :             {
    1634       28704 :                 PsychAdaptLowFreqDeemph( spectrum, gainlpc, NULL );
    1635             :             }
    1636             :         }
    1637             :     }
    1638             : 
    1639             : #ifdef DEBUGGING
    1640             :     /*-----------------------------------------------------------*
    1641             :      * TCX SNR for Analysis purposes                             *
    1642             :      *-----------------------------------------------------------*/
    1643             :     {
    1644             :         float diff[N_MAX];
    1645             :         char name[50] = "TCX_output_chX  ";
    1646             : 
    1647             :         for ( i = 0; i < min( L_frame, L_spec ); i++ )
    1648             :         {
    1649             :             diff[i] = x_orig[i] - *gain_tcx * spectrum[i];
    1650             :         }
    1651             : 
    1652             :         if ( st->id_element == 0 )
    1653             :         {
    1654             :             name[13] = (char) ( st->idchan + '0' );
    1655             :         }
    1656             :         else
    1657             :         {
    1658             :             char name2[50] = "TCX_output.idX_chX  ";
    1659             :             name2[13] = (char) ( st->id_element + '0' );
    1660             :             name2[17] = (char) ( st->idchan + '0' );
    1661             :             strcpy( name, name2 );
    1662             :         }
    1663             : 
    1664             :         snr( x_orig, diff, min( L_frame, L_spec ), name );
    1665             :     }
    1666             : #endif
    1667             : 
    1668     2366858 :     return;
    1669             : }
    1670             : 
    1671             : 
    1672             : /*-------------------------------------------------------------------*
    1673             :  * InternalTCXDecoder()
    1674             :  *
    1675             :  *
    1676             :  *-------------------------------------------------------------------*/
    1677             : 
    1678      472513 : void InternalTCXDecoder(
    1679             :     Encoder_State *st,                /* i/o: state handle                            */
    1680             :     const int16_t frame_cnt,          /* i  : frame counter in the super_frame        */
    1681             :     const int16_t L_frameTCX,         /* i  : full frame length                       */
    1682             :     const int16_t L_frame,            /* i  : frame length                            */
    1683             :     const int16_t L_spec,             /* i  : length of the coded spectrum            */
    1684             :     const int16_t tcx_offset,         /* i  : folding point offset relative to the end of the previous frame */
    1685             :     const int16_t noiseFillingBorder, /* i  : noise filling border                    */
    1686             :     const float *x_quant,             /* i  : quantized spectrum                      */
    1687             :     const float ener,                 /* i  : energy of the quantized spectrum        */
    1688             :     float lf_deemph_fact[],           /* i/o: low frequency deemphasis factors        */
    1689             :     const float fac_ns,               /* i  : noise filling level                     */
    1690             :     const int16_t nf_seed,            /* i  : noise filling random seed               */
    1691             :     const float *A,                   /* i  : LPC representation of the FDNS gains    */
    1692             :     float *gainlpc,                   /* i/o: FDNS gains                              */
    1693             :     const int16_t hm_active,          /* i  : flag indicating if the harmonic model is active */
    1694             :     float gain_tcx,                   /* i/o: global gain / quantized global gain             */
    1695             :     float spectrum[],                 /* o  : dequantized spectrum                    */
    1696             :     float synth[],                    /* o  : time domain signal                      */
    1697             :     int16_t *gain_tcx_q               /* o  : quantized global gain (at low bitrates) */
    1698             : )
    1699             : {
    1700      472513 :     TCX_ENC_HANDLE hTcxEnc = st->hTcxEnc;
    1701             :     int16_t i, iStart, noiseTransWidth;
    1702             :     int16_t tcx_last_overlap_mode, overlap;
    1703             :     int16_t nz;   /* non-zero length in ALDO window*/
    1704             :     int16_t aldo; /* ALDO flag in current frame*/
    1705             :     float xn_buf[L_MDCT_OVLP_MAX + L_FRAME_PLUS + L_MDCT_OVLP_MAX];
    1706             :     float Aq_old[M + 1];
    1707             :     float sns_interpolated_scalefactors[FDNS_NPTS];
    1708             : 
    1709      472513 :     mvr2r( x_quant, spectrum, max( L_frame, L_spec ) );
    1710             : 
    1711             :     /* Replication of ACELP formant enhancement for low rates */
    1712      472513 :     if ( st->total_brate < ACELP_13k20 || st->rf_mode )
    1713             :     {
    1714       55417 :         tcxFormantEnhancement( lf_deemph_fact, gainlpc, spectrum, L_frame );
    1715             :     }
    1716             : 
    1717             :     /*-----------------------------------------------------------*
    1718             :      * Noise Filling.                                            *
    1719             :      *-----------------------------------------------------------*/
    1720             : 
    1721      472513 :     if ( fac_ns > 0.0f )
    1722             :     {
    1723      401124 :         iStart = tcxGetNoiseFillingTilt( A, L_frame, ( st->total_brate >= ACELP_13k20 && !st->rf_mode ), &hTcxEnc->noiseTiltFactor );
    1724             : 
    1725      401124 :         noiseTransWidth = GetTransWidth( st->tcxonly, ( L_frame == st->L_frame >> 1 ), hTcxEnc->tcxltp_gain, ( st->hTcxCfg->ctx_hm && st->last_core != ACELP_CORE && hm_active ) );
    1726      401124 :         assert( st->element_mode != IVAS_CPE_MDCT );
    1727      401124 :         tcx_noise_filling( spectrum, nf_seed, iStart, noiseFillingBorder, noiseTransWidth, L_frame, hTcxEnc->noiseTiltFactor, fac_ns, NULL, st->element_mode );
    1728             :     }
    1729             : 
    1730      472513 :     if ( st->total_brate < ACELP_13k20 || st->rf_mode )
    1731             :     {
    1732             :         /* partially recompute global gain (energy part), taking noise filling and formant enhancement into account */
    1733       55417 :         float ener_nf = 1e-6f;
    1734    34859537 :         for ( i = 0; i < L_spec; i++ )
    1735             :         {
    1736    34804120 :             ener_nf += spectrum[i] * spectrum[i];
    1737             :         }
    1738       55417 :         gain_tcx *= (float) sqrt( ener / ener_nf );
    1739       55417 :         tcx_QuantizeGain( L_spec, &gain_tcx, gain_tcx_q );
    1740             :     }
    1741             : 
    1742             :     /*end of noise filling*/
    1743             : 
    1744             :     /*-----------------------------------------------------------*
    1745             :      * Noise shaping in frequency domain (1/Wz)                  *
    1746             :      *-----------------------------------------------------------*/
    1747             : 
    1748      472513 :     if ( st->element_mode == IVAS_CPE_MDCT )
    1749             :     {
    1750           0 :         sns_interpolate_scalefactors( sns_interpolated_scalefactors, A, DEC );
    1751           0 :         sns_shape_spectrum( spectrum, st->hTcxCfg->psychParamsCurrent, sns_interpolated_scalefactors, L_frame );
    1752             :     }
    1753             :     else
    1754             :     {
    1755      472513 :         mdct_noiseShaping( spectrum, L_frame, gainlpc, FDNS_NPTS );
    1756             :     }
    1757             : 
    1758             :     /*-----------------------------------------------------------*
    1759             :      * Apply gain                                                *
    1760             :      *-----------------------------------------------------------*/
    1761             : 
    1762      472513 :     if ( st->hTcxCfg->coder_type == INACTIVE )
    1763             :     {
    1764             : 
    1765       30002 :         gain_tcx *= st->hTcxCfg->na_scale;
    1766             :     }
    1767             : 
    1768      472513 :     v_multc( spectrum, gain_tcx, spectrum, L_spec );
    1769             : 
    1770      472513 :     tcx_last_overlap_mode = st->hTcxCfg->tcx_last_overlap_mode; /* backup last TCX overlap mode */
    1771             : 
    1772      472513 :     if ( ( L_frame == st->L_frame >> 1 ) && st->tcxonly )
    1773             :     {
    1774        7284 :         int16_t L = L_frame;
    1775             : 
    1776        7284 :         if ( ( st->hTcxCfg->fIsTNSAllowed && hTcxEnc->fUseTns[frame_cnt] != 0 ) || ( L_spec > L_frame ) )
    1777             :         {
    1778        6106 :             L = L_spec;
    1779             :         }
    1780             : 
    1781        7284 :         tcxInvertWindowGrouping( st->hTcxCfg, xn_buf, spectrum, L, hTcxEnc->fUseTns[frame_cnt], st->last_core, tcx_last_overlap_mode, frame_cnt, 0 );
    1782             :     }
    1783             : 
    1784             :     /*-----------------------------------------------------------*
    1785             :      * Temporal Noise Shaping Synthesis                          *
    1786             :      *-----------------------------------------------------------*/
    1787             : 
    1788      472513 :     if ( st->hTcxCfg->fIsTNSAllowed )
    1789             :     {
    1790      337459 :         SetTnsConfig( st->hTcxCfg, st->core == TCX_20_CORE, ( st->last_core == ACELP_CORE ) && ( frame_cnt == 0 ) );
    1791             : 
    1792             :         /* Apply TNS to get the reconstructed signal */
    1793      337459 :         if ( hTcxEnc->fUseTns[frame_cnt] != 0 )
    1794             :         {
    1795       33895 :             ApplyTnsFilter( st->hTcxCfg->pCurrentTnsConfig, &hTcxEnc->tnsData[frame_cnt], spectrum, 0 );
    1796             : 
    1797       33895 :             if ( ( L_frame == st->L_frame >> 1 ) && ( st->tcxonly ) )
    1798             :             {
    1799        3846 :                 if ( ( st->hTcxCfg->tcx_last_overlap_mode != FULL_OVERLAP ) ||
    1800        2239 :                      ( ( st->hTcxCfg->tcx_curr_overlap_mode == FULL_OVERLAP ) && ( frame_cnt == 0 ) && ( tcx_last_overlap_mode == 0 ) ) )
    1801             :                 {
    1802        2949 :                     const int16_t L_win = L_spec >> 1;
    1803             : 
    1804             :                     /* undo rearrangement of LF sub-window lines for TNS synthesis filter */
    1805        2949 :                     if ( L_frame > L_spec )
    1806             :                     {
    1807           0 :                         assert( 0 );
    1808             :                     }
    1809             :                     else
    1810             :                     {
    1811        2949 :                         mvr2r( spectrum + 8, xn_buf, L_win );
    1812        2949 :                         mvr2r( xn_buf, spectrum + L_win, 8 );
    1813        2949 :                         mvr2r( xn_buf + 8, spectrum + 8, L_win - 8 );
    1814             :                     }
    1815             :                 }
    1816             :             }
    1817             :         }
    1818             :     }
    1819             : 
    1820             :     /*-----------------------------------------------------------*
    1821             :      * Compute inverse MDCT of spectrum[].                        *
    1822             :      *-----------------------------------------------------------*/
    1823             : 
    1824      472513 :     lsp2a_stab( st->lsp_old, Aq_old, M );
    1825      472513 :     overlap = st->hTcxCfg->tcx_mdct_window_length;
    1826      472513 :     nz = NS2SA( st->sr_core, N_ZERO_MDCT_NS );
    1827      472513 :     aldo = 0;
    1828             : 
    1829      472513 :     if ( ( L_frame == st->L_frame >> 1 ) && ( st->tcxonly ) )
    1830             :     {
    1831        7284 :         if ( st->hTcxCfg->tcx_last_overlap_mode != FULL_OVERLAP )
    1832             :         {
    1833             :             /* minimum or half overlap, two transforms, grouping into one window */
    1834             :             float win[( L_FRAME_PLUS + L_MDCT_OVLP_MAX ) / 2];
    1835        2386 :             const int16_t L_win = L_frame >> 1;
    1836        2386 :             const int16_t L_spec_TCX5 = max( L_frame, L_spec ) >> 1;
    1837        2386 :             const int16_t L_ola = ( st->hTcxCfg->tcx_last_overlap_mode == MIN_OVERLAP ) ? st->hTcxCfg->tcx_mdct_window_min_length : st->hTcxCfg->tcx_mdct_window_half_length;
    1838             :             int16_t w;
    1839             : 
    1840        2386 :             set_f( win, 0, ( L_FRAME_PLUS + L_MDCT_OVLP_MAX ) / 2 );
    1841        2386 :             set_zero( xn_buf, tcx_offset + ( L_ola >> 1 ) ); /* zero left end of buffer */
    1842             : 
    1843        7158 :             for ( w = 0; w < 2; w++ )
    1844             :             {
    1845        4772 :                 if ( st->hTcxCfg->tcx_last_overlap_mode == MIN_OVERLAP )
    1846             :                 {
    1847        2076 :                     TCX_MDCT_Inverse( spectrum + w * L_spec_TCX5, win, L_ola, L_win - L_ola, L_ola, st->element_mode );
    1848             :                 }
    1849             :                 else
    1850             :                 {
    1851        2696 :                     TCX_MDCT_Inverse( spectrum + w * L_spec_TCX5, win, L_ola, L_win - L_ola, L_ola, st->element_mode );
    1852             :                 }
    1853             : 
    1854        4772 :                 tcx_windowing_synthesis_current_frame( win, st->hTcxCfg->tcx_aldo_window_2, st->hTcxCfg->tcx_mdct_window_half, st->hTcxCfg->tcx_mdct_window_minimum, L_ola, st->hTcxCfg->tcx_mdct_window_half_length, st->hTcxCfg->tcx_mdct_window_min_length, w == 0 && st->last_core == ACELP_CORE, ( w > 0 ) || ( w == 0 && tcx_last_overlap_mode == 2 ) ? MIN_OVERLAP : st->hTcxCfg->tcx_last_overlap_mode, st->hTcxEnc->acelp_zir, st->hTcxEnc->Txnq, NULL, Aq_old, st->hTcxCfg->tcx_mdct_window_trans, L_win, tcx_offset < 0 ? -tcx_offset : 0, ( w > 0 ) ? 1 : st->last_core, 0, 0 );
    1855             : 
    1856        4772 :                 if ( w > 0 )
    1857             :                 {
    1858        2386 :                     tcx_windowing_synthesis_past_frame( xn_buf + tcx_offset - ( L_ola >> 1 ) + w * L_win, st->hTcxCfg->tcx_aldo_window_1_trunc, st->hTcxCfg->tcx_mdct_window_half, st->hTcxCfg->tcx_mdct_window_minimum, L_ola, st->hTcxCfg->tcx_mdct_window_half_length, st->hTcxCfg->tcx_mdct_window_min_length, 2 );
    1859             :                 }
    1860             : 
    1861             :                 /* add part of current sub-window overlapping with previous window */
    1862        4772 :                 v_add( win, xn_buf + tcx_offset - ( L_ola >> 1 ) + w * L_win, xn_buf + tcx_offset - ( L_ola >> 1 ) + w * L_win, L_ola );
    1863             : 
    1864             :                 /* copy new sub-window region not overlapping with previous window */
    1865        4772 :                 mvr2r( win + L_ola, xn_buf + tcx_offset + ( L_ola >> 1 ) + w * L_win, L_win );
    1866             :             }
    1867             : 
    1868             :             /* To assure that no garbage values are copied to Txnq */
    1869        2386 :             set_zero( xn_buf + L_frame + tcx_offset + ( L_ola >> 1 ), overlap - tcx_offset - ( L_ola >> 1 ) );
    1870             :         }
    1871        4898 :         else if ( ( frame_cnt == 0 ) && ( st->hTcxCfg->tcx_curr_overlap_mode == FULL_OVERLAP ) )
    1872        1412 :         {
    1873             :             /* special overlap attempt, two transforms, grouping into one window */
    1874             :             float win[( L_FRAME_PLUS + L_MDCT_OVLP_MAX ) / 2];
    1875        1412 :             const int16_t L_win = L_frame >> 1;
    1876        1412 :             const int16_t L_spec_TCX5 = max( L_frame, L_spec ) >> 1;
    1877        1412 :             const int16_t L_ola = st->hTcxCfg->tcx_mdct_window_min_length;
    1878             :             int16_t w;
    1879             : 
    1880        1412 :             set_f( win, 0, ( L_FRAME_PLUS + L_MDCT_OVLP_MAX ) / 2 );
    1881             : 
    1882             :             /* Resize overlap (affect only asymmetric window)*/
    1883        1412 :             overlap = st->hTcxCfg->tcx_mdct_window_delay;
    1884             : 
    1885             :             /* 1st TCX-5 window, special MDCT with minimum overlap on right side */
    1886        1412 :             TCX_MDCT_Inverse( spectrum, win + L_win, 0, L_win - ( L_ola >> 1 ), L_ola, st->element_mode );
    1887             : 
    1888             :             /* copy new sub-window region not overlapping with previous window */
    1889        1412 :             mvr2r( win + L_win, xn_buf + ( overlap >> 1 ), L_win + ( L_ola >> 1 ) );
    1890             : 
    1891             :             /* 2nd TCX-5 window, regular MDCT with minimum overlap on both sides */
    1892        1412 :             TCX_MDCT_Inverse( spectrum + L_spec_TCX5, win, L_ola, L_win - L_ola, L_ola, st->element_mode );
    1893             : 
    1894        1412 :             tcx_windowing_synthesis_current_frame( win, st->hTcxCfg->tcx_aldo_window_2, st->hTcxCfg->tcx_mdct_window_half, st->hTcxCfg->tcx_mdct_window_minimum, L_ola, st->hTcxCfg->tcx_mdct_window_half_length, st->hTcxCfg->tcx_mdct_window_min_length, 0, /* left_rect */
    1895        1412 :                                                    2, /* left_mode */ st->hTcxEnc->acelp_zir, st->hTcxEnc->Txnq, NULL, Aq_old, st->hTcxCfg->tcx_mdct_window_trans, L_win, tcx_offset < 0 ? -tcx_offset : 0, 1, /* not st->last_core */ 0, 0 );
    1896             : 
    1897        1412 :             tcx_windowing_synthesis_past_frame( xn_buf + ( overlap >> 1 ) + L_win - ( L_ola >> 1 ), st->hTcxCfg->tcx_aldo_window_1_trunc, st->hTcxCfg->tcx_mdct_window_half, st->hTcxCfg->tcx_mdct_window_minimum, L_ola, st->hTcxCfg->tcx_mdct_window_half_length, st->hTcxCfg->tcx_mdct_window_min_length, 2 );
    1898             : 
    1899             :             /* add part of current sub-window overlapping with previous window */
    1900        1412 :             v_add( win, xn_buf + ( overlap >> 1 ) + L_win - ( L_ola >> 1 ), xn_buf + ( overlap >> 1 ) + L_win - ( L_ola >> 1 ), L_ola );
    1901             : 
    1902             :             /* copy new sub-window region not overlapping with previous window */
    1903        1412 :             mvr2r( win + L_ola, xn_buf + ( overlap >> 1 ) + L_win + ( L_ola >> 1 ), L_win );
    1904             : 
    1905             :             /* extra folding-out on left side of win, for perfect reconstruction */
    1906      182348 :             for ( w = ( overlap >> 1 ); w < overlap; w++ )
    1907             :             {
    1908      180936 :                 xn_buf[overlap - 1 - w] = -1.0f * xn_buf[w];
    1909             :             }
    1910             : 
    1911        1412 :             tcx_windowing_synthesis_current_frame( xn_buf, st->hTcxCfg->tcx_aldo_window_2, st->hTcxCfg->tcx_mdct_window_half, st->hTcxCfg->tcx_mdct_window_minimum, overlap, /*st->hTcxCfg->tcx_mdct_window_length*/ st->hTcxCfg->tcx_mdct_window_half_length, st->hTcxCfg->tcx_mdct_window_min_length, st->last_core == ACELP_CORE, 0, /* left_mode */ st->hTcxEnc->acelp_zir, st->hTcxEnc->Txnq, NULL, Aq_old, st->hTcxCfg->tcx_mdct_window_trans, L_win, tcx_offset < 0 ? -tcx_offset : 0, st->last_core, 0, 0 );
    1912             :         }
    1913             :         else
    1914             :         {
    1915             :             /* default, i.e. maximum overlap, single transform, no grouping */
    1916        3486 :             TCX_MDCT_Inverse( spectrum, xn_buf, overlap, L_frame - overlap, overlap, st->element_mode );
    1917             : 
    1918        3486 :             tcx_windowing_synthesis_current_frame( xn_buf, st->hTcxCfg->tcx_aldo_window_2, st->hTcxCfg->tcx_mdct_window_half, st->hTcxCfg->tcx_mdct_window_minimum, overlap, /*st->hTcxCfg->tcx_mdct_window_length*/ st->hTcxCfg->tcx_mdct_window_half_length, st->hTcxCfg->tcx_mdct_window_min_length, st->last_core == ACELP_CORE, ( frame_cnt > 0 ) && ( tcx_last_overlap_mode == 0 ) && ( st->last_core != ACELP_CORE ) ? 2 : tcx_last_overlap_mode, st->hTcxEnc->acelp_zir, st->hTcxEnc->Txnq, NULL, Aq_old, st->hTcxCfg->tcx_mdct_window_trans, st->L_frame >> 2, tcx_offset < 0 ? -tcx_offset : 0, st->last_core, 0, 0 );
    1919             : 
    1920             :         } /* tcx_last_overlap_mode != FULL_OVERLAP */
    1921             :     }
    1922             :     else
    1923             :     {
    1924             :         /* frame is TCX-20 or not TCX-only */
    1925      465229 :         if ( st->hTcxCfg->tcx_last_overlap_mode != TRANSITION_OVERLAP )
    1926             :         {
    1927             :             float tmp[L_FRAME_PLUS];
    1928             : 
    1929      447951 :             edct( spectrum, xn_buf + overlap / 2 + nz, L_frame, st->element_mode );
    1930             : 
    1931      447951 :             v_multc( xn_buf + overlap / 2 + nz, (float) sqrt( (float) L_frame / NORM_MDCT_FACTOR ), tmp, L_frame );
    1932             : 
    1933      447951 :             window_ola( tmp, xn_buf, st->hTcxEnc->old_out, L_frame, st->hTcxCfg->tcx_last_overlap_mode, st->hTcxCfg->tcx_curr_overlap_mode, 0, 0, NULL );
    1934      447951 :             aldo = 1;
    1935             :         }
    1936             :         else
    1937             :         {
    1938       17278 :             TCX_MDCT_Inverse( spectrum, xn_buf, overlap, L_frame - overlap, overlap, st->element_mode );
    1939             : 
    1940             :             /* Windowing, overlap and add */
    1941             :             /* Window current frame */
    1942       17278 :             tcx_windowing_synthesis_current_frame( xn_buf, st->hTcxCfg->tcx_aldo_window_2, st->hTcxCfg->tcx_mdct_window_half, st->hTcxCfg->tcx_mdct_window_minimum, overlap, /*st->hTcxCfg->tcx_mdct_window_length*/ st->hTcxCfg->tcx_mdct_window_half_length, st->hTcxCfg->tcx_mdct_window_min_length, st->last_core == ACELP_CORE, st->hTcxCfg->tcx_last_overlap_mode, /*left mode*/ st->hTcxEnc->acelp_zir, st->hTcxEnc->Txnq, NULL, Aq_old, st->hTcxCfg->tcx_mdct_window_trans, st->L_frame >> 1, tcx_offset < 0 ? -tcx_offset : 0, st->last_core, 0, 0 );
    1943             :         }
    1944             :     } /* TCX-20/TCX-10 and TCX-only */
    1945             : 
    1946             :     /* Window and overlap-add past frame if past frame is TCX */
    1947      472513 :     if ( st->last_core > ACELP_CORE && ( ( ( L_frameTCX == hTcxEnc->L_frameTCX >> 1 ) && ( st->tcxonly ) ) || ( st->hTcxCfg->tcx_last_overlap_mode == TRANSITION_OVERLAP ) ) )
    1948             :     {
    1949        7204 :         if ( st->hTcxCfg->last_aldo )
    1950             :         {
    1951      751351 :             for ( i = 0; i < overlap - st->hTcxCfg->tcx_mdct_window_min_length; i++ )
    1952             :             {
    1953      747936 :                 xn_buf[i] += st->hTcxEnc->old_out[i + nz];
    1954             :             }
    1955             :             /* fade truncated ALDO window */
    1956      128071 :             for ( ; i < overlap; i++ )
    1957             :             {
    1958      124656 :                 xn_buf[i] += st->hTcxEnc->old_out[i + nz] * st->hTcxCfg->tcx_mdct_window_minimum[overlap - 1 - i];
    1959             :             }
    1960             :         }
    1961             :         else
    1962             :         {
    1963        3789 :             if ( frame_cnt > 0 && tcx_last_overlap_mode == 0 && st->hTcxCfg->tcx_curr_overlap_mode == FULL_OVERLAP && st->last_core != ACELP_CORE )
    1964             :             {
    1965        1372 :                 tcx_last_overlap_mode = 2; /* use minimum overlap between the two TCX-10 windows */
    1966             :             }
    1967             : 
    1968        3789 :             tcx_windowing_synthesis_past_frame( st->hTcxEnc->Txnq, st->hTcxCfg->tcx_aldo_window_1_trunc, st->hTcxCfg->tcx_mdct_window_half, st->hTcxCfg->tcx_mdct_window_minimum, overlap, st->hTcxCfg->tcx_mdct_window_half_length, st->hTcxCfg->tcx_mdct_window_min_length, ( tcx_last_overlap_mode == 0 || st->hTcxCfg->tcx_last_overlap_mode == MIN_OVERLAP ) ? st->hTcxCfg->tcx_last_overlap_mode : tcx_last_overlap_mode );
    1969             : 
    1970      980205 :             for ( i = 0; i < overlap; i++ )
    1971             :             {
    1972      976416 :                 xn_buf[i] += st->hTcxEnc->Txnq[i];
    1973             :             }
    1974             :         }
    1975             :     }
    1976             : 
    1977      472513 :     if ( !aldo && ( ( ( L_frameTCX == hTcxEnc->L_frameTCX >> 1 ) && frame_cnt > 0 ) || L_frameTCX != ( hTcxEnc->L_frameTCX >> 1 ) ) )
    1978             :     {
    1979             :         /*Compute windowed synthesis in case of switching to ALDO windows in next frame*/
    1980       20920 :         mvr2r( xn_buf + L_frame - nz, st->hTcxEnc->old_out, nz + overlap );
    1981       20920 :         set_zero( st->hTcxEnc->old_out + nz + overlap, nz );
    1982             : 
    1983       20920 :         tcx_windowing_synthesis_past_frame( st->hTcxEnc->old_out + nz, st->hTcxCfg->tcx_aldo_window_1_trunc, st->hTcxCfg->tcx_mdct_window_half, st->hTcxCfg->tcx_mdct_window_minimum, overlap, st->hTcxCfg->tcx_mdct_window_half_length, st->hTcxCfg->tcx_mdct_window_min_length, st->hTcxCfg->tcx_curr_overlap_mode );
    1984             : 
    1985       20920 :         if ( st->hTcxCfg->tcx_curr_overlap_mode == FULL_OVERLAP )
    1986             :         {
    1987     1787072 :             for ( i = 0; i < nz; i++ )
    1988             :             {
    1989     1768014 :                 st->hTcxEnc->old_out[nz + overlap + i] = xn_buf[L_frame - 1 - i] * st->hTcxCfg->tcx_aldo_window_1_trunc[-1 - i];
    1990             :             }
    1991             :         }
    1992             :     }
    1993             : 
    1994      472513 :     st->hTcxCfg->last_aldo = aldo;
    1995             : 
    1996             :     /* Update Txnq */
    1997      472513 :     if ( !st->hTcxCfg->last_aldo )
    1998             :     {
    1999       24562 :         mvr2r( xn_buf + L_frame, st->hTcxEnc->Txnq, overlap );
    2000             :     }
    2001             : 
    2002             :     /* Output */
    2003      472513 :     mvr2r( xn_buf + ( overlap >> 1 ) - tcx_offset, synth, ( st->core == TCX_20_CORE ) ? st->L_frame : L_frame );
    2004             : 
    2005      472513 :     return;
    2006             : }
    2007             : 
    2008             : /*-------------------------------------------------------------------*
    2009             :  * QuantizeSpectrum()
    2010             :  *
    2011             :  *
    2012             :  *-------------------------------------------------------------------*/
    2013             : 
    2014      472513 : void QuantizeSpectrum(
    2015             :     Encoder_State *st,           /* i/o: encoder state structure                         */
    2016             :     const float A[],             /* i  : quantized coefficients NxAz_q[M+1]              */
    2017             :     const Word16 Aqind[],        /* i  : frame-independent quantized coefficients (M+1)  */
    2018             :     float gainlpc[],             /* i  : MDCT gains of the previous frame                */
    2019             :     float synth[],               /* o  : synthesis buffer                                */
    2020             :     const int16_t nb_bits,       /* i  : bit budget                                      */
    2021             :     const int16_t tnsSize,       /* i  : number of tns parameters put into prm           */
    2022             :     int16_t prm[],               /* o  : tcx parameters                                  */
    2023             :     const int16_t frame_cnt,     /* i  : frame counter in the super_frame                */
    2024             :     CONTEXT_HM_CONFIG *hm_cfg,   /* i  : HM configuration                             */
    2025             :     const int16_t vad_hover_flag /* i  : VAD hangover flag                            */
    2026             : )
    2027             : {
    2028             :     int16_t L_frameTCX;                                                     /* full frame length */
    2029             :     int16_t L_frame;                                                        /* frame length */
    2030             :     int16_t L_spec;                                                         /* length of the coded spectrum */
    2031             :     int16_t tcx_offset;                                                     /* folding point offset relative to the end of the previous frame */
    2032             :     int16_t noiseFillingBorder;                                             /* noise filling border */
    2033             :     float quantized_spectrum[N_MAX];                                        /* quantized MDCT spectrum */
    2034             :     float lf_deemph_fact[L_MDCT_OVLP_MAX + L_FRAME_PLUS + L_MDCT_OVLP_MAX]; /* low frequency deemphasis factors */
    2035             :     int16_t hm_active;                                                      /* flag indicating if the harmonic model is active */
    2036             :     float fac_ns;                                                           /* noise filling level */
    2037             :     int16_t nf_seed;                                                        /* noise filling random seed */
    2038             :     float ener;                                                             /* energy of the quantized spectrum */
    2039             :     float gain_tcx;                                                         /* global gain */
    2040      472513 :     TCX_ENC_HANDLE hTcxEnc = st->hTcxEnc;
    2041             : 
    2042             :     /*-----------------------------------------------------------*
    2043             :      * Quantize the MDCT spectrum                                *
    2044             :      *-----------------------------------------------------------*/
    2045             : 
    2046      472513 :     QuantizeTCXSpectrum( st, frame_cnt, hTcxEnc->spectrum[frame_cnt], gainlpc, Aqind, tnsSize, nb_bits, vad_hover_flag,
    2047             :                          &L_frameTCX, &L_frame, &L_spec, &tcx_offset, &noiseFillingBorder, quantized_spectrum, hm_cfg, &hm_active, lf_deemph_fact, &nf_seed, &ener, &gain_tcx, prm );
    2048             : 
    2049             :     /*-----------------------------------------------------------*
    2050             :      * Estimate and quantize noise factor                        *
    2051             :      *-----------------------------------------------------------*/
    2052             : 
    2053      472513 :     EstimateTCXNoiseLevel( st, hTcxEnc->spectrum[frame_cnt], quantized_spectrum, gain_tcx, L_frame, noiseFillingBorder, hm_active, &fac_ns, &prm[1] );
    2054             : 
    2055             :     /*-----------------------------------------------------------*
    2056             :      * Internal decoder                                          *
    2057             :      *-----------------------------------------------------------*/
    2058             : 
    2059      472513 :     InternalTCXDecoder( st, frame_cnt, L_frameTCX, L_frame, L_spec, tcx_offset, noiseFillingBorder, quantized_spectrum, ener, lf_deemph_fact, fac_ns, nf_seed, A, gainlpc, hm_active, gain_tcx, hTcxEnc->spectrum[frame_cnt], synth, &prm[0] );
    2060             : 
    2061             :     /* Update L_frame_past */
    2062      472513 :     st->L_frame_past = L_frame;
    2063             : 
    2064             :     /* Update overlap */
    2065      472513 :     if ( ( ( ( L_frameTCX == hTcxEnc->L_frameTCX >> 1 ) && frame_cnt > 0 ) || ( st->hTcxCfg->tcx_last_overlap_mode == TRANSITION_OVERLAP ) ) && ( st->hTcxCfg->tcx_curr_overlap_mode == FULL_OVERLAP ) )
    2066             :     {
    2067       19058 :         st->hTcxCfg->tcx_curr_overlap_mode = ALDO_WINDOW;
    2068             :     }
    2069             : 
    2070             : 
    2071      472513 :     return;
    2072             : }
    2073             : 
    2074             : 
    2075             : /*-------------------------------------------------------------------*
    2076             :  * coder_tcx()
    2077             :  *
    2078             :  *
    2079             :  *-------------------------------------------------------------------*/
    2080             : 
    2081        1358 : void coder_tcx(
    2082             :     Encoder_State *st,          /* i/o: encoder state structure             */
    2083             :     TCX_CONFIG_HANDLE hTcxCfg,  /* i  : configuration of TCX                */
    2084             :     const float A[],            /* i  : quantized coefficients NxAz_q[M+1]  */
    2085             :     const Word16 Aqind[],       /* i  : frame-independent quantized coefficients (M+1) */
    2086             :     float synth[],              /* o  : decoded synthesis                   */
    2087             :     const int16_t L_frame_glob, /* i  : frame length                        */
    2088             :     const int16_t L_frameTCX_glob,
    2089             :     const int16_t L_spec,
    2090             :     int16_t nb_bits,  /* i  : bit budget                          */
    2091             :     float spectrum[], /* i/o: MDCT spectrum                       */
    2092             :     int16_t prm[],    /* o  : tcx parameters                      */
    2093             :     CONTEXT_HM_CONFIG *hm_cfg,
    2094             :     const int16_t vad_hover_flag /* i  : VAD hangover flag */
    2095             : )
    2096             : {
    2097             :     int16_t L_frame;
    2098        1358 :     int16_t left_overlap = -1, right_overlap = -1;
    2099        1358 :     int16_t tnsSize = 0; /* number of tns parameters put into prm */
    2100        1358 :     int16_t tnsBits = 0; /* number of tns bits in the frame */
    2101        1358 :     int16_t ltpBits = 0;
    2102             :     float gainlpc[FDNS_NPTS];
    2103             :     float buf[N_MAX + L_MDCT_OVLP_MAX];
    2104             :     float winMDST[N_MAX + L_MDCT_OVLP_MAX];
    2105             :     float *win;
    2106             :     float *powerSpec;
    2107        1358 :     TCX_ENC_HANDLE hTcxEnc = st->hTcxEnc;
    2108             : 
    2109        1358 :     powerSpec = win = buf; /* Share memory for windowed TD signal and for the power spectrum */
    2110             : 
    2111        1358 :     L_frame = L_frameTCX_glob;
    2112             : 
    2113             :     /*-----------------------------------------------------------*
    2114             :      * Windowing and MDCT                                        *
    2115             :      *-----------------------------------------------------------*/
    2116             : 
    2117        1358 :     if ( st->hTcxCfg->tcx_last_overlap_mode == TRANSITION_OVERLAP )
    2118             :     {
    2119         159 :         WindowSignal( hTcxCfg, hTcxCfg->tcx_offsetFB, hTcxCfg->tcx_last_overlap_mode, hTcxCfg->tcx_curr_overlap_mode, &left_overlap, &right_overlap, st->hTcxEnc->speech_TCX, &L_frame, win, 1, 1 );
    2120             : 
    2121             :         /* Compute MDCT for xn_buf[] */
    2122         159 :         TCX_MDCT( win, spectrum, left_overlap, L_frame - ( left_overlap + right_overlap ) / 2, right_overlap, st->element_mode );
    2123             :     }
    2124             :     else
    2125             :     {
    2126        1199 :         wtda( st->hTcxEnc->new_speech_TCX, win, NULL, hTcxCfg->tcx_last_overlap_mode, hTcxCfg->tcx_curr_overlap_mode, L_frame );
    2127             : 
    2128        1199 :         WindowSignal( hTcxCfg, hTcxCfg->tcx_offsetFB, hTcxCfg->tcx_last_overlap_mode == ALDO_WINDOW ? FULL_OVERLAP : hTcxCfg->tcx_last_overlap_mode, hTcxCfg->tcx_curr_overlap_mode == ALDO_WINDOW ? FULL_OVERLAP : hTcxCfg->tcx_curr_overlap_mode, &left_overlap, &right_overlap, st->hTcxEnc->speech_TCX, &L_frame, winMDST, 1, 1 );
    2129             : 
    2130        1199 :         edct( win, spectrum, L_frame, st->element_mode );
    2131             : 
    2132        1199 :         v_multc( spectrum, (float) sqrt( (float) NORM_MDCT_FACTOR / L_frame ), spectrum, L_frame );
    2133             :     }
    2134             : 
    2135             :     /*-----------------------------------------------------------*
    2136             :      * Attenuate upper end of NB spectrum,                       *
    2137             :      * to simulate ACELP behavior                                *
    2138             :      *-----------------------------------------------------------*/
    2139             : 
    2140        1358 :     if ( st->narrowBand )
    2141             :     {
    2142          57 :         attenuateNbSpectrum( L_frame, spectrum );
    2143             :     }
    2144             : 
    2145             :     /*-----------------------------------------------------------*
    2146             :      * Compute noise-measure flags for spectrum filling          *
    2147             :      * and quantization (0: tonal, 1: noise-like).               *
    2148             :      * Detect low pass if present.                               *
    2149             :      *-----------------------------------------------------------*/
    2150             : 
    2151        1358 :     AnalyzePowerSpectrum( st, L_frame * st->L_frame / hTcxEnc->L_frameTCX, L_frame, left_overlap, right_overlap, spectrum, ( st->hTcxCfg->tcx_last_overlap_mode == TRANSITION_OVERLAP ) ? win : winMDST, powerSpec );
    2152             : 
    2153        1358 :     if ( hTcxCfg->fIsTNSAllowed )
    2154             :     {
    2155         459 :         SetTnsConfig( hTcxCfg, L_frame_glob == st->L_frame, st->last_core == ACELP_CORE );
    2156             : 
    2157         459 :         TNSAnalysis( hTcxCfg, L_frame, L_spec, TCX_20, st->last_core == ACELP_CORE, spectrum, NULL, -1, hTcxEnc->tnsData, hTcxEnc->fUseTns, &st->hIGFEnc->tns_predictionGain );
    2158             :     }
    2159             :     else
    2160             :     {
    2161         899 :         hTcxEnc->fUseTns[0] = hTcxEnc->fUseTns[1] = 0;
    2162             :     }
    2163             : 
    2164        1358 :     if ( st->igf )
    2165             :     {
    2166        1190 :         ProcessIGF( st, spectrum, spectrum, powerSpec, 1, 0, 0, vad_hover_flag );
    2167             :     }
    2168             : 
    2169        1358 :     ShapeSpectrum( hTcxCfg, A, gainlpc, L_frame_glob, L_spec, spectrum, hTcxEnc->fUseTns[0], st, NULL );
    2170             : 
    2171        1358 :     if ( st->igf )
    2172             :     {
    2173        1190 :         nb_bits -= st->hIGFEnc->infoTotalBitsPerFrameWritten;
    2174             :     }
    2175             : 
    2176        1358 :     if ( hTcxCfg->fIsTNSAllowed )
    2177             :     {
    2178         459 :         EncodeTnsData( hTcxCfg->pCurrentTnsConfig, hTcxEnc->tnsData, prm + 1 + NOISE_FILL_RANGES + LTPSIZE, &tnsSize, &tnsBits );
    2179             :     }
    2180             : 
    2181        1358 :     QuantizeSpectrum( st, A, Aqind, gainlpc, synth, nb_bits - tnsBits - ltpBits, tnsSize, prm, 0, hm_cfg, vad_hover_flag );
    2182             : 
    2183        1358 :     return;
    2184             : }
    2185             : 
    2186             : /*-------------------------------------------------------------------*
    2187             :  * coder_tcx_post()
    2188             :  *
    2189             :  *
    2190             :  *-------------------------------------------------------------------*/
    2191             : 
    2192      468871 : void coder_tcx_post(
    2193             :     Encoder_State *st, /* i/o: encoder memory state                        */
    2194             :     float *A,          /* o  : Quantized LPC coefficients                  */
    2195             :     const float *Ai    /* i  : Unquantized (interpolated) LPC coefficients */
    2196             : )
    2197             : {
    2198             :     float xn_buf[L_FRAME_MAX];
    2199             : 
    2200             :     /* TCX output */
    2201      468871 :     mvr2r( st->synth, xn_buf, st->L_frame );
    2202             : 
    2203             :     /*-----------------------------------------------------------*
    2204             :      * Memory update                                             *
    2205             :      *-----------------------------------------------------------*/
    2206             : 
    2207             :     /* Update LPDmem (Txnq,syn,syn_pe,old_exc,wsyn,Ai,Aq) */
    2208      468871 :     tcx_encoder_memory_update( st, xn_buf, Ai, A );
    2209             : 
    2210      468871 :     return;
    2211             : }

Generated by: LCOV version 1.14