1/***********************************************************************
2Copyright (c) 2006-2011, Skype Limited. All rights reserved.
3Redistribution and use in source and binary forms, with or without
4modification, are permitted provided that the following conditions
5are met:
6- Redistributions of source code must retain the above copyright notice,
7this list of conditions and the following disclaimer.
8- Redistributions in binary form must reproduce the above copyright
9notice, this list of conditions and the following disclaimer in the
10documentation and/or other materials provided with the distribution.
11- Neither the name of Internet Society, IETF or IETF Trust, nor the
12names of specific contributors, may be used to endorse or promote
13products derived from this software without specific prior written
14permission.
15THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
16AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
19LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
20CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
21SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
22INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
23CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
24ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25POSSIBILITY OF SUCH DAMAGE.
26***********************************************************************/
27
28#ifdef HAVE_CONFIG_H
29#include "config.h"
30#endif
31
32#include "main.h"
33#include "stack_alloc.h"
34
35/**********************************************************/
36/* Core decoder. Performs inverse NSQ operation LTP + LPC */
37/**********************************************************/
38void silk_decode_core(
39    silk_decoder_state          *psDec,                         /* I/O  Decoder state                               */
40    silk_decoder_control        *psDecCtrl,                     /* I    Decoder control                             */
41    opus_int16                  xq[],                           /* O    Decoded speech                              */
42    const opus_int              pulses[ MAX_FRAME_LENGTH ]      /* I    Pulse signal                                */
43)
44{
45    opus_int   i, k, lag = 0, start_idx, sLTP_buf_idx, NLSF_interpolation_flag, signalType;
46    opus_int16 *A_Q12, *B_Q14, *pxq, A_Q12_tmp[ MAX_LPC_ORDER ];
47    VARDECL( opus_int16, sLTP );
48    VARDECL( opus_int32, sLTP_Q15 );
49    opus_int32 LTP_pred_Q13, LPC_pred_Q10, Gain_Q10, inv_gain_Q31, gain_adj_Q16, rand_seed, offset_Q10;
50    opus_int32 *pred_lag_ptr, *pexc_Q14, *pres_Q14;
51    VARDECL( opus_int32, res_Q14 );
52    VARDECL( opus_int32, sLPC_Q14 );
53    SAVE_STACK;
54
55    silk_assert( psDec->prev_gain_Q16 != 0 );
56
57    ALLOC( sLTP, psDec->ltp_mem_length, opus_int16 );
58    ALLOC( sLTP_Q15, psDec->ltp_mem_length + psDec->frame_length, opus_int32 );
59    ALLOC( res_Q14, psDec->subfr_length, opus_int32 );
60    ALLOC( sLPC_Q14, psDec->subfr_length + MAX_LPC_ORDER, opus_int32 );
61
62    offset_Q10 = silk_Quantization_Offsets_Q10[ psDec->indices.signalType >> 1 ][ psDec->indices.quantOffsetType ];
63
64    if( psDec->indices.NLSFInterpCoef_Q2 < 1 << 2 ) {
65        NLSF_interpolation_flag = 1;
66    } else {
67        NLSF_interpolation_flag = 0;
68    }
69
70    /* Decode excitation */
71    rand_seed = psDec->indices.Seed;
72    for( i = 0; i < psDec->frame_length; i++ ) {
73        rand_seed = silk_RAND( rand_seed );
74        psDec->exc_Q14[ i ] = silk_LSHIFT( (opus_int32)pulses[ i ], 14 );
75        if( psDec->exc_Q14[ i ] > 0 ) {
76            psDec->exc_Q14[ i ] -= QUANT_LEVEL_ADJUST_Q10 << 4;
77        } else
78        if( psDec->exc_Q14[ i ] < 0 ) {
79            psDec->exc_Q14[ i ] += QUANT_LEVEL_ADJUST_Q10 << 4;
80        }
81        psDec->exc_Q14[ i ] += offset_Q10 << 4;
82        if( rand_seed < 0 ) {
83           psDec->exc_Q14[ i ] = -psDec->exc_Q14[ i ];
84        }
85
86        rand_seed = silk_ADD32_ovflw( rand_seed, pulses[ i ] );
87    }
88
89    /* Copy LPC state */
90    silk_memcpy( sLPC_Q14, psDec->sLPC_Q14_buf, MAX_LPC_ORDER * sizeof( opus_int32 ) );
91
92    pexc_Q14 = psDec->exc_Q14;
93    pxq      = xq;
94    sLTP_buf_idx = psDec->ltp_mem_length;
95    /* Loop over subframes */
96    for( k = 0; k < psDec->nb_subfr; k++ ) {
97        pres_Q14 = res_Q14;
98        A_Q12 = psDecCtrl->PredCoef_Q12[ k >> 1 ];
99
100        /* Preload LPC coeficients to array on stack. Gives small performance gain */
101        silk_memcpy( A_Q12_tmp, A_Q12, psDec->LPC_order * sizeof( opus_int16 ) );
102        B_Q14        = &psDecCtrl->LTPCoef_Q14[ k * LTP_ORDER ];
103        signalType   = psDec->indices.signalType;
104
105        Gain_Q10     = silk_RSHIFT( psDecCtrl->Gains_Q16[ k ], 6 );
106        inv_gain_Q31 = silk_INVERSE32_varQ( psDecCtrl->Gains_Q16[ k ], 47 );
107
108        /* Calculate gain adjustment factor */
109        if( psDecCtrl->Gains_Q16[ k ] != psDec->prev_gain_Q16 ) {
110            gain_adj_Q16 =  silk_DIV32_varQ( psDec->prev_gain_Q16, psDecCtrl->Gains_Q16[ k ], 16 );
111
112            /* Scale short term state */
113            for( i = 0; i < MAX_LPC_ORDER; i++ ) {
114                sLPC_Q14[ i ] = silk_SMULWW( gain_adj_Q16, sLPC_Q14[ i ] );
115            }
116        } else {
117            gain_adj_Q16 = (opus_int32)1 << 16;
118        }
119
120        /* Save inv_gain */
121        silk_assert( inv_gain_Q31 != 0 );
122        psDec->prev_gain_Q16 = psDecCtrl->Gains_Q16[ k ];
123
124        /* Avoid abrupt transition from voiced PLC to unvoiced normal decoding */
125        if( psDec->lossCnt && psDec->prevSignalType == TYPE_VOICED &&
126            psDec->indices.signalType != TYPE_VOICED && k < MAX_NB_SUBFR/2 ) {
127
128            silk_memset( B_Q14, 0, LTP_ORDER * sizeof( opus_int16 ) );
129            B_Q14[ LTP_ORDER/2 ] = SILK_FIX_CONST( 0.25, 14 );
130
131            signalType = TYPE_VOICED;
132            psDecCtrl->pitchL[ k ] = psDec->lagPrev;
133        }
134
135        if( signalType == TYPE_VOICED ) {
136            /* Voiced */
137            lag = psDecCtrl->pitchL[ k ];
138
139            /* Re-whitening */
140            if( k == 0 || ( k == 2 && NLSF_interpolation_flag ) ) {
141                /* Rewhiten with new A coefs */
142                start_idx = psDec->ltp_mem_length - lag - psDec->LPC_order - LTP_ORDER / 2;
143                silk_assert( start_idx > 0 );
144
145                if( k == 2 ) {
146                    silk_memcpy( &psDec->outBuf[ psDec->ltp_mem_length ], xq, 2 * psDec->subfr_length * sizeof( opus_int16 ) );
147                }
148
149                silk_LPC_analysis_filter( &sLTP[ start_idx ], &psDec->outBuf[ start_idx + k * psDec->subfr_length ],
150                    A_Q12, psDec->ltp_mem_length - start_idx, psDec->LPC_order );
151
152                /* After rewhitening the LTP state is unscaled */
153                if( k == 0 ) {
154                    /* Do LTP downscaling to reduce inter-packet dependency */
155                    inv_gain_Q31 = silk_LSHIFT( silk_SMULWB( inv_gain_Q31, psDecCtrl->LTP_scale_Q14 ), 2 );
156                }
157                for( i = 0; i < lag + LTP_ORDER/2; i++ ) {
158                    sLTP_Q15[ sLTP_buf_idx - i - 1 ] = silk_SMULWB( inv_gain_Q31, sLTP[ psDec->ltp_mem_length - i - 1 ] );
159                }
160            } else {
161                /* Update LTP state when Gain changes */
162                if( gain_adj_Q16 != (opus_int32)1 << 16 ) {
163                    for( i = 0; i < lag + LTP_ORDER/2; i++ ) {
164                        sLTP_Q15[ sLTP_buf_idx - i - 1 ] = silk_SMULWW( gain_adj_Q16, sLTP_Q15[ sLTP_buf_idx - i - 1 ] );
165                    }
166                }
167            }
168        }
169
170        /* Long-term prediction */
171        if( signalType == TYPE_VOICED ) {
172            /* Set up pointer */
173            pred_lag_ptr = &sLTP_Q15[ sLTP_buf_idx - lag + LTP_ORDER / 2 ];
174            for( i = 0; i < psDec->subfr_length; i++ ) {
175                /* Unrolled loop */
176                /* Avoids introducing a bias because silk_SMLAWB() always rounds to -inf */
177                LTP_pred_Q13 = 2;
178                LTP_pred_Q13 = silk_SMLAWB( LTP_pred_Q13, pred_lag_ptr[  0 ], B_Q14[ 0 ] );
179                LTP_pred_Q13 = silk_SMLAWB( LTP_pred_Q13, pred_lag_ptr[ -1 ], B_Q14[ 1 ] );
180                LTP_pred_Q13 = silk_SMLAWB( LTP_pred_Q13, pred_lag_ptr[ -2 ], B_Q14[ 2 ] );
181                LTP_pred_Q13 = silk_SMLAWB( LTP_pred_Q13, pred_lag_ptr[ -3 ], B_Q14[ 3 ] );
182                LTP_pred_Q13 = silk_SMLAWB( LTP_pred_Q13, pred_lag_ptr[ -4 ], B_Q14[ 4 ] );
183                pred_lag_ptr++;
184
185                /* Generate LPC excitation */
186                pres_Q14[ i ] = silk_ADD_LSHIFT32( pexc_Q14[ i ], LTP_pred_Q13, 1 );
187
188                /* Update states */
189                sLTP_Q15[ sLTP_buf_idx ] = silk_LSHIFT( pres_Q14[ i ], 1 );
190                sLTP_buf_idx++;
191            }
192        } else {
193            pres_Q14 = pexc_Q14;
194        }
195
196        for( i = 0; i < psDec->subfr_length; i++ ) {
197            /* Short-term prediction */
198            silk_assert( psDec->LPC_order == 10 || psDec->LPC_order == 16 );
199            /* Avoids introducing a bias because silk_SMLAWB() always rounds to -inf */
200            LPC_pred_Q10 = silk_RSHIFT( psDec->LPC_order, 1 );
201            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i -  1 ], A_Q12_tmp[ 0 ] );
202            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i -  2 ], A_Q12_tmp[ 1 ] );
203            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i -  3 ], A_Q12_tmp[ 2 ] );
204            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i -  4 ], A_Q12_tmp[ 3 ] );
205            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i -  5 ], A_Q12_tmp[ 4 ] );
206            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i -  6 ], A_Q12_tmp[ 5 ] );
207            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i -  7 ], A_Q12_tmp[ 6 ] );
208            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i -  8 ], A_Q12_tmp[ 7 ] );
209            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i -  9 ], A_Q12_tmp[ 8 ] );
210            LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i - 10 ], A_Q12_tmp[ 9 ] );
211            if( psDec->LPC_order == 16 ) {
212                LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i - 11 ], A_Q12_tmp[ 10 ] );
213                LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i - 12 ], A_Q12_tmp[ 11 ] );
214                LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i - 13 ], A_Q12_tmp[ 12 ] );
215                LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i - 14 ], A_Q12_tmp[ 13 ] );
216                LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i - 15 ], A_Q12_tmp[ 14 ] );
217                LPC_pred_Q10 = silk_SMLAWB( LPC_pred_Q10, sLPC_Q14[ MAX_LPC_ORDER + i - 16 ], A_Q12_tmp[ 15 ] );
218            }
219
220            /* Add prediction to LPC excitation */
221            sLPC_Q14[ MAX_LPC_ORDER + i ] = silk_ADD_LSHIFT32( pres_Q14[ i ], LPC_pred_Q10, 4 );
222
223            /* Scale with gain */
224            pxq[ i ] = (opus_int16)silk_SAT16( silk_RSHIFT_ROUND( silk_SMULWW( sLPC_Q14[ MAX_LPC_ORDER + i ], Gain_Q10 ), 8 ) );
225        }
226
227        /* DEBUG_STORE_DATA( dec.pcm, pxq, psDec->subfr_length * sizeof( opus_int16 ) ) */
228
229        /* Update LPC filter state */
230        silk_memcpy( sLPC_Q14, &sLPC_Q14[ psDec->subfr_length ], MAX_LPC_ORDER * sizeof( opus_int32 ) );
231        pexc_Q14 += psDec->subfr_length;
232        pxq      += psDec->subfr_length;
233    }
234
235    /* Save LPC state */
236    silk_memcpy( psDec->sLPC_Q14_buf, sLPC_Q14, MAX_LPC_ORDER * sizeof( opus_int32 ) );
237    RESTORE_STACK;
238}
239