Line data Source code
1 : /*====================================================================================
2 : EVS Codec 3GPP TS26.452 Aug 12, 2021. Version 16.3.0
3 : ====================================================================================*/
4 :
5 : #include <stdint.h>
6 : #include <assert.h>
7 : #include "options.h"
8 : #include "cnst.h"
9 : //#include "prot_fx.h"
10 : #include "basop_util.h"
11 : #include "options.h"
12 : #include "rom_basop_util.h"
13 : #include "rom_com.h" /* Common constants */
14 : #include "prot_fx.h" /* Function prototypes */
15 : #include "prot_fx_enc.h" /* Function prototypes */
16 : #include "basop_util.h" /* Function prototypes */
17 :
18 : /*-------------------------------------------------------------------*
19 : * coder_acelp_fx()
20 : *
21 : * Encode ACELP frame
22 : *-------------------------------------------------------------------*/
23 :
24 604 : Word16 coder_acelp_fx( /* o : SEGSNR for CL decision */
25 : const Word16 A[], /* i : coefficients 4xAz[M+1] Qx*/
26 : const Word16 Aq[], /* i : coefficients 4xAz_q[M+1] Q12*/
27 : const Word16 speech[], /* i : speech[-M..lg] Qx*/
28 : Word16 *prm, /* o : acelp parameters */
29 : Word16 stab_fac, /*Q15 */
30 : Encoder_State *st,
31 : PLC_ENC_EVS_HANDLE hPlc_Ext,
32 : const Word16 target_bits, /* i/o: coder memory state */
33 : const Word16 Q_new,
34 : const Word16 shift,
35 : Word16 *pitch_buf, /* o : pitch values for each subfr.*/
36 : Word16 *voice_factors, /* o : voicing factors Q15 */
37 : Word16 *bwe_exc /* o : excitation for SWB TBE Qx */
38 : )
39 : {
40 : Word16 i, i_subfr, j_subfr;
41 : Word16 tmp, Es_pred;
42 : Word16 T0, T0_min, T0_min_frac, T0_max, T0_max_frac, T0_res;
43 : Word16 T0_frac;
44 : Word16 gain_pit, voice_fac;
45 : Word32 gain_code, Ltmp, Ltmp2;
46 : ACELP_CbkCorr g_corr;
47 : const Word16 *p_A, *p_Aq;
48 : Word16 h1[L_SUBFR]; /* weighted impulse response of LP */
49 : Word16 code[L_SUBFR];
50 : Word16 xn_exp;
51 : Word16 Q_xn;
52 : Word16 Q_new_p5;
53 : Word16 cn[L_SUBFR];
54 : Word16 xn[L_SUBFR];
55 : Word16 y1[L_SUBFR]; /* Filtered adaptive excitation */
56 : Word16 y2[L_SUBFR]; /* Filtered adaptive excitation */
57 : Word16 res_save;
58 : Word16 exc_buf[L_EXC_MEM + L_DIV_MAX + 1], *exc;
59 : Word16 exc2[L_SUBFR];
60 : Word16 *syn, syn_buf[M + L_DIV_MAX + L_DIV_MAX / 2]; /*128 for the memory, L_DIV for the current synth and 128 for the ZIR for next TCX*/
61 : Word16 syn2[L_DIV_MAX];
62 : Word16 gain_inov;
63 : Word32 past_gcode;
64 : Word16 L_frame;
65 : Word16 clip_gain;
66 : Word32 gain_code2;
67 : Word16 code2[L_SUBFR];
68 : Word16 y22[L_SUBFR]; /* Filtered adaptive excitation */
69 604 : Word16 error = 0;
70 604 : move16();
71 604 : Word16 gain_preQ = 0; /* Gain of prequantizer excitation */
72 604 : move16();
73 : Word16 code_preQ[L_SUBFR]; /* Prequantizer excitation */
74 :
75 604 : Word16 dummy = 0;
76 604 : move16();
77 : ACELP_config *acelp_cfg;
78 : #ifdef BASOP_NOGLOB_DECLARE_LOCAL
79 604 : Flag Overflow = 0;
80 604 : move32();
81 : #endif
82 :
83 604 : acelp_cfg = &( st->acelp_cfg );
84 604 : LPD_state_HANDLE hLPDmem = st->hLPDmem;
85 604 : RF_ENC_HANDLE hRF = st->hRF;
86 604 : TD_BWE_ENC_HANDLE hBWE_TD = st->hBWE_TD;
87 604 : TCX_ENC_HANDLE hTcxEnc = st->hTcxEnc;
88 :
89 604 : set16_fx( code_preQ, 0, L_SUBFR );
90 :
91 :
92 604 : T0 = 0; /* to avoid compilation warnings */
93 604 : T0_frac = 0; /* to avoid compilation warnings */
94 604 : T0_res = 0; /* to avoid compilation warnings */
95 604 : gain_pit = 0; /* to avoid compilation warnings */
96 :
97 :
98 : /* Configure ACELP */
99 :
100 604 : BITS_ALLOC_config_acelp( target_bits, st->coder_type, acelp_cfg, st->narrowBand, st->nb_subfr );
101 :
102 : /* Init Framing parameters */
103 604 : move16();
104 604 : move16();
105 604 : move16();
106 604 : move16();
107 604 : L_frame = st->L_frame;
108 604 : move16();
109 :
110 : /*------------------------------------------------------------------------*
111 : * Previous frame is TCX (for non-EVS modes)(deactivated permanently) *
112 : *------------------------------------------------------------------------*/
113 :
114 : /*------------------------------------------------------------------------*
115 : * Initialize buffers *
116 : *------------------------------------------------------------------------*/
117 :
118 : /* Rescale ACELP memories, which were not scaled yet*/
119 604 : xn_exp = sub( sub( 15 + 1, Q_new ), shift );
120 604 : Q_xn = add( sub( Q_new, 1 ), shift );
121 604 : Q_new_p5 = add( Q_new, 5 );
122 :
123 : /* Reset phase dispersion */
124 604 : IF( st->last_core > ACELP_CORE )
125 : {
126 30 : move16();
127 30 : move16();
128 :
129 30 : hLPDmem->dm_fx.prev_gain_code = 0;
130 30 : set16_fx( hLPDmem->dm_fx.prev_gain_pit, 0, 6 );
131 30 : hLPDmem->dm_fx.prev_state = 0;
132 : }
133 :
134 : /* set excitation memory*/
135 604 : exc = exc_buf + L_EXC_MEM;
136 604 : Copy( hLPDmem->old_exc, exc_buf, L_EXC_MEM );
137 604 : *( exc + st->L_frame ) = 0;
138 :
139 : /* Init syn buffer */
140 604 : move16();
141 604 : syn = syn_buf + M;
142 604 : Copy( hLPDmem->mem_syn, syn_buf, M );
143 :
144 :
145 : /* calculate residual */
146 604 : calc_residu_fx( st, speech, exc, Aq );
147 : /*------------------------------------------------------------------------*
148 : * Find and quantize mean_ener_code for gain quantizer *
149 : *------------------------------------------------------------------------*/
150 :
151 604 : Es_pred = 0;
152 604 : move16();
153 604 : IF( acelp_cfg->nrg_mode > 0 )
154 : {
155 604 : Es_pred_enc_fx( &Es_pred, prm, L_frame, exc, st->voicing_fx, acelp_cfg->nrg_bits, acelp_cfg->nrg_mode > 1, Q_new );
156 604 : prm++;
157 : }
158 :
159 604 : IF( EQ_16( st->L_frame, L_FRAME ) )
160 : {
161 0 : Copy( Aq + 2 * ( M + 1 ), hBWE_TD->cur_sub_Aq_fx, ( M + 1 ) );
162 : }
163 : ELSE
164 : {
165 604 : Copy( Aq + 3 * ( M + 1 ), hBWE_TD->cur_sub_Aq_fx, ( M + 1 ) );
166 : }
167 :
168 :
169 : /*------------------------------------------------------------------------*
170 : * Loop for every subframe in the analysis frame *
171 : *------------------------------------------------------------------------*
172 : * To find the pitch and innovation parameters. The subframe size is *
173 : * L_SUBFR and the loop is repeated L_FRAME_PLUS/L_SUBFR *
174 : * times. *
175 : * - compute impulse response of weighted synthesis filter (h1[]) *
176 : * - compute the target signal for pitch search *
177 : * - find the closed-loop pitch parameters *
178 : * - encode the pitch delay *
179 : * - update the impulse response h1[] by including fixed-gain pitch *
180 : * - find target vector for codebook search *
181 : * - correlation between target vector and impulse response *
182 : * - codebook search *
183 : * - encode codebook address *
184 : * - VQ of pitch and codebook gains *
185 : * - find synthesis speech *
186 : * - update states of weighting filter *
187 : *------------------------------------------------------------------------*/
188 :
189 604 : p_A = A;
190 604 : p_Aq = Aq;
191 :
192 604 : move16();
193 604 : res_save = exc[0];
194 :
195 604 : j_subfr = 0;
196 604 : move16();
197 3624 : FOR( i_subfr = 0; i_subfr < L_frame; i_subfr += L_SUBFR )
198 : {
199 :
200 : /* Restore exc[i_subfr] and save next exc[L_SUBFR+i_subfr] */
201 3020 : move16();
202 3020 : move16();
203 3020 : exc[i_subfr] = res_save;
204 3020 : res_save = exc[L_SUBFR + i_subfr];
205 :
206 : /*--------------------------------------------------------------------------*
207 : * Find target for pitch search (xn[]), target for innovation search (cn[]) *
208 : * and impulse response of the weighted synthesis filter (h1[]). *
209 : *--------------------------------------------------------------------------*/
210 3020 : find_targets_fx( speech, &syn[i_subfr - M], i_subfr, &hLPDmem->mem_w0, p_Aq, exc, L_SUBFR, p_A, st->preemph_fac, xn, cn, h1 );
211 :
212 : /*---------------------------------------------------------------*
213 : * Compute impulse response, h1[], of weighted synthesis filter *
214 : *---------------------------------------------------------------*/
215 3020 : Scale_sig( h1, L_SUBFR, add( 1, shift ) ); /* Q13+1-shift */
216 :
217 : /* scaling of xn[] to limit dynamic at 12 bits */
218 3020 : Scale_sig( xn, L_SUBFR, shift );
219 :
220 : /*-----------------------------------------------------------------*
221 : * Gain clipping test to avoid unstable synthesis on frame erasure
222 : * or in case of floating point encoder & fixed p. decoder
223 : *-----------------------------------------------------------------*/
224 :
225 3020 : clip_gain = Mode2_gp_clip_fx( st->voicing_fx, i_subfr, st->coder_type, xn, st->clip_var_fx, L_SUBFR, Q_xn );
226 :
227 : /*-----------------------------------------------------------------*
228 : * - find unity gain pitch excitation (adaptive codebook entry) *
229 : * with fractional interpolation. *
230 : * - find filtered pitch exc. y1[]=exc[] convolved with h1[]) *
231 : * - compute pitch gain1 *
232 : *-----------------------------------------------------------------*/
233 :
234 3020 : IF( acelp_cfg->ltp_bits != 0 )
235 : {
236 : /* Adaptive Codebook (GC and VC) */
237 :
238 3020 : Mode2_pit_encode_fx( acelp_cfg->ltp_mode, i_subfr, &prm, &exc[i_subfr], st->pitch, &T0_min, &T0_min_frac, &T0_max, &T0_max_frac,
239 3020 : &T0, &T0_frac, &T0_res, h1, xn, st->pit_min, st->pit_fr1, st->pit_fr1b, st->pit_fr2, st->pit_max, st->pit_res_max );
240 :
241 3020 : E_ACELP_adaptive_codebook( exc, T0, T0_frac, T0_res, st->pit_res_max, acelp_cfg->ltf_mode, i_subfr, L_SUBFR, L_frame, h1, clip_gain, xn,
242 : y1, &g_corr, &prm, &gain_pit, xn_exp, 0, 0, &dummy );
243 : }
244 0 : ELSE IF( acelp_cfg->ltp_bits == 0 )
245 : {
246 : /* No adaptive codebook (UC) */
247 0 : gain_pit = 0;
248 0 : g_corr.xy1 = 0;
249 0 : g_corr.xy1_e = 0;
250 0 : g_corr.y1y1 = 0;
251 0 : g_corr.y1y1_e = 0;
252 0 : set16_fx( y1, 0, L_SUBFR );
253 0 : set16_fx( exc + i_subfr, 0, L_SUBFR );
254 0 : T0 = L_SUBFR;
255 0 : T0_frac = 0;
256 0 : T0_res = 1;
257 0 : move16();
258 0 : move16();
259 0 : move16();
260 0 : move16();
261 0 : move16();
262 0 : move16();
263 0 : move16();
264 0 : move16();
265 : }
266 :
267 3020 : IF( st->igf != 0 )
268 : {
269 3020 : tbe_celp_exc( L_frame, i_subfr, T0, T0_frac, &error, bwe_exc );
270 : }
271 :
272 3020 : pitch_buf[i_subfr / L_SUBFR] = shl( add( shl( T0, 2 ), T0_frac ), 4 );
273 :
274 : /*----------------------------------------------------------------------*
275 : * Encode the algebraic innovation *
276 : *----------------------------------------------------------------------*/
277 :
278 3020 : E_ACELP_innovative_codebook_fx( exc, T0, T0_frac, T0_res, gain_pit, hLPDmem->tilt_code, acelp_cfg, i_subfr, p_Aq, h1, xn, cn, y1, y2, (Word8) st->acelp_autocorr, &prm, code, shift, st->L_frame, st->last_L_frame, st->total_brate );
279 :
280 3020 : E_ACELP_xy2_corr( xn, y1, y2, &g_corr, L_SUBFR, Q_xn );
281 :
282 3020 : g_corr.y2y2_e = sub( g_corr.y2y2_e, 18 ); /* -18 (y2*y2: Q9*Q9) */
283 3020 : g_corr.xy2_e = sub( g_corr.xy2_e, add( Q_xn, 9 ) ); /* -(Q_xn+9) (xn: Q_xn y2: Q9) */
284 3020 : g_corr.y1y2_e = sub( g_corr.y1y2_e, add( Q_xn, 9 ) ); /* -(Q_xn+9) (y1: Q_xn y2: Q9) */
285 3020 : g_corr.xx_e = sub( g_corr.xx_e, add( Q_xn, Q_xn ) ); /* -(Q_xn+Q_xn) (xn: Q_xn) */
286 3020 : move16();
287 3020 : move16();
288 3020 : move16();
289 3020 : move16();
290 :
291 : /*----------------------------------------------------------------------*
292 : * Add Gaussian excitation *
293 : *----------------------------------------------------------------------*/
294 :
295 3020 : IF( EQ_16( acelp_cfg->gains_mode[j_subfr], 7 ) )
296 : {
297 0 : assert( gain_pit == 0 );
298 0 : gauss_L2_fx( h1, code2, y2, y22, &gain_code2, &g_corr, gain_pit, hLPDmem->tilt_code, p_Aq, acelp_cfg->formant_enh_num, &( st->seed_acelp ), shift );
299 : }
300 : ELSE
301 : {
302 3020 : gain_code2 = L_deposit_l( 0 );
303 3020 : set16_fx( code2, 0, L_SUBFR );
304 3020 : set16_fx( y22, 0, L_SUBFR );
305 : }
306 :
307 : /*----------------------------------------------------------*
308 : * - Compute the fixed codebook gain *
309 : * - quantize fixed codebook gain *
310 : *----------------------------------------------------------*/
311 :
312 3020 : encode_acelp_gains_fx( code, acelp_cfg->gains_mode[j_subfr], Es_pred, clip_gain, &g_corr, &gain_pit, &gain_code, &prm,
313 3020 : &past_gcode, &gain_inov, L_SUBFR, code2, &gain_code2, st->flag_noisy_speech_snr );
314 :
315 3020 : gp_clip_test_gain_pit_fx( st->element_mode, st->core_brate, gain_pit, st->clip_var_fx );
316 :
317 : /*----------------------------------------------------------*
318 : * - voice factor (for pitch enhancement) *
319 : *----------------------------------------------------------*/
320 3020 : E_UTIL_voice_factor( exc, i_subfr, code, gain_pit, gain_code, &voice_fac, &( hLPDmem->tilt_code ), L_SUBFR, acelp_cfg->voice_tilt, Q_new, shift );
321 :
322 3020 : IF( st->Opt_RF_ON )
323 : {
324 0 : hRF->rf_tilt_buf[i_subfr / L_SUBFR] = hLPDmem->tilt_code;
325 0 : move16();
326 : }
327 : /*-----------------------------------------------------------------*
328 : * Update memory of the weighting filter
329 : *-----------------------------------------------------------------*/
330 : /* st_fx->mem_w0 = xn[L_SUBFR-1] - (gain_pit*y1[L_SUBFR-1]) - (gain_code*y2[L_SUBFR-1]); */
331 3020 : Ltmp = Mpy_32_16_1( gain_code, y2[L_SUBFR - 1] );
332 3020 : Ltmp = L_shl( Ltmp, add( 5, Q_xn ) );
333 3020 : Ltmp = L_mac( Ltmp, y1[L_SUBFR - 1], gain_pit );
334 : /* Add Gaussian contribution*/
335 3020 : Ltmp2 = Mpy_32_16_1( gain_code2, y22[L_SUBFR - 1] );
336 3020 : Ltmp2 = L_shl( Ltmp2, add( 5, Q_xn ) );
337 3020 : Ltmp = L_add( Ltmp, Ltmp2 );
338 3020 : hLPDmem->mem_w0 = sub( xn[L_SUBFR - 1], round_fx( L_shl( Ltmp, 1 ) ) );
339 3020 : move16();
340 : BASOP_SATURATE_WARNING_OFF_EVS;
341 3020 : hLPDmem->mem_w0 = shr_sat( hLPDmem->mem_w0, shift ); /*Qnew-1*/
342 3020 : move16();
343 : BASOP_SATURATE_WARNING_ON_EVS;
344 :
345 : /*-------------------------------------------------------*
346 : * - Find the total excitation. *
347 : *-------------------------------------------------------*/
348 196300 : FOR( i = 0; i < L_SUBFR; i++ )
349 : {
350 : /* code in Q9, gain_pit in Q14; exc Q_new */
351 193280 : Ltmp = Mpy_32_16_1( gain_code2, code2[i] );
352 193280 : Ltmp = L_shl( Ltmp, Q_new_p5 );
353 193280 : Ltmp = L_mac( Ltmp, gain_pit, exc[i + i_subfr] );
354 193280 : exc2[i] = round_fx_sat( L_shl_o( Ltmp, 1, &Overflow ) );
355 193280 : move16();
356 193280 : Ltmp2 = Mpy_32_16_1( gain_code, code[i] );
357 193280 : Ltmp2 = L_shl_sat( Ltmp2, Q_new_p5 );
358 193280 : Ltmp = L_add_sat( Ltmp, Ltmp2 );
359 193280 : Ltmp = L_shl_o( Ltmp, 1, &Overflow ); /* saturation can occur here */
360 193280 : exc[i + i_subfr] = round_fx_o( Ltmp, &Overflow );
361 193280 : move16();
362 : }
363 : /*-----------------------------------------------------------------*
364 : * Prepare TBE excitation
365 : *-----------------------------------------------------------------*/
366 :
367 3020 : IF( st->igf != 0 )
368 : {
369 : #ifdef REMOVE_EVS_DUPLICATES
370 3020 : prep_tbe_exc_ivas_fx( L_frame, L_SUBFR, i_subfr, gain_pit, gain_code, code, voice_fac, &voice_factors[i_subfr / L_SUBFR],
371 3020 : bwe_exc, gain_preQ, code_preQ, Q_new, T0, T0_frac, st->coder_type, st->core_brate,
372 3020 : st->element_mode, st->idchan, st->hBWE_TD != NULL, st->tdm_LRTD_flag );
373 : #else
374 : prep_tbe_exc_fx( L_frame, i_subfr, gain_pit, gain_code, code, voice_fac, &voice_factors[i_subfr / L_SUBFR],
375 : bwe_exc, gain_preQ, code_preQ, Q_new, T0, T0_frac, st->coder_type, st->core_brate );
376 : #endif
377 : }
378 :
379 : /*---------------------------------------------------------*
380 : * Enhance the excitation *
381 : *---------------------------------------------------------*/
382 :
383 3020 : E_UTIL_enhancer( voice_fac, stab_fac, past_gcode, gain_inov, &hLPDmem->gc_threshold, code, exc2, gain_pit, &hLPDmem->dm_fx.prev_gain_code,
384 3020 : hLPDmem->dm_fx.prev_gain_pit, &hLPDmem->dm_fx.prev_state, st->coder_type, acelp_cfg->fixed_cdk_index[j_subfr], L_SUBFR, L_frame, Q_new );
385 :
386 : /*----------------------------------------------------------*
387 : * - compute the synthesis speech *
388 : *----------------------------------------------------------*/
389 :
390 3020 : E_UTIL_synthesis( 1, p_Aq, exc2, &syn2[i_subfr], L_SUBFR, hLPDmem->mem_syn2, 1, M );
391 :
392 : /*Save data for BPF*/
393 :
394 3020 : move16();
395 3020 : move16();
396 : /* st->bpf_T[j_subfr] = (int)((float)T0+(float)T0_frac/(float)T0_res+0.5f); */
397 3020 : st->bpf_T[j_subfr] = add( T0, shr( div_s( T0_frac, T0_res ), 14 ) );
398 3020 : st->bpf_gainT[j_subfr] = gain_pit;
399 :
400 3020 : E_UTIL_synthesis( 1, p_Aq, &exc[i_subfr], &syn[i_subfr], L_SUBFR, &syn[i_subfr - M], 0, M );
401 :
402 : /*----------------------------------------------------------*
403 : * Update *
404 : *----------------------------------------------------------*/
405 :
406 3020 : p_A += ( M + 1 );
407 3020 : p_Aq += ( M + 1 );
408 :
409 3020 : IF( hPlc_Ext != NULL )
410 : {
411 3020 : hPlc_Ext->T0_4th = T0;
412 3020 : move16();
413 : }
414 :
415 3020 : move32();
416 3020 : st->gain_code[j_subfr] = gain_code;
417 :
418 3020 : j_subfr = add( j_subfr, 1 );
419 : } /* end of subframe loop */
420 :
421 604 : p_A -= ( M + 1 );
422 604 : p_Aq -= ( M + 1 );
423 :
424 :
425 : /*----------------------------------------------------------*
426 : * Update LPD memory *
427 : *----------------------------------------------------------*/
428 604 : Copy( exc + L_frame - L_EXC_MEM, hLPDmem->old_exc, L_EXC_MEM );
429 604 : Copy( syn + L_frame - M, hLPDmem->mem_syn, M );
430 604 : Copy( syn + L_frame - L_SYN_MEM, hLPDmem->mem_syn_r, L_SYN_MEM );
431 :
432 604 : IF( hPlc_Ext != NULL )
433 : {
434 604 : hPlc_Ext->Q_exp = sub( Q_new, hPlc_Ext->Q_new );
435 604 : move16();
436 604 : hPlc_Ext->Q_new = Q_new;
437 604 : move16();
438 604 : Copy( exc + L_frame - L_EXC_MEM - 8, hPlc_Ext->old_exc_Qold, 8 );
439 : }
440 :
441 : /*----------------------------------------------------------*
442 : * ZIR at the end of the ACELP frame (for TCX) *
443 : *----------------------------------------------------------*/
444 604 : Copy( syn2, syn, L_frame );
445 604 : move16();
446 604 : tmp = hLPDmem->syn[M];
447 604 : E_UTIL_deemph2( sub( Q_new, 1 ), syn, st->preemph_fac, L_frame, &tmp );
448 :
449 604 : IF( st->hTcxEnc != NULL )
450 : {
451 604 : bufferCopyFx( syn + L_frame - ( L_frame / 2 ), hTcxEnc->Txnq, shr( L_frame, 1 ), 0 /*Qf_syn*/, -1 /*Qf_Txnq*/, 0 /*Q_syn*/, 0 /*Q_Txnq*/ );
452 : }
453 604 : Copy( syn + L_frame - M - 1, hLPDmem->syn, 1 + M ); /*Q0*/
454 604 : Copy( syn, st->synth, L_frame );
455 :
456 604 : assert( T0_res <= 6 );
457 :
458 : /*Update MODE1*/
459 604 : Copy( p_Aq, st->old_Aq_12_8_fx, M + 1 );
460 604 : st->old_Es_pred_fx = Es_pred;
461 604 : move16();
462 604 : return 0;
463 : }
|