1 /* ------------------------------------------------------------------
2 * Copyright (C) 1998-2009 PacketVideo
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
13 * express or implied.
14 * See the License for the specific language governing permissions
15 * and limitations under the License.
16 * -------------------------------------------------------------------
17 */
18 /*
19
20 Pathname: trans4m_freq_2_time_fxp.c
21 Function: trans4m_freq_2_time_fxp
22
23
24 ------------------------------------------------------------------------------
25 REVISION HISTORY
26
27 Description:
28 changed to decrement loop
29 change wnd_shape from structure to passing parameters
30 modified window tables from UInt to UInt16 to assure proper operation
31 without dubious typecast
32 changed logic to hit most common states first.
33 modified Time_data from Int to Int32 to hold
34 possible overflow before saturation process.
35
36 Description:
37 Increase processing on some loop by using more pointers
38 changed interface to avoid passing a pointer for wnd_shape_prev_bk, this
39 element is not change in this function because of this function use
40 in the LTP module
41
42 Description:
43 Added rounding to multiplication
44
45 Description:
46 Update input description and eliminate unneeded comments
47
48 Description:
49 LONG_START_WINDOW was using SHORT_WINDOW instead of
50 HALF_SHORT_WINDOW, causing a for loop to exceed its count
51
52 Description:
53 Modified structure of code so exp is not tested before it
54 is initialized. Also, new structure avoids double-testing
55 of exp_freq = ALL_ZEROS_BUFFER.
56
57 Description:
58 The result of a shift is undefined if the right operand is greater than
59 or equal to the number of bits in the left expression's type
60 To avoid undefined shift by 32, a check of the shift has been
61 added, so the function proceeds only when the exponent is less
62 than 32. By design the shift up is related to the global gain,
63 and controlled by the encoder, so saturation is not allowed.
64 In both short and long window, processing is skip if an all zero
65 input buffer or excessive down shift is detected.
66
67 Description:
68 Changes according to code review comments. Also, modified if-else
69 structure so the imdct_fxp is not called with an all zero input buffer
70
71 Description:
72 Replaced function buffer_normalization by buffer_adaptation, to ease
73 use of 16 bits. Function buffer_normalization becomes obsolete.
74
75 Description:
76 Modified call to imdct_fxp to reflect extended precision use. Added
77 routine buffer_adaptation to extract 16 MSB and keep highest.
78 precision. Modify casting to ensure proper operations for different
79 platforms
80
81 Description:
82 Eliminate double access to memory by loading data directly to the
83 time array. Also reduced cycle count and added precision by combining
84 downshifting in only one operation. Added adaptive rounding factor.
85 Change exponent threshold when operations are waived. It is use to be 32
86 but by combining downshifting, this new threshold is now 16. This may
87 avoid unneeded calculations for extremely small numbers.
88
89 Description:
90 Per review comments:
91 - Added comments to clarify buffer_adaptation function
92 - Deleted reference to include file "buffer_normalization.h"
93 - Modified IF-ELSE so long_windows case is considered first
94 - Eliminated extra IF when computing the rounding, so when exp ==0
95 less cycles are used shifting than in an extra if-else
96 - Corrected negative shift when computing rounding factor
97 - Added condition when exp > 16 (for long windows)
98
99 Description:
100 Modified IF-ELSE structure so now ALL_ZEROS_BUFFER condition is share
101 with exp > 16 condition. This avoid code duplication for both cases.
102
103 Description:
104 - Modified function interface to add output_buffer
105 - Eliminated the 32 bit version of the current output, calculations
106 are placed directly in output_buffer. In this way the buffer
107 Time_data needs only to be 1024 Int32, instead of 2048 (per channel).
108 Also, added the limit macro inside the function (this reduces access
109 to memory).
110 - Updated Pseudo - Code
111
112 Description:
113 Per review comments:
114 Corrected line sizes and mispelling, added comments and swap
115 order or switch statement for ONLY_LONG_SEQUENCE.
116
117 Description:
118 Eliminated adaptive rounding due to potential saturation.
119
120 Description:
121 Eliminated use of buffer adaptation by shifting this functionality inside
122 the imdct_fxp() routine. Also modified the call to imdct_fxp to accomodate
123 new function interface.
124 Modified macro limit() to save cycles when testing the most common case:
125 no saturation.
126
127 Description:
128 Changed new function interface for imdct_fxp().
129
130 Description:
131 Replaced for-loop with memset and memcopy.
132
133 Who: Date:
134 Description:
135
136 ------------------------------------------------------------------------------
137 INPUT AND OUTPUT DEFINITIONS
138
139 Inputs:
140 Frequency_data = vector with spectral information, size 2048
141 type Int32
142
143 Time_data = buffer with data from previous Frequency to Time
144 conversion, used for overlap and add, size 1024
145 type Int32
146
147 Output_buffer = place holder for current output, size 1024
148 type Int16
149
150 wnd_seq = window sequence
151 type WINDOW_SEQUENCE
152
153 wnd_shape_prev_bk = previous window shape type
154 type Int
155
156 wnd_shape_this_bk = current window shape type
157 type Int
158
159 Q_format = Q format for the input frequency data
160 type Int
161
162 freq_2_time_buffer[] = scratch memory for computing FFT
163 type Int32
164
165
166 Local Stores/Buffers/Pointers Needed:
167 None
168
169 Global Stores/Buffers/Pointers Needed:
170 None
171
172 Outputs:
173 None
174
175 Pointers and Buffers Modified:
176 Output_buffer
177 Time_data
178 Frequency_data
179 pWnd_shape_prev_bk
180
181 Local Stores Modified:
182 None
183
184 Global Stores Modified:
185 None
186
187 ------------------------------------------------------------------------------
188 FUNCTION DESCRIPTION
189
190 The time/frequency representation of the signal is mapped onto the time
191 domain by feeding it into the filterbank module. This module consists of
192 an inverse modified discrete cosine transform (IMDCT), and a window and an
193 overlap-add function. In order to adapt the time/frequency resolution of the
194 filterbank to the characteristics of the input signal, a block switching tool
195 is also adopted. N represents the window length, where N is a function of the
196 window_sequence. For each channel, the N/2 time-frequency values are
197 transformed into the N time domain values via the IMDCT. After applying the
198 window function, for each channel, the first half of the sequence is added to
199 the second half of the previous block windowed sequence to reconstruct the
200 output samples for each channel outi,n.
201
202 The adaptation of the time-frequency resolution of the filterbank to the
203 characteristics of the input signal is done by shifting between transforms
204 whose input lengths are either 2048 or 256 samples. By enabling the block
205 switching tool, the following transitions are meaningful:
206
207 from ONLY_LONG_SEQUENCE to { LONG_START_SEQUENCE
208 ONLY_LONG_SEQUENCE
209
210 from LONG_START_SEQUENCE to { LONG_STOP_SEQUENCE
211 EIGHT_SHORT_SEQUENCE
212
213 from LONG_STOP_SEQUENCE to { LONG_START_SEQUENCE
214 ONLY_LONG_SEQUENCE
215
216 from EIGHT_SHORT_SEQUENCE to { LONG_STOP_SEQUENCE
217 EIGHT_SHORT_SEQUENCE
218
219 Window shape decisions are made by the encoder on a frame-by-frame-basis.
220 The window selected is applicable to the second half of the window function
221 only, since the first half is constrained to use the appropriate window
222 shape from the preceding frame.
223 The 2048 time-domain values x'(i)(n), (i window, n sample) to be windowed are
224 the last 1024 values of the previous window_sequence concatenated with 1024
225 values of the current block. The formula below shows this fact:
226
227 | x(i-1)(n+1024) for 0 < n < 1024
228 x'(i)(n) {
229 | x(i)(n) for 1024 < n < 2048
230
231
232 Buffer Time_data data from previous Frequency to Time conversion, used
233 for overlap and add
234
235 Once the window shape is selected, the window_shape syntax element is
236 initialized. Together with the chosen window_sequence all information needed
237 for windowing exist.
238 With the window halves described below all window_sequences can be assembled.
239 For window_shape == 1, the window coefficients are given by the Kaiser -
240 Bessel derived (KBD) window.
241 Otherwise, for window_shape == 0, a sine window is employed.
242
243 The window length N can be 2048 or 256 for the KBD and the sine window.
244 All four window_sequences explained below have a total length of 2048
245 samples.
246 For all kinds of window_sequences the window_shape of the left half of
247 the first transform window is determined by the window shape of the previous
248 block.
249
250 In the case of EIGHT_SHORT_SEQUENCE the processing is done in-place and
251 in descendent order to avoid using extra memory.
252 The ordering is as follows:
253
254 Pn: Previous data for window n
255 Cn: Current data for window n
256
257
258 128 freq.
259 samples
260 FREQ ++++++
261 IN ===========================
262 \
263 \
264 -> 256 time
265 samples
266
267 P8 C8
268 8 #######++++++
269 P7 C7
270 7 #######++++++
271 : :
272 : :
273 P2 C2
274 2 #######++++++
275 P1 C1
276 1 #######++++++
277 TIME
278 OUT ==============================================================
279
280 ------------------------------------------------------------------------------
281 REQUIREMENTS
282
283 This module shall implement a scheme to switch between window types
284
285 ------------------------------------------------------------------------------
286 REFERENCES
287
288 [1] ISO 14496-3:1999, pag 111
289
290 ------------------------------------------------------------------------------
291 PSEUDO-CODE
292
293
294
295 IF ( wnd_seq == EIGHT_SHORT_SEQUENCE)
296 THEN
297
298 FOR ( i=0; i<LONG_WINDOW; i++)
299 Time_data[LONG_WINDOW + i] = 0;
300 ENDFOR
301
302 FOR ( wnd=NUM_SHORT_WINDOWS-1; wnd>=0; wnd--)
303
304 pFreqInfo = &Frequency_data[ wnd*SHORT_WINDOW];
305
306 CALL IMDCT( pFreqInfo, SHORT_BLOCK1);
307 MODIFYING(pFreqInfo)
308
309
310 IF (wnd == 0)
311 THEN
312 pShort_Window_1 = &Short_Window[wnd_shape_prev_bk][0];
313 ELSE
314 pShort_Window_1 = &Short_Window[wnd_shape_this_bk][0];
315 ENDIF
316
317 pShort_Window_2 =
318 &Short_Window[wnd_shape->this_bk][SHORT_WINDOW_m_1];
319
320 FOR( i=0, j=SHORT_WINDOW; i<SHORT_WINDOW; i++, j--)
321 pFreqInfo[ i] *= pShort_Window_1[i];
322 pFreqInfo[SHORT_WINDOW+i] *= pShort_Window_2[j];
323 ENDFOR
324
325
326 FOR( i=0; i<SHORT_BLOCK1; i++)
327 Time_data[W_L_STOP_1 + SHORT_WINDOW*wnd + i] += pFreqInfo[i];
328 ENDFOR
329
330 ENDFOR
331
332 FOR ( i=0; i<LONG_WINDOW; i++)
333 temp = Time_data[i];
334 Output_buffer[i] = Time_data[i];
335 Time_data[i] = temp;
336 ENDFOR
337 ELSE
338
339 CALL IMDCT( Frequency_data, LONG_BLOCK1)
340 MODIFYING(Frequency_data)
341
342 SWITCH ( wnd_seq)
343
344 CASE ( ONLY_LONG_SEQUENCE)
345
346 pLong_Window_1 = &Long_Window[wnd_shape_prev_bk][0];
347 pLong_Window_2 =
348 &Long_Window[wnd_shape_this_bk][LONG_WINDOW_m_1];
349
350 FOR (i=0; i<LONG_WINDOW; i++)
351 Frequency_data[ i] *= *pLong_Window_1++;
352 Frequency_data[LONG_WINDOW+i] *= *pLong_Window_2--;
353 ENDFOR
354
355 BREAK
356
357 CASE ( LONG_START_SEQUENCE)
358
359 pLong_Window_1 = &Long_Window[wnd_shape_prev_bk][0];
360
361 FOR ( i=0; i<LONG_WINDOW; i++)
362 Frequency_data[ i] *= *pLong_Window_1++;
363 ENDFOR
364
365 pShort_Window_1 =
366 &Short_Window[wnd_shape_this_bk][SHORT_WINDOW_m_1];
367
368 FOR ( i=0; i<SHORT_WINDOW; i++)
369 Frequency_data[W_L_START_1 + i] *= *pShort_Window_1--;
370 ENDFOR
371
372 FOR ( i=W_L_START_2; i<LONG_BLOCK1; i++)
373 Frequency_data[W_L_START_2 + i] = 0;
374 ENDFOR
375
376 BREAK
377
378
379 CASE ( LONG_STOP_SEQUENCE )
380
381 FOR ( i=0; i<W_L_STOP_1; i++)
382 Frequency_data[ i] = 0;
383 ENDFOR
384
385 pShort_Window_1 = &Short_Window[wnd_shape_prev_bk][0];
386
387 FOR ( i=0; i<SHORT_WINDOW; i++)
388 Frequency_data[W_L_STOP_1+ i] *= *pShort_Window_1++;
389 ENDFOR
390
391 pLong_Window_1 =
392 &Long_Window[wnd_shape_this_bk][LONG_WINDOW_m_1];
393
394 FOR ( i=0; i<LONG_WINDOW; i++)
395 Frequency_data[LONG_WINDOW + i] *= *pLong_Window_1--;
396 ENDFOR
397
398 BREAK
399
400 }
401
402
403 FOR ( i=0; i<LONG_WINDOW; i++)
404 Output_buffer[i] = Frequency_data[i] + Time_data[i];
405 Time_data[i] = Frequency_data[LONG_WINDOW+i];
406 ENDFOR
407
408 }
409
410 ENDIF
411
412
413
414 ------------------------------------------------------------------------------
415 RESOURCES USED
416 When the code is written for a specific target processor the
417 the resources used should be documented below.
418
419 STACK USAGE: [stack count for this module] + [variable to represent
420 stack usage for each subroutine called]
421
422 where: [stack usage variable] = stack usage for [subroutine
423 name] (see [filename].ext)
424
425 DATA MEMORY USED: x words
426
427 PROGRAM MEMORY USED: x words
428
429 CLOCK CYCLES: [cycle count equation for this module] + [variable
430 used to represent cycle count for each subroutine
431 called]
432
433 where: [cycle count variable] = cycle count for [subroutine
434 name] (see [filename].ext)
435
436 ------------------------------------------------------------------------------
437 */
438
439
440 /*----------------------------------------------------------------------------
441 ; INCLUDES
442 ----------------------------------------------------------------------------*/
443
444 #include "pv_audio_type_defs.h"
445 #include "aac_mem_funcs.h"
446 #include "window_block_fxp.h"
447 #include "imdct_fxp.h"
448
449 #include "fxp_mul32.h"
450
451
452 /*----------------------------------------------------------------------------
453 ; MACROS
454 ; limit(x) saturates any number that exceeds a 16-bit representation into a
455 ; 16 bit number.
456 ----------------------------------------------------------------------------*/
457
458 #define ROUNDING_SCALED (ROUNDING<<(16 - SCALING))
459
460
461 #if defined(PV_ARM_V5)
462
463
sat(Int32 y)464 __inline Int16 sat(Int32 y)
465 {
466 Int32 x;
467 Int32 z;
468 __asm
469 {
470 mov x, ROUNDING_SCALED
471 mov y, y, lsl #(15-SCALING)
472 qdadd z, x, y
473 mov y, z, lsr #16
474 }
475 return((Int16)y);
476 }
477
478 #define limiter( y, x) y = sat(x);
479
480
481
482 #elif defined(PV_ARM_GCC_V5)
483
484
sat(Int32 y)485 __inline Int16 sat(Int32 y)
486 {
487 register Int32 x;
488 register Int32 ra = (Int32)y;
489 register Int32 z = ROUNDING_SCALED;
490
491
492 asm volatile(
493 "mov %0, %1, lsl #5\n\t" // (15-SCALING) assembler does not take symbols
494 "qdadd %0, %2, %0\n\t"
495 "mov %0, %0, lsr #16"
496 : "=&r*i"(x)
497 : "r"(ra),
498 "r"(z));
499
500 return ((Int16)x);
501 }
502
503 #define limiter( y, x) y = sat(x);
504
505
506 #elif defined(PV_ARM_MSC_EVC_V5)
507
508
509 #define limiter( y, x) z = x<< (15-SCALING); \
510 y = _DAddSatInt( ROUNDING_SCALED, z)>>16;
511
512
513 #else
514
515 #define limiter( y, x) z = ((x + ROUNDING )>>SCALING); \
516 if ((z>>15) != (z>>31)) \
517 { \
518 z = (z >> 31) ^ INT16_MAX; \
519 } \
520 y = (Int16)(z);
521
522 #endif
523
524
525 /*----------------------------------------------------------------------------
526 ; DEFINES
527 ; Include all pre-processor statements here. Include conditional
528 ; compile variables also.
529 ----------------------------------------------------------------------------*/
530
531 /*----------------------------------------------------------------------------
532 ; LOCAL FUNCTION DEFINITIONS
533 ; Function Prototype declaration
534 ----------------------------------------------------------------------------*/
535
536
537 /*----------------------------------------------------------------------------
538 ; LOCAL VARIABLE DEFINITIONS
539 ; Variable declaration - defined here and used outside this module
540 ----------------------------------------------------------------------------*/
541
542 /*----------------------------------------------------------------------------
543 ; EXTERNAL FUNCTION REFERENCES
544 ; Declare functions defined elsewhere and referenced in this module
545 ----------------------------------------------------------------------------*/
546
547 /*----------------------------------------------------------------------------
548 ; EXTERNAL VARIABLES REFERENCES
549 ; Declare variables used in this module but defined elsewhere
550 ----------------------------------------------------------------------------*/
551
552 /*----------------------------------------------------------------------------
553 ; EXTERNAL GLOBAL STORE/BUFFER/POINTER REFERENCES
554 ; Declare variables used in this module but defined elsewhere
555 ----------------------------------------------------------------------------*/
556
557 /*----------------------------------------------------------------------------
558 ; FUNCTION CODE
559 ----------------------------------------------------------------------------*/
560
561 #ifdef AAC_PLUS
562
563
trans4m_freq_2_time_fxp_1(Int32 Frequency_data[],Int32 Time_data[],Int16 Output_buffer[],WINDOW_SEQUENCE wnd_seq,Int wnd_shape_prev_bk,Int wnd_shape_this_bk,Int Q_format,Int32 abs_max_per_window[],Int32 freq_2_time_buffer[])564 void trans4m_freq_2_time_fxp_1(
565 Int32 Frequency_data[],
566 Int32 Time_data[],
567 Int16 Output_buffer[],
568 WINDOW_SEQUENCE wnd_seq,
569 Int wnd_shape_prev_bk,
570 Int wnd_shape_this_bk,
571 Int Q_format,
572 Int32 abs_max_per_window[],
573 Int32 freq_2_time_buffer[])
574
575 {
576 Int exp;
577 Int shift;
578
579 Int i;
580 Int wnd;
581 #if !(defined( PV_ARM_GCC_V5)||(PV_ARM_V5))
582 Int32 z;
583 #endif
584
585 Int16 *pFreqInfo;
586 Int32 temp;
587 Int32 test;
588
589 Int16 *pFreq_2_Time_data_1;
590 Int16 *pFreq_2_Time_data_2;
591
592 const Int16 *pLong_Window_1;
593 const Int16 *pLong_Window_2;
594 const Int16 *pShort_Window_1;
595 const Int16 *pShort_Window_2;
596
597 Int32 *pOverlap_and_Add_Buffer_1;
598 Int32 *pOverlap_and_Add_Buffer_2;
599
600 Int16 *pOutput_buffer;
601 Int16 *pOutput_buffer_2;
602
603 const Int16 * Long_Window_fxp[NUM_WINDOW_SHAPES];
604 const Int16 * Short_Window_fxp[NUM_WINDOW_SHAPES];
605
606 Long_Window_fxp[0] = Long_Window_sine_fxp;
607 Long_Window_fxp[1] = Long_Window_KBD_fxp;
608 Short_Window_fxp[0] = Short_Window_sine_fxp;
609 Short_Window_fxp[1] = Short_Window_KBD_fxp;
610
611
612 if (wnd_seq != EIGHT_SHORT_SEQUENCE)
613 {
614
615 pFreqInfo = (Int16 *)Frequency_data;
616
617
618 exp = imdct_fxp(
619 (Int32 *)pFreqInfo,
620 freq_2_time_buffer,
621 LONG_BLOCK1,
622 Q_format,
623 abs_max_per_window[0]);
624
625
626
627 /*
628 * The C Programming Language, Second Edition, Kernighan & Ritchie,
629 * page 206.
630 * "The result [of a shift] is undefined if the right operand is
631 * negative, or greater than or equal to the number of bits in the
632 * left expression's type"
633 * => avoid shift by 32 or 16
634 */
635
636 if (exp < 16)
637 {
638
639 pFreq_2_Time_data_1 = pFreqInfo;
640
641 switch (wnd_seq)
642 {
643
644 case ONLY_LONG_SEQUENCE:
645 default:
646
647 pOutput_buffer = Output_buffer;
648
649 pOverlap_and_Add_Buffer_1 = Time_data;
650
651 {
652 const Int16 *pLong_Window_2 = &Long_Window_fxp[wnd_shape_this_bk][LONG_WINDOW_m_1];
653
654 Int32 * pFreq2T = (Int32 *)pFreqInfo;
655 Int32 * win = (Int32 *) & Long_Window_fxp[wnd_shape_prev_bk][0];
656 Int shift = exp + 15 - SCALING;
657
658
659 Int32 * pFreq2T_2 = &pFreq2T[HALF_LONG_WINDOW];
660
661
662 for (i = HALF_LONG_WINDOW; i != 0; i--)
663 {
664 Int16 win1, win2;
665 Int32 temp2, test2;
666
667 Int32 winx;
668
669 temp2 = *(pFreq2T++);
670 winx = *(win++);
671
672 test = *(pOverlap_and_Add_Buffer_1++);
673 test2 = *(pOverlap_and_Add_Buffer_1--);
674 temp = fxp_mul_16_by_16bb(temp2, winx) >> shift;
675 temp2 = fxp_mul_16_by_16tt(temp2, winx) >> shift;
676 limiter(*(pOutput_buffer++), (temp + test));
677 limiter(*(pOutput_buffer++), (temp2 + test2));
678
679 temp2 = *(pFreq2T_2++);
680
681 win1 = *(pLong_Window_2--);
682 win2 = *(pLong_Window_2--);
683 temp = fxp_mul_16_by_16bb(temp2, win1) >> shift;
684 test2 = fxp_mul_16_by_16tb(temp2, win2) >> shift;
685 *(pOverlap_and_Add_Buffer_1++) = temp;
686 *(pOverlap_and_Add_Buffer_1++) = test2;
687
688 }
689 }
690
691 break;
692
693 case LONG_START_SEQUENCE:
694
695
696 pFreq_2_Time_data_2 =
697 &pFreq_2_Time_data_1[ HALF_LONG_WINDOW];
698
699 pLong_Window_1 = &Long_Window_fxp[wnd_shape_prev_bk][0];
700 pLong_Window_2 = &pLong_Window_1[ HALF_LONG_WINDOW];
701
702 pOverlap_and_Add_Buffer_1 = &Time_data[0];
703 pOverlap_and_Add_Buffer_2 = &Time_data[HALF_LONG_WINDOW];
704
705 pOutput_buffer = Output_buffer;
706 pOutput_buffer_2 = pOutput_buffer + HALF_LONG_WINDOW;
707
708
709 shift = exp + 15 - SCALING;
710
711 for (i = HALF_LONG_WINDOW; i != 0; i--)
712 {
713
714 Int16 win1, win2;
715 Int16 dat1, dat2;
716 Int32 test1, test2;
717
718 dat1 = *(pFreq_2_Time_data_1++);
719 win1 = *(pLong_Window_1++);
720 test1 = *(pOverlap_and_Add_Buffer_1++);
721
722 dat2 = *(pFreq_2_Time_data_2++);
723 win2 = *(pLong_Window_2++);
724 test2 = *(pOverlap_and_Add_Buffer_2++);
725
726 limiter(*(pOutput_buffer++), (test1 + (fxp_mul_16_by_16(dat1, win1) >> shift)));
727
728 limiter(*(pOutput_buffer_2++), (test2 + (fxp_mul_16_by_16(dat2, win2) >> shift)));
729
730 }
731
732 /*
733 * data unchanged from LONG_WINDOW to W_L_START_1
734 * only scaled accordingly
735 */
736
737 pOverlap_and_Add_Buffer_1 = &Time_data[0];
738 pFreq_2_Time_data_1 = &pFreqInfo[LONG_WINDOW];
739
740 exp -= SCALING;
741
742 if (exp >= 0)
743 {
744
745 for (i = (W_L_START_1 - LONG_WINDOW) >> 1; i != 0; i--)
746 {
747 *(pOverlap_and_Add_Buffer_1++) =
748 *(pFreq_2_Time_data_1++) >> exp;
749 *(pOverlap_and_Add_Buffer_1++) =
750 *(pFreq_2_Time_data_1++) >> exp;
751
752 }
753
754 }
755 else if (exp < 0)
756 {
757
758 Int shift = -exp;
759 for (i = (W_L_START_1 - LONG_WINDOW) >> 1; i != 0 ; i--)
760 {
761 Int32 temp2 = ((Int32) * (pFreq_2_Time_data_1++)) << shift;
762 *(pOverlap_and_Add_Buffer_1++) = temp2;
763 temp2 = ((Int32) * (pFreq_2_Time_data_1++)) << shift;
764 *(pOverlap_and_Add_Buffer_1++) = temp2;
765 }
766
767 }
768 else
769 {
770
771 for (i = (W_L_START_1 - LONG_WINDOW) >> 1; i != 0; i--)
772 {
773 *(pOverlap_and_Add_Buffer_1++) =
774 *(pFreq_2_Time_data_1++);
775 *(pOverlap_and_Add_Buffer_1++) =
776 *(pFreq_2_Time_data_1++);
777
778 }
779
780 }
781
782
783 pFreq_2_Time_data_1 = &pFreqInfo[W_L_START_1];
784 pFreq_2_Time_data_2 =
785 &pFreq_2_Time_data_1[HALF_SHORT_WINDOW];
786
787 pShort_Window_1 =
788 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
789
790 pShort_Window_2 = pShort_Window_1 - HALF_SHORT_WINDOW;
791
792 pOverlap_and_Add_Buffer_2 = pOverlap_and_Add_Buffer_1 +
793 HALF_SHORT_WINDOW;
794
795
796 for (i = HALF_SHORT_WINDOW; i != 0; i--)
797 {
798 Int16 win1, win2;
799 Int16 dat1, dat2;
800 Int32 temp2;
801 dat1 = (*pFreq_2_Time_data_1++);
802 dat2 = (*pFreq_2_Time_data_2++);
803 win1 = *(pShort_Window_1--);
804 win2 = *(pShort_Window_2--);
805
806 temp = fxp_mul_16_by_16(dat1, win1) >> shift;
807 *(pOverlap_and_Add_Buffer_1++) = temp;
808
809 temp2 = fxp_mul_16_by_16(dat2, win2) >> shift;
810 *(pOverlap_and_Add_Buffer_2++) = temp2;
811
812
813 }
814
815
816 pOverlap_and_Add_Buffer_1 += HALF_SHORT_WINDOW;
817
818 pv_memset(
819 pOverlap_and_Add_Buffer_1,
820 0,
821 (LONG_BLOCK1 - W_L_START_2)
822 *sizeof(*pOverlap_and_Add_Buffer_1));
823
824
825 break;
826
827
828 case LONG_STOP_SEQUENCE:
829
830 pOverlap_and_Add_Buffer_1 = &Time_data[ W_L_STOP_2];
831
832 pOutput_buffer = &Output_buffer[W_L_STOP_2];
833
834 pFreq_2_Time_data_1 = &pFreqInfo[W_L_STOP_2];
835
836 exp -= SCALING; /* !!!! */
837
838 if (exp > 0)
839 {
840 Int16 tmp1 = (*(pFreq_2_Time_data_1++) >> exp);
841 temp = *(pOverlap_and_Add_Buffer_1++);
842
843 for (i = (LONG_WINDOW - W_L_STOP_2); i != 0; i--)
844 {
845 limiter(*(pOutput_buffer++), (temp + tmp1));
846
847 tmp1 = *(pFreq_2_Time_data_1++) >> exp;
848 temp = *(pOverlap_and_Add_Buffer_1++);
849
850 }
851 }
852 else if (exp < 0)
853 {
854 shift = -exp;
855 Int32 temp1 = ((Int32) * (pFreq_2_Time_data_1++)) << shift;
856 temp = *(pOverlap_and_Add_Buffer_1++);
857
858 for (i = (LONG_WINDOW - W_L_STOP_2); i != 0; i--)
859 {
860 limiter(*(pOutput_buffer++), (temp + temp1));
861
862 temp1 = ((Int32) * (pFreq_2_Time_data_1++)) << shift;
863 temp = *(pOverlap_and_Add_Buffer_1++);
864
865 }
866 }
867 else
868 {
869 Int16 tmp1 = *(pFreq_2_Time_data_1++);
870 temp = *(pOverlap_and_Add_Buffer_1++);
871
872 for (i = (LONG_WINDOW - W_L_STOP_2); i != 0; i--)
873 {
874 limiter(*(pOutput_buffer++), (temp + tmp1));
875
876 tmp1 = *(pFreq_2_Time_data_1++);
877 temp = *(pOverlap_and_Add_Buffer_1++);
878
879 }
880 }
881
882
883 pShort_Window_1 = &Short_Window_fxp[wnd_shape_prev_bk][0];
884 pShort_Window_2 = &pShort_Window_1[HALF_SHORT_WINDOW];
885
886 pFreq_2_Time_data_1 = &pFreqInfo[W_L_STOP_1];
887 pFreq_2_Time_data_2 =
888 &pFreq_2_Time_data_1[HALF_SHORT_WINDOW];
889
890 pOverlap_and_Add_Buffer_1 = &Time_data[ W_L_STOP_1];
891 pOverlap_and_Add_Buffer_2 = pOverlap_and_Add_Buffer_1
892 + HALF_SHORT_WINDOW;
893
894 pOutput_buffer = &Output_buffer[W_L_STOP_1];
895 pOutput_buffer_2 = pOutput_buffer + HALF_SHORT_WINDOW;
896
897 exp += SCALING; /* +8 back to what it was */
898
899 shift = exp + 15 - SCALING;
900
901
902 for (i = HALF_SHORT_WINDOW; i != 0; i--)
903 {
904 Int16 win1;
905 Int16 dat1;
906
907 dat1 = *(pFreq_2_Time_data_1++);
908 win1 = *(pShort_Window_1++);
909 temp = *(pOverlap_and_Add_Buffer_1++);
910
911 test = fxp_mul_16_by_16(dat1, win1);
912
913 limiter(*(pOutput_buffer++), (temp + (test >> shift)));
914
915 dat1 = *(pFreq_2_Time_data_2++);
916 win1 = *(pShort_Window_2++);
917 temp = *(pOverlap_and_Add_Buffer_2++);
918 test = fxp_mul_16_by_16(dat1, win1);
919 limiter(*(pOutput_buffer_2++), (temp + (test >> shift)));
920
921 }
922
923
924 pFreq_2_Time_data_2 = &pFreqInfo[LONG_WINDOW];
925
926 pOverlap_and_Add_Buffer_1 = Time_data;
927
928 pOutput_buffer = Output_buffer;
929
930 pLong_Window_2 =
931 &Long_Window_fxp[wnd_shape_this_bk][LONG_WINDOW_m_1];
932
933
934 /*
935 * Copy previous time in current buffer, also copy overlap
936 * and add buffer
937 */
938
939 for (i = W_L_STOP_1; i != 0; i--)
940 {
941 Int16 win1;
942 Int16 dat1;
943
944 win1 = *(pLong_Window_2--);
945 dat1 = *pFreq_2_Time_data_2++;
946
947 limiter(*(pOutput_buffer++), *(pOverlap_and_Add_Buffer_1));
948
949
950 temp = fxp_mul_16_by_16(dat1, win1) >> shift;
951 *(pOverlap_and_Add_Buffer_1++) = temp ;
952
953 }
954
955 for (i = (LONG_WINDOW - W_L_STOP_1); i != 0; i--)
956 {
957 temp = fxp_mul_16_by_16(*pFreq_2_Time_data_2++, *(pLong_Window_2--)) >> shift;
958 *(pOverlap_and_Add_Buffer_1++) = temp ;
959 }
960
961
962 break;
963
964
965
966 } /* switch (wnd_seq) */
967
968 } /* if (exp < 16) */
969
970 else
971 {
972 /* all zeros buffer or excessive down shift */
973
974 /* Overlap and add, setup buffer for next iteration */
975 pOverlap_and_Add_Buffer_1 = &Time_data[0];
976
977 pOutput_buffer = Output_buffer;
978
979 temp = (*pOverlap_and_Add_Buffer_1++);
980
981 for (i = LONG_WINDOW; i != 0; i--)
982 {
983
984 limiter(*(pOutput_buffer++), temp);
985
986 temp = (*pOverlap_and_Add_Buffer_1++);
987
988 }
989
990 pv_memset(Time_data, 0, LONG_WINDOW*sizeof(Time_data[0]));
991
992
993 }
994
995 }
996 else
997 {
998
999 Int32 *pScrath_mem;
1000 Int32 *pScrath_mem_entry;
1001 Int32 *pFrequency_data = Frequency_data;
1002
1003 Int32 * pOverlap_and_Add_Buffer_1;
1004 Int32 * pOverlap_and_Add_Buffer_2;
1005 Int32 * pOverlap_and_Add_Buffer_1x;
1006 Int32 * pOverlap_and_Add_Buffer_2x;
1007
1008 /*
1009 * Frequency_data is 2*LONG_WINDOW length but only
1010 * the first LONG_WINDOW elements are filled in,
1011 * then the second part can be used as scratch mem,
1012 * then grab data from one window at a time in
1013 * reverse order.
1014 * The upper LONG_WINDOW Int32 are used to hold the
1015 * computed overlap and add, used in the next call to
1016 * this function, and also as sctrach memory
1017 */
1018
1019 /*
1020 * Frequency_data usage for the case EIGHT_SHORT_SEQUENCE
1021
1022 |<----- Input Freq. data ----->|< Overlap & Add ->| Unused |-Scratch-|
1023 | | Store for next | | memory |
1024 | | call | | |
1025 | | | | |
1026 |//////////////////////////////|\\\\\\\\\\\\\\\\\\|--------|+++++++++|
1027 | | | | |
1028 0 LONG_WINDOW LONG_WINDOW | 2*LONG_WINDOW
1029 + | |
1030 W_L_STOP_2 | |
1031 |<-- -->|
1032 SHORT_WINDOW +
1033 HALF_SHORT_WINDOW
1034 *
1035 */
1036
1037 pOverlap_and_Add_Buffer_1 = &pFrequency_data[
1038 LONG_WINDOW + 3*SHORT_WINDOW + HALF_SHORT_WINDOW];
1039
1040 /*
1041 * Initialize to zero, only the firt short window used in overlap
1042 * and add
1043 */
1044 pv_memset(
1045 pOverlap_and_Add_Buffer_1,
1046 0,
1047 SHORT_WINDOW*sizeof(*pOverlap_and_Add_Buffer_1));
1048
1049 /*
1050 * Showt windows are evaluated in decresing order. Windows from 7
1051 * to 0 are break down in four cases: window numbers 7 to 5, 4, 3,
1052 * and 2 to 0.
1053 * The data from short windows 3 and 4 is situated at the boundary
1054 * between the 'overlap and add' buffer and the output buffer.
1055 */
1056 for (wnd = NUM_SHORT_WINDOWS - 1; wnd >= NUM_SHORT_WINDOWS / 2 + 1; wnd--)
1057 {
1058
1059 pFreqInfo = (Int16 *) & pFrequency_data[ wnd*SHORT_WINDOW];
1060
1061 exp = imdct_fxp(
1062 (Int32 *)pFreqInfo,
1063 freq_2_time_buffer,
1064 SHORT_BLOCK1,
1065 Q_format,
1066 abs_max_per_window[wnd]);
1067
1068 pOverlap_and_Add_Buffer_1 =
1069 &pFrequency_data[ W_L_STOP_1 + SHORT_WINDOW*wnd];
1070
1071
1072 pOverlap_and_Add_Buffer_2 =
1073 pOverlap_and_Add_Buffer_1 + SHORT_WINDOW;
1074
1075 /*
1076 * If all element are zero or if the exponent is bigger than
1077 * 16 ( it becomes an undefined shift) -> skip
1078 */
1079
1080 if (exp < 16)
1081 {
1082
1083
1084 pFreq_2_Time_data_1 = &pFreqInfo[0];
1085 pFreq_2_Time_data_2 = &pFreqInfo[SHORT_WINDOW];
1086
1087
1088 /*
1089 * Each of the eight short blocks is windowed separately.
1090 * Window shape decisions are made on a frame-by-frame
1091 * basis.
1092 */
1093
1094 pShort_Window_1 = &Short_Window_fxp[wnd_shape_this_bk][0];
1095
1096 pShort_Window_2 =
1097 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
1098
1099
1100
1101
1102 /*
1103 * For short windows from 7 to 5
1104 * | =========================
1105 * | | 5 6 7
1106 * _--_ _--_ _--_ _--_ | _-|-_ _--_ _--_ _--_
1107 * / \/ \/ \/ \|/ | \/ \/ \/ \
1108 * / /\ /\ /\ /|\ | /\ /\ /\ \
1109 * / / \ / \ / \ / | \ | / \ / \ / \ \
1110 * / / \/ \/ \/ | \|/ \/ \ \ \
1111 * --------------------------------|---[///////////////////////]--------
1112 *
1113 */
1114
1115
1116 shift = exp + 15 - SCALING;
1117
1118
1119 for (i = SHORT_WINDOW; i != 0; i--)
1120 {
1121 Int16 win1, win2;
1122 Int16 dat1, dat2;
1123
1124 dat2 = *(pFreq_2_Time_data_2++);
1125 win2 = *(pShort_Window_2--);
1126 temp = *pOverlap_and_Add_Buffer_2;
1127 dat1 = *(pFreq_2_Time_data_1++);
1128 win1 = *(pShort_Window_1++);
1129
1130 *(pOverlap_and_Add_Buffer_2++) = temp + (fxp_mul_16_by_16(dat2, win2) >> shift);
1131
1132 *(pOverlap_and_Add_Buffer_1++) = fxp_mul_16_by_16(dat1, win1) >> shift;
1133
1134 }
1135
1136 } /* if (exp < 16) */
1137 else
1138 {
1139 pv_memset(
1140 pOverlap_and_Add_Buffer_1,
1141 0,
1142 SHORT_WINDOW*sizeof(*pOverlap_and_Add_Buffer_1));
1143 }
1144
1145
1146 }/* for ( wnd=NUM_SHORT_WINDOWS-1; wnd>=NUM_SHORT_WINDOWS/2; wnd--) */
1147
1148
1149 wnd = NUM_SHORT_WINDOWS / 2;
1150
1151 pFreqInfo = (Int16 *) & pFrequency_data[ wnd*SHORT_WINDOW];
1152
1153 /*
1154 * scratch memory is allocated in an unused part of memory
1155 */
1156
1157
1158 pScrath_mem = &pFrequency_data[ 2*LONG_WINDOW - HALF_SHORT_WINDOW];
1159
1160 pOverlap_and_Add_Buffer_1 = &pFrequency_data[ LONG_WINDOW];
1161
1162 pOverlap_and_Add_Buffer_2 = pOverlap_and_Add_Buffer_1
1163 + HALF_SHORT_WINDOW;
1164
1165
1166 exp = imdct_fxp(
1167 (Int32 *)pFreqInfo,
1168 freq_2_time_buffer,
1169 SHORT_BLOCK1,
1170 Q_format,
1171 abs_max_per_window[wnd]);
1172
1173 /*
1174 * If all element are zero or if the exponent is bigger than
1175 * 16 ( it becomes an undefined shift) -> skip
1176 */
1177
1178
1179 if (exp < 16)
1180 {
1181
1182 pFreq_2_Time_data_1 = &pFreqInfo[0];
1183 pFreq_2_Time_data_2 = &pFreqInfo[SHORT_WINDOW];
1184
1185 pShort_Window_1 = &Short_Window_fxp[wnd_shape_this_bk][0];
1186
1187 pShort_Window_2 =
1188 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
1189
1190
1191 /*
1192 * For short window 4
1193 * ====|===========
1194 * | 4
1195 * | | | |
1196 * _--_ _--_ _--_ _-|-_ | _-|-_ _-|-_ _--_ _--_
1197 * / \/ \/ \/ | \|/ | \/ | \/ \/ \
1198 * / /\ /\ /\ | /|\ | /\ | /\ /\ \
1199 * / / \ / \ / \ | / | \ | / \ | / \ / \ \
1200 * / / \/ \/ \|/ | \|/ \|/ \/ \ \
1201 * ------------------------------[\\\|\\\|//////]-------------------
1202 * | | A | B | C |
1203 * |
1204 * W_L_STOP_1
1205 */
1206
1207 shift = exp + 15 - SCALING;
1208 {
1209 Int16 win1;
1210 Int16 dat1;
1211 /* -------- segment A ---------------*/
1212 dat1 = *(pFreq_2_Time_data_1++);
1213 win1 = *(pShort_Window_1++);
1214 for (i = HALF_SHORT_WINDOW; i != 0; i--)
1215 {
1216 *(pScrath_mem++) = fxp_mul_16_by_16(dat1, win1) >> (shift);
1217 dat1 = *(pFreq_2_Time_data_1++);
1218 win1 = *(pShort_Window_1++);
1219 }
1220
1221 /* -------- segment B ---------------*/
1222 for (i = HALF_SHORT_WINDOW; i != 0; i--)
1223 {
1224 *(pOverlap_and_Add_Buffer_1++) = fxp_mul_16_by_16(dat1, win1) >> shift;
1225
1226 dat1 = *(pFreq_2_Time_data_1++);
1227 win1 = *(pShort_Window_1++);
1228 }
1229
1230 /* -------- segment C ---------------*/
1231 temp = *pOverlap_and_Add_Buffer_2;
1232 dat1 = *(pFreq_2_Time_data_2++);
1233 win1 = *(pShort_Window_2--);
1234
1235 for (i = SHORT_WINDOW; i != 0; i--)
1236 {
1237 *(pOverlap_and_Add_Buffer_2++) = temp + (fxp_mul_16_by_16(dat1, win1) >> shift);
1238
1239 temp = *pOverlap_and_Add_Buffer_2;
1240 dat1 = *(pFreq_2_Time_data_2++);
1241 win1 = *(pShort_Window_2--);
1242 }
1243 }
1244
1245 } /* if (exp < 16) */
1246 else
1247 {
1248 pv_memset(
1249 pScrath_mem,
1250 0,
1251 HALF_SHORT_WINDOW*sizeof(*pScrath_mem));
1252
1253 pv_memset(
1254 pOverlap_and_Add_Buffer_1,
1255 0,
1256 HALF_SHORT_WINDOW*sizeof(*pOverlap_and_Add_Buffer_1));
1257 }
1258
1259
1260 wnd = NUM_SHORT_WINDOWS / 2 - 1;
1261
1262 pFreqInfo = (Int16 *) & pFrequency_data[ wnd*SHORT_WINDOW];
1263
1264 pScrath_mem_entry =
1265 &pFrequency_data[2*LONG_WINDOW - HALF_SHORT_WINDOW - SHORT_WINDOW];
1266 pScrath_mem = pScrath_mem_entry;
1267
1268 pOverlap_and_Add_Buffer_1 = &pFrequency_data[ LONG_WINDOW];
1269
1270 /* point to end of buffer less HALF_SHORT_WINDOW */
1271
1272 pOutput_buffer_2 = &Output_buffer[LONG_WINDOW - HALF_SHORT_WINDOW];
1273 pOutput_buffer = pOutput_buffer_2;
1274
1275 pOverlap_and_Add_Buffer_1x = &Time_data[W_L_STOP_1 + SHORT_WINDOW*(wnd+1)]; /* !!!! */
1276
1277 exp = imdct_fxp(
1278 (Int32 *)pFreqInfo,
1279 freq_2_time_buffer,
1280 SHORT_BLOCK1,
1281 Q_format,
1282 abs_max_per_window[wnd]);
1283
1284 /*
1285 * If all element are zero or if the exponent is bigger than
1286 * 16 ( it becomes an undefined shift) -> skip
1287 */
1288
1289 if (exp < 16)
1290 {
1291
1292 pFreq_2_Time_data_1 = &pFreqInfo[0];
1293 pFreq_2_Time_data_2 = &pFreqInfo[SHORT_WINDOW];
1294
1295
1296 /*
1297 * For short window 3
1298 * ===========|====
1299 * 3 |
1300 * | | | |
1301 * _--_ _--_ _-|-_ _-|-_ | _-|-_ _--_ _--_ _--_
1302 * / \/ \/ | \/ | \|/ | \/ \/ \/ \
1303 * / /\ /\ | /\ | /|\ | /\ /\ /\ \
1304 * / / \ / \ | / \ | / | \ | / \ / \ / \ \
1305 * / / \/ \|/ \|/ | \|/ \/ \ \ \
1306 * -----|------------------[\\\\\\|///|///]--------------------------
1307 * | | A | B | C |
1308 *
1309 * W_L_STOP_1
1310 */
1311
1312
1313 pShort_Window_1 = &Short_Window_fxp[wnd_shape_this_bk][0];
1314
1315 pShort_Window_2 =
1316 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
1317
1318 shift = exp + 15 - SCALING;
1319
1320
1321 Int16 win1;
1322 Int16 dat1;
1323 /* -------- segment A ---------------*/
1324 dat1 = *(pFreq_2_Time_data_1++);
1325 win1 = *(pShort_Window_1++);
1326 for (i = SHORT_WINDOW; i != 0; i--)
1327 {
1328 *(pScrath_mem++) = fxp_mul_16_by_16(dat1, win1) >> shift;
1329 dat1 = *(pFreq_2_Time_data_1++);
1330 win1 = *(pShort_Window_1++);
1331 }
1332
1333 dat1 = *(pFreq_2_Time_data_2++);
1334 win1 = *(pShort_Window_2--);
1335
1336 /* -------- segment B ---------------*/
1337 for (i = HALF_SHORT_WINDOW; i != 0; i--)
1338 {
1339 test = fxp_mul_16_by_16(dat1, win1) >> shift;
1340
1341 temp = *(pScrath_mem++) + test;
1342
1343
1344 test = *(pOverlap_and_Add_Buffer_1x++); /* !!!! */
1345
1346 limiter(*(pOutput_buffer++), (temp + test));
1347
1348 dat1 = *(pFreq_2_Time_data_2++);
1349 win1 = *(pShort_Window_2--);
1350
1351 }
1352
1353 /* -------- segment C ---------------*/
1354 for (i = HALF_SHORT_WINDOW; i != 0; i--)
1355 {
1356 temp = fxp_mul_16_by_16(dat1, win1) >> (shift);
1357
1358 *(pOverlap_and_Add_Buffer_1++) += temp;
1359
1360 dat1 = *(pFreq_2_Time_data_2++);
1361 win1 = *(pShort_Window_2--);
1362 }
1363
1364 } /* if (exp < 16) */
1365 else
1366 {
1367
1368 pv_memset(
1369 pScrath_mem,
1370 0,
1371 SHORT_WINDOW*sizeof(*pScrath_mem));
1372
1373 pScrath_mem += SHORT_WINDOW;
1374
1375 temp = *(pScrath_mem++);
1376 for (i = HALF_SHORT_WINDOW; i != 0; i--)
1377 {
1378 limiter(*(pOutput_buffer++), temp);
1379 temp = *(pScrath_mem++);
1380
1381
1382 }
1383 }
1384
1385
1386 for (wnd = NUM_SHORT_WINDOWS / 2 - 2; wnd >= 0; wnd--)
1387 {
1388
1389
1390 pOutput_buffer_2 -= SHORT_WINDOW;
1391 pOutput_buffer = pOutput_buffer_2;
1392
1393 /*
1394 * The same memory is used as scratch in every iteration
1395 */
1396 pScrath_mem = pScrath_mem_entry;
1397
1398 pOverlap_and_Add_Buffer_2x =
1399 &Time_data[W_L_STOP_1 + SHORT_WINDOW*(wnd+1)];
1400
1401 pFreqInfo = (Int16 *) & pFrequency_data[ wnd*SHORT_WINDOW];
1402
1403
1404
1405 exp = imdct_fxp(
1406 (Int32 *)pFreqInfo,
1407 freq_2_time_buffer,
1408 SHORT_BLOCK1,
1409 Q_format,
1410 abs_max_per_window[wnd]);
1411
1412 /*
1413 * If all element are zero or if the exponent is bigger than
1414 * 16 ( it becomes an undefined shift) -> skip
1415 */
1416
1417 if (exp < 16)
1418 {
1419
1420 pFreq_2_Time_data_1 = &pFreqInfo[0];
1421 pFreq_2_Time_data_2 = &pFreqInfo[SHORT_WINDOW];
1422
1423
1424 /*
1425 * Each of the eight short blocks is windowed separately.
1426 * Window shape decisions are made on a frame-by-frame
1427 * basis.
1428 */
1429
1430 pShort_Window_1 = &Short_Window_fxp[wnd_shape_this_bk][0];
1431
1432 if (wnd == 0)
1433 {
1434 pShort_Window_1 =
1435 &Short_Window_fxp[wnd_shape_prev_bk][0];
1436 }
1437
1438 pShort_Window_2 =
1439 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
1440
1441
1442 /*
1443 * For short windows from 2 to 0
1444 *
1445 * =========================
1446 * |
1447 * 0 1 2 | |
1448 * _--_ _--_ _--_ _-|-_ | _--_ _--_ _--_ _--_
1449 * / \/ \/ \/ | \|/ \/ \/ \/ \
1450 * / /\ /\ /\ | /|\ /\ /\ /\ \
1451 * / / \ / \ / \ | / | \ / \ / \ / \ \
1452 * / / \/ \/ \|/ | \/ \/ \ \ \
1453 * ----[\\\\\\\\\\\\\\\\\\\\\\\\]---|-----------------------------
1454 * |
1455 *
1456 * W_L_STOP_1
1457 */
1458
1459 shift = exp + 15 - SCALING;
1460
1461 Int16 dat1 = *(pFreq_2_Time_data_2++);
1462 Int16 win1 = *(pShort_Window_2--);
1463
1464 temp = *(pScrath_mem);
1465 for (i = SHORT_WINDOW; i != 0; i--)
1466 {
1467 test = fxp_mul_16_by_16(dat1, win1) >> shift;
1468
1469 temp += test;
1470
1471 dat1 = *(pFreq_2_Time_data_1++);
1472 win1 = *(pShort_Window_1++);
1473
1474 limiter(*(pOutput_buffer++), (temp + *(pOverlap_and_Add_Buffer_2x++)));
1475
1476
1477 *(pScrath_mem++) = fxp_mul_16_by_16(dat1, win1) >> shift;
1478 dat1 = *(pFreq_2_Time_data_2++);
1479 win1 = *(pShort_Window_2--);
1480 temp = *(pScrath_mem);
1481
1482 }
1483
1484 } /* if (exp < 16) */
1485 else
1486 {
1487 test = *(pScrath_mem);
1488 temp = *(pOverlap_and_Add_Buffer_2x++);
1489
1490 for (i = SHORT_WINDOW; i != 0; i--)
1491 {
1492 limiter(*(pOutput_buffer++), (temp + test));
1493
1494 *(pScrath_mem++) = 0;
1495 test = *(pScrath_mem);
1496 temp = *(pOverlap_and_Add_Buffer_2x++);
1497
1498 }
1499 }
1500
1501 } /* for ( wnd=NUM_SHORT_WINDOWS/2-1; wnd>=0; wnd--) */
1502
1503 pOverlap_and_Add_Buffer_2x = &Time_data[W_L_STOP_1];
1504
1505 pScrath_mem = pScrath_mem_entry;
1506
1507 pOutput_buffer_2 -= SHORT_WINDOW;
1508 pOutput_buffer = pOutput_buffer_2;
1509
1510 test = *(pScrath_mem++);
1511 temp = *(pOverlap_and_Add_Buffer_2x++);
1512
1513 for (i = SHORT_WINDOW; i != 0; i--)
1514 {
1515 limiter(*(pOutput_buffer++), (temp + test));
1516
1517 test = *(pScrath_mem++);
1518 temp = *(pOverlap_and_Add_Buffer_2x++);
1519
1520 }
1521
1522 pOverlap_and_Add_Buffer_1x = Time_data;
1523
1524 pOutput_buffer = Output_buffer;
1525
1526
1527 temp = *(pOverlap_and_Add_Buffer_1x++);
1528
1529 for (i = W_L_STOP_1; i != 0; i--)
1530 {
1531 limiter(*(pOutput_buffer++), temp);
1532
1533 temp = *(pOverlap_and_Add_Buffer_1x++);
1534 }
1535
1536 pOverlap_and_Add_Buffer_1x = &Time_data[0];
1537
1538 pOverlap_and_Add_Buffer_2 = &pFrequency_data[LONG_WINDOW];
1539
1540 /*
1541 * update overlap and add buffer,
1542 * so is ready for next iteration
1543 */
1544
1545 for (int i = 0; i < W_L_STOP_2; i++)
1546 {
1547 temp = *(pOverlap_and_Add_Buffer_2++);
1548 *(pOverlap_and_Add_Buffer_1x++) = temp;
1549 }
1550
1551 pv_memset(
1552 pOverlap_and_Add_Buffer_1x,
1553 0,
1554 W_L_STOP_1*sizeof(*pOverlap_and_Add_Buffer_1x));
1555
1556 } /* if ( wnd_seq != EIGHT_SHORT_SEQUENCE) */
1557
1558 }
1559
1560 #endif
1561 /*----------------------------------------------------------------------------
1562 ; FUNCTION CODE
1563 ----------------------------------------------------------------------------*/
1564
1565
1566
trans4m_freq_2_time_fxp_2(Int32 Frequency_data[],Int32 Time_data[],WINDOW_SEQUENCE wnd_seq,Int wnd_shape_prev_bk,Int wnd_shape_this_bk,Int Q_format,Int32 abs_max_per_window[],Int32 freq_2_time_buffer[],Int16 * Interleaved_output)1567 void trans4m_freq_2_time_fxp_2(
1568 Int32 Frequency_data[],
1569 Int32 Time_data[],
1570 WINDOW_SEQUENCE wnd_seq,
1571 Int wnd_shape_prev_bk,
1572 Int wnd_shape_this_bk,
1573 Int Q_format,
1574 Int32 abs_max_per_window[],
1575 Int32 freq_2_time_buffer[],
1576 Int16 *Interleaved_output)
1577
1578 {
1579
1580 Int exp;
1581 Int shift;
1582
1583 Int i;
1584 Int wnd;
1585 #if !(defined( PV_ARM_GCC_V5)||(PV_ARM_V5))
1586 Int32 z;
1587 #endif
1588 Int16 *pFreqInfo;
1589 Int32 temp;
1590 Int32 test;
1591
1592 Int16 *pFreq_2_Time_data_1;
1593 Int16 *pFreq_2_Time_data_2;
1594
1595 const Int16 *pLong_Window_1;
1596 const Int16 *pLong_Window_2;
1597 const Int16 *pShort_Window_1;
1598 const Int16 *pShort_Window_2;
1599
1600 Int32 *pOverlap_and_Add_Buffer_1;
1601 Int32 *pOverlap_and_Add_Buffer_2;
1602
1603 Int16 *pInterleaved_output;
1604 Int16 *pInterleaved_output_2;
1605
1606
1607 const Int16 * Long_Window_fxp[NUM_WINDOW_SHAPES];
1608 const Int16 * Short_Window_fxp[NUM_WINDOW_SHAPES];
1609
1610 Long_Window_fxp[0] = Long_Window_sine_fxp;
1611 Long_Window_fxp[1] = Long_Window_KBD_fxp;
1612 Short_Window_fxp[0] = Short_Window_sine_fxp;
1613 Short_Window_fxp[1] = Short_Window_KBD_fxp;
1614
1615 if (wnd_seq != EIGHT_SHORT_SEQUENCE)
1616 {
1617
1618 pFreqInfo = (Int16 *)Frequency_data;
1619
1620
1621 exp = imdct_fxp(
1622 (Int32 *)pFreqInfo,
1623 freq_2_time_buffer,
1624 LONG_BLOCK1,
1625 Q_format,
1626 abs_max_per_window[0]);
1627
1628
1629 /*
1630 * The C Programming Language, Second Edition, Kernighan & Ritchie,
1631 * page 206.
1632 * "The result [of a shift] is undefined if the right operand is
1633 * negative, or greater than or equal to the number of bits in the
1634 * left expression's type"
1635 * => avoid shift by 32 or 16
1636 */
1637
1638 if (exp < 16)
1639 {
1640
1641 pFreq_2_Time_data_1 = pFreqInfo;
1642
1643
1644 switch (wnd_seq)
1645 {
1646
1647 case ONLY_LONG_SEQUENCE:
1648 default:
1649
1650 {
1651 pOverlap_and_Add_Buffer_1 = Time_data;
1652
1653 pInterleaved_output = Interleaved_output;
1654
1655 {
1656
1657 const Int16 *pLong_Window_2 = &Long_Window_fxp[wnd_shape_this_bk][LONG_WINDOW_m_1];
1658
1659 Int32 * pFreq2T = (Int32 *)pFreqInfo;
1660 Int32 * pFreq2T_2 = &pFreq2T[HALF_LONG_WINDOW];
1661 Int32 * win = (Int32 *) & Long_Window_fxp[wnd_shape_prev_bk][0];
1662
1663 Int shift = exp + 15 - SCALING;
1664
1665 for (i = HALF_LONG_WINDOW; i != 0; i--)
1666 {
1667 Int16 win1, win2;
1668 Int32 temp2, test2;
1669
1670 Int32 winx;
1671
1672 temp2 = *(pFreq2T++);
1673 winx = *(win++);
1674
1675 test = *(pOverlap_and_Add_Buffer_1++);
1676 test2 = *(pOverlap_and_Add_Buffer_1--);
1677 temp = fxp_mul_16_by_16bb(temp2, winx) >> shift;
1678 temp2 = fxp_mul_16_by_16tt(temp2, winx) >> shift;
1679
1680 limiter(*(pInterleaved_output), (temp + test));
1681
1682 limiter(*(pInterleaved_output + 2), (temp2 + test2));
1683 pInterleaved_output += 4;
1684
1685 temp2 = *(pFreq2T_2++);
1686
1687 win1 = *(pLong_Window_2--);
1688 win2 = *(pLong_Window_2--);
1689 temp = fxp_mul_16_by_16bb(temp2, win1) >> shift;
1690 test2 = fxp_mul_16_by_16tb(temp2, win2) >> shift;
1691
1692 *(pOverlap_and_Add_Buffer_1++) = temp;
1693 *(pOverlap_and_Add_Buffer_1++) = test2;
1694 }
1695
1696 }
1697
1698 }
1699
1700 break;
1701
1702 case LONG_START_SEQUENCE:
1703
1704 pFreq_2_Time_data_2 =
1705 &pFreq_2_Time_data_1[ HALF_LONG_WINDOW];
1706
1707 pLong_Window_1 = &Long_Window_fxp[wnd_shape_prev_bk][0];
1708 pLong_Window_2 = &pLong_Window_1[ HALF_LONG_WINDOW];
1709
1710 pOverlap_and_Add_Buffer_1 = &Time_data[0];
1711 pOverlap_and_Add_Buffer_2 = &Time_data[HALF_LONG_WINDOW];
1712
1713
1714 pInterleaved_output = Interleaved_output;
1715 pInterleaved_output_2 = pInterleaved_output + (2 * HALF_LONG_WINDOW);
1716
1717
1718 /*
1719 * process first LONG_WINDOW elements
1720 */
1721
1722 shift = exp + 15 - SCALING;
1723
1724 for (i = HALF_LONG_WINDOW; i != 0; i--)
1725 {
1726 Int16 win1, win2;
1727 Int16 dat1, dat2;
1728 Int32 test1, test2;
1729
1730 dat1 = *(pFreq_2_Time_data_1++);
1731 win1 = *(pLong_Window_1++);
1732 test1 = *(pOverlap_and_Add_Buffer_1++);
1733
1734 dat2 = *(pFreq_2_Time_data_2++);
1735 win2 = *(pLong_Window_2++);
1736 test2 = *(pOverlap_and_Add_Buffer_2++);
1737
1738 limiter(*(pInterleaved_output), (test1 + (fxp_mul_16_by_16(dat1, win1) >> shift)));
1739
1740 pInterleaved_output += 2;
1741
1742 limiter(*(pInterleaved_output_2), (test2 + (fxp_mul_16_by_16(dat2, win2) >> shift)));
1743
1744 pInterleaved_output_2 += 2;
1745 }
1746
1747
1748 /*
1749 * data unchanged from LONG_WINDOW to W_L_START_1
1750 * only scaled accordingly
1751 */
1752
1753 pOverlap_and_Add_Buffer_1 = &Time_data[0];
1754 pFreq_2_Time_data_1 = &pFreqInfo[LONG_WINDOW];
1755
1756 exp -= SCALING;
1757
1758 if (exp >= 0)
1759 {
1760
1761 for (i = (W_L_START_1 - LONG_WINDOW) >> 1; i != 0; i--)
1762 {
1763 *(pOverlap_and_Add_Buffer_1++) =
1764 *(pFreq_2_Time_data_1++) >> exp;
1765 *(pOverlap_and_Add_Buffer_1++) =
1766 *(pFreq_2_Time_data_1++) >> exp;
1767
1768 }
1769
1770 }
1771 else if (exp < 0)
1772 {
1773
1774 Int shift = -exp;
1775 for (i = (W_L_START_1 - LONG_WINDOW) >> 1; i != 0 ; i--)
1776 {
1777 Int32 temp2 = ((Int32) * (pFreq_2_Time_data_1++)) << shift;
1778 *(pOverlap_and_Add_Buffer_1++) = temp2;
1779 temp2 = ((Int32) * (pFreq_2_Time_data_1++)) << shift;
1780 *(pOverlap_and_Add_Buffer_1++) = temp2;
1781 }
1782
1783 }
1784 else
1785 {
1786
1787 for (i = (W_L_START_1 - LONG_WINDOW) >> 1; i != 0; i--)
1788 {
1789 *(pOverlap_and_Add_Buffer_1++) =
1790 *(pFreq_2_Time_data_1++);
1791 *(pOverlap_and_Add_Buffer_1++) =
1792 *(pFreq_2_Time_data_1++);
1793
1794 }
1795
1796 }
1797
1798
1799 pFreq_2_Time_data_1 = &pFreqInfo[W_L_START_1];
1800 pFreq_2_Time_data_2 =
1801 &pFreq_2_Time_data_1[HALF_SHORT_WINDOW];
1802
1803 pShort_Window_1 =
1804 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
1805
1806 pShort_Window_2 = pShort_Window_1 - HALF_SHORT_WINDOW;
1807
1808 pOverlap_and_Add_Buffer_2 = pOverlap_and_Add_Buffer_1 +
1809 HALF_SHORT_WINDOW;
1810
1811 {
1812 Int16 win1, win2;
1813 Int16 dat1, dat2;
1814 Int32 temp2;
1815
1816 for (i = HALF_SHORT_WINDOW; i != 0; i--)
1817 {
1818
1819 dat1 = (*pFreq_2_Time_data_1++);
1820 dat2 = (*pFreq_2_Time_data_2++);
1821 win1 = *(pShort_Window_1--);
1822 win2 = *(pShort_Window_2--);
1823
1824 temp = fxp_mul_16_by_16(dat1, win1) >> shift;
1825 *(pOverlap_and_Add_Buffer_1++) = temp;
1826
1827 temp2 = fxp_mul_16_by_16(dat2, win2) >> shift;
1828 *(pOverlap_and_Add_Buffer_2++) = temp2;
1829
1830 }
1831 }
1832
1833 pOverlap_and_Add_Buffer_1 += HALF_SHORT_WINDOW;
1834
1835
1836 pv_memset(
1837 pOverlap_and_Add_Buffer_1,
1838 0,
1839 (LONG_BLOCK1 - W_L_START_2)
1840 *sizeof(*pOverlap_and_Add_Buffer_1));
1841
1842
1843 break;
1844
1845
1846 case LONG_STOP_SEQUENCE:
1847
1848 pOverlap_and_Add_Buffer_1 = &Time_data[ W_L_STOP_2];
1849
1850 pInterleaved_output = &Interleaved_output[2*W_L_STOP_2];
1851
1852 pFreq_2_Time_data_1 = &pFreqInfo[W_L_STOP_2];
1853
1854 exp -= SCALING;
1855
1856
1857 if (exp > 0)
1858 {
1859 Int16 tmp1 = (*(pFreq_2_Time_data_1++) >> exp);
1860 temp = *(pOverlap_and_Add_Buffer_1++);
1861
1862 for (i = (LONG_WINDOW - W_L_STOP_2); i != 0; i--)
1863 {
1864 limiter(*(pInterleaved_output), (temp + tmp1));
1865
1866 pInterleaved_output += 2;
1867 tmp1 = *(pFreq_2_Time_data_1++) >> exp;
1868 temp = *(pOverlap_and_Add_Buffer_1++);
1869 }
1870 }
1871 else if (exp < 0)
1872 {
1873 shift = -exp;
1874
1875 Int32 temp1 = ((Int32) * (pFreq_2_Time_data_1++)) << shift;
1876 temp = *(pOverlap_and_Add_Buffer_1++);
1877
1878 for (i = (LONG_WINDOW - W_L_STOP_2); i != 0; i--)
1879 {
1880 limiter(*(pInterleaved_output), (temp + temp1));
1881
1882 pInterleaved_output += 2;
1883 temp1 = ((Int32) * (pFreq_2_Time_data_1++)) << shift;
1884 temp = *(pOverlap_and_Add_Buffer_1++);
1885 }
1886 }
1887 else
1888 {
1889 Int16 tmp1 = *(pFreq_2_Time_data_1++);
1890 temp = *(pOverlap_and_Add_Buffer_1++);
1891 for (i = (LONG_WINDOW - W_L_STOP_2); i != 0; i--)
1892 {
1893 limiter(*(pInterleaved_output), (temp + tmp1));
1894
1895 pInterleaved_output += 2;
1896 tmp1 = *(pFreq_2_Time_data_1++);
1897 temp = *(pOverlap_and_Add_Buffer_1++);
1898 }
1899 }
1900
1901
1902
1903 pShort_Window_1 = &Short_Window_fxp[wnd_shape_prev_bk][0];
1904 pShort_Window_2 = &pShort_Window_1[HALF_SHORT_WINDOW];
1905
1906 pFreq_2_Time_data_1 = &pFreqInfo[W_L_STOP_1];
1907 pFreq_2_Time_data_2 =
1908 &pFreq_2_Time_data_1[HALF_SHORT_WINDOW];
1909
1910 pOverlap_and_Add_Buffer_1 = &Time_data[ W_L_STOP_1];
1911 pOverlap_and_Add_Buffer_2 = pOverlap_and_Add_Buffer_1
1912 + HALF_SHORT_WINDOW;
1913
1914
1915 pInterleaved_output = &Interleaved_output[2*W_L_STOP_1];
1916 pInterleaved_output_2 = pInterleaved_output + (2 * HALF_SHORT_WINDOW);
1917
1918 exp += SCALING; /* +8 back to what it was */
1919 shift = exp + 15 - SCALING;
1920
1921
1922 for (i = HALF_SHORT_WINDOW; i != 0; i--)
1923 {
1924
1925 Int16 win1;
1926 Int16 dat1;
1927
1928 dat1 = *(pFreq_2_Time_data_1++);
1929 win1 = *(pShort_Window_1++);
1930 temp = *(pOverlap_and_Add_Buffer_1++);
1931
1932 test = fxp_mul_16_by_16(dat1, win1);
1933
1934 limiter(*(pInterleaved_output), (temp + (test >> shift)));
1935
1936 pInterleaved_output += 2;
1937
1938 dat1 = *(pFreq_2_Time_data_2++);
1939 win1 = *(pShort_Window_2++);
1940 temp = *(pOverlap_and_Add_Buffer_2++);
1941 test = fxp_mul_16_by_16(dat1, win1);
1942
1943 limiter(*(pInterleaved_output_2), (temp + (test >> shift)));
1944
1945 pInterleaved_output_2 += 2;
1946
1947 }
1948
1949
1950
1951 pFreq_2_Time_data_2 = &pFreqInfo[LONG_WINDOW];
1952
1953 pOverlap_and_Add_Buffer_1 = Time_data;
1954
1955
1956 pInterleaved_output = Interleaved_output;
1957
1958 pLong_Window_2 =
1959 &Long_Window_fxp[wnd_shape_this_bk][LONG_WINDOW_m_1];
1960
1961
1962 /*
1963 * Copy previous time in current buffer, also copy overlap
1964 * and add buffer
1965 */
1966
1967 for (i = W_L_STOP_1; i != 0; i--)
1968 {
1969
1970 Int16 win1;
1971 Int16 dat1;
1972
1973 win1 = *(pLong_Window_2--);
1974 dat1 = *pFreq_2_Time_data_2++;
1975
1976 limiter(*(pInterleaved_output), *(pOverlap_and_Add_Buffer_1));
1977
1978 pInterleaved_output += 2;
1979
1980 temp = fxp_mul_16_by_16(dat1, win1) >> shift;
1981 *(pOverlap_and_Add_Buffer_1++) = temp ;
1982
1983 }
1984
1985 for (i = (LONG_WINDOW - W_L_STOP_1); i != 0; i--)
1986 {
1987
1988 temp = fxp_mul_16_by_16(*pFreq_2_Time_data_2++, *(pLong_Window_2--)) >> shift;
1989 *(pOverlap_and_Add_Buffer_1++) = temp ;
1990
1991 }
1992
1993 break;
1994
1995
1996
1997 } /* switch (wnd_seq) */
1998
1999 } /* if (exp < 16) */
2000
2001 else
2002 {
2003 /* all zeros buffer or excessive down shift */
2004
2005 /* Overlap and add, setup buffer for next iteration */
2006 pOverlap_and_Add_Buffer_1 = &Time_data[0];
2007
2008 pInterleaved_output = Interleaved_output;
2009
2010
2011 temp = (*pOverlap_and_Add_Buffer_1++);
2012 for (i = LONG_WINDOW; i != 0; i--)
2013 {
2014
2015 limiter(*(pInterleaved_output), temp);
2016
2017 pInterleaved_output += 2;
2018 temp = (*pOverlap_and_Add_Buffer_1++);
2019 }
2020 pv_memset(Time_data, 0, LONG_WINDOW*sizeof(Time_data[0]));
2021 }
2022
2023 }
2024 else
2025 {
2026
2027 Int32 *pScrath_mem;
2028 Int32 *pScrath_mem_entry;
2029 Int32 *pFrequency_data = Frequency_data;
2030
2031 Int32 * pOverlap_and_Add_Buffer_1;
2032 Int32 * pOverlap_and_Add_Buffer_2;
2033 Int32 * pOverlap_and_Add_Buffer_1x;
2034 Int32 * pOverlap_and_Add_Buffer_2x;
2035
2036
2037 /*
2038 * Frequency_data is 2*LONG_WINDOW length but only
2039 * the first LONG_WINDOW elements are filled in,
2040 * then the second part can be used as scratch mem,
2041 * then grab data from one window at a time in
2042 * reverse order.
2043 * The upper LONG_WINDOW Int32 are used to hold the
2044 * computed overlap and add, used in the next call to
2045 * this function, and also as sctrach memory
2046 */
2047
2048 /*
2049 * Frequency_data usage for the case EIGHT_SHORT_SEQUENCE
2050
2051 |<----- Input Freq. data ----->|< Overlap & Add ->| Unused |-Scratch-|
2052 | | Store for next | | memory |
2053 | | call | | |
2054 | | | | |
2055 |//////////////////////////////|\\\\\\\\\\\\\\\\\\|--------|+++++++++|
2056 | | | | |
2057 0 LONG_WINDOW LONG_WINDOW | 2*LONG_WINDOW
2058 + | |
2059 W_L_STOP_2 | |
2060 |<-- -->|
2061 SHORT_WINDOW +
2062 HALF_SHORT_WINDOW
2063 *
2064 */
2065
2066 pOverlap_and_Add_Buffer_1 = &pFrequency_data[
2067 LONG_WINDOW + 3*SHORT_WINDOW + HALF_SHORT_WINDOW];
2068
2069 /*
2070 * Initialize to zero, only the firt short window used in overlap
2071 * and add
2072 */
2073 pv_memset(
2074 pOverlap_and_Add_Buffer_1,
2075 0,
2076 SHORT_WINDOW*sizeof(*pOverlap_and_Add_Buffer_1));
2077
2078 /*
2079 * Showt windows are evaluated in decresing order. Windows from 7
2080 * to 0 are break down in four cases: window numbers 7 to 5, 4, 3,
2081 * and 2 to 0.
2082 * The data from short windows 3 and 4 is situated at the boundary
2083 * between the 'overlap and add' buffer and the output buffer.
2084 */
2085 for (wnd = NUM_SHORT_WINDOWS - 1; wnd >= NUM_SHORT_WINDOWS / 2 + 1; wnd--)
2086 {
2087
2088 pFreqInfo = (Int16 *) & pFrequency_data[ wnd*SHORT_WINDOW];
2089
2090 exp = imdct_fxp(
2091 (Int32 *)pFreqInfo,
2092 freq_2_time_buffer,
2093 SHORT_BLOCK1,
2094 Q_format,
2095 abs_max_per_window[wnd]);
2096
2097 /* W_L_STOP_1 == (LONG_WINDOW - SHORT_WINDOW)>>1 */
2098 pOverlap_and_Add_Buffer_1 =
2099 &pFrequency_data[ W_L_STOP_1 + SHORT_WINDOW*wnd];
2100
2101
2102 pOverlap_and_Add_Buffer_2 =
2103 pOverlap_and_Add_Buffer_1 + SHORT_WINDOW;
2104
2105 /*
2106 * If all element are zero or if the exponent is bigger than
2107 * 16 ( it becomes an undefined shift) -> skip
2108 */
2109
2110 if (exp < 16)
2111 {
2112
2113
2114 pFreq_2_Time_data_1 = &pFreqInfo[0];
2115 pFreq_2_Time_data_2 = &pFreqInfo[SHORT_WINDOW];
2116
2117
2118 /*
2119 * Each of the eight short blocks is windowed separately.
2120 * Window shape decisions are made on a frame-by-frame
2121 * basis.
2122 */
2123
2124 pShort_Window_1 = &Short_Window_fxp[wnd_shape_this_bk][0];
2125
2126 pShort_Window_2 =
2127 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
2128
2129
2130
2131
2132 /*
2133 * For short windows from 7 to 5
2134 * | =========================
2135 * | | 5 6 7
2136 * _--_ _--_ _--_ _--_ | _-|-_ _--_ _--_ _--_
2137 * / \/ \/ \/ \|/ | \/ \/ \/ \
2138 * / /\ /\ /\ /|\ | /\ /\ /\ \
2139 * / / \ / \ / \ / | \ | / \ / \ / \ \
2140 * / / \/ \/ \/ | \|/ \/ \ \ \
2141 * --------------------------------|---[///////////////////////]--------
2142 *
2143 */
2144
2145
2146 shift = exp + 15 - SCALING;
2147
2148
2149 for (i = SHORT_WINDOW; i != 0; i--)
2150 {
2151 Int16 win1, win2;
2152 Int16 dat1, dat2;
2153
2154 dat2 = *(pFreq_2_Time_data_2++);
2155 win2 = *(pShort_Window_2--);
2156 temp = *pOverlap_and_Add_Buffer_2;
2157 dat1 = *(pFreq_2_Time_data_1++);
2158 win1 = *(pShort_Window_1++);
2159
2160 *(pOverlap_and_Add_Buffer_2++) = temp + (fxp_mul_16_by_16(dat2, win2) >> shift);
2161
2162 *(pOverlap_and_Add_Buffer_1++) = fxp_mul_16_by_16(dat1, win1) >> shift;
2163
2164 }
2165
2166 } /* if (exp < 16) */
2167 else
2168 {
2169 pv_memset(
2170 pOverlap_and_Add_Buffer_1,
2171 0,
2172 SHORT_WINDOW*sizeof(*pOverlap_and_Add_Buffer_1));
2173 }
2174
2175
2176 }/* for ( wnd=NUM_SHORT_WINDOWS-1; wnd>=NUM_SHORT_WINDOWS/2; wnd--) */
2177
2178
2179 wnd = NUM_SHORT_WINDOWS / 2;
2180
2181 pFreqInfo = (Int16 *) & pFrequency_data[ wnd*SHORT_WINDOW];
2182
2183 /*
2184 * scratch memory is allocated in an unused part of memory
2185 */
2186
2187
2188 pScrath_mem = &pFrequency_data[ 2*LONG_WINDOW - HALF_SHORT_WINDOW];
2189
2190 pOverlap_and_Add_Buffer_1 = &pFrequency_data[ LONG_WINDOW];
2191
2192 pOverlap_and_Add_Buffer_2 = pOverlap_and_Add_Buffer_1
2193 + HALF_SHORT_WINDOW;
2194
2195
2196 exp = imdct_fxp(
2197 (Int32 *)pFreqInfo,
2198 freq_2_time_buffer,
2199 SHORT_BLOCK1,
2200 Q_format,
2201 abs_max_per_window[wnd]);
2202
2203 /*
2204 * If all element are zero or if the exponent is bigger than
2205 * 16 ( it becomes an undefined shift) -> skip
2206 */
2207
2208
2209 if (exp < 16)
2210 {
2211
2212 pFreq_2_Time_data_1 = &pFreqInfo[0];
2213 pFreq_2_Time_data_2 = &pFreqInfo[SHORT_WINDOW];
2214
2215 pShort_Window_1 = &Short_Window_fxp[wnd_shape_this_bk][0];
2216
2217 pShort_Window_2 =
2218 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
2219
2220
2221 /*
2222 * For short window 4
2223 * ====|===========
2224 * | 4
2225 * | | | |
2226 * _--_ _--_ _--_ _-|-_ | _-|-_ _-|-_ _--_ _--_
2227 * / \/ \/ \/ | \|/ | \/ | \/ \/ \
2228 * / /\ /\ /\ | /|\ | /\ | /\ /\ \
2229 * / / \ / \ / \ | / | \ | / \ | / \ / \ \
2230 * / / \/ \/ \|/ | \|/ \|/ \/ \ \
2231 * ------------------------------[\\\|\\\|//////]-------------------
2232 * | | A | B | C |
2233 * |
2234 * W_L_STOP_1
2235 */
2236
2237 shift = exp + 15 - SCALING;
2238 {
2239 Int16 win1;
2240 Int16 dat1;
2241 /* -------- segment A ---------------*/
2242 dat1 = *(pFreq_2_Time_data_1++);
2243 win1 = *(pShort_Window_1++);
2244 for (i = HALF_SHORT_WINDOW; i != 0; i--)
2245 {
2246 *(pScrath_mem++) = fxp_mul_16_by_16(dat1, win1) >> shift;
2247 dat1 = *(pFreq_2_Time_data_1++);
2248 win1 = *(pShort_Window_1++);
2249 }
2250
2251 /* -------- segment B ---------------*/
2252 for (i = HALF_SHORT_WINDOW; i != 0; i--)
2253 {
2254 *(pOverlap_and_Add_Buffer_1++) = fxp_mul_16_by_16(dat1, win1) >> shift;
2255
2256 dat1 = *(pFreq_2_Time_data_1++);
2257 win1 = *(pShort_Window_1++);
2258 }
2259
2260 /* -------- segment C ---------------*/
2261 temp = *pOverlap_and_Add_Buffer_2;
2262 dat1 = *(pFreq_2_Time_data_2++);
2263 win1 = *(pShort_Window_2--);
2264
2265 for (i = SHORT_WINDOW; i != 0; i--)
2266 {
2267 *(pOverlap_and_Add_Buffer_2++) = temp + (fxp_mul_16_by_16(dat1, win1) >> shift);
2268
2269 temp = *pOverlap_and_Add_Buffer_2;
2270 dat1 = *(pFreq_2_Time_data_2++);
2271 win1 = *(pShort_Window_2--);
2272 }
2273 }
2274
2275 } /* if (exp < 16) */
2276 else
2277 {
2278 pv_memset(
2279 pScrath_mem,
2280 0,
2281 HALF_SHORT_WINDOW*sizeof(*pScrath_mem));
2282
2283 pv_memset(
2284 pOverlap_and_Add_Buffer_1,
2285 0,
2286 HALF_SHORT_WINDOW*sizeof(*pOverlap_and_Add_Buffer_1));
2287 }
2288
2289
2290 wnd = NUM_SHORT_WINDOWS / 2 - 1;
2291
2292 pFreqInfo = (Int16 *) & pFrequency_data[ wnd*SHORT_WINDOW];
2293
2294 pScrath_mem_entry =
2295 &pFrequency_data[2*LONG_WINDOW - HALF_SHORT_WINDOW - SHORT_WINDOW];
2296
2297
2298 pScrath_mem = pScrath_mem_entry;
2299
2300 pOverlap_and_Add_Buffer_1 = &pFrequency_data[ LONG_WINDOW];
2301
2302 /* point to end of buffer less HALF_SHORT_WINDOW */
2303
2304 pInterleaved_output_2 = &Interleaved_output[2*(LONG_WINDOW - HALF_SHORT_WINDOW)];
2305 pInterleaved_output = pInterleaved_output_2;
2306
2307 pOverlap_and_Add_Buffer_1x = &Time_data[W_L_STOP_1 + SHORT_WINDOW*(wnd+1)];
2308
2309
2310 exp = imdct_fxp(
2311 (Int32 *)pFreqInfo,
2312 freq_2_time_buffer,
2313 SHORT_BLOCK1,
2314 Q_format,
2315 abs_max_per_window[wnd]);
2316
2317 /*
2318 * If all element are zero or if the exponent is bigger than
2319 * 16 ( it becomes an undefined shift) -> skip
2320 */
2321
2322 if (exp < 16)
2323 {
2324
2325 pFreq_2_Time_data_1 = &pFreqInfo[0];
2326 pFreq_2_Time_data_2 = &pFreqInfo[SHORT_WINDOW];
2327
2328
2329 /*
2330 * For short window 3
2331 * ===========|====
2332 * 3 |
2333 * | | | |
2334 * _--_ _--_ _-|-_ _-|-_ | _-|-_ _--_ _--_ _--_
2335 * / \/ \/ | \/ | \|/ | \/ \/ \/ \
2336 * / /\ /\ | /\ | /|\ | /\ /\ /\ \
2337 * / / \ / \ | / \ | / | \ | / \ / \ / \ \
2338 * / / \/ \|/ \|/ | \|/ \/ \ \ \
2339 * -----|------------------[\\\\\\|///|///]--------------------------
2340 * | | A | B | C |
2341 *
2342 * W_L_STOP_1
2343 */
2344
2345
2346 pShort_Window_1 = &Short_Window_fxp[wnd_shape_this_bk][0];
2347
2348 pShort_Window_2 =
2349 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
2350
2351 shift = exp + 15 - SCALING;
2352
2353 Int16 win1;
2354 Int16 dat1;
2355 /* -------- segment A ---------------*/
2356 dat1 = *(pFreq_2_Time_data_1++);
2357 win1 = *(pShort_Window_1++);
2358 for (i = SHORT_WINDOW; i != 0; i--)
2359 {
2360 *(pScrath_mem++) = fxp_mul_16_by_16(dat1, win1) >> shift;
2361 dat1 = *(pFreq_2_Time_data_1++);
2362 win1 = *(pShort_Window_1++);
2363 }
2364
2365 dat1 = *(pFreq_2_Time_data_2++);
2366 win1 = *(pShort_Window_2--);
2367
2368
2369 /* -------- segment B ---------------*/
2370 for (i = HALF_SHORT_WINDOW; i != 0; i--)
2371 {
2372 test = fxp_mul_16_by_16(dat1, win1) >> shift;
2373
2374 temp = *(pScrath_mem++) + test;
2375
2376 test = *(pOverlap_and_Add_Buffer_1x++);
2377 limiter(*(pInterleaved_output), (temp + test));
2378
2379
2380 pInterleaved_output += 2;
2381 dat1 = *(pFreq_2_Time_data_2++);
2382 win1 = *(pShort_Window_2--);
2383
2384 }
2385
2386 /* -------- segment C ---------------*/
2387 for (i = HALF_SHORT_WINDOW; i != 0; i--)
2388 {
2389
2390 temp = fxp_mul_16_by_16(dat1, win1) >> shift;
2391
2392 *(pOverlap_and_Add_Buffer_1++) += temp;
2393
2394 dat1 = *(pFreq_2_Time_data_2++);
2395 win1 = *(pShort_Window_2--);
2396 }
2397
2398
2399 } /* if (exp < 16) */
2400 else
2401 {
2402
2403 pv_memset(
2404 pScrath_mem,
2405 0,
2406 SHORT_WINDOW*sizeof(*pScrath_mem));
2407
2408 pScrath_mem += SHORT_WINDOW;
2409
2410 temp = *(pScrath_mem++);
2411 for (i = HALF_SHORT_WINDOW; i != 0; i--)
2412 {
2413 limiter(*(pInterleaved_output), (temp));
2414
2415 pInterleaved_output += 2;
2416 temp = *(pScrath_mem++);
2417
2418 }
2419 }
2420
2421
2422 for (wnd = NUM_SHORT_WINDOWS / 2 - 2; wnd >= 0; wnd--)
2423 {
2424
2425
2426 pInterleaved_output_2 -= (SHORT_WINDOW * 2);
2427 pInterleaved_output = pInterleaved_output_2;
2428
2429 /*
2430 * The same memory is used as scratch in every iteration
2431 */
2432 pScrath_mem = pScrath_mem_entry;
2433
2434 pOverlap_and_Add_Buffer_2x =
2435 &Time_data[W_L_STOP_1 + SHORT_WINDOW*(wnd+1)];
2436
2437 pFreqInfo = (Int16 *) & pFrequency_data[ wnd*SHORT_WINDOW];
2438
2439
2440
2441 exp = imdct_fxp(
2442 (Int32 *)pFreqInfo,
2443 freq_2_time_buffer,
2444 SHORT_BLOCK1,
2445 Q_format,
2446 abs_max_per_window[wnd]);
2447
2448 /*
2449 * If all element are zero or if the exponent is bigger than
2450 * 16 ( it becomes an undefined shift) -> skip
2451 */
2452
2453 if (exp < 16)
2454 {
2455
2456 pFreq_2_Time_data_1 = &pFreqInfo[0];
2457 pFreq_2_Time_data_2 = &pFreqInfo[SHORT_WINDOW];
2458
2459
2460 /*
2461 * Each of the eight short blocks is windowed separately.
2462 * Window shape decisions are made on a frame-by-frame
2463 * basis.
2464 */
2465
2466 pShort_Window_1 = &Short_Window_fxp[wnd_shape_this_bk][0];
2467
2468 if (wnd == 0)
2469 {
2470 pShort_Window_1 =
2471 &Short_Window_fxp[wnd_shape_prev_bk][0];
2472 }
2473
2474 pShort_Window_2 =
2475 &Short_Window_fxp[wnd_shape_this_bk][SHORT_WINDOW_m_1];
2476
2477
2478 /*
2479 * For short windows from 2 to 0
2480 *
2481 * =========================
2482 * |
2483 * 0 1 2 | |
2484 * _--_ _--_ _--_ _-|-_ | _--_ _--_ _--_ _--_
2485 * / \/ \/ \/ | \|/ \/ \/ \/ \
2486 * / /\ /\ /\ | /|\ /\ /\ /\ \
2487 * / / \ / \ / \ | / | \ / \ / \ / \ \
2488 * / / \/ \/ \|/ | \/ \/ \ \ \
2489 * ----[\\\\\\\\\\\\\\\\\\\\\\\\]---|-----------------------------
2490 * |
2491 *
2492 * W_L_STOP_1
2493 */
2494
2495 shift = exp + 15 - SCALING;
2496
2497 Int16 dat1 = *(pFreq_2_Time_data_2++);
2498 Int16 win1 = *(pShort_Window_2--);
2499
2500 temp = *(pScrath_mem);
2501 for (i = SHORT_WINDOW; i != 0; i--)
2502 {
2503 test = fxp_mul_16_by_16(dat1, win1) >> shift;
2504
2505 temp += test;
2506 dat1 = *(pFreq_2_Time_data_1++);
2507 win1 = *(pShort_Window_1++);
2508
2509 limiter(*(pInterleaved_output), (temp + *(pOverlap_and_Add_Buffer_2x++)));
2510
2511 pInterleaved_output += 2;
2512
2513 *(pScrath_mem++) = fxp_mul_16_by_16(dat1, win1) >> shift;
2514 dat1 = *(pFreq_2_Time_data_2++);
2515 win1 = *(pShort_Window_2--);
2516 temp = *(pScrath_mem);
2517
2518 }
2519
2520 } /* if (exp < 16) */
2521 else
2522 {
2523 test = *(pScrath_mem);
2524 temp = *(pOverlap_and_Add_Buffer_2x++);
2525
2526 for (i = SHORT_WINDOW; i != 0; i--)
2527 {
2528 limiter(*(pInterleaved_output), (temp + test));
2529
2530 pInterleaved_output += 2;
2531
2532 *(pScrath_mem++) = 0;
2533 test = *(pScrath_mem);
2534 temp = *(pOverlap_and_Add_Buffer_2x++);
2535 }
2536 }
2537
2538 } /* for ( wnd=NUM_SHORT_WINDOWS/2-1; wnd>=0; wnd--) */
2539
2540 pOverlap_and_Add_Buffer_2x = &Time_data[W_L_STOP_1];
2541
2542 pScrath_mem = pScrath_mem_entry;
2543
2544 pInterleaved_output_2 -= (SHORT_WINDOW * 2);
2545 pInterleaved_output = pInterleaved_output_2;
2546
2547 test = *(pScrath_mem++);
2548 temp = *(pOverlap_and_Add_Buffer_2x++);
2549
2550 for (i = SHORT_WINDOW; i != 0; i--)
2551 {
2552 limiter(*(pInterleaved_output), (temp + test));
2553
2554 pInterleaved_output += 2;
2555 test = *(pScrath_mem++);
2556 temp = *(pOverlap_and_Add_Buffer_2x++);
2557
2558 }
2559
2560 pOverlap_and_Add_Buffer_1x = Time_data;
2561
2562 pInterleaved_output = Interleaved_output;
2563
2564
2565 temp = *(pOverlap_and_Add_Buffer_1x++);
2566 for (i = W_L_STOP_1; i != 0; i--)
2567 {
2568 limiter(*(pInterleaved_output), temp);
2569
2570 pInterleaved_output += 2;
2571 temp = *(pOverlap_and_Add_Buffer_1x++);
2572
2573 }
2574
2575 pOverlap_and_Add_Buffer_1x = &Time_data[0];
2576
2577 pOverlap_and_Add_Buffer_2 = &pFrequency_data[LONG_WINDOW];
2578
2579 /*
2580 * update overlap and add buffer,
2581 * so is ready for next iteration
2582 */
2583
2584 for (int i = 0; i < W_L_STOP_2; i++)
2585 {
2586 temp = *(pOverlap_and_Add_Buffer_2++);
2587 *(pOverlap_and_Add_Buffer_1x++) = temp;
2588 }
2589
2590 pv_memset(
2591 pOverlap_and_Add_Buffer_1x,
2592 0,
2593 W_L_STOP_1*sizeof(*pOverlap_and_Add_Buffer_1x));
2594
2595 } /* if ( wnd_seq != EIGHT_SHORT_SEQUENCE) */
2596
2597
2598
2599
2600 } /* trans4m_freq_2_time_fxp */
2601
2602
2603
2604
2605