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 Portions of this file are derived from the following 3GPP standard:
20
21 3GPP TS 26.073
22 ANSI-C code for the Adaptive Multi-Rate (AMR) speech codec
23 Available from http://www.3gpp.org
24
25 (C) 2004, 3GPP Organizational Partners (ARIB, ATIS, CCSA, ETSI, TTA, TTC)
26 Permission to distribute, modify and use this file under the standard license
27 terms listed above has been obtained from the copyright holder.
28 ****************************************************************************************/
29 /*
30 ------------------------------------------------------------------------------
31
32
33
34 Pathname: ./audio/gsm-amr/c/src/pitch_ol.c
35 Funtions: Pitch_ol
36 Lag_max
37
38 ------------------------------------------------------------------------------
39 MODULE DESCRIPTION
40
41 The modules in this file compute the open loop pitch lag.
42 ------------------------------------------------------------------------------
43 */
44
45
46 /*----------------------------------------------------------------------------
47 ; INCLUDES
48 ----------------------------------------------------------------------------*/
49 #include <string.h>
50
51 #include "pitch_ol.h"
52 #include "typedef.h"
53 #include "basicop_malloc.h"
54 #include "cnst.h"
55 #include "inv_sqrt.h"
56 #include "vad.h"
57 #include "calc_cor.h"
58 #include "hp_max.h"
59 #include "basic_op.h"
60
61 /*----------------------------------------------------------------------------
62 ; MACROS
63 ; Define module specific macros here
64 ----------------------------------------------------------------------------*/
65
66
67 /*----------------------------------------------------------------------------
68 ; DEFINES
69 ; Include all pre-processor statements here. Include conditional
70 ; compile variables also.
71 ----------------------------------------------------------------------------*/
72 #define THRESHOLD 27853
73
74 /*----------------------------------------------------------------------------
75 ; LOCAL FUNCTION DEFINITIONS
76 ; Function Prototype declaration
77 ----------------------------------------------------------------------------*/
78
79 /*----------------------------------------------------------------------------
80 ; LOCAL VARIABLE DEFINITIONS
81 ; Variable declaration - defined here and used outside this module
82 ----------------------------------------------------------------------------*/
83
84
85 /*
86 ------------------------------------------------------------------------------
87 FUNCTION NAME: Lag_max
88 ------------------------------------------------------------------------------
89 INPUT AND OUTPUT DEFINITIONS (If VAD2 is defined)
90
91 Inputs
92 corr = pointer to buffer of correlation values (Word32)
93 scal_sig = pointer to buffer of scaled signal values (Word16)
94 scal_fac = scaled signal factor (Word16)
95 scal_flag = EFR compatible scaling flag (Word16)
96 L_frame = length of frame to compute pitch (Word16)
97 lag_max = maximum lag (Word16)
98 lag_min = minimum lag (Word16)
99 cor_max = pointer to the normalized correlation of selected lag (Word16)
100 rmax = pointer to max(<s[i]*s[j]>), (Word32)
101 r0 = pointer to the residual energy (Word32)
102 dtx = dtx flag; equal to 1, if dtx is enabled, 0, otherwise (Flag)
103
104 Outputs:
105 cor_max contains the newly calculated normalized correlation of the
106 selected lag
107 rmax contains the newly calculated max(<s[i]*s[j]>)
108 r0 contains the newly calculated residual energy
109
110 Returns:
111 p_max = lag of the max correlation found (Word16)
112
113 Global Variables Used:
114 None.
115
116 Local Variables Needed:
117 None.
118
119 ------------------------------------------------------------------------------
120 INPUT AND OUTPUT DEFINITIONS (If VAD2 is not defined)
121
122 Inputs
123 vadSt = pointer to a vadState structure
124 corr = pointer to buffer of correlation values (Word32)
125 scal_sig = pointer to buffer of scaled signal values (Word16)
126 scal_fac = scaled signal factor (Word16)
127 scal_flag = EFR compatible scaling flag (Word16)
128 L_frame = length of frame to compute pitch (Word16)
129 lag_max = maximum lag (Word16)
130 lag_min = minimum lag (Word16)
131 cor_max = pointer to the normalized correlation of selected lag (Word16)
132 dtx = dtx flag; equal to 1, if dtx is enabled, 0, otherwise (Flag)
133 pOverflow = pointer to overflow indicator (Flag)
134
135 Outputs:
136 cor_max contains the newly calculated normalized correlation of the
137 selected lag
138 vadSt contains the updated VAD state parameters
139 pOverflow -> 1 if the math operations called by this routine saturate
140
141 Returns:
142 p_max = lag of the max correlation found (Word16)
143
144 Global Variables Used:
145 None.
146
147 Local Variables Needed:
148 None.
149
150 ------------------------------------------------------------------------------
151 FUNCTION DESCRIPTION
152
153 Find the lag that has maximum correlation of scal_sig in a given delay range.
154 The correlation is given by:
155
156 cor[t] = <scal_sig[n],scal_sig[n-t]>, t=lag_min,...,lag_max
157
158 The function returns the maximum correlation after normalization and the
159 corresponding lag.
160
161 ------------------------------------------------------------------------------
162 REQUIREMENTS
163
164 None.
165
166 ------------------------------------------------------------------------------
167 REFERENCES
168
169 pitch_ol.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
170
171 ------------------------------------------------------------------------------
172 PSEUDO-CODE
173
174 #ifdef VAD2
175 static Word16 Lag_max ( // o : lag found
176 Word32 corr[], // i : correlation vector.
177 Word16 scal_sig[], // i : scaled signal.
178 Word16 scal_fac, // i : scaled signal factor.
179 Word16 scal_flag, // i : if 1 use EFR compatible scaling
180 Word16 L_frame, // i : length of frame to compute pitch
181 Word16 lag_max, // i : maximum lag
182 Word16 lag_min, // i : minimum lag
183 Word16 *cor_max, // o : normalized correlation of selected lag
184 Word32 *rmax, // o : max(<s[i]*s[j]>)
185 Word32 *r0, // o : residual energy
186 Flag dtx // i : dtx flag; use dtx=1, do not use dtx=0
187 )
188 #else
189 static Word16 Lag_max ( // o : lag found
190 vadState *vadSt, // i/o : VAD state struct
191 Word32 corr[], // i : correlation vector.
192 Word16 scal_sig[], // i : scaled signal.
193 Word16 scal_fac, // i : scaled signal factor.
194 Word16 scal_flag, // i : if 1 use EFR compatible scaling
195 Word16 L_frame, // i : length of frame to compute pitch
196 Word16 lag_max, // i : maximum lag
197 Word16 lag_min, // i : minimum lag
198 Word16 *cor_max, // o : normalized correlation of selected lag
199 Flag dtx // i : dtx flag; use dtx=1, do not use dtx=0
200 )
201 #endif
202 {
203 Word16 i, j;
204 Word16 *p;
205 Word32 max, t0;
206 Word16 max_h, max_l, ener_h, ener_l;
207 Word16 p_max = 0; // initialization only needed to keep gcc silent
208
209 max = MIN_32;
210 p_max = lag_max;
211
212 for (i = lag_max, j = (PIT_MAX-lag_max-1); i >= lag_min; i--, j--)
213 {
214 if (L_sub (corr[-i], max) >= 0)
215 {
216 max = corr[-i];
217 p_max = i;
218 }
219 }
220
221 // compute energy
222
223 t0 = 0;
224 p = &scal_sig[-p_max];
225 for (i = 0; i < L_frame; i++, p++)
226 {
227 t0 = L_mac (t0, *p, *p);
228 }
229 // 1/sqrt(energy)
230
231 if (dtx)
232 { // no test() call since this if is only in simulation env
233 #ifdef VAD2
234 *rmax = max;
235 *r0 = t0;
236 #else
237 // check tone
238 vad_tone_detection (vadSt, max, t0);
239 #endif
240 }
241
242 t0 = Inv_sqrt (t0);
243
244 if (scal_flag)
245 {
246 t0 = L_shl (t0, 1);
247 }
248
249 // max = max/sqrt(energy)
250
251 L_Extract (max, &max_h, &max_l);
252 L_Extract (t0, &ener_h, &ener_l);
253
254 t0 = Mpy_32 (max_h, max_l, ener_h, ener_l);
255
256 if (scal_flag)
257 {
258 t0 = L_shr (t0, scal_fac);
259 *cor_max = extract_h (L_shl (t0, 15)); // divide by 2
260 }
261 else
262 {
263 *cor_max = extract_l(t0);
264 }
265
266 return (p_max);
267 }
268
269 ------------------------------------------------------------------------------
270 RESOURCES USED [optional]
271
272 When the code is written for a specific target processor the
273 the resources used should be documented below.
274
275 HEAP MEMORY USED: x bytes
276
277 STACK MEMORY USED: x bytes
278
279 CLOCK CYCLES: (cycle count equation for this function) + (variable
280 used to represent cycle count for each subroutine
281 called)
282 where: (cycle count variable) = cycle count for [subroutine
283 name]
284
285 ------------------------------------------------------------------------------
286 CAUTION [optional]
287 [State any special notes, constraints or cautions for users of this function]
288
289 ------------------------------------------------------------------------------
290 */
291
292 #ifdef VAD2
Lag_max(Word32 corr[],Word16 scal_sig[],Word16 scal_fac,Word16 scal_flag,Word16 L_frame,Word16 lag_max,Word16 lag_min,Word16 * cor_max,Word32 * rmax,Word32 * r0,Flag dtx,Flag * pOverflow)293 static Word16 Lag_max( /* o : lag found */
294 Word32 corr[], /* i : correlation vector. */
295 Word16 scal_sig[], /* i : scaled signal. */
296 Word16 scal_fac, /* i : scaled signal factor. */
297 Word16 scal_flag, /* i : if 1 use EFR compatible scaling */
298 Word16 L_frame, /* i : length of frame to compute pitch */
299 Word16 lag_max, /* i : maximum lag */
300 Word16 lag_min, /* i : minimum lag */
301 Word16 *cor_max, /* o : normalized correlation of selected lag */
302 Word32 *rmax, /* o : max(<s[i]*s[j]>) */
303 Word32 *r0, /* o : residual energy */
304 Flag dtx, /* i : dtx flag; use dtx=1, do not use dtx=0 */
305 Flag *pOverflow /* i/o : overflow Flag */
306 )
307 #else
308 static Word16 Lag_max( /* o : lag found */
309 vadState *vadSt, /* i/o : VAD state struct */
310 Word32 corr[], /* i : correlation vector. */
311 Word16 scal_sig[], /* i : scaled signal. */
312 Word16 scal_fac, /* i : scaled signal factor. */
313 Word16 scal_flag, /* i : if 1 use EFR compatible scaling */
314 Word16 L_frame, /* i : length of frame to compute pitch */
315 Word16 lag_max, /* i : maximum lag */
316 Word16 lag_min, /* i : minimum lag */
317 Word16 *cor_max, /* o : normalized correlation of selected lag */
318 Flag dtx, /* i : dtx flag; use dtx=1, do not use dtx=0 */
319 Flag *pOverflow /* i/o : overflow Flag */
320 )
321 #endif
322 {
323 Word16 i;
324 Word16 *p;
325 Word32 max;
326 Word32 t0;
327 Word16 max_h;
328 Word16 max_l;
329 Word16 ener_h;
330 Word16 ener_l;
331 Word16 p_max = 0; /* initialization only needed to keep gcc silent */
332 Word32 L_temp;
333 Word32 L_temp_2;
334 Word32 L_temp_3;
335 Word32 *p_corr = &corr[-lag_max];
336
337 max = MIN_32;
338 p_max = lag_max;
339
340 for (i = lag_max; i >= lag_min; i--)
341 {
342 /* The negative array index is equivalent to a negative */
343 /* address offset, i.e., corr[-i] == *(corr - i) */
344 if (*(p_corr++) >= max)
345 {
346 p_corr--;
347 max = *(p_corr++);
348 p_max = i;
349 }
350 }
351
352 /* compute energy */
353
354 t0 = 0;
355
356 /* The negative array index is equivalent to a negative */
357 /* address offset, i.e., scal_sig[-p_max] == *(scal_sig - p_max) */
358 p = &scal_sig[-p_max];
359 for (i = (L_frame >> 2); i != 0; i--)
360 {
361 t0 = amrnb_fxp_mac_16_by_16bb((Word32) * (p), (Word32) * (p), t0);
362 p++;
363 t0 = amrnb_fxp_mac_16_by_16bb((Word32) * (p), (Word32) * (p), t0);
364 p++;
365 t0 = amrnb_fxp_mac_16_by_16bb((Word32) * (p), (Word32) * (p), t0);
366 p++;
367 t0 = amrnb_fxp_mac_16_by_16bb((Word32) * (p), (Word32) * (p), t0);
368 p++;
369 }
370
371 t0 <<= 1;
372 /* 1/sqrt(energy) */
373
374 if (dtx)
375 { /* no test() call since this if is only in simulation env */
376 /* check tone */
377 #ifdef VAD2
378 *rmax = max;
379 *r0 = t0;
380 #else
381 /* check tone */
382 vad_tone_detection(vadSt, max, t0, pOverflow);
383 #endif
384 }
385
386 t0 = Inv_sqrt(t0, pOverflow);
387
388 if (scal_flag)
389 {
390 if (t0 > (Word32) 0x3fffffffL)
391 {
392 t0 = MAX_32;
393 }
394 else
395 {
396 t0 = t0 << 1;
397 }
398 }
399
400 /* max = max/sqrt(energy) */
401 /* The following code is an inlined version of */
402 /* L_Extract (max, &max_h, &max_l), i.e. */
403 /* */
404 /* *max_h = extract_h (max); */
405 max_h = (Word16)(max >> 16);
406
407 /* L_temp_2 = L_shr(max,1), which is used in */
408 /* the calculation of *max_l (see next operation) */
409 L_temp_2 = max >> 1;
410
411 /* *max_l = extract_l (L_msu (L_shr (max, 1), *max_h, 16384)); */
412 L_temp_3 = (Word32)(max_h << 15);
413
414 L_temp = L_temp_2 - L_temp_3;
415
416 max_l = (Word16)L_temp;
417
418 /* The following code is an inlined version of */
419 /* L_Extract (t0, &ener_h, &ener_l), i.e. */
420 /* */
421 /* *ener_h = extract_h (t0); */
422 ener_h = (Word16)(t0 >> 16);
423
424 /* L_temp_2 = L_shr(t0,1), which is used in */
425 /* the calculation of *ener_l (see next operation) */
426
427 L_temp_2 = t0 >> 1;
428
429 L_temp_3 = (Word32)(ener_h << 15);
430
431 L_temp = L_temp_2 - L_temp_3;
432
433 ener_l = (Word16)L_temp;
434
435 t0 = Mpy_32(max_h, max_l, ener_h, ener_l, pOverflow);
436
437 if (scal_flag)
438 {
439 t0 = L_shr(t0, scal_fac, pOverflow);
440
441 if (t0 > (Word32) 0X0000FFFFL)
442 {
443 *cor_max = MAX_16;
444 }
445 else if (t0 < (Word32) 0xFFFF0000L)
446 {
447 *cor_max = MIN_16;
448 }
449 else
450 {
451 *cor_max = (Word16)(t0 >> 1);
452 }
453 }
454 else
455 {
456 *cor_max = (Word16)t0;
457 }
458
459 return (p_max);
460 }
461
462 /*----------------------------------------------------------------------------
463 ; End Function: Lag_max
464 ----------------------------------------------------------------------------*/
465
466
467 /*
468 ------------------------------------------------------------------------------
469 FUNCTION NAME: Lag_max_wrapper
470 ------------------------------------------------------------------------------
471 INPUT AND OUTPUT DEFINITIONS
472
473 Inputs
474 corr = pointer to buffer of correlation values (Word32)
475 scal_sig = pointer to buffer of scaled signal values (Word16)
476 scal_fac = scaled signal factor (Word16)
477 scal_flag = EFR compatible scaling flag (Word16)
478 L_frame = length of frame to compute pitch (Word16)
479 lag_max = maximum lag (Word16)
480 lag_min = minimum lag (Word16)
481 cor_max = pointer to the normalized correlation of selected lag (Word16)
482 rmax = pointer to max(<s[i]*s[j]>), (Word32)
483 r0 = pointer to the residual energy (Word32)
484 dtx = dtx flag; equal to 1, if dtx is enabled, 0, otherwise (Flag)
485 pOverflow = pointer to overflow indicator (Flag)
486
487 Outputs:
488 cor_max contains the newly calculated normalized correlation of the
489 selected lag
490 rmax contains the newly calculated max(<s[i]*s[j]>)
491 r0 contains the newly calculated residual energy
492 pOverflow -> 1 if the math operations called by this routine saturate
493
494 Returns:
495 p_max = lag of the max correlation found (Word16)
496
497 Global Variables Used:
498 None.
499
500 Local Variables Needed:
501 None.
502
503 ------------------------------------------------------------------------------
504 INPUT AND OUTPUT DEFINITIONS (If VAD2 is not defined)
505
506 Inputs
507 vadSt = pointer to a vadState structure
508 corr = pointer to buffer of correlation values (Word32)
509 scal_sig = pointer to buffer of scaled signal values (Word16)
510 scal_fac = scaled signal factor (Word16)
511 scal_flag = EFR compatible scaling flag (Word16)
512 L_frame = length of frame to compute pitch (Word16)
513 lag_max = maximum lag (Word16)
514 lag_min = minimum lag (Word16)
515 cor_max = pointer to the normalized correlation of selected lag (Word16)
516 dtx = dtx flag; equal to 1, if dtx is enabled, 0, otherwise (Flag)
517 pOverflow = pointer to overflow indicator (Flag)
518
519 Outputs:
520 cor_max contains the newly calculated normalized correlation of the
521 selected lag
522 vadSt contains the updated VAD state parameters
523 pOverflow -> 1 if the math operations called by this routine saturate
524
525 Returns:
526 p_max = lag of the max correlation found (Word16)
527
528 Global Variables Used:
529 None.
530
531 Local Variables Needed:
532 None.
533
534 ------------------------------------------------------------------------------
535 FUNCTION DESCRIPTION
536
537 This function provides external access to the local function Lag_max.
538
539 ------------------------------------------------------------------------------
540 REQUIREMENTS
541
542 None
543
544 ------------------------------------------------------------------------------
545 REFERENCES
546
547 pitch_ol.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
548
549 ------------------------------------------------------------------------------
550 PSEUDO-CODE
551
552 #ifdef VAD2
553 CALL Lag_max(corr = corr
554 scal_sig = scal_sig
555 scal_fac = scal_fac
556 scal_flag = scal_flag
557 L_frame = L_frame
558 lag_max = lag_max
559 lag_min = lag_min
560 cor_max = cor_max
561 rmax = rmax
562 r0 = r0
563 dtx = dtx
564 pOverflow = pOverflow)
565 MODIFYING(nothing)
566 RETURNING(temp)
567
568 #else
569 CALL Lag_max(vadSt = vadSt
570 corr = corr
571 scal_sig = scal_sig
572 scal_fac = scal_fac
573 scal_flag = scal_flag
574 L_frame = L_frame
575 lag_max = lag_max
576 lag_min = lag_min
577 cor_max = cor_max
578 dtx = dtx
579 pOverflow = pOverflow)
580 MODIFYING(nothing)
581 RETURNING(temp)
582
583 #endif
584
585 ------------------------------------------------------------------------------
586 RESOURCES USED [optional]
587
588 When the code is written for a specific target processor the
589 the resources used should be documented below.
590
591 HEAP MEMORY USED: x bytes
592
593 STACK MEMORY USED: x bytes
594
595 CLOCK CYCLES: (cycle count equation for this function) + (variable
596 used to represent cycle count for each subroutine
597 called)
598 where: (cycle count variable) = cycle count for [subroutine
599 name]
600
601 ------------------------------------------------------------------------------
602 CAUTION [optional]
603 [State any special notes, constraints or cautions for users of this function]
604
605 ------------------------------------------------------------------------------
606 */
607
608 #ifdef VAD2
Lag_max_wrapper(Word32 corr[],Word16 scal_sig[],Word16 scal_fac,Word16 scal_flag,Word16 L_frame,Word16 lag_max,Word16 lag_min,Word16 * cor_max,Word32 * rmax,Word32 * r0,Flag dtx,Flag * pOverflow)609 Word16 Lag_max_wrapper( /* o : lag found */
610 Word32 corr[], /* i : correlation vector. */
611 Word16 scal_sig[], /* i : scaled signal. */
612 Word16 scal_fac, /* i : scaled signal factor. */
613 Word16 scal_flag, /* i : if 1 use EFR compatible scaling */
614 Word16 L_frame, /* i : length of frame to compute pitch */
615 Word16 lag_max, /* i : maximum lag */
616 Word16 lag_min, /* i : minimum lag */
617 Word16 *cor_max, /* o : normalized correlation of selected lag */
618 Word32 *rmax, /* o : max(<s[i]*s[j]>) */
619 Word32 *r0, /* o : residual energy */
620 Flag dtx, /* i : dtx flag; use dtx=1, do not use dtx=0 */
621 Flag *pOverflow /* i/o : overflow Flag */
622 )
623 {
624 Word16 temp;
625
626 temp = Lag_max(corr, scal_sig, scal_fac, scal_flag, L_frame, lag_max,
627 lag_min, cor_max, rmax, r0, dtx, pOverflow);
628
629 return(temp);
630 }
631
632 #else
Lag_max_wrapper(vadState * vadSt,Word32 corr[],Word16 scal_sig[],Word16 scal_fac,Word16 scal_flag,Word16 L_frame,Word16 lag_max,Word16 lag_min,Word16 * cor_max,Flag dtx,Flag * pOverflow)633 Word16 Lag_max_wrapper( /* o : lag found */
634 vadState *vadSt, /* i/o : VAD state struct */
635 Word32 corr[], /* i : correlation vector. */
636 Word16 scal_sig[], /* i : scaled signal. */
637 Word16 scal_fac, /* i : scaled signal factor. */
638 Word16 scal_flag, /* i : if 1 use EFR compatible scaling */
639 Word16 L_frame, /* i : length of frame to compute pitch */
640 Word16 lag_max, /* i : maximum lag */
641 Word16 lag_min, /* i : minimum lag */
642 Word16 *cor_max, /* o : normalized correlation of selected lag */
643 Flag dtx, /* i : dtx flag; use dtx=1, do not use dtx=0 */
644 Flag *pOverflow /* i/o : overflow Flag */
645 )
646 {
647 Word16 temp;
648
649 temp = Lag_max(vadSt, corr, scal_sig, scal_fac, scal_flag, L_frame,
650 lag_max, lag_min, cor_max, dtx, pOverflow);
651
652 return(temp);
653 }
654
655 #endif
656
657 /*----------------------------------------------------------------------------
658 ; End Function: Lag_max_wrapper
659 ----------------------------------------------------------------------------*/
660
661 /*
662 ------------------------------------------------------------------------------
663 FUNCTION NAME: Pitch_ol
664 ------------------------------------------------------------------------------
665 INPUT AND OUTPUT DEFINITIONS
666
667 Inputs:
668 vadSt = pointer to a vadState structure
669 mode = data of type enum Mode specifies the mode.
670 signal = pointer to buffer of signal used to compute the open loop
671 pitch
672 where signal[-pit_max] to signal[-1] should be known
673 pit_min = 16 bit value specifies the minimum pitch lag
674 pit_max = 16 bit value specifies the maximum pitch lag
675 L_frame = 16 bit value specifies the length of frame to compute pitch
676 idx = 16 bit value specifies the frame index
677 dtx = Data of type 'Flag' used for dtx. Use dtx=1, do not use dtx=0
678 pOverflow = pointer to overflow indicator (Flag)
679
680 Outputs
681 vadSt = The vadSt state structure may be modified.
682 pOverflow -> 1 if the math operations called by this routine saturate
683
684 Returns:
685 p_max1 = 16 bit value representing the open loop pitch lag.
686
687 Global Variables Used:
688 None.
689
690 Local Variables Needed:
691 None.
692
693 ------------------------------------------------------------------------------
694 FUNCTION DESCRIPTION
695
696 This function computes the open loop pitch lag based on the perceptually
697 weighted speech signal. This is done in the following steps:
698 - find three maxima of the correlation <sw[n],sw[n-T]>,
699 dividing the search range into three parts:
700 pit_min ... 2*pit_min-1
701 2*pit_min ... 4*pit_min-1
702 4*pit_min ... pit_max
703 - divide each maximum by <sw[n-t], sw[n-t]> where t is the delay at
704 that maximum correlation.
705 - select the delay of maximum normalized correlation (among the
706 three candidates) while favoring the lower delay ranges.
707
708
709 ------------------------------------------------------------------------------
710 REQUIREMENTS
711
712 None.
713
714 ------------------------------------------------------------------------------
715 REFERENCES
716
717 pitch_ol.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
718
719 ------------------------------------------------------------------------------
720 PSEUDO-CODE
721
722 Word16 Pitch_ol ( // o : open loop pitch lag
723 vadState *vadSt, // i/o : VAD state struct
724 enum Mode mode, // i : coder mode
725 Word16 signal[], // i : signal used to compute the open loop pitch
726 // signal[-pit_max] to signal[-1] should be known
727 Word16 pit_min, // i : minimum pitch lag
728 Word16 pit_max, // i : maximum pitch lag
729 Word16 L_frame, // i : length of frame to compute pitch
730 Word16 idx, // i : frame index
731 Flag dtx // i : dtx flag; use dtx=1, do not use dtx=0
732 )
733 {
734 Word16 i, j;
735 Word16 max1, max2, max3;
736 Word16 p_max1, p_max2, p_max3;
737 Word16 scal_flag = 0;
738 Word32 t0;
739 #ifdef VAD2
740 Word32 r01, r02, r03;
741 Word32 rmax1, rmax2, rmax3;
742 #else
743 Word16 corr_hp_max;
744 #endif
745 Word32 corr[PIT_MAX+1], *corr_ptr;
746
747 // Scaled signal
748
749 Word16 scaled_signal[L_FRAME + PIT_MAX];
750 Word16 *scal_sig, scal_fac;
751
752 #ifndef VAD2
753 if (dtx)
754 { // no test() call since this if is only in simulation env
755 // update tone detection
756 if ((sub(mode, MR475) == 0) || (sub(mode, MR515) == 0))
757 {
758 vad_tone_detection_update (vadSt, 1);
759 }
760 else
761 {
762 vad_tone_detection_update (vadSt, 0);
763 }
764 }
765 #endif
766
767 scal_sig = &scaled_signal[pit_max];
768
769 t0 = 0L;
770 for (i = -pit_max; i < L_frame; i++)
771 {
772 t0 = L_mac (t0, signal[i], signal[i]);
773 }
774
775 *--------------------------------------------------------*
776 * Scaling of input signal. *
777 * *
778 * if Overflow -> scal_sig[i] = signal[i]>>3 *
779 * else if t0 < 1^20 -> scal_sig[i] = signal[i]<<3 *
780 * else -> scal_sig[i] = signal[i] *
781 *--------------------------------------------------------*
782
783 *--------------------------------------------------------*
784 * Verification for risk of overflow. *
785 *--------------------------------------------------------*
786
787 if (L_sub (t0, MAX_32) == 0L) // Test for overflow
788 {
789 for (i = -pit_max; i < L_frame; i++)
790 {
791 scal_sig[i] = shr (signal[i], 3);
792 }
793 scal_fac = 3;
794 }
795 else if (L_sub (t0, (Word32) 1048576L) < (Word32) 0)
796 // if (t0 < 2^20)
797 {
798 for (i = -pit_max; i < L_frame; i++)
799 {
800 scal_sig[i] = shl (signal[i], 3);
801 }
802 scal_fac = -3;
803 }
804 else
805 {
806 for (i = -pit_max; i < L_frame; i++)
807 {
808 scal_sig[i] = signal[i];
809 }
810 scal_fac = 0;
811 }
812
813 // calculate all coreelations of scal_sig, from pit_min to pit_max
814 corr_ptr = &corr[pit_max];
815 comp_corr (scal_sig, L_frame, pit_max, pit_min, corr_ptr);
816
817 *--------------------------------------------------------------------*
818 * The pitch lag search is divided in three sections. *
819 * Each section cannot have a pitch multiple. *
820 * We find a maximum for each section. *
821 * We compare the maximum of each section by favoring small lags. *
822 * *
823 * First section: lag delay = pit_max downto 4*pit_min *
824 * Second section: lag delay = 4*pit_min-1 downto 2*pit_min *
825 * Third section: lag delay = 2*pit_min-1 downto pit_min *
826 *--------------------------------------------------------------------*
827
828 // mode dependent scaling in Lag_max
829 if (sub(mode, MR122) == 0)
830 {
831 scal_flag = 1;
832 }
833 else
834 {
835 scal_flag = 0;
836 }
837
838 #ifdef VAD2
839 j = shl (pit_min, 2);
840 p_max1 = Lag_max (corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
841 pit_max, j, &max1, &rmax1, &r01, dtx);
842
843 i = sub (j, 1);
844 j = shl (pit_min, 1);
845 p_max2 = Lag_max (corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
846 i, j, &max2, &rmax2, &r02, dtx);
847
848 i = sub (j, 1);
849 p_max3 = Lag_max (corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
850 i, pit_min, &max3, &rmax3, &r03, dtx);
851 #else
852 j = shl (pit_min, 2);
853 p_max1 = Lag_max (vadSt, corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
854 pit_max, j, &max1, dtx);
855
856 i = sub (j, 1);
857 j = shl (pit_min, 1);
858 p_max2 = Lag_max (vadSt, corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
859 i, j, &max2, dtx);
860
861 i = sub (j, 1);
862 p_max3 = Lag_max (vadSt, corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
863 i, pit_min, &max3, dtx);
864
865 if (dtx)
866 { // no test() call since this if is only in simulation env
867 if (sub(idx, 1) == 0)
868 {
869 // calculate max high-passed filtered correlation of all lags
870 hp_max (corr_ptr, scal_sig, L_frame, pit_max, pit_min, &corr_hp_max);
871
872 // update complex background detector
873 vad_complex_detection_update(vadSt, corr_hp_max);
874 }
875 }
876 #endif
877
878 *--------------------------------------------------------------------*
879 * Compare the 3 sections maximum, and favor small lag. *
880 *--------------------------------------------------------------------*
881
882 if (sub (mult (max1, THRESHOLD), max2) < 0)
883 {
884 max1 = max2;
885 p_max1 = p_max2;
886 #ifdef VAD2
887 if (dtx)
888 {
889 rmax1 = rmax2;
890 r01 = r02;
891 #endif
892 }
893 if (sub (mult (max1, THRESHOLD), max3) < 0)
894 {
895 p_max1 = p_max3;
896 #ifdef VAD2
897 if (dtx)
898 {
899 rmax1 = rmax3;
900 r01 = r03;
901 }
902 #endif
903 }
904
905 #ifdef VAD2
906 if (dtx)
907 {
908 vadSt->L_Rmax = L_add(vadSt->L_Rmax, rmax1); // Save max correlation
909 vadSt->L_R0 = L_add(vadSt->L_R0, r01); // Save max energy
910 }
911 #endif
912
913 return (p_max1);
914 }
915
916 ------------------------------------------------------------------------------
917 RESOURCES USED [optional]
918
919 When the code is written for a specific target processor the
920 the resources used should be documented below.
921
922 HEAP MEMORY USED: x bytes
923
924 STACK MEMORY USED: x bytes
925
926 CLOCK CYCLES: (cycle count equation for this function) + (variable
927 used to represent cycle count for each subroutine
928 called)
929 where: (cycle count variable) = cycle count for [subroutine
930 name]
931
932 ------------------------------------------------------------------------------
933 CAUTION [optional]
934 [State any special notes, constraints or cautions for users of this function]
935
936 ------------------------------------------------------------------------------
937 */
938
Pitch_ol(vadState * vadSt,enum Mode mode,Word16 signal[],Word16 pit_min,Word16 pit_max,Word16 L_frame,Word16 idx,Flag dtx,Flag * pOverflow)939 Word16 Pitch_ol( /* o : open loop pitch lag */
940 vadState *vadSt, /* i/o : VAD state struct */
941 enum Mode mode, /* i : coder mode */
942 Word16 signal[], /* i : signal used to compute the open loop pitch */
943 /* signal[-pit_max] to signal[-1] should be known */
944 Word16 pit_min, /* i : minimum pitch lag */
945 Word16 pit_max, /* i : maximum pitch lag */
946 Word16 L_frame, /* i : length of frame to compute pitch */
947 Word16 idx, /* i : frame index */
948 Flag dtx, /* i : dtx flag; use dtx=1, do not use dtx=0 */
949 Flag *pOverflow /* i/o : overflow Flag */
950 )
951 {
952 Word16 i;
953 Word16 j;
954 Word16 max1;
955 Word16 max2;
956 Word16 max3;
957 Word16 p_max1;
958 Word16 p_max2;
959 Word16 p_max3;
960 Word16 scal_flag = 0;
961 Word32 t0;
962
963 #ifdef VAD2
964 Word32 r01;
965 Word32 r02;
966 Word32 r03;
967 Word32 rmax1;
968 Word32 rmax2;
969 Word32 rmax3;
970 #else
971 Word16 corr_hp_max;
972 #endif
973 Word32 corr[PIT_MAX+1];
974 Word32 *corr_ptr;
975
976 /* Scaled signal */
977
978 Word16 scaled_signal[L_FRAME + PIT_MAX];
979 Word16 *scal_sig;
980 Word16 *p_signal;
981 Word16 scal_fac;
982 Word32 L_temp;
983
984 #ifndef VAD2
985 if (dtx)
986 { /* no test() call since this if is only in simulation env */
987 /* update tone detection */
988 if ((mode == MR475) || (mode == MR515))
989 {
990 vad_tone_detection_update(vadSt, 1, pOverflow);
991 }
992 else
993 {
994 vad_tone_detection_update(vadSt, 0, pOverflow);
995 }
996 }
997 #endif
998
999
1000 t0 = 0L;
1001 p_signal = &signal[-pit_max];
1002
1003 for (i = -pit_max; i < L_frame; i++)
1004 {
1005 t0 += (((Word32) * (p_signal)) * *(p_signal)) << 1;
1006 p_signal++;
1007 if (t0 < 0)
1008 {
1009 t0 = MAX_32;
1010 break;
1011 }
1012
1013 }
1014
1015 /*--------------------------------------------------------*
1016 * Scaling of input signal. *
1017 * *
1018 * if Overflow -> scal_sig[i] = signal[i]>>3 *
1019 * else if t0 < 1^20 -> scal_sig[i] = signal[i]<<3 *
1020 * else -> scal_sig[i] = signal[i] *
1021 *--------------------------------------------------------*/
1022
1023 /*--------------------------------------------------------*
1024 * Verification for risk of overflow. *
1025 *--------------------------------------------------------*/
1026
1027 scal_sig = &scaled_signal[0];
1028 p_signal = &signal[-pit_max];
1029
1030 if (t0 == MAX_32) /* Test for overflow */
1031 {
1032
1033 for (i = (pit_max + L_frame) >> 1; i != 0; i--)
1034 {
1035 *(scal_sig++) = (Word16)(((Word32) * (p_signal++) >> 3));
1036 *(scal_sig++) = (Word16)(((Word32) * (p_signal++) >> 3));
1037 }
1038
1039 if ((pit_max + L_frame) & 1)
1040 {
1041 *(scal_sig) = (Word16)(((Word32) * (p_signal) >> 3));
1042 }
1043
1044 scal_fac = 3;
1045 }
1046 else if (t0 < (Word32)1048576L)
1047 /* if (t0 < 2^20) */
1048 {
1049 for (i = (pit_max + L_frame) >> 1; i != 0; i--)
1050 {
1051 *(scal_sig++) = (Word16)(((Word32) * (p_signal++) << 3));
1052 *(scal_sig++) = (Word16)(((Word32) * (p_signal++) << 3));
1053 }
1054
1055 if ((pit_max + L_frame) & 1)
1056 {
1057 *(scal_sig) = (Word16)(((Word32) * (p_signal) << 3));
1058 }
1059 scal_fac = -3;
1060 }
1061 else
1062 {
1063
1064 memcpy(scal_sig, p_signal, (L_frame + pit_max)*sizeof(*signal));
1065 scal_fac = 0;
1066 }
1067
1068 /* calculate all coreelations of scal_sig, from pit_min to pit_max */
1069 corr_ptr = &corr[pit_max];
1070
1071 scal_sig = &scaled_signal[pit_max];
1072
1073 comp_corr(scal_sig, L_frame, pit_max, pit_min, corr_ptr);
1074
1075 /*--------------------------------------------------------------------*
1076 * The pitch lag search is divided in three sections. *
1077 * Each section cannot have a pitch multiple. *
1078 * We find a maximum for each section. *
1079 * We compare the maximum of each section by favoring small lags. *
1080 * *
1081 * First section: lag delay = pit_max downto 4*pit_min *
1082 * Second section: lag delay = 4*pit_min-1 downto 2*pit_min *
1083 * Third section: lag delay = 2*pit_min-1 downto pit_min *
1084 *--------------------------------------------------------------------*/
1085
1086 /* mode dependent scaling in Lag_max */
1087
1088 if (mode == MR122)
1089 {
1090 scal_flag = 1;
1091 }
1092 else
1093 {
1094 scal_flag = 0;
1095 }
1096
1097 #ifdef VAD2
1098 L_temp = ((Word32)pit_min) << 2;
1099 if (L_temp != (Word32)((Word16) L_temp))
1100 {
1101 *pOverflow = 1;
1102 j = (pit_min > 0) ? MAX_16 : MIN_16;
1103 }
1104 else
1105 {
1106 j = (Word16)L_temp;
1107 }
1108
1109 p_max1 = Lag_max(corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
1110 pit_max, j, &max1, &rmax1, &r01, dtx, pOverflow);
1111
1112 i = j - 1;
1113
1114 j = pit_min << 1;
1115
1116 p_max2 = Lag_max(corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
1117 i, j, &max2, &rmax2, &r02, dtx, pOverflow);
1118
1119 i = j - 1;
1120
1121 p_max3 = Lag_max(corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
1122 i, pit_min, &max3, &rmax3, &r03, dtx, pOverflow);
1123
1124 #else
1125 L_temp = ((Word32)pit_min) << 2;
1126 if (L_temp != (Word32)((Word16) L_temp))
1127 {
1128 *pOverflow = 1;
1129 j = (pit_min > 0) ? MAX_16 : MIN_16;
1130 }
1131 else
1132 {
1133 j = (Word16)L_temp;
1134 }
1135
1136 p_max1 = Lag_max(vadSt, corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
1137 pit_max, j, &max1, dtx, pOverflow);
1138
1139 i = j - 1;
1140
1141
1142 j = pit_min << 1;
1143
1144
1145 p_max2 = Lag_max(vadSt, corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
1146 i, j, &max2, dtx, pOverflow);
1147
1148 i = j - 1;
1149 p_max3 = Lag_max(vadSt, corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,
1150 i, pit_min, &max3, dtx, pOverflow);
1151
1152 if (dtx)
1153 { /* no test() call since this if is only in simulation env */
1154
1155 if (idx == 1)
1156 {
1157 /* calculate max high-passed filtered correlation of all lags */
1158 hp_max(corr_ptr, scal_sig, L_frame, pit_max, pit_min, &corr_hp_max,
1159 pOverflow);
1160
1161 /* update complex background detector */
1162 vad_complex_detection_update(vadSt, corr_hp_max);
1163 }
1164 }
1165 #endif
1166
1167 /*--------------------------------------------------------------------*
1168 * Compare the 3 sections maximum, and favor small lag. *
1169 *--------------------------------------------------------------------*/
1170
1171 i = mult(max1, THRESHOLD, pOverflow);
1172
1173 if (i < max2)
1174 {
1175 max1 = max2;
1176 p_max1 = p_max2;
1177
1178 #ifdef VAD2
1179 if (dtx)
1180 {
1181 rmax1 = rmax2;
1182 r01 = r02;
1183 }
1184 #endif
1185 }
1186
1187 i = mult(max1, THRESHOLD, pOverflow);
1188
1189 if (i < max3)
1190 {
1191 p_max1 = p_max3;
1192
1193 #ifdef VAD2
1194 if (dtx)
1195 {
1196 rmax1 = rmax3;
1197 r01 = r03;
1198 }
1199 #endif
1200 }
1201
1202 #ifdef VAD2
1203 if (dtx)
1204 {
1205 /* Save max correlation */
1206 vadSt->L_Rmax = L_add(vadSt->L_Rmax, rmax1, pOverflow);
1207 /* Save max energy */
1208 vadSt->L_R0 = L_add(vadSt->L_R0, r01, pOverflow);
1209 }
1210 #endif
1211
1212 return (p_max1);
1213 }
1214