LCOV - code coverage report
Current view: top level - lib_enc - lsf_msvq_ma_enc.c (source / functions) Hit Total Coverage
Test: Coverage on main -- short test vectors @ 6c9ddc4024a9c0e1ecb8f643f114a84a0e26ec6b Lines: 271 271 100.0 %
Date: 2025-05-23 08:37:30 Functions: 8 8 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 <stdint.h>
      38             : #include "options.h"
      39             : #ifdef DEBUGGING
      40             : #include "debug.h"
      41             : #endif
      42             : #include "cnst.h"
      43             : #include "ivas_prot.h"
      44             : #include "prot.h"
      45             : #include "rom_com.h"
      46             : #include "rom_enc.h"
      47             : #include "basop_proto_func.h"
      48             : #include "wmc_auto.h"
      49             : 
      50             : 
      51             : /*--------------------------------------------------------------------------*
      52             :  * Local constants
      53             :  *--------------------------------------------------------------------------*/
      54             : 
      55             : #define kMaxC 8
      56             : 
      57             : 
      58             : /*--------------------------------------------------------------------------*
      59             :  * msvq_encmsvq_stage1_dct_search()
      60             :  *
      61             :  *  stage1 search in a segmentwise  truncated dct N  domain without  weights
      62             :  *--------------------------------------------------------------------------*/
      63             : 
      64             : /*! r: (p_max , best candidate sofar ) */
      65        3088 : int16_t msvq_stage1_dct_search(
      66             :     const float *u,                           /* i  : target                                        */
      67             :     const int16_t N,                          /* i  : target length and  IDCT synthesis length      */
      68             :     const int16_t maxC_st1,                   /* i  : number of final stage 1 candidates to provide */
      69             :     const DCTTYPE dcttype,                    /* e.g. DCT_T2_16_XX, DCT_T2_24_XX;                   */
      70             :     const int16_t max_dct_trunc,              /* i  :  maximum of truncation lenghts                */
      71             :     float *invTrfMatrix,                      /* i  : IDCT synthesis matrix for dim N               */
      72             :     const float *midQ_truncQ,                 /* i  : midQ  vector                                  */
      73             :     const float *dct_invScaleF,               /* i  : global inv scale factors                      */
      74             :     const float *dct_scaleF,                  /* i  : global scale factors                          */
      75             :     const Word16 n_segm,                      /* i  : number of segments                            */
      76             :     const Word16 *cols_per_segment,           /* i  : remaining length per segment                  */
      77             :     const Word16 *trunc_dct_cols_per_segment, /* i  : trunc length per segment                      */
      78             :     const Word16 *entries_per_segment,        /* i  : number of rows per segment                    */
      79             :     const Word16 *cum_entries_per_segment,    /* i  : number of cumulative entries                  */
      80             :     const Word8 *const W8Qx_dct_sections[],   /* i  : Word8(byte) segment  table ptrs               */
      81             :     const Word16 *col_syn_shift[],            /* i  : columnwise  syn shift tables                  */
      82             :     const Word8 *segm_neighbour_fwd,          /* i  : circular neighbour list fwd                   */
      83             :     const Word8 *segm_neighbour_rev,          /* i  : circular neighbour list reverse               */
      84             :     const Word16 npost_check,                 /* i  : number of neigbours to check , should be even */
      85             :     float *st1_mse_ptr,                       /* i  : dynRAM buffer for MSEs                        */
      86             :     int16_t *indices_st1_local,               /* o  :  selected cand indices                        */
      87             :     float *st1_syn_vec_ptr,                   /* i/o:  buffer for IDCT24 synthesis                  */
      88             :     float *dist1_ptr                          /* o  :  resulting stage 1 MSEs in DCT-N domain       */
      89             : )
      90             : {
      91             :     float dct_target[FDCNG_VQ_DCT_MAXTRUNC];
      92             :     float u_mr[FDCNG_VQ_MAX_LEN];
      93             :     float u_mr_scaled[FDCNG_VQ_MAX_LEN];
      94             :     float mse_trunc_segm[FDCNG_VQ_DCT_NSEGM];
      95             :     float tmp, check_mse;
      96             :     float mse; /* Word32 in BASOP */
      97             : 
      98             :     int16_t p_max, c, c2, segm, j_full, j, i;
      99             :     int16_t n_ana, p_mins[2], idx_min[2];
     100             : 
     101             :     const Word8 *cbpW8;
     102             :     const Word16 *dct_col_shift_tab;
     103             : 
     104             :     float *st1_mse_pair;
     105             :     int16_t *st1_idx_pair;
     106             : 
     107             :     float tmp2;
     108             :     int16_t check_ind[FDCNG_VQ_DCT_NPOST];
     109        3088 :     assert( ( npost_check % 2 == 0 ) && ( npost_check <= FDCNG_VQ_DCT_NPOST ) );
     110             : 
     111        3088 :     assert( n_segm <= FDCNG_VQ_DCT_NSEGM );
     112             : 
     113        3088 :     n_ana = N;                        /*  VQ stage#1 core is currently always using stored DCT N coeffs */
     114        3088 :     assert( n_ana >= max_dct_trunc ); /* check for  FDCNGVQ  WB , SWB, FB operation  */
     115             : 
     116             :     /* remove  mid  stage#1 vector,  in original  input  domain */
     117        3088 :     v_sub( u, midQ_truncQ, u_mr, n_ana );
     118             : 
     119        3088 :     v_multc( u_mr, dct_invScaleF[1], u_mr_scaled, n_ana ); /* scale up target to upscaled  W8x storage  domain  */
     120             :     /* 16.0-->scale up from Q0 to  search  domain  in Q4,  not really  needed in BASOP , impl. by shifts */
     121             : 
     122        3088 :     dctT2_N_apply_matrix( (const float *) u_mr_scaled, dct_target, min( max_dct_trunc, n_ana ), n_ana, invTrfMatrix, max_dct_trunc, dcttype );
     123             : 
     124             :     /* init search state  ptr's  at the top */
     125        3088 :     set_f( dist1_ptr, FLT_MAX, maxC_st1 );
     126        3088 :     st1_mse_pair = &( dist1_ptr[0] );         /* req. ptr post upd +=2 */
     127        3088 :     st1_idx_pair = &( indices_st1_local[0] ); /* req. ptr post upd +=2 */
     128        3088 :     set_f( mse_trunc_segm, 0.0f, n_segm );
     129             : 
     130       15440 :     for ( segm = 0; segm < n_segm; segm++ )
     131             :     {              /*  point to a  new paired location for each segment  */
     132       12352 :         p_max = 0; /* req. to point to one of 1 or 0, this init  can potentially be omitted here,as p_max is always 1 or 0 */
     133             : 
     134             :         /* compute segment common trunction error in dctN domain */
     135       12352 :         mse_trunc_segm[segm] += sum2_f( (const float *) ( &( dct_target[cols_per_segment[segm]] ) ), trunc_dct_cols_per_segment[segm] );
     136             : 
     137       12352 :         cbpW8 = W8Qx_dct_sections[segm]; /* Word8 column variable Qx storage , table ptr init */
     138             : 
     139      407616 :         for ( j = 0; j < entries_per_segment[segm]; j++ )
     140             :         {
     141             :             /* unweighted segmented search DCT domain loop */
     142      395264 :             j_full = j + cum_entries_per_segment[segm]; /* or simply use j_full++ */
     143             : 
     144      395264 :             mse = mse_trunc_segm[segm]; /* init mse with with common mse truncation part, in  BASOP a move32() */
     145             : 
     146      395264 :             dct_col_shift_tab = col_syn_shift[segm]; /* ptr init */
     147             : 
     148     6490976 :             for ( c2 = 0; c2 < cols_per_segment[segm]; c2++ )
     149             :             {
     150             : #define WMC_TOOL_SKIP
     151     6095712 :                 tmp = dct_target[c2] - (float) shl( (Word16) cbpW8[c2], dct_col_shift_tab[c2] ); /*   note:  BASOP shift left defined for signed integers      */
     152             :                 LOGIC( 1 );
     153             :                 SHIFT( 1 );
     154             :                 ADD( 1 ); /* in BASOP:    s_and(for W8->W16), shl(), sub()*/
     155             : #undef WMC_TOOL_SKIP
     156     6095712 :                 mse += tmp * tmp; /*  L_mac or L_mac0()   square Word16 -> Word32*/
     157             :             }
     158      395264 :             st1_mse_ptr[j_full] = mse; /* save MSE in shared dynamic RAM,  move32() in BASOP */
     159             : 
     160             : #define WMC_TOOL_SKIP
     161      395264 :             cbpW8 += cols_per_segment[segm]; /*   fixed  pointer increment for each segment  */
     162             : #undef WMC_TOOL_SKIP
     163             : 
     164             :             /* overwrite with a new worst index at p_max  */
     165             : 
     166             :             /* Note: The three inner loop if's below are not 100% properly instrumented by WMC tool */
     167      395264 :             if ( mse < st1_mse_pair[p_max] ) /* L_sub  */
     168             :             {
     169      162938 :                 st1_idx_pair[p_max] = j_full; /* move16, single BASOP */
     170             :             }                                 /* BASOP 2 ops */
     171             : 
     172      395264 :             if ( st1_idx_pair[p_max] == j_full )
     173             :             {                              /* idx updated  -->  also update mse */
     174      162938 :                 st1_mse_pair[p_max] = mse; /* move32(), single BASOP  */
     175             :             }                              /* BASOP 3 ops */
     176             : 
     177             :             /* avoid WC costly candidate list management by always updating p_max,
     178             :                as we have only a pair in each segment to maintain */
     179      395264 :             p_max = 0;                                       /* move16() */
     180      395264 :             if ( ( st1_mse_pair[0] - st1_mse_pair[1] ) < 0 ) /* L_sub()*/
     181             :             {
     182      201646 :                 p_max = 1; /*  move16() */
     183             :             }              /* BASOP 3 ops  ,Note  2 ops possible in BASOP with L_sub and  L_lshr  */
     184             : 
     185             :             /* Note: logical shift right not available in ANSI-C */
     186             :             /* p_max = (st1_mse_pair[0] - st1_mse_pair[1]) ">>>" 31; */
     187             :             /* in java logical shift right is available as  >>> ,  in BASOP  it is available as L_lshr */
     188             : 
     189             :             /* Cost: weighted sum with cond moves ('if') => 8 in float ,   7 in BASOP with L_lshr  */
     190             :         } /* j in section */
     191             : 
     192       12352 :         st1_mse_pair += 2; /* req. ptr init  */
     193       12352 :         st1_idx_pair += 2; /* req.  ptr init */
     194             : 
     195             :     } /* next segment */
     196             : 
     197       27792 :     for ( j = 0; j < maxC_st1; j++ )
     198             :     {
     199             :         /* compute_full mse using stored DCT24 domain  MSE's   */
     200             :         /* calculate MSE  from stage1 inner using existing  inner  DCT domain variables */
     201       24704 :         dist1_ptr[j] *= dct_scaleF[2]; /*  multiplication to get the DCT inner MSE scale  to the correct input domain   */
     202             :     }
     203             : 
     204        3088 :     assert( ( maxC_st1 >= 3 ) );
     205        3088 :     assert( ( maxC_st1 <= 8 ) );
     206             : 
     207        3088 :     p_max = maximum( dist1_ptr, maxC_st1, NULL ); /* establish  current worst candidate for MSVQ stage#2  among all  maxC_st1 candidates so far */
     208             : 
     209        3088 :     p_mins[0] = minimum( dist1_ptr, maxC_st1, NULL ); /* find best  entry among all maxC_pre   */
     210        3088 :     tmp = dist1_ptr[p_mins[0]];
     211        3088 :     dist1_ptr[p_mins[0]] = FLT_MAX; /* exclude 1st */
     212             : 
     213        3088 :     p_mins[1] = minimum( dist1_ptr, maxC_st1, NULL ); /* find 2nd best entry  */
     214        3088 :     tmp2 = dist1_ptr[p_mins[1]];
     215        3088 :     dist1_ptr[p_mins[1]] = FLT_MAX; /* exclude 2nd */
     216             : 
     217        3088 :     dist1_ptr[p_mins[0]] = tmp;  /* restore 1st */
     218        3088 :     dist1_ptr[p_mins[1]] = tmp2; /* restore 2nd */
     219             : 
     220        3088 :     idx_min[0] = indices_st1_local[p_mins[0]];
     221        3088 :     idx_min[1] = indices_st1_local[p_mins[1]];
     222             : 
     223             : 
     224             :     /* use global exclusion list to never reselect  the two  (best) global  MSE values sofar  */
     225        3088 :     st1_mse_ptr[idx_min[0]] = FLT_MAX; /* move32() */
     226        3088 :     st1_mse_ptr[idx_min[1]] = FLT_MAX; /* move32() */
     227             : 
     228             :     /* circular MSE-neigbour list in use to potentially replace some segment search candidates */
     229             :     /* using both 1st and 2nd best neighbours   in fwd and rev directions */
     230        3088 :     check_ind[0] = segm_neighbour_fwd[idx_min[0]];
     231        3088 :     check_ind[1] = segm_neighbour_rev[idx_min[0]];
     232             : 
     233        3088 :     check_ind[2] = segm_neighbour_fwd[idx_min[1]];
     234        3088 :     check_ind[3] = segm_neighbour_rev[idx_min[1]];
     235             : 
     236        3088 :     check_ind[4] = segm_neighbour_fwd[check_ind[0]];
     237        3088 :     check_ind[5] = segm_neighbour_rev[check_ind[1]];
     238             : 
     239        3088 :     check_ind[6] = segm_neighbour_fwd[check_ind[2]];
     240        3088 :     check_ind[FDCNG_VQ_DCT_NPOST - 1] = segm_neighbour_rev[check_ind[3]];
     241             : 
     242       27792 :     for ( i = 0; i < npost_check; i++ )
     243             :     {
     244             :         /*   move MSE from DCT-inner loop search  to  input synthesis domain */
     245             :         /*   multiplication by fdcng_dct_scaleF[2]   to get the float outer loop scale correct in IDCT synthesis domain  */
     246       24704 :         check_mse = st1_mse_ptr[check_ind[i]] * dct_scaleF[2];
     247             : 
     248       24704 :         if ( check_mse < dist1_ptr[p_max] )
     249             :         { /* new winner , replace worst */
     250       11929 :             dist1_ptr[p_max] = check_mse;
     251       11929 :             indices_st1_local[p_max] = check_ind[i];
     252       11929 :             st1_mse_ptr[check_ind[i]] = FLT_MAX;          /* exclude,   BASOP: move32() */
     253       11929 :             p_max = maximum( dist1_ptr, maxC_st1, NULL ); /* establish a new  current worst candidate   among all maxC */
     254             :         }
     255             :     }
     256             : 
     257             :     /* extract the selected stage one vectors in DCT_N domain , apply IDCT_N and scale up */
     258             :     /* always extract full length signal(e.g. 24) to be able to update WB(e.g.  N_in==21) candidate MSE values */
     259             :     /* in the case that only a part of the IDCT N  vector is in final use    */
     260             : 
     261             :     /* note: synthesis not yet fully parameterized/generalized for other IDCT lengths */
     262        3088 :     assert( N == 24 );
     263             :     {
     264       27792 :         for ( c = 0; c < maxC_st1; c++ )
     265             :         {
     266       24704 :             dec_FDCNG_MSVQ_stage1( indices_st1_local[c], N, invTrfMatrix, dcttype + 1, &( st1_syn_vec_ptr[c * N] ), NULL );
     267             :         }
     268             :     }
     269             : 
     270        3088 :     return p_max; /*ptr to worst performing candidate */
     271             : }
     272             : 
     273             : 
     274             : /*--------------------------------------------------------------------------*
     275             :  * msvq_stage1_dct_recalc_candidates_fdcng_wb()
     276             :  *
     277             :  * recalc MSE for fdcng WB(0..20) coeffs ,
     278             :            essentially subtract res21^2 ,res22^2, res23^2 that was included in stage1  MSE in the DCT24 domain truncated search,
     279             :            excludes the waveform contributions at pos 21,22,23 to the MSE, important to keep the WB MSEs update for the subsequent stages
     280             :  *--------------------------------------------------------------------------*/
     281             : 
     282             : /*! r: (updated p_max) */
     283         888 : int16_t msvq_stage1_dct_recalc_candidates_fdcng_wb(
     284             :     const float *st1_syn_vec_ptr, /* i  : IDCT24 synthesis vectors       */
     285             :     const float *u,               /* i  : target   signal                */
     286             :     const int16_t maxC_st1,       /* i  : number of candidates in stage1 */
     287             :     float *dist_ptr               /* i/o: updated  MSE vector for stage1 */
     288             : )
     289             : {
     290             :     int16_t p_max_local, c;
     291             :     const float *p2;
     292             :     float res24, high_diff[FDCNG_VQ_MAX_LEN - FDCNG_VQ_MAX_LEN_WB];
     293             : 
     294        7992 :     for ( c = 0; c < maxC_st1; c++ )
     295             :     {                                                                                          /* point to extended  synthesis part */
     296        7104 :         p2 = (const float *) &( st1_syn_vec_ptr[c * FDCNG_VQ_MAX_LEN + FDCNG_VQ_MAX_LEN_WB] ); /* ptr init to synthesis candidate c */
     297             :         /* for stage#1 use "u" instead of the shortened resid[0], to access the extended/extrapolated  input target */
     298        7104 :         v_sub( p2, &( u[FDCNG_VQ_MAX_LEN_WB] ), high_diff, FDCNG_VQ_MAX_LEN - FDCNG_VQ_MAX_LEN_WB );
     299        7104 :         res24 = dotp( high_diff, high_diff, FDCNG_VQ_MAX_LEN - FDCNG_VQ_MAX_LEN_WB ); /* sum squared over top  env. values above WB coeffs */
     300             : 
     301        7104 :         dist_ptr[c] -= res24; /* remove DCT24 high band error contribution */
     302             :     }
     303             : 
     304             :     /* finally update p_max,  as it may potentially change,
     305             :        due to the core DCT24 search originally optimizing over the longer basis vectors than DCT21 */
     306         888 :     p_max_local = maximum( dist_ptr, maxC_st1, NULL );
     307             : 
     308         888 :     return p_max_local;
     309             : }
     310             : 
     311             : 
     312             : /*--------------------------------------------------------------------------*
     313             :  * msvq_enc()
     314             :  *
     315             :  * MSVQ encoder
     316             :  *--------------------------------------------------------------------------*/
     317             : 
     318      126913 : void msvq_enc(
     319             :     const float *const *cb,      /* i  : Codebook (indexed cb[*stages][levels][p])            */
     320             :     const int16_t dims[],        /* i  : Dimension of each codebook stage (NULL: full dim.)   */
     321             :     const int16_t offs[],        /* i  : Starting dimension of each codebook stage (NULL: 0)  */
     322             :     const float u[],             /* i  : Vector to be encoded (prediction and mean removed)   */
     323             :     const int16_t *levels,       /* i  : Number of levels in each stage                       */
     324             :     const int16_t maxC,          /* i  : Tree search size (number of candidates kept from one stage to the next == M-best) */
     325             :     const int16_t stages,        /* i  : Number of stages                                     */
     326             :     const float w[],             /* i  : Weights                                              */
     327             :     const int16_t N,             /* i  : Vector dimension                                     */
     328             :     const int16_t maxN,          /* i  : Codebook dimension                                   */
     329             :     const int16_t applyDCT_flag, /* i  : applyDCT flag                                        */
     330             :     float *invTrfMatrix,         /* i/o: synthesis matrix                                     */
     331             :     int16_t Idx[]                /* o  : Indices                                              */
     332             : )
     333             : {
     334             :     float *resid[2], *dist[2];
     335             :     float en, tmp, *pTmp, *p1;
     336             :     const float *cb_stage, *cbp, *p2;
     337             :     int16_t *indices[2];
     338             :     int16_t j, m, s, c, c2, p_max, i;
     339             :     float resid_buf[2 * LSFMBEST_MAX * M_MAX], dist_buf[2 * LSFMBEST_MAX], Tmp[M_MAX];
     340             :     int16_t idx_buf[2 * LSFMBEST_MAX * MAX_VQ_STAGES_USED], parents[LSFMBEST_MAX];
     341             :     int16_t n, maxn, start;
     342             :     float *st1_syn_vec_ptr;                            /* ptr to buffer in dynRAM */
     343             :     float *st1_mse_ptr;                                /* ptr to  buffer in existing dRAM used for stage 1 candidate analysis */
     344             :     int16_t indices_st1_local[FDCNG_VQ_DCT_NSEGM * 2]; /* after stage#1 DCT search  this is copied to the global  indices[1][s*stages] structure */
     345      126913 :     assert( maxC <= LSFMBEST_MAX );
     346      126913 :     assert( ( LSFMBEST_MAX * M_MAX ) > ( N * maxC ) );
     347             :     /*   top of resid_buf  is   resid[1]  and used for stage#1 residuals (input target u),
     348             :          we here reuse  resid[0] part of the buffer for stage#1 DCT dynamic RAM needs  */
     349      126913 :     st1_mse_ptr = &( resid_buf[1 * LSFMBEST_MAX * M_MAX] ) - ( levels[0] ); /* reuse top of residual resid[0] scratch RAM for stage1 MSEs */
     350             : 
     351      126913 :     st1_syn_vec_ptr = &( resid_buf[1 * LSFMBEST_MAX * M_MAX] ) - FDCNG_VQ_MAX_LEN * maxC; /*   reuse top of resid[0] scratch RAM for residual */
     352             : 
     353             : 
     354             :     /*----------------------------------------------------------------*
     355             :      *   Allocate memory for previous (parent) and current nodes.
     356             :      *   Parent node is indexed [0], current node is indexed [1].
     357             :      *----------------------------------------------------------------*/
     358             : 
     359      126913 :     indices[0] = idx_buf;
     360      126913 :     indices[1] = idx_buf + maxC * stages;
     361      126913 :     set_s( idx_buf, 0, 2 * stages * maxC );
     362             : 
     363      126913 :     resid[0] = resid_buf;
     364      126913 :     pTmp = resid_buf + maxC * N;
     365      126913 :     resid[1] = pTmp;
     366             : 
     367      126913 :     dist[0] = dist_buf;
     368      126913 :     dist[1] = dist_buf + maxC;
     369      126913 :     set_s( parents, 0, maxC );
     370             : 
     371             :     /* Set up initial distance vector */
     372     2179561 :     for ( tmp = 0.0, j = 0; j < N; j++ )
     373             :     {
     374     2052648 :         tmp += u[j] * u[j] * w[j];
     375             :     }
     376      126913 :     set_f( dist[1], tmp, maxC );
     377             : 
     378             :     /* Set up initial error (residual) vectors */
     379      697662 :     for ( c = 0; c < maxC; c++ )
     380             :     {
     381     9879053 :         for ( i = 0; i < N; i++ )
     382             :         {
     383     9308304 :             *pTmp++ = u[i];
     384             :         }
     385             :     }
     386             : 
     387             :     /* Loop over all stages */
     388      495431 :     for ( m = 1, s = 0; s < stages; s++ )
     389             :     {
     390             :         /* codebook pointer is set to point to first stage */
     391      368518 :         cbp = cb[s];
     392             :         /* Save pointer to beginning of current stage */
     393      368518 :         cb_stage = cbp;
     394             : 
     395             :         /* Set up pointers to parent and current nodes */
     396             : #define WMC_TOOL_SKIP
     397      368518 :         swap( indices[0], indices[1], int16_t * );
     398             :         MOVE( 3 );
     399      368518 :         swap( resid[0], resid[1], float * );
     400             :         MOVE( 3 );
     401      368518 :         swap( dist[0], dist[1], float * );
     402             :         MOVE( 3 );
     403             : #undef WMC_TOOL_SKIP
     404             : 
     405             :         /* p_max points to maximum distortion node (worst of best) */
     406      368518 :         p_max = 0;
     407             : 
     408      368518 :         if ( dims )
     409             :         {
     410       69828 :             n = dims[s];
     411       69828 :             maxn = dims[s];
     412             :         }
     413             :         else
     414             :         {
     415      298690 :             n = N;
     416      298690 :             maxn = maxN;
     417             :         }
     418             : 
     419      368518 :         if ( offs )
     420             :         {
     421       69828 :             start = offs[s];
     422             :         }
     423             :         else
     424             :         {
     425      298690 :             start = 0;
     426             :         }
     427             : 
     428      368518 :         set_zero( Tmp, start );
     429      368518 :         set_zero( Tmp + start + n, N - ( start + n ) );
     430             :         /* Set distortions to a large value */
     431     1911692 :         for ( j = 0; j < maxC; j++ )
     432             :         {
     433     1543174 :             dist[1][j] = FLT_MAX;
     434             :         }
     435             : 
     436      368518 :         if ( !s && applyDCT_flag != 0 ) /* means: m==1 */
     437             :         {
     438             :             /* stage 1 candidates search in truncated dct24  domain without any weights  */
     439        3088 :             assert( N == FDCNG_VQ_MAX_LEN || N == FDCNG_VQ_MAX_LEN_WB ); /* 21 and 24 allowed */
     440        3088 :             assert( maxC == 2 * FDCNG_VQ_DCT_NSEGM );
     441             : 
     442        3088 :             p_max = msvq_stage1_dct_search( u, FDCNG_VQ_MAX_LEN, maxC, DCT_T2_24_XX, FDCNG_VQ_DCT_MAXTRUNC, invTrfMatrix, cdk1r_tr_midQ_truncQ, fdcng_dct_invScaleF, fdcng_dct_scaleF, FDCNG_VQ_DCT_NSEGM,
     443             :                                             cdk1_ivas_cols_per_segment, cdk1_ivas_trunc_dct_cols_per_segment, cdk1_ivas_entries_per_segment, cdk1_ivas_cum_entries_per_segment, cdk_37bits_ivas_stage1_W8Qx_dct_sections,
     444             :                                             stage1_dct_col_syn_shift, cdk1_ivas_segm_neighbour_fwd, cdk1_ivas_segm_neighbour_rev, FDCNG_VQ_DCT_NPOST, st1_mse_ptr, indices_st1_local, st1_syn_vec_ptr, dist[1] );
     445             : 
     446             : 
     447             :             /*    move established stage#1  indices  to the global MSVQ list structure */
     448       27792 :             for ( c = 0; c < maxC; c++ )
     449             :             {
     450       24704 :                 indices[1][c * stages] = indices_st1_local[c];
     451             :             }
     452             :         }
     453             :         else
     454             :             /* non-DCT Stage #1 code below */
     455      365430 :             if ( !s ) /* means: m==1 */
     456             :             {
     457             :                 /* This loop is identical to the one below, except, that the inner loop over c=0..m is hardcoded to c=0, since m=1.    */
     458             :                 /* dist[0][0] */
     459     8689653 :                 for ( j = 0; j < levels[s]; j++ )
     460             :                 {
     461     8565828 :                     en = 0.0f;
     462             :                     /* w,Tmp */
     463             :                     /* Compute weighted codebook element and its energy */
     464   144641484 :                     for ( c2 = 0; c2 < n; c2++ )
     465             :                     {
     466   136075656 :                         Tmp[start + c2] = w[start + c2] * cbp[c2];
     467   136075656 :                         en += cbp[c2] * Tmp[start + c2];
     468             :                     }
     469     8565828 :                     cbp += maxn; /*  pointer is incremented */
     470             : 
     471     8565828 :                     pTmp = &resid[0][0];
     472             :                     /* Tmp */
     473     8565828 :                     tmp = ( *pTmp++ ) * Tmp[0];
     474   137053248 :                     for ( c2 = 1; c2 < N; c2++ )
     475             :                     {
     476   128487420 :                         tmp += ( *pTmp++ ) * Tmp[c2];
     477             :                     }
     478     8565828 :                     tmp = en - 2.0f * tmp;
     479     8565828 :                     tmp += dist[0][0];
     480     8565828 :                     if ( tmp < dist[1][p_max] )
     481             :                     {
     482             :                         /* Replace worst */
     483     1574549 :                         dist[1][p_max] = tmp;
     484     1574549 :                         indices[1][p_max * stages] = j;
     485     1574549 :                         parents[p_max] = 0;
     486             : 
     487     1574549 :                         p_max = 0;
     488     6623762 :                         for ( c2 = 1; c2 < maxC; c2++ )
     489             :                         {
     490     5049213 :                             if ( dist[1][c2] > dist[1][p_max] )
     491             :                             {
     492     1690979 :                                 p_max = c2;
     493             :                             }
     494             :                         }
     495             :                     } /* if (tmp <= dist[1][p_max]) */
     496             :                 }     /* for (j=0; j<levels[s]; j++) */
     497             :                 /* update p_max location , for next stage */
     498      123825 :                 p_max = maximum( dist[1], maxC, NULL );
     499             :             }
     500             :             else
     501             :             {
     502             :                 /* subsequent stages  after first stage */
     503             :                 /* dist[0][0] */
     504     9377629 :                 for ( j = 0; j < levels[s]; j++ )
     505             :                 {
     506     9136024 :                     en = 0.0f;
     507             :                     /* w,Tmp */
     508             :                     /* Compute weighted codebook element and its energy */
     509   157533592 :                     for ( c2 = 0; c2 < n; c2++ )
     510             :                     {
     511   148397568 :                         Tmp[start + c2] = w[start + c2] * cbp[c2];
     512   148397568 :                         en += cbp[c2] * Tmp[start + c2];
     513             :                     }
     514     9136024 :                     cbp += maxn; /*  pointer is incremented */
     515             : 
     516             :                     /* dist[0][0] */
     517     9136024 :                     pTmp = &resid[0][0];
     518             :                     /* Iterate over all parent nodes */
     519    44011776 :                     for ( c = 0; c < m; c++ )
     520             :                     {
     521             :                         /* Tmp[0] */
     522    34875752 :                         tmp = ( *pTmp++ ) * Tmp[0];
     523   611533440 :                         for ( c2 = 1; c2 < N; c2++ )
     524             :                         {
     525   576657688 :                             tmp += ( *pTmp++ ) * Tmp[c2];
     526             :                         }
     527    34875752 :                         tmp = en - 2.0f * tmp;
     528    34875752 :                         tmp += dist[0][c];
     529    34875752 :                         if ( tmp < dist[1][p_max] )
     530             :                         {
     531             :                             /* Replace worst */
     532     4442099 :                             dist[1][p_max] = tmp;
     533     4442099 :                             indices[1][p_max * stages + s] = j;
     534     4442099 :                             parents[p_max] = c;
     535             : 
     536     4442099 :                             p_max = 0;
     537    22111502 :                             for ( c2 = 1; c2 < maxC; c2++ )
     538             :                             {
     539    17669403 :                                 if ( dist[1][c2] > dist[1][p_max] )
     540             :                                 {
     541     5443201 :                                     p_max = c2;
     542             :                                 }
     543             :                             }
     544             :                         } /* if (tmp <= dist[1][p_max]) */
     545             :                     }     /* for(c=0; c<m; c++) */
     546             :                 }         /* for (j=0; j<levels[s]; j++) */
     547             :             }
     548             : 
     549             :         /*------------------------------------------------------------*
     550             :          * Compute error vectors for each node
     551             :          *------------------------------------------------------------*/
     552             :         /* parents[0] */
     553      368518 :         pTmp = resid[1];
     554     1911692 :         for ( c = 0; c < maxC; c++ )
     555             :         {
     556             :             /* Subtract codebook entry from residual vector of parent node  */
     557     1543174 :             p1 = resid[0] + parents[c] * N;
     558     1543174 :             p2 = NULL;
     559     1543174 :             if ( cb_stage != NULL )
     560             :             {
     561     1518470 :                 p2 = cb_stage + ( indices[1][c * stages + s] ) * maxn; /* regular ptr init */
     562             :             }
     563     1543174 :             if ( s == 0 && applyDCT_flag != 0 )
     564             :             {
     565       24704 :                 p2 = (const float *) &( st1_syn_vec_ptr[c * FDCNG_VQ_MAX_LEN] ); /*ptr init of stage 1 */
     566             :             }
     567             : 
     568     1543174 :             mvr2r( p1, pTmp, start );
     569    23056870 :             for ( j = 0; j < n; j++ )
     570             :             {
     571    21513696 :                 pTmp[start + j] = ( p1[start + j] - p2[j] );
     572             :             }
     573     1543174 :             mvr2r( p1 + start + n, pTmp + start + n, N - ( start + n ) );
     574     1543174 :             pTmp += N; /*  pointer is incremented */
     575             : 
     576             :             /* Get indices that were used for parent node */
     577     1543174 :             mvs2s( indices[0] + parents[c] * stages, indices[1] + c * stages, s );
     578             :         } /* for (c=0; c<maxC; c++) */
     579             : 
     580             :         /* recalc MSE for WB(0..20) coeffs ,
     581             :            essentially subtract res21^2 ,res22^2, res23^2 that was included in stage1  MSE in the DCT24 domain truncated search,
     582             :            excludes the waveform contributions at pos 21,22,23 to the MSE, important to keep WB MSEs update for the subsequent stages
     583             :            */
     584      368518 :         if ( s == 0 && applyDCT_flag != 0 && n == FDCNG_VQ_MAX_LEN_WB )
     585             :         {
     586         888 :             p_max = msvq_stage1_dct_recalc_candidates_fdcng_wb( st1_syn_vec_ptr, u, maxC, dist[1] );
     587             :         }
     588      368518 :         m = maxC;
     589             :     } /* for (m=1, s=0; s<stages; s++) */
     590             : 
     591             :     /* Find the optimum candidate */
     592      126913 :     c2 = minimum( dist[1], maxC, 0 );
     593      126913 :     mvs2s( indices[1] + c2 * stages, Idx, stages );
     594             : 
     595      126913 :     return;
     596             : }
     597             : 
     598             : /*--------------------------------------------------------------------------*
     599             :  * lsf_msvq_ma_encprm()
     600             :  *
     601             :  *
     602             :  *--------------------------------------------------------------------------*/
     603             : 
     604      111839 : int16_t lsf_msvq_ma_encprm(
     605             :     BSTR_ENC_HANDLE hBstr,
     606             :     const int16_t *param_lpc,
     607             :     const int16_t core,
     608             :     const int16_t acelp_mode,
     609             :     const int16_t acelp_midLpc,
     610             :     const int16_t bits_param_lpc[],
     611             :     const int16_t no_indices )
     612             : {
     613             :     int16_t i, nbits_lpc, bits_midlpc;
     614             : 
     615      111839 :     bits_midlpc = MIDLSF_NBITS;
     616             : 
     617      111839 :     nbits_lpc = 0;
     618      459980 :     for ( i = 0; i < no_indices; i++ )
     619             :     {
     620      348141 :         push_next_indice( hBstr, *param_lpc, bits_param_lpc[i] );
     621      348141 :         param_lpc++;
     622      348141 :         nbits_lpc += bits_param_lpc[i];
     623             :     }
     624      111839 :     if ( acelp_mode != VOICED )
     625             :     {
     626       88191 :         if ( core == ACELP_CORE && acelp_midLpc )
     627             :         {
     628         336 :             push_next_indice( hBstr, *param_lpc, bits_midlpc );
     629         336 :             nbits_lpc += bits_midlpc;
     630             :         }
     631             :     }
     632             : 
     633      111839 :     return nbits_lpc;
     634             : }
     635             : 
     636             : /*--------------------------------------------------------------------------*
     637             :  * midlsf_enc()
     638             :  *
     639             :  *
     640             :  *--------------------------------------------------------------------------*/
     641             : 
     642         717 : void midlsf_enc(
     643             :     const float qlsf0[],
     644             :     const float qlsf1[],
     645             :     const float lsf[],
     646             :     int16_t *idx,
     647             :     const int16_t N,
     648             :     const float *Bin_Ener,
     649             :     const int16_t narrowBand,
     650             :     const int32_t sr_core,
     651             :     const int16_t coder_type )
     652             : {
     653             :     float pred[M], wghts[M], err, err_min, tmp;
     654             :     int16_t NS, j, k;
     655         717 :     const float *ratio = NULL;
     656             : 
     657             :     /* Select codebook */
     658         717 :     if ( coder_type == UNVOICED )
     659             :     {
     660          26 :         ratio = tbl_mid_unv_wb_5b;
     661             :     }
     662             :     else
     663             :     {
     664         691 :         ratio = tbl_mid_gen_wb_5b;
     665             :     }
     666         717 :     NS = 32;
     667             : 
     668             :     /* Weights */
     669         717 :     Unified_weighting( Bin_Ener, lsf, wghts, narrowBand, coder_type == UNVOICED, sr_core, M );
     670         717 :     err_min = FLT_MAX;
     671         717 :     *idx = 0;
     672       23661 :     for ( k = 0; k < NS; k++ )
     673             :     {
     674       22944 :         err = 0;
     675             : 
     676      390048 :         for ( j = 0; j < N; j++ )
     677             :         {
     678      367104 :             pred[j] = ( 1.0f - ratio[k * N + j] ) * qlsf0[j] + ratio[k * N + j] * qlsf1[j];
     679             : 
     680      367104 :             if ( j > 0 && j < N && pred[j] < pred[j - 1] + LSF_GAP_MID )
     681             :             {
     682        2179 :                 pred[j] = pred[j - 1] + LSF_GAP_MID;
     683             :             }
     684             : 
     685      367104 :             tmp = lsf[j] - pred[j];
     686      367104 :             err += wghts[j] * tmp * tmp;
     687             :         }
     688             : 
     689       22944 :         if ( err < err_min )
     690             :         {
     691        2864 :             err_min = err;
     692        2864 :             *idx = k;
     693             :         }
     694             :     }
     695             : 
     696         717 :     return;
     697             : }
     698             : 
     699             : 
     700             : /*--------------------------------------------------------------------------*
     701             :  * Q_lsf_tcxlpc()
     702             :  *
     703             :  *
     704             :  *--------------------------------------------------------------------------*/
     705             : 
     706             : /*! r: number of indices */
     707       17457 : int16_t Q_lsf_tcxlpc(
     708             :     /* const */ float lsf[],  /* i  : original lsf                         */
     709             :     float lsf_q[],            /* o  : quantized lsf                        */
     710             :     Word16 lsp_q_ind[],       /* o  : quantized lsp (w/o MA prediction)    */
     711             :     int16_t indices[],        /* o  : VQ indices                           */
     712             :     const int16_t narrowband, /* i  : narrowband flag                      */
     713             :     const int16_t cdk,        /* i  : codebook selector                    */
     714             :     const float mem_MA[],     /* i  : MA memory                            */
     715             :     const int16_t coder_type, /* i  : acelp extended mode                  */
     716             :     const float *Bin_Ener     /* i  : Spectrum energy                      */
     717             : )
     718             : {
     719             :     float weights[M];
     720             :     float pred[M16k];
     721             :     int16_t i, NumIndices;
     722             :     const float *means;
     723             :     Word16 lsf_q_ind[M16k];
     724             :     float lsf_rem[M];
     725             :     float lsf_rem_q[M];
     726             :     Word16 lsf_rem_q_ind[M];
     727             : 
     728       17457 :     Unified_weighting( &Bin_Ener[L_FFT / 2], lsf, weights, narrowband, coder_type == UNVOICED, 12800, M );
     729             : 
     730       17457 :     NumIndices = 0;
     731             : 
     732             :     /* Put disabled flag */
     733       17457 :     indices[NumIndices++] = 0;
     734             : 
     735             :     /* Inter-frame prediction */
     736       17457 :     means = lsf_means[narrowband];
     737      296769 :     for ( i = 0; i < M; ++i )
     738             :     {
     739      279312 :         pred[i] = means[i] + MU_MA * mem_MA[i];
     740             :     }
     741             : 
     742             :     /* Subtract prediction */
     743      296769 :     for ( i = 0; i < M; ++i )
     744             :     {
     745      279312 :         lsf[i] -= pred[i];
     746             :     }
     747             : 
     748             : 
     749       17457 :     msvq_enc( lsf_codebook[narrowband][cdk], lsf_dims, lsf_offs, lsf, lsf_numlevels, kMaxC, TCXLPC_NUMSTAGES, weights, M, M, 0, NULL, indices + NumIndices );
     750       17457 :     msvq_dec( lsf_codebook[narrowband][cdk], lsf_dims, lsf_offs, TCXLPC_NUMSTAGES, M, M, indices + NumIndices, 0, NULL, lsf_q, lsf_q_ind );
     751             : 
     752       17457 :     NumIndices += TCXLPC_NUMSTAGES;
     753             : 
     754             :     /* Update flag */
     755       17457 :     indices[0] = lsf_ind_is_active( lsf_q_ind, lsf_means[narrowband], narrowband, cdk );
     756             : 
     757             :     /* Get residual vector */
     758      296769 :     for ( i = 0; i < M; ++i )
     759             :     {
     760      279312 :         lsf_rem[i] = ( pred[i] + lsf[i] ) - ( lsf_means[narrowband][i] + lsf_q_ind[i] / (float) ( 2.0f * 1.28f ) );
     761             :     }
     762             :     /* Quantize using extra stage(s) */
     763       17457 :     msvq_enc( lsf_ind_codebook[narrowband][cdk], lsf_ind_dims, lsf_ind_offs, lsf_rem, lsf_ind_numlevels, kMaxC, TCXLPC_IND_NUMSTAGES, weights, M, M, 0, NULL, indices + NumIndices );
     764             : 
     765             :     /* Only add contribution if flag is enabled */
     766       17457 :     if ( indices[0] )
     767             :     {
     768             :         /* Decode */
     769        4832 :         msvq_dec( lsf_ind_codebook[narrowband][cdk], lsf_ind_dims, lsf_ind_offs, TCXLPC_IND_NUMSTAGES, M, M, indices + NumIndices, 0, NULL, lsf_rem_q, lsf_rem_q_ind );
     770        4832 :         NumIndices += TCXLPC_IND_NUMSTAGES;
     771             : 
     772             :         /* Add to MA-removed vector */
     773       82144 :         for ( i = 0; i < M; ++i )
     774             :         {
     775       77312 :             lsf_q_ind[i] = add( lsf_q_ind[i], lsf_rem_q_ind[i] );
     776             :         }
     777             :     }
     778             : 
     779             :     /* Add inter-frame prediction */
     780      296769 :     for ( i = 0; i < M; ++i )
     781             :     {
     782      279312 :         lsf_q[i] += pred[i];
     783      279312 :         lsf[i] += pred[i];
     784             :     }
     785             : 
     786       17457 :     reorder_lsf( lsf_q, TCXLPC_LSF_GAP, M, INT_FS_12k8 );
     787      296769 :     for ( i = 0; i < M; ++i )
     788             :     {
     789      279312 :         lsf_q_ind[i] = add( lsf_q_ind[i], LSFM( lsf_means[narrowband][i] ) );
     790      279312 :         move16();
     791             :     }
     792             : 
     793       17457 :     basop_reorder_lsf( lsf_q_ind, LSF_GAP_VAL( TCXLPC_LSF_GAP ), M, INT_FS_FX );
     794       17457 :     if ( lsp_q_ind )
     795             :     {
     796       17457 :         basop_lsf2lsp( lsf_q_ind, lsp_q_ind );
     797             :     }
     798             : 
     799       17457 :     return NumIndices;
     800             : }
     801             : 
     802             : 
     803             : /*--------------------------------------------------------------------------*
     804             :  * enc_lsf_tcxlpc()
     805             :  *
     806             :  *
     807             :  *--------------------------------------------------------------------------*/
     808             : 
     809             : /*! r: number of bits written */
     810       17457 : int16_t enc_lsf_tcxlpc(
     811             :     const int16_t **indices, /* i  : Ptr to VQ indices           */
     812             :     BSTR_ENC_HANDLE hBstr    /* i/o: encoder bitstream handle    */
     813             : )
     814             : {
     815             :     int16_t i, NumBits, flag;
     816             : 
     817             :     /* Read flag */
     818       17457 :     flag = ( *indices )[0];
     819       17457 :     ++*indices;
     820             : 
     821       17457 :     NumBits = TCXLPC_NUMBITS;
     822       69828 :     for ( i = 0; i < TCXLPC_NUMSTAGES; ++i )
     823             :     {
     824       52371 :         push_next_indice( hBstr, **indices, lsf_numbits[i] );
     825       52371 :         ++*indices;
     826             :     }
     827       17457 :     if ( flag )
     828             :     {
     829        4832 :         NumBits += TCXLPC_IND_NUMBITS;
     830        9664 :         for ( i = 0; i < TCXLPC_IND_NUMSTAGES; ++i )
     831             :         {
     832        4832 :             push_next_indice( hBstr, **indices, lsf_ind_numbits[i] );
     833        4832 :             ++*indices;
     834             :         }
     835             :     }
     836             : 
     837       17457 :     return NumBits;
     838             : }
     839             : 
     840             : 
     841             : /*--------------------------------------------------------------------------*
     842             :  * lsf_bctcvq_encprm()
     843             :  *
     844             :  *
     845             :  *--------------------------------------------------------------------------*/
     846             : 
     847         268 : int16_t lsf_bctcvq_encprm(
     848             :     BSTR_ENC_HANDLE hBstr,
     849             :     const int16_t *param_lpc,
     850             :     const int16_t *bits_param_lpc,
     851             :     const int16_t no_indices )
     852             : {
     853             :     int16_t i, nbits_lpc;
     854             : 
     855         268 :     nbits_lpc = 0;
     856             : 
     857        2948 :     for ( i = 0; i < no_indices; i++ )
     858             :     {
     859        2680 :         push_next_indice( hBstr, *param_lpc, bits_param_lpc[i] );
     860        2680 :         param_lpc++;
     861        2680 :         nbits_lpc += bits_param_lpc[i];
     862             :     }
     863             : 
     864         268 :     return nbits_lpc;
     865             : }

Generated by: LCOV version 1.14