Line data Source code
1 : /*====================================================================================
2 : EVS Codec 3GPP TS26.452 Aug 12, 2021. Version 16.3.0
3 : ====================================================================================*/
4 : #include <stdint.h>
5 : #include "options.h" /* Compilation switches */
6 : #include "cnst.h" /* Common constants */
7 : #include "rom_com.h" /* Static table prototypes */
8 : #include "prot_fx.h" /* required by wmc_tool */
9 : #include "stat_com.h"
10 : /*--------------------------------------------------------------------------*
11 : * mvr2r_inv()
12 : *
13 : *
14 : *--------------------------------------------------------------------------*/
15 75887 : static void mvs2s_inv(
16 : const Word16 *in, /* i : input vector */
17 : Word16 *out, /* o : output vector */
18 : const Word16 L, /* i : length */
19 : const Word16 decimate /* i : decimation flag [-1,1] */
20 : )
21 : {
22 : Word16 i;
23 75887 : in = in + shr( sub( decimate, 1 ), 1 );
24 75887 : out = out + sub( L, 1 );
25 7216623 : FOR( i = 0; i < L; i++ )
26 : {
27 7140736 : *out = *in;
28 7140736 : move16();
29 7140736 : in += decimate;
30 7140736 : out--;
31 : }
32 75887 : }
33 : /*--------------------------------------------------------------------------*
34 : * mvr2r_dec()
35 : *
36 : *
37 : *--------------------------------------------------------------------------*/
38 75398 : static void mvs2s_dec(
39 : const Word16 *in, /* i : input vector */
40 : Word16 *out, /* o : output vector */
41 : const Word16 L, /* i : length */
42 : const Word16 decimate /* i : decimation flag [-1,1] */
43 : )
44 : {
45 : Word16 i;
46 75398 : in = in + shr( sub( decimate, 1 ), 1 );
47 7154166 : FOR( i = 0; i < L; i++ )
48 : {
49 7078768 : *out = *in;
50 7078768 : move16();
51 7078768 : in += decimate;
52 7078768 : out++;
53 : }
54 75398 : }
55 : /*--------------------------------------------------------------------------*
56 : * copy_win()
57 : *
58 : *
59 : *--------------------------------------------------------------------------*/
60 :
61 151285 : static void copy_win(
62 : Word16 *out_win, /* o : output window buffer Q15*/
63 : const Word16 nb_zero, /* i : length of zero padding */
64 : const Word16 *in_win, /* i : input window */
65 : const Word16 win_lenght, /* i : length */
66 : const Word16 nb_one, /* i : length of flat section (ones) */
67 : const Word16 decimate /* i : input window */
68 : )
69 : {
70 151285 : IF( decimate < 0 )
71 : {
72 75887 : set16_fx( out_win, 32767, nb_one ); // Q15
73 75887 : mvs2s_inv( in_win, out_win + nb_one, win_lenght, negate( decimate ) );
74 75887 : set16_fx( out_win + add( win_lenght, nb_one ), 0, nb_zero );
75 : }
76 : ELSE
77 : {
78 75398 : set16_fx( out_win, 0, nb_zero );
79 75398 : mvs2s_dec( in_win, out_win + nb_zero, win_lenght, decimate );
80 75398 : set16_fx( out_win + add( nb_zero, win_lenght ), 32767, nb_one ); // Q15
81 : }
82 151285 : }
83 : /*--------------------------------------------------------------------------*
84 : * tcx_get_windows_mode1()
85 : *
86 : *
87 : *--------------------------------------------------------------------------*/
88 :
89 3272154 : void tcx_get_windows_mode1(
90 : const Word16 left_mode, /* i: overlap mode of left window half */
91 : const Word16 right_mode, /* i: overlap mode of right window half */
92 : Word16 *left_win, /* o: left overlap window */
93 : Word16 *right_win, /* o: right overlap window */
94 : Word16 *left_win_int, /* o: left overlap window */
95 : Word16 *right_win_int, /* o: right overlap window */
96 : const Word16 L /* i : length */
97 : )
98 : {
99 : /* Left part */
100 3272154 : IF( EQ_16( left_mode, MIN_OVERLAP ) )
101 : {
102 12419 : test();
103 12419 : IF( EQ_16( L, 256 ) || EQ_16( L, 512 ) )
104 : {
105 1108 : copy_win( left_win, R1_25 - 4 * R2_25 / 7, small_overlap_25, R2_25 / 7, 3 * R2_25 / 7, 1 ); // Q15
106 : }
107 : ELSE
108 : {
109 11311 : copy_win( left_win, R1_48 - 4 * R2_48 / 7, small_overlap_48, R2_48 / 7, 3 * R2_48 / 7, 1 ); // Q15
110 11311 : copy_win( left_win_int, R1_16 - 4 * R2_16 / 7, small_overlap_int, R2_16 / 7, 3 * R2_16 / 7, 1 ); // Q15
111 : }
112 : }
113 3259735 : ELSE IF( EQ_16( left_mode, HALF_OVERLAP ) )
114 : {
115 27120 : test();
116 27120 : IF( EQ_16( L, 256 ) || EQ_16( L, 512 ) )
117 : {
118 2572 : copy_win( left_win, R1_25 - 5 * R2_25 / 7, half_overlap_25, 3 * R2_25 / 7, 2 * R2_25 / 7, 1 ); // Q15
119 : }
120 : ELSE
121 : {
122 24548 : copy_win( left_win, R1_48 - 5 * R2_48 / 7, half_overlap_48, 3 * R2_48 / 7, 2 * R2_48 / 7, 1 ); // Q15
123 24548 : copy_win( left_win_int, R1_16 - 5 * R2_16 / 7, half_overlap_int, 3 * R2_16 / 7, 2 * R2_16 / 7, 1 ); // Q15
124 : }
125 : }
126 3232615 : ELSE IF( EQ_16( left_mode, ALDO_WINDOW ) ) /* ALDO */
127 : {
128 3232615 : test();
129 3232615 : IF( EQ_16( L, 256 ) || EQ_16( L, 512 ) )
130 : {
131 321219 : Copy( window_256kHz, left_win, R1_25 ); // Q15
132 : }
133 : ELSE
134 : {
135 2911396 : Copy( window_48kHz_fx, left_win, R1_48 ); // Q15
136 2911396 : Copy( window_8_16_32kHz_fx, left_win_int, R1_16 ); // Q15
137 : }
138 : }
139 : ELSE
140 : {
141 : /*assert(!"Window not supported");*/
142 : }
143 :
144 : /* Right part */
145 3272154 : test();
146 3272154 : IF( EQ_16( right_mode, MIN_OVERLAP ) || EQ_16( right_mode, TRANSITION_OVERLAP ) )
147 : {
148 12587 : test();
149 12587 : IF( EQ_16( L, 256 ) || EQ_16( L, 512 ) )
150 : {
151 1559 : copy_win( right_win, 3 * R2_25 / 7, small_overlap_25, R2_25 / 7, 3 * R2_25 / 7, -1 ); // Q15
152 : }
153 : ELSE
154 : {
155 :
156 11028 : copy_win( right_win, 3 * R2_48 / 7, small_overlap_48, R2_48 / 7, 3 * R2_48 / 7, -1 ); // Q15
157 11028 : copy_win( right_win_int, 3 * R2_16 / 7, small_overlap_int, R2_16 / 7, 3 * R2_16 / 7, -1 ); // Q15
158 : }
159 : }
160 3259567 : ELSE IF( EQ_16( right_mode, HALF_OVERLAP ) )
161 : {
162 27470 : test();
163 27470 : IF( EQ_16( L, 256 ) || EQ_16( L, 512 ) )
164 : {
165 2668 : copy_win( right_win, 2 * R2_25 / 7, half_overlap_25, 3 * R2_25 / 7, 2 * R2_25 / 7, -1 ); // Q15
166 : }
167 : ELSE
168 : {
169 24802 : copy_win( right_win, 2 * R2_48 / 7, half_overlap_48, 3 * R2_48 / 7, 2 * R2_48 / 7, -1 ); // Q15
170 24802 : copy_win( right_win_int, 2 * R2_16 / 7, half_overlap_int, 3 * R2_16 / 7, 2 * R2_16 / 7, -1 ); // Q15
171 : }
172 : }
173 3232097 : ELSE IF( EQ_16( right_mode, ALDO_WINDOW ) )
174 : {
175 3232097 : test();
176 3232097 : IF( EQ_16( L, 256 ) || EQ_16( L, 512 ) )
177 : {
178 320672 : Copy( window_256kHz + R1_25, right_win, R2_25 ); // Q15
179 : }
180 : ELSE
181 : {
182 2911425 : Copy( window_48kHz_fx + R1_48, right_win, R2_48 ); // Q15
183 2911425 : Copy( window_8_16_32kHz_fx + R1_16, right_win_int, R2_16 ); // Q15
184 : }
185 : }
186 : ELSE
187 : {
188 : /* assert(!"Window not supported");*/
189 : }
190 3272154 : }
191 :
192 : /*--------------------------------------------------------------------------*
193 : * wtda()
194 : *
195 : * Windowing and time-domain aliasing
196 : *--------------------------------------------------------------------------*/
197 :
198 868476 : void wtda_fx(
199 : Word16 *new_audio, /* i : input audio Q0 */
200 : Word16 *Q, /* i/o : Q of input/Output Audio */
201 : Word32 *wtda_audio, /* o : windowed audio Qout */
202 : Word16 *old_wtda, /* i/o: windowed audio from previous frame Qout */
203 : Word16 *Qold_wtda,
204 : const Word16 left_mode, /* i : window overlap of previous frame (0: full, 2: none, or 3: half) */
205 : const Word16 right_mode, /* i : window overlap of current frame (0: full, 2: none, or 3: half) */
206 : const Word16 L /* i : length */
207 : )
208 : {
209 : Word16 i, decimate, decay, tmp;
210 : Word16 n, windecay48;
211 : Word16 *allsig_l;
212 : Word16 *allsig_r;
213 : Word16 win_right[R2_48];
214 : Word16 win_int_left[R1_16];
215 : Word16 win_left[R1_48];
216 : Word16 win_int_right[R2_16];
217 : Word16 *p1, *p2, *p3, *p4, *p5, *p6;
218 : Word32 *pa;
219 :
220 868476 : tcx_get_windows_mode1( left_mode, right_mode, win_left, win_right, win_int_left, win_int_right, L );
221 :
222 868476 : decimate = 1;
223 868476 : move16(); /* L_FRAME 48k */
224 868476 : decay = 0;
225 868476 : move16();
226 868476 : windecay48 = WINDECAY48;
227 868476 : move16();
228 868476 : n = R1_48 - R2_48;
229 868476 : move16();
230 :
231 868476 : test();
232 868476 : IF( EQ_16( L, L_FRAME32k ) || EQ_16( L, L_FRAME16k ) )
233 : {
234 228232 : decimate = 3;
235 228232 : move16();
236 228232 : decay = 1;
237 228232 : move16();
238 228232 : n = R1_16 - R2_16;
239 228232 : move16();
240 :
241 228232 : if ( EQ_16( L, L_FRAME32k ) )
242 : {
243 180635 : n = 2 * N16_CORE_SW;
244 180635 : move16();
245 : }
246 : }
247 640244 : ELSE IF( EQ_16( L, L_FRAME8k ) )
248 : {
249 0 : decimate = 6;
250 0 : move16();
251 0 : decay = 2;
252 0 : move16();
253 0 : n = ( R1_16 - R2_16 ) / 2;
254 0 : move16();
255 : }
256 :
257 868476 : IF( old_wtda == NULL )
258 : {
259 :
260 843007 : allsig_r = new_audio + n;
261 843007 : allsig_l = new_audio + sub( n, L );
262 : }
263 : ELSE
264 : {
265 : /* Rescale signals if Q are not identical */
266 :
267 25469 : IF( GT_16( *Qold_wtda, *Q ) )
268 : {
269 :
270 11044 : Copy_Scale_sig( old_wtda, old_wtda, L, sub( *Q, *Qold_wtda ) );
271 11044 : *Qold_wtda = *Q;
272 11044 : move16();
273 : }
274 14425 : ELSE IF( LT_16( *Qold_wtda, *Q ) )
275 : {
276 6 : Copy_Scale_sig( new_audio, new_audio, L, sub( *Qold_wtda, *Q ) );
277 6 : *Q = *Qold_wtda;
278 6 : move16();
279 : }
280 :
281 25469 : allsig_r = new_audio + n;
282 25469 : allsig_l = old_wtda + n;
283 : }
284 :
285 :
286 868476 : IF( EQ_16( L, L_FRAME32k ) )
287 : {
288 :
289 : /* decimate = 3 */
290 : /* decay =1 */
291 :
292 180635 : pa = wtda_audio;
293 180635 : p1 = allsig_r + L_FRAME16k - 1;
294 180635 : p2 = win_int_right + ( 3 * L_FRAME16k / 2 - 1 - WINDECAY16 ); /* 3*L/2*decimate-decimate+decay-windecay48;*/
295 180635 : p3 = p1 + 1;
296 180635 : p4 = p2 + 1;
297 :
298 180635 : p5 = win_right + ( ( 3 * L_FRAME16k / 2 - 1 ) * 3 + 1 - WINDECAY48 );
299 180635 : p6 = win_right + ( ( 3 * L_FRAME16k / 2 + 1 ) * 3 - 1 - 1 - WINDECAY48 );
300 :
301 12825085 : FOR( i = 0; i < L_FRAME16k - 2 * N16_CORE_SW; i += 2 )
302 : {
303 12644450 : *pa++ = L_negate( L_mac0( L_mult0( *p1--, *p2-- ), *p3++, *p4++ ) );
304 12644450 : move32();
305 12644450 : *pa++ = L_negate( L_mac0( L_mult0( *p1--, *p5 ), *p3++, *p6 ) );
306 12644450 : move32();
307 12644450 : p5 -= decimate;
308 12644450 : p6 += decimate;
309 : /* Q + 15 */
310 : }
311 :
312 16437785 : FOR( i = 0; i < n; i += 2 )
313 : {
314 16257150 : *pa++ = L_mult( *p1--, -16384 );
315 16257150 : move32();
316 16257150 : *pa++ = L_mult( *p1--, -16384 );
317 16257150 : move32();
318 : }
319 :
320 180635 : pa = wtda_audio + L_FRAME16k;
321 180635 : p1 = allsig_l;
322 180635 : p2 = win_left + 1;
323 180635 : p3 = new_audio + 2 * N16_CORE_SW - 1;
324 180635 : p4 = win_int_left;
325 :
326 16437785 : FOR( i = 0; i < n; i += 2 )
327 : {
328 16257150 : *pa++ = L_mac0( L_mult0( *p1++, *p2 ), *p3--, -32768 );
329 16257150 : move32();
330 16257150 : *pa++ = L_mac0( L_mult0( *p1++, *p4++ ), *p3--, -32768 );
331 16257150 : move32();
332 16257150 : p2 += decimate;
333 : }
334 :
335 180635 : p5 = allsig_l + L_FRAME32k - 1 - N16_CORE_SW * 2;
336 180635 : p6 = win_left + ( L_FRAME16k - N16_CORE_SW ) * 3 - 1 - 1;
337 180635 : p3 = win_int_left + ( L_FRAME16k - N16_CORE_SW - 1 );
338 :
339 180635 : tmp = sub( shr( L, 1 ), n );
340 12825085 : FOR( i = 0; i < tmp; i += 2 )
341 : {
342 12644450 : *pa++ = L_msu0( L_mult0( *p1++, *p2 ), *p5--, *p6 );
343 12644450 : move32();
344 12644450 : *pa++ = L_msu0( L_mult0( *p1++, *p4++ ), *p5--, *p3-- );
345 12644450 : move32();
346 12644450 : p2 += decimate;
347 12644450 : p6 -= decimate;
348 : }
349 : }
350 : ELSE
351 : {
352 687841 : pa = wtda_audio;
353 687841 : p1 = allsig_r + sub( shr( L, 1 ), 1 );
354 687841 : p2 = win_right + sub( add( sub( i_mult2( i_mult2( 3, shr( L, 1 ) ), decimate ), decimate ), decay ), windecay48 ); /* 3*L/2*decimate-decimate+decay-windecay48;*/
355 687841 : p3 = p1 + 1;
356 687841 : p4 = win_right + sub( sub( sub( add( i_mult2( i_mult2( 3, shr( L, 1 ) ), decimate ), decimate ), decay ), windecay48 ), 1 );
357 :
358 687841 : tmp = sub( shr( L, 1 ), n );
359 138470871 : FOR( i = 0; i < tmp; i++ )
360 : {
361 : /* wtda_audio[i]=-allsig_r[L/2-i-1]*win_right[3*L/2*decimate-(i+1)*decimate+decay-windecay48]-allsig_r[L/2+i]*win_right[3*L/2*decimate-1+(i+1)*decimate-decay-windecay48];*/
362 137783030 : *pa++ = L_msu0( L_msu0( 0, *p1--, *p2 ), *p3++, *p4 );
363 137783030 : move32();
364 137783030 : p2 -= decimate;
365 137783030 : p4 += decimate;
366 : /* Q + 15 */
367 : }
368 :
369 177837451 : FOR( i = 0; i < n; i++ )
370 : {
371 177149610 : *pa++ = L_negate( L_shr( L_deposit_h( *p1-- ), 1 ) );
372 177149610 : move32();
373 : /* wtda_audio[i]=-allsig_r[L/2-i-1]; */
374 : }
375 :
376 :
377 687841 : pa = wtda_audio + shr( L, 1 );
378 687841 : p1 = allsig_l;
379 687841 : p2 = win_left + decay;
380 687841 : p3 = new_audio + sub( n, 1 );
381 :
382 177837451 : FOR( i = 0; i < n; i++ )
383 : {
384 177149610 : *pa++ = L_mac0( L_mult0( *p1++, *p2 ), *p3--, -32768 );
385 177149610 : move32();
386 177149610 : p2 += decimate;
387 : /* wtda_audio[i+L/2]=allsig_l[i]*win_left[i*decimate+decay]-new_audio[n-i-1];*/
388 : }
389 :
390 687841 : p3 = allsig_l + sub( sub( L, 1 ), n );
391 687841 : p4 = win_left + sub( sub( i_mult2( sub( L, n ), decimate ), 1 ), decay );
392 :
393 687841 : tmp = sub( shr( L, 1 ), n );
394 138470871 : FOR( i = 0; i < tmp; i++ )
395 : {
396 137783030 : *pa++ = L_msu0( L_mult0( *p1++, *p2 ), *p3--, *p4 );
397 137783030 : move32();
398 137783030 : p2 += decimate;
399 137783030 : p4 -= decimate;
400 : /* wtda_audio[i+L/2]=allsig_l[i]*win_left[i*decimate+decay]-allsig_l[L-i-1]*win_left[L*decimate-i*decimate-1-decay];*/
401 : }
402 : }
403 :
404 868476 : *Q = add( *Q, 15 ); /* output Q */
405 868476 : move16();
406 :
407 868476 : IF( old_wtda != NULL )
408 : {
409 :
410 25469 : Copy( new_audio, old_wtda, L );
411 : }
412 868476 : return;
413 : }
414 :
415 :
416 0 : void wtda_ivas_fx(
417 : Word16 *new_audio, /* i : input audio Q0 */
418 : Word16 *Q, /* i/o : Q of input/Output Audio */
419 : Word16 *wtda_audio, /* o : windowed audio Qout */
420 : Word16 *old_wtda, /* i/o: windowed audio from previous frame Qout */
421 : Word16 *Qold_wtda,
422 : const Word16 left_mode, /* i : window overlap of previous frame (0: full, 2: none, or 3: half) */
423 : const Word16 right_mode, /* i : window overlap of current frame (0: full, 2: none, or 3: half) */
424 : const Word16 L /* i : length */
425 : )
426 : {
427 : Word16 i, decimate, decay;
428 : Word16 n, windecay48, windecay16;
429 : const Word16 *allsig_l, *allsig_r;
430 : Word16 win_right[R2_48];
431 : Word16 win_int_left[R1_16];
432 : Word16 win_left[R1_48];
433 : Word16 win_int_right[R2_16];
434 :
435 0 : tcx_get_windows_mode1( left_mode, right_mode, win_left, win_right, win_int_left, win_int_right, L );
436 :
437 0 : decimate = 1; /* L_FRAME48k */
438 0 : move16();
439 0 : decay = 0;
440 0 : move16();
441 0 : windecay48 = ( 2 * ( (Word64) L_FRAME48k * N_ZERO_MDCT_NS / FRAME_SIZE_NS ) ) + R1_48;
442 0 : move16();
443 :
444 0 : test();
445 0 : IF( EQ_16( L, L_FRAME32k ) || EQ_16( L, L_FRAME16k ) )
446 : {
447 0 : decimate = 3;
448 0 : move16();
449 0 : decay = 1;
450 0 : move16();
451 : }
452 0 : ELSE IF( EQ_16( L, L_FRAME8k ) )
453 : {
454 0 : decimate = 6;
455 0 : move16();
456 0 : decay = 2;
457 0 : move16();
458 : }
459 :
460 0 : n = extract_l( Mpy_32_32( L, 603979776 /* N_ZERO_MDCT_NS / FRAME_SIZE_NS in Q31 */ ) );
461 :
462 0 : windecay16 = ( 2 * ( L_FRAME16k * N_ZERO_MDCT_NS / FRAME_SIZE_NS ) ) + R1_16;
463 0 : move16();
464 :
465 : /* algorithmic delay reduction */
466 0 : i = 0;
467 0 : move16();
468 :
469 0 : IF( old_wtda == NULL )
470 : {
471 0 : allsig_r = new_audio + n;
472 0 : allsig_l = new_audio + n - L;
473 : }
474 : ELSE
475 : {
476 : /* Rescale signals if Q are not identical */
477 0 : IF( GT_16( *Qold_wtda, *Q ) )
478 : {
479 0 : Copy_Scale_sig( old_wtda, old_wtda, L, sub( *Q, *Qold_wtda ) );
480 0 : *Qold_wtda = *Q;
481 0 : move16();
482 : }
483 0 : ELSE IF( LT_16( *Qold_wtda, *Q ) )
484 : {
485 0 : Copy_Scale_sig( new_audio, new_audio, L, sub( *Qold_wtda, *Q ) );
486 0 : *Q = *Qold_wtda;
487 0 : move16();
488 : }
489 :
490 0 : allsig_r = new_audio + n;
491 0 : allsig_l = old_wtda + n;
492 : }
493 :
494 0 : IF( EQ_16( L, L_FRAME32k ) )
495 : {
496 0 : FOR( i = 0; i < L / 2 - n; i += 2 )
497 : {
498 0 : wtda_audio[i] = round_fx( L_msu0( L_mult0( negate( allsig_r[L / 2 - i - 1] ), win_int_right[3 * L_FRAME16k / 2 - i / 2 - 1 - windecay16] ),
499 0 : allsig_r[L / 2 + i], win_int_right[3 * L_FRAME16k / 2 + i / 2 - windecay16] ) );
500 0 : move16();
501 0 : wtda_audio[i + 1] = round_fx( L_msu0( L_mult0( negate( allsig_r[L / 2 - ( i + 1 ) - 1] ), win_right[( 3 * L_FRAME16k / 2 - i / 2 - 1 ) * decimate + decay - windecay48] ),
502 0 : allsig_r[L / 2 + i + 1], win_right[( 3 * L_FRAME16k / 2 + 1 + i / 2 ) * decimate - decay - 1 - windecay48] ) );
503 0 : move16();
504 : }
505 :
506 0 : FOR( i = L / 2 - n; i < L / 2; i += 2 )
507 : {
508 0 : wtda_audio[i] = shr( negate( allsig_r[L / 2 - i - 1] ), 1 );
509 0 : move16();
510 0 : wtda_audio[i + 1] = shr( negate( allsig_r[L / 2 - ( i + 1 ) - 1] ), 1 );
511 0 : move16();
512 : }
513 :
514 0 : FOR( i = 0; i < n; i += 2 )
515 : {
516 0 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( allsig_l[i], win_left[( i / 2 ) * decimate + decay] ),
517 0 : new_audio[n - i - 1], MAX16B ) );
518 0 : move16();
519 0 : wtda_audio[i + L / 2 + 1] = round_fx( L_msu0( L_mult0( allsig_l[i + 1], win_int_left[i / 2] ),
520 0 : new_audio[n - ( i + 1 ) - 1], MAX16B ) );
521 0 : move16();
522 : }
523 :
524 0 : FOR( i = n; i < L / 2; i += 2 )
525 : {
526 0 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( allsig_l[i], win_left[( i / 2 ) * decimate + decay] ),
527 0 : allsig_l[L - i - 1], win_left[( L / 2 - i / 2 ) * decimate - 1 - decay] ) );
528 0 : move16();
529 0 : wtda_audio[i + L / 2 + 1] = round_fx( L_msu0( L_mult0( allsig_l[i + 1], win_int_left[i / 2] ),
530 0 : allsig_l[L - ( i + 1 ) - 1], win_int_left[L / 2 - i / 2 - 1] ) );
531 0 : move16();
532 : }
533 : }
534 : ELSE
535 : {
536 0 : FOR( i = 0; i < L / 2 - n; i++ )
537 : {
538 0 : wtda_audio[i] = round_fx( L_msu0( L_mult0( negate( allsig_r[L / 2 - i - 1] ), win_right[3 * L / 2 * decimate - ( i + 1 ) * decimate + decay - windecay48] ),
539 0 : allsig_r[L / 2 + i], win_right[3 * L / 2 * decimate - 1 + ( i + 1 ) * decimate - decay - windecay48] ) );
540 0 : move16();
541 : }
542 :
543 0 : FOR( i = L / 2 - n; i < L / 2; i++ )
544 : {
545 0 : wtda_audio[i] = shr( negate( allsig_r[L / 2 - i - 1] ), 1 );
546 0 : move16();
547 : }
548 :
549 0 : FOR( i = 0; i < n; i++ )
550 : {
551 0 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( allsig_l[i], win_left[i * decimate + decay] ),
552 0 : new_audio[n - i - 1], MAX16B ) );
553 0 : move16();
554 : }
555 :
556 0 : FOR( i = n; i < L / 2; i++ )
557 : {
558 0 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( allsig_l[i], win_left[i * decimate + decay] ),
559 0 : allsig_l[L - i - 1], win_left[L * decimate - i * decimate - 1 - decay] ) );
560 0 : move16();
561 : }
562 : }
563 :
564 0 : IF( old_wtda != NULL )
565 : {
566 0 : Copy( new_audio, old_wtda, L );
567 : }
568 :
569 0 : return;
570 : }
571 :
572 :
573 608853 : void wtda_ext_fx(
574 : const Word16 *new_audio, /* i : input audio (Q_in) */
575 : Word16 *wtda_audio, /* o : windowed audio (Q_in - 1) */
576 : const Word16 left_mode, /* i : window overlap of previous frame (0: full, 2: none, or 3: half) */
577 : const Word16 right_mode, /* i : window overlap of current frame (0: full, 2: none, or 3: half) */
578 : const Word16 L, /* i : length */
579 : const UWord16 kernel_type /* i : transform kernel type (0 - 3) */
580 : )
581 : {
582 : Word16 i, decimate, decay;
583 : Word16 n, windecay48, windecay16;
584 : const Word16 *allsig_l, *allsig_r;
585 : Word16 win_right[R2_48];
586 : Word16 win_int_left[R1_16];
587 : Word16 win_left[R1_48];
588 : Word16 win_int_right[R2_16];
589 :
590 608853 : tcx_get_windows_mode1( left_mode, right_mode, win_left, win_right, win_int_left, win_int_right, L );
591 :
592 608853 : decimate = 1; /* L_FRAME48k */
593 608853 : move16();
594 608853 : decay = 0;
595 608853 : move16();
596 608853 : windecay48 = ( 2 * ( (Word64) L_FRAME48k * N_ZERO_MDCT_NS / FRAME_SIZE_NS ) ) + R1_48;
597 608853 : move16();
598 :
599 608853 : test();
600 608853 : IF( EQ_16( L, L_FRAME32k ) || EQ_16( L, L_FRAME16k ) )
601 : {
602 191979 : decimate = 3;
603 191979 : move16();
604 191979 : decay = 1;
605 191979 : move16();
606 : }
607 416874 : ELSE IF( EQ_16( L, L_FRAME8k ) )
608 : {
609 0 : decimate = 6;
610 0 : move16();
611 0 : decay = 2;
612 0 : move16();
613 : }
614 :
615 608853 : n = extract_l( Mpy_32_32( L, 603979776 /* N_ZERO_MDCT_NS / FRAME_SIZE_NS in Q31 */ ) );
616 608853 : move16();
617 :
618 608853 : windecay16 = ( 2 * ( L_FRAME16k * N_ZERO_MDCT_NS / FRAME_SIZE_NS ) ) + R1_16;
619 608853 : move16();
620 :
621 608853 : allsig_r = new_audio + n;
622 608853 : allsig_l = new_audio + n - L;
623 :
624 608853 : IF( EQ_16( L, L_FRAME32k ) )
625 : {
626 154407 : IF( UL_and( kernel_type, 1 ) )
627 : {
628 10956507 : FOR( i = 0; i < L / 2 - n; i += 2 )
629 : {
630 10802190 : wtda_audio[i] = round_fx( L_mac0( L_mult0( negate( allsig_r[L / 2 - i - 1] ), win_int_right[3 * L_FRAME16k / 2 - i / 2 - 1 - windecay16] ),
631 10802190 : allsig_r[L / 2 + i], win_int_right[3 * L_FRAME16k / 2 + i / 2 - windecay16] ) ); // q_in - 1
632 10802190 : move16();
633 10802190 : wtda_audio[i + 1] = round_fx( L_mac0( L_mult0( negate( allsig_r[L / 2 - ( i + 1 ) - 1] ), win_right[( 3 * L_FRAME16k / 2 - i / 2 - 1 ) * decimate + decay - windecay48] ),
634 10802190 : allsig_r[L / 2 + i + 1], win_right[( 3 * L_FRAME16k / 2 + 1 + i / 2 ) * decimate - decay - 1 - windecay48] ) ); // q_in - 1
635 10802190 : move16();
636 : }
637 : }
638 : ELSE
639 : {
640 6390 : FOR( i = 0; i < L / 2 - n; i += 2 )
641 : {
642 6300 : wtda_audio[i] = round_fx( L_msu0( L_mult0( negate( allsig_r[L / 2 - i - 1] ), win_int_right[3 * L_FRAME16k / 2 - i / 2 - 1 - windecay16] ),
643 6300 : allsig_r[L / 2 + i], win_int_right[3 * L_FRAME16k / 2 + i / 2 - windecay16] ) ); // q_in - 1
644 6300 : move16();
645 6300 : wtda_audio[i + 1] = round_fx( L_msu0( L_mult0( negate( allsig_r[L / 2 - ( i + 1 ) - 1] ), win_right[( 3 * L_FRAME16k / 2 - i / 2 - 1 ) * decimate + decay - windecay48] ),
646 6300 : allsig_r[L / 2 + i + 1], win_right[( 3 * L_FRAME16k / 2 + 1 + i / 2 ) * decimate - decay - 1 - windecay48] ) ); // q_in - 1
647 6300 : move16();
648 : }
649 : }
650 :
651 14051037 : FOR( i = L / 2 - n; i < L / 2; i += 2 )
652 : {
653 13896630 : wtda_audio[i] = shr( negate( allsig_r[L / 2 - i - 1] ), 1 ); // q_in - 1
654 13896630 : move16();
655 13896630 : wtda_audio[i + 1] = shr( negate( allsig_r[L / 2 - ( i + 1 ) - 1] ), 1 ); // q_in - 1
656 13896630 : move16();
657 : }
658 :
659 154407 : IF( GE_32( kernel_type, 2 ) )
660 : {
661 14042392 : FOR( i = 0; i < n; i += 2 )
662 : {
663 13888080 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( negate( allsig_l[i] ), win_left[( i / 2 ) * decimate + decay] ),
664 13888080 : new_audio[n - i - 1], MAX16B ) ); // q_in - 1
665 13888080 : move16();
666 13888080 : wtda_audio[i + L / 2 + 1] = round_fx( L_msu0( L_mult0( negate( allsig_l[i + 1] ), win_int_left[i / 2] ),
667 13888080 : new_audio[n - ( i + 1 ) - 1], MAX16B ) ); // q_in - 1
668 13888080 : move16();
669 : }
670 :
671 10956152 : FOR( i = n; i < L / 2; i += 2 )
672 : {
673 10801840 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( negate( allsig_l[i] ), win_left[( i / 2 ) * decimate + decay] ),
674 10801840 : allsig_l[L - i - 1], win_left[( L / 2 - i / 2 ) * decimate - 1 - decay] ) ); // q_in - 1
675 10801840 : move16();
676 10801840 : wtda_audio[i + L / 2 + 1] = round_fx( L_msu0( L_mult0( negate( allsig_l[i + 1] ), win_int_left[i / 2] ),
677 10801840 : allsig_l[L - ( i + 1 ) - 1], win_int_left[L / 2 - i / 2 - 1] ) ); // q_in - 1
678 10801840 : move16();
679 : }
680 : }
681 : ELSE
682 : {
683 8645 : FOR( i = 0; i < n; i += 2 )
684 : {
685 8550 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( allsig_l[i], win_left[( i / 2 ) * decimate + decay] ),
686 8550 : new_audio[n - i - 1], MAX16B ) ); // q_in - 1
687 8550 : move16();
688 8550 : wtda_audio[i + L / 2 + 1] = round_fx( L_msu0( L_mult0( allsig_l[i + 1], win_int_left[i / 2] ),
689 8550 : new_audio[n - ( i + 1 ) - 1], MAX16B ) ); // q_in - 1
690 8550 : move16();
691 : }
692 :
693 6745 : FOR( i = n; i < L / 2; i += 2 )
694 : {
695 6650 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( allsig_l[i], win_left[( i / 2 ) * decimate + decay] ),
696 6650 : allsig_l[L - i - 1], win_left[( L / 2 - i / 2 ) * decimate - 1 - decay] ) ); // q_in - 1
697 6650 : move16();
698 6650 : wtda_audio[i + L / 2 + 1] = round_fx( L_msu0( L_mult0( allsig_l[i + 1], win_int_left[i / 2] ),
699 6650 : allsig_l[L - ( i + 1 ) - 1], win_int_left[L / 2 - i / 2 - 1] ) ); // q_in - 1
700 6650 : move16();
701 : }
702 : }
703 : }
704 : ELSE
705 : {
706 454446 : IF( UL_and( kernel_type, 1 ) )
707 : {
708 90609467 : FOR( i = 0; i < L / 2 - n; i++ )
709 : {
710 90155170 : wtda_audio[i] = round_fx( L_mac0( L_mult0( negate( allsig_r[L / 2 - i - 1] ), win_right[3 * L / 2 * decimate - ( i + 1 ) * decimate + decay - windecay48] ),
711 90155170 : allsig_r[L / 2 + i], win_right[3 * L / 2 * decimate - 1 + ( i + 1 ) * decimate - decay - windecay48] ) ); // q_in - 1
712 90155170 : move16();
713 : }
714 : }
715 : ELSE
716 : {
717 18559 : FOR( i = 0; i < L / 2 - n; i++ )
718 : {
719 18410 : wtda_audio[i] = round_fx( L_msu0( L_mult0( negate( allsig_r[L / 2 - i - 1] ), win_right[3 * L / 2 * decimate - ( i + 1 ) * decimate + decay - windecay48] ),
720 18410 : allsig_r[L / 2 + i], win_right[3 * L / 2 * decimate - 1 + ( i + 1 ) * decimate - decay - windecay48] ) ); // q_in - 1
721 18410 : move16();
722 : }
723 : }
724 :
725 116391906 : FOR( i = L / 2 - n; i < L / 2; i++ )
726 : {
727 115937460 : wtda_audio[i] = shr( negate( allsig_r[L / 2 - i - 1] ), 1 ); // q_in - 1
728 115937460 : move16();
729 : }
730 :
731 454446 : IF( GE_32( kernel_type, 2 ) )
732 : {
733 116366995 : FOR( i = 0; i < n; i++ )
734 : {
735 115912710 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( negate( allsig_l[i] ), win_left[i * decimate + decay] ),
736 115912710 : new_audio[n - i - 1], MAX16B ) ); // q_in - 1
737 115912710 : move16();
738 : }
739 :
740 90608615 : FOR( i = n; i < L / 2; i++ )
741 : {
742 90154330 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( negate( allsig_l[i] ), win_left[i * decimate + decay] ),
743 90154330 : allsig_l[L - i - 1], win_left[L * decimate - i * decimate - 1 - decay] ) ); // q_in - 1
744 90154330 : move16();
745 : }
746 : }
747 : ELSE
748 : {
749 24911 : FOR( i = 0; i < n; i++ )
750 : {
751 24750 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( allsig_l[i], win_left[i * decimate + decay] ),
752 24750 : new_audio[n - i - 1], MAX16B ) ); // q_in - 1
753 24750 : move16();
754 : }
755 :
756 19411 : FOR( i = n; i < L / 2; i++ )
757 : {
758 19250 : wtda_audio[i + L / 2] = round_fx( L_msu0( L_mult0( allsig_l[i], win_left[i * decimate + decay] ),
759 19250 : allsig_l[L - i - 1], win_left[L * decimate - i * decimate - 1 - decay] ) ); // q_in - 1
760 19250 : move16();
761 : }
762 : }
763 : }
764 :
765 608853 : return;
766 : }
|