Commit cedd8d6f authored by Sandesh Venkatesh's avatar Sandesh Venkatesh
Browse files

Fix for EVS BE issue

parent c7d647c3
Loading
Loading
Loading
Loading
Loading
+191 −2
Original line number Diff line number Diff line
@@ -2125,6 +2125,196 @@ static void first_VQstages(
    set16_fx( idx_buf, 0, ( const Word16 )( 2 * stagesVQ * maxC ) );
    set16_fx( parents, 0, maxC );

    /* Set up inital distance vector */
    L_tmp = L_deposit_l( 0 );
    FOR( j = 0; j < N; j++ )
    {
        L_tmp1 = L_shl_o( L_mult0( u[j], w[j] ), 7, &Overflow ); /*x2.56 + Q8 + Q7 */
        L_tmp1 = Mult_32_16( L_tmp1, u[j] );                     /*x2.56 + Q15 + x2.56 -Q15 */
        L_tmp = L_add( L_tmp, L_tmp1 );                          /*Q0 + x2.56 +x2.56 */
    }
    set32_fx( dist[1], L_tmp, maxC );

    /* Set up initial error (residual) vectors */
    pTmp = resid[1];
    move16();
    FOR( c = 0; c < maxC; c++ )
    {
        Copy( u, pTmp, N );
        pTmp += N;
    }

    /*----------------------------------------------------------------*
     * LSF quantization
     *----------------------------------------------------------------*/

    /* Loop over all stages */
    m = 1;
    move16();
    FOR( s = 0; s < stagesVQ; s++ )
    {
        /* set codebook pointer to point to first stage */
        cbp = cb[s];
        move16();

        /* save pointer to the beginning of the current stage */
        cb_stage = cbp;
        move16();

        /* swap pointers to parent and current nodes */
        pTmp_short = indices[0];
        indices[0] = indices[1];
        move16();
        indices[1] = pTmp_short;
        move16();

        pTmp = resid[0];
        resid[0] = resid[1];
        move16();
        resid[1] = pTmp;
        move16();

        pTmp32 = dist[0];
        dist[0] = dist[1];
        move32();
        dist[1] = pTmp32;
        move32();

        /* p_max points to maximum distortion node (worst of best) */
        p_max = 0;
        move16();

        /* set distortions to a large value */
        set32_fx( dist[1], MAXINT32, maxC );

        FOR( j = 0; j < levels[s]; j++ )
        {
            /* compute weighted codebook element and its energy */
            FOR( c2 = 0; c2 < N; c2++ )
            {
                Tmp[c2] = shl( mult( w[c2], cbp[c2] ), 2 ); /* Q8 + x2.56 -Q15 +Q2 */
                move16();
            }

            en = L_mult( cbp[0], Tmp[0] );

            FOR( c2 = 1; c2 < N; c2++ )
            {
                en = L_mac( en, cbp[c2], Tmp[c2] ); /*x2.56 + x2.56 + Q-5 +Q1 */
            }
            cbp += N;
            move16();

            /* iterate over all parent nodes */
            FOR( c = 0; c < m; c++ )
            {
                pTmp = &resid[0][c * N];
                move16();
                L_tmp = L_mult( pTmp[0], Tmp[0] );
                FOR( c2 = 1; c2 < N; c2++ )
                {
                    L_tmp = L_mac( L_tmp, pTmp[c2], Tmp[c2] ); /* */
                }

                L_tmp = L_add( dist[0][c], L_sub( en, L_shl( L_tmp, 1 ) ) );

                IF( LE_32( L_tmp, dist[1][p_max] ) )
                {
                    /* replace worst */
                    dist[1][p_max] = L_tmp;
                    move32();
                    indices[1][p_max * stagesVQ + s] = j;
                    move16();
                    parents[p_max] = c;
                    move16();

                    /* limit number of times inner loop is entered */
                    IF( LT_16( counter, max_inner ) )
                    {
                        counter = add( counter, 1 );
                        IF( LT_16( counter, max_inner ) )
                        {
                            /* find new worst */
                            p_max = maximum_32_fx( dist[1], maxC, &f_tmp );
                        }
                        ELSE
                        {
                            /* find minimum distortion */
                            p_max = minimum_32_fx( dist[1], maxC, &f_tmp );
                        }
                    }
                }
            }
        }

        /*------------------------------------------------------------*
         * Compute error vectors for each node
         *------------------------------------------------------------*/
        cs = 0;
        move16();
        FOR( c = 0; c < maxC; c++ )
        {
            /* subtract codebook entry from the residual vector of the parent node */
            pTmp = resid[1] + c * N;
            move16();
            Copy( resid[0] + parents[c] * N, pTmp, N );
            Vr_subt( pTmp, cb_stage + ( indices[1][cs + s] ) * N, pTmp, N );

            /* get indices that were used for parent node */
            Copy( indices[0] + parents[c] * stagesVQ, indices[1] + cs, s );
            cs = add( cs, stagesVQ );
        }

        m = maxC;
        move16();
    }

    Copy( indices[1], indices_VQstage, maxC * stagesVQ );

    return;
}

static void first_VQstages_ivas_fx(
    const Word16 *const *cb,
    Word16 u[],       /* i  : vector to be encoded (prediction and mean removed)  */
    Word16 *levels,   /* i  : number of levels in each stage                      */
    Word16 stagesVQ,  /* i  : number of stages                                    */
    Word16 w[],       /* i  : weights                                             */
    Word16 N,         /* i  : vector dimension                                    */
    Word16 max_inner, /* i  : maximum number of swaps in inner loop               */
    Word16 indices_VQstage[] )
{
    Word16 resid_buf[2 * LSFMBEST * M], *resid[2];
    Word32 dist_buf[2 * LSFMBEST], *dist[2], en;
    Word32 f_tmp, L_tmp, L_tmp1, *pTmp32;
    Word16 Tmp[M], *pTmp, cs;
    Word16 *pTmp_short, idx_buf[2 * LSFMBEST * MAX_VQ_STAGES], parents[LSFMBEST], counter = 0, j,
                                                                                  m, s, c, c2, p_max, *indices[2];
    Word16 maxC = LSFMBEST;
#ifdef BASOP_NOGLOB_DECLARE_LOCAL
    Flag Overflow = 0;
#endif

    /*float dd[16];*/
    const Word16 *cb_stage, *cbp;

    /* Set pointers to previous (parent) and current node (parent node is indexed [0], current node is indexed [1]) */
    indices[0] = idx_buf;
    move16();
    indices[1] = idx_buf + maxC * stagesVQ;
    move16();
    resid[0] = resid_buf;
    move16();
    resid[1] = resid_buf + maxC * N;
    move16();
    dist[0] = dist_buf;
    move16();
    dist[1] = dist_buf + maxC;
    move16();

    set16_fx( idx_buf, 0, ( const Word16 )( 2 * stagesVQ * maxC ) );
    set16_fx( parents, 0, maxC );

    /* Set up inital distance vector */
    L_tmp = L_deposit_l( 0 );
    FOR( j = 0; j < N; j++ )
@@ -2273,7 +2463,6 @@ static void first_VQstages(

    return;
}

/*---------------------------------------------------------------------------
 * vq_enc_lsf_lvq()
 *
@@ -2457,7 +2646,7 @@ static Word32 vq_lvq_lsf_enc_ivas_fx(
    IF( stagesVQ > 0 )
    {
        /* first VQ stages */
        first_VQstages( cb, u, levels, stagesVQ, w, M, MSVQ_MAXCNT, indices_firstVQ );
        first_VQstages_ivas_fx( cb, u, levels, stagesVQ, w, M, MSVQ_MAXCNT, indices_firstVQ );
    }