Git init
[external/opencore-amr.git] / opencore / codecs_v2 / audio / gsm_amr / amr_nb / common / src / vad2.cpp
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  Filename: vad2.cpp
31  Functions:
32
33 ------------------------------------------------------------------------------
34  MODULE DESCRIPTION
35
36
37 ------------------------------------------------------------------------------
38 */
39
40 /*----------------------------------------------------------------------------
41 ; INCLUDES
42 ----------------------------------------------------------------------------*/
43 #include "typedef.h"
44 #include "cnst.h"
45 #include "log2.h"
46 #include "pow2.h"
47 #include "sub.h"
48 #include "l_shr_r.h"
49 #include "abs_s.h"
50 #include "norm_s.h"
51 #include "shl.h"
52 #include "l_add.h"
53 #include "shr_r.h"
54 #include "add.h"
55 #include "mult.h"
56 #include "l_shr.h"
57 #include "mpy_32_16.h"
58 #include "l_mac.h"
59 #include "l_extract.h"
60 #include "l_sub.h"
61 #include "l_mult.h"
62 #include "round.h"
63 #include "shr.h"
64 #include "l_shl.h"
65 #include "mult_r.h"
66 #include "div_s.h"
67 #include "oscl_mem.h"
68
69
70 #include "vad2.h"
71
72 /*----------------------------------------------------------------------------
73 ; MACROS
74 ; Define module specific macros here
75 ----------------------------------------------------------------------------*/
76
77 /*----------------------------------------------------------------------------
78 ; DEFINES
79 ; Include all pre-processor statements here. Include conditional
80 ; compile variables also.
81 ----------------------------------------------------------------------------*/
82
83 /*----------------------------------------------------------------------------
84 ; LOCAL FUNCTION DEFINITIONS
85 ; Function Prototype declaration
86 ----------------------------------------------------------------------------*/
87
88 /*----------------------------------------------------------------------------
89 ; LOCAL VARIABLE DEFINITIONS
90 ; Variable declaration - defined here and used outside this module
91 ----------------------------------------------------------------------------*/
92
93 /*
94  * The channel table is defined below.  In this table, the
95  * lower and higher frequency coefficients for each of the 16
96  * channels are specified.  The table excludes the coefficients
97  * with numbers 0 (DC), 1, and 64 (Foldover frequency).
98  */
99
100 const Word16 ch_tbl[NUM_CHAN][2] =
101 {
102
103     {2, 3},
104     {4, 5},
105     {6, 7},
106     {8, 9},
107     {10, 11},
108     {12, 13},
109     {14, 16},
110     {17, 19},
111     {20, 22},
112     {23, 26},
113     {27, 30},
114     {31, 35},
115     {36, 41},
116     {42, 48},
117     {49, 55},
118     {56, 63}
119
120 };
121
122 /* channel energy scaling table - allows efficient division by number
123      * of DFT bins in the channel: 1/2, 1/3, 1/4, etc.
124  */
125
126 const Word16 ch_tbl_sh[NUM_CHAN] =
127 {
128     16384, 16384, 16384, 16384, 16384, 16384, 10923, 10923,
129     10923, 8192, 8192, 6554, 5461, 4681, 4681, 4096
130 };
131
132 /*
133  * The voice metric table is defined below.  It is a non-
134  * linear table with a deadband near zero.  It maps the SNR
135  * index (quantized SNR value) to a number that is a measure
136  * of voice quality.
137  */
138
139 const Word16 vm_tbl[90] =
140 {
141     2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
142     3, 3, 3, 3, 3, 4, 4, 4, 5, 5, 5, 6, 6, 7, 7, 7,
143     8, 8, 9, 9, 10, 10, 11, 12, 12, 13, 13, 14, 15,
144     15, 16, 17, 17, 18, 19, 20, 20, 21, 22, 23, 24,
145     24, 25, 26, 27, 28, 28, 29, 30, 31, 32, 33, 34,
146     35, 36, 37, 37, 38, 39, 40, 41, 42, 43, 44, 45,
147     46, 47, 48, 49, 50, 50, 50, 50, 50, 50, 50, 50,
148     50, 50
149 };
150
151 /* hangover as a function of peak SNR (3 dB steps) */
152 const Word16 hangover_table[20] =
153 {
154     30, 30, 30, 30, 30, 30, 28, 26, 24, 22, 20, 18, 16, 14, 12, 10, 8, 8, 8, 8
155 };
156
157 /* burst sensitivity as a function of peak SNR (3 dB steps) */
158 const Word16 burstcount_table[20] =
159 {
160     8, 8, 8, 8, 8, 8, 8, 8, 7, 6, 5, 4, 4, 4, 4, 4, 4, 4, 4, 4
161 };
162
163 /* voice metric sensitivity as a function of peak SNR (3 dB steps) */
164 const Word16 vm_threshold_table[20] =
165 {
166     34, 34, 34, 34, 34, 34, 34, 34, 34, 34,
167     34, 40, 51, 71, 100, 139, 191, 257, 337, 432
168 };
169
170 /*
171 ------------------------------------------------------------------------------
172  FUNCTION NAME: fn10Log10
173 ------------------------------------------------------------------------------
174  INPUT AND OUTPUT DEFINITIONS
175
176  Inputs:
177    L_Input -- Word32 -- (scaled as 31-fbits,fbits)
178    fbits   -- Word16 -- number of fractional bits on input
179
180  Outputs:
181    pOverflow -- pointer to type Flag -- overflow indicator
182
183  Returns:
184    output -- Word16 -- (scaled as 7,8)
185
186  Global Variables Used:
187     None
188
189  Local Variables Needed:
190     None
191
192 ------------------------------------------------------------------------------
193  FUNCTION DESCRIPTION
194
195  PURPOSE:
196    The purpose of this function is to take the 10*log base 10 of input and
197    divide by 128 and return; i.e. output = 10*log10(input)/128 (scaled as 7,8)
198
199  DESCRIPTION:
200
201    10*log10(x)/128 = 10*(log10(2) * (log2(x<<fbits)-log2(1<<fbits)) >> 7
202                    = 3.0103 * (log2(x<<fbits) - fbits) >> 7
203                    = ((3.0103/4.0 * (log2(x<<fbits) - fbits) << 2) >> 7
204                    = (3.0103/4.0 * (log2(x<<fbits) - fbits) >> 5
205
206 ------------------------------------------------------------------------------
207  REQUIREMENTS
208
209  None
210
211 ------------------------------------------------------------------------------
212  REFERENCES
213
214  vad2.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
215
216 ------------------------------------------------------------------------------
217  PSEUDO-CODE
218
219
220 ------------------------------------------------------------------------------
221  CAUTION [optional]
222  [State any special notes, constraints or cautions for users of this function]
223
224 ------------------------------------------------------------------------------
225 */
226
227 Word16 fn10Log10(Word32 L_Input, Word16 fbits, Flag *pOverflow)
228 {
229
230     Word16 integer;     /* Integer part of Log2.   (range: 0<=val<=30) */
231     Word16 fraction;    /* Fractional part of Log2. (range: 0<=val<1) */
232
233     Word32 Ltmp;
234     Word16 tmp;
235
236     Log2(L_Input, &integer, &fraction, pOverflow);
237
238     integer = sub(integer, fbits, pOverflow);
239
240     /* 24660 = 10*log10(2)/4 scaled 0,15 */
241     Ltmp = Mpy_32_16(integer, fraction, 24660, pOverflow);
242
243     /* extra shift for 30,1 => 15,0 extract correction */
244     Ltmp = L_shr_r(Ltmp, 5 + 1, pOverflow);
245
246     tmp = (Word16) Ltmp;
247
248     return (tmp);
249 }
250
251 /*
252 ------------------------------------------------------------------------------
253  FUNCTION NAME: block_norm
254 ------------------------------------------------------------------------------
255  INPUT AND OUTPUT DEFINITIONS
256
257  Inputs:
258     in -- array of type Word16 -- pointer to data sequence to be normalised
259     length -- Word16 -- number of elements in data sequence
260     headroom -- Word16 -- number of headroom bits
261
262  Outputs:
263     out -- array of type Word16 -- normalised output data sequence
264     pOverflow -- pointer to type Flag -- overflow indicator
265
266  Returns:
267     Word16 -- number of bits sequence was left shifted
268
269  Global Variables Used:
270     None
271
272  Local Variables Needed:
273     None
274
275 ------------------------------------------------------------------------------
276  FUNCTION DESCRIPTION
277
278  The purpose of this function is block normalise the input data sequence
279
280  1) Search for maximum absolute valued data element
281  2) Normalise the max element with "headroom"
282  3) Transfer/shift the input sequence to the output buffer
283  4) Return the number of left shifts
284
285 ------------------------------------------------------------------------------
286  REQUIREMENTS
287
288  None
289
290 ------------------------------------------------------------------------------
291  REFERENCES
292
293  vad2.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
294
295 ------------------------------------------------------------------------------
296  PSEUDO-CODE
297
298
299 ------------------------------------------------------------------------------
300  CAUTION
301
302      An input sequence of all zeros will return the maximum
303      number of left shifts allowed, NOT the value returned
304      by a norm_s(0) call, since it desired to associate an
305      all zeros sequence with low energy.
306 ------------------------------------------------------------------------------
307 */
308
309 Word16 block_norm(
310     Word16 * in,
311     Word16 * out,
312     Word16 length,
313     Word16 headroom,
314     Flag *pOverflow)
315 {
316
317     Word16 i;
318     Word16 max;
319     Word16 scnt;
320     Word16 adata;
321
322     max = abs_s(in[0]);
323
324     for (i = 1; i < length; i++)
325     {
326         adata = abs_s(in[i]);
327
328         if (adata > max)
329         {
330             max = adata;
331         }
332     }
333     if (max != 0)
334     {
335         scnt = sub(norm_s(max), headroom, pOverflow);
336         for (i = 0; i < length; i++)
337         {
338             out[i] = shl(in[i], scnt, pOverflow);
339         }
340     }
341     else
342     {
343         scnt = sub(16, headroom, pOverflow);
344         for (i = 0; i < length; i++)
345         {
346             out[i] = 0;
347         }
348     }
349     return (scnt);
350 }
351
352
353
354
355 /*
356 ------------------------------------------------------------------------------
357  FUNCTION NAME: vad2
358 ------------------------------------------------------------------------------
359  INPUT AND OUTPUT DEFINITIONS
360
361  Inputs:
362     farray_ptr -- array of type Word16, length 80 (input array)
363     vadState2 -- pointer to vadState2 state structure
364
365  Outputs:
366     vadState2 -- pointer to vadState2 state structure --
367                         state variables are updated
368    pOverflow -- pointer to type Flag -- overflow indicator
369
370  Returns:
371     Word16
372                  VAD(m) - two successive calls to vad2() yield
373                  the VAD decision for the 20 ms frame:
374                  VAD_flag = VAD(m-1) || VAD(m)
375
376  Global Variables Used:
377
378
379  Local Variables Needed:
380     None
381
382 ------------------------------------------------------------------------------
383  FUNCTION DESCRIPTION
384
385  This function provides the Voice Activity Detection function option 2
386  for the Adaptive Multi-rate (AMR) codec.
387
388 ------------------------------------------------------------------------------
389  REQUIREMENTS
390
391  None
392
393 ------------------------------------------------------------------------------
394  REFERENCES
395
396  vad2.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
397
398 ------------------------------------------------------------------------------
399  PSEUDO-CODE
400
401
402 ------------------------------------------------------------------------------
403  CAUTION [optional]
404  [State any special notes, constraints or cautions for users of this function]
405
406 ------------------------------------------------------------------------------
407 */
408
409 Word16 vad2(Word16 * farray_ptr, vadState2 * st, Flag *pOverflow)
410 {
411
412     /* State tables that use 22,9 or 27,4 scaling for ch_enrg[] */
413
414     const Word16 noise_floor_chan[2] = {NOISE_FLOOR_CHAN_0, NOISE_FLOOR_CHAN_1};
415     const Word16 min_chan_enrg[2] =    {MIN_CHAN_ENRG_0, MIN_CHAN_ENRG_1};
416     const Word16 ine_noise[2] =        {INE_NOISE_0, INE_NOISE_1};
417     const Word16 fbits[2] =        {FRACTIONAL_BITS_0, FRACTIONAL_BITS_1};
418     const Word16 state_change_shift_r[2] = {STATE_1_TO_0_SHIFT_R, STATE_0_TO_1_SHIFT_R};
419
420     /* Energy scale table given 30,1 input scaling (also account for -6 dB shift on input) */
421     const Word16 enrg_norm_shift[2] =  {(FRACTIONAL_BITS_0 - 1 + 2), (FRACTIONAL_BITS_1 - 1 + 2)};
422
423
424     /* Automatic variables */
425
426     Word32 Lenrg;               /* scaled as 30,1 */
427     Word32 Ltne;                /* scaled as 22,9 */
428     Word32 Ltce;                /* scaled as 22,9 or 27,4 */
429
430     Word16 tne_db;              /* scaled as 7,8 */
431     Word16 tce_db;              /* scaled as 7,8 */
432
433     Word16 input_buffer[FRM_LEN];       /* used for block normalising input data */
434     Word16 data_buffer[FFT_LEN];        /* used for in-place FFT */
435
436     Word16 ch_snr[NUM_CHAN];        /* scaled as 7,8 */
437     Word16 ch_snrq;             /* scaled as 15,0 (in 0.375 dB steps) */
438     Word16 vm_sum;              /* scaled as 15,0 */
439     Word16 ch_enrg_dev;         /* scaled as 7,8 */
440
441     Word32 Lpeak;               /* maximum channel energy */
442     Word16 p2a_flag;            /* flag to indicate spectral peak-to-average ratio > 10 dB */
443
444     Word16 ch_enrg_db[NUM_CHAN];        /* scaled as 7,8 */
445     Word16 ch_noise_db;         /* scaled as 7,8 */
446
447     Word16 alpha;               /* scaled as 0,15 */
448     Word16 one_m_alpha;         /* scaled as 0,15 */
449     Word16 update_flag;         /* set to indicate a background noise estimate update */
450
451     Word16 i;
452     Word16 j;
453     Word16 j1;
454     Word16 j2;            /* Scratch variables */
455
456     Word16 hi1;
457     Word16 lo1;
458
459     Word32 Ltmp;
460     Word32 Ltmp1;
461     Word32 Ltmp2;
462     Word16 tmp;
463
464     Word16 normb_shift;     /* block norm shift count */
465
466     Word16 ivad;            /* intermediate VAD decision (return value) */
467     Word16 tsnrq;           /* total signal-to-noise ratio (quantized 3 dB steps) scaled as 15,0 */
468     Word16 xt;          /* instantaneous frame SNR in dB, scaled as 7,8 */
469
470     Word16 state_change;
471
472
473     /* Increment frame counter */
474     st->Lframe_cnt = L_add(st->Lframe_cnt, 1, pOverflow);
475
476     /* Block normalize the input */
477     normb_shift = block_norm(farray_ptr, input_buffer, FRM_LEN, FFT_HEADROOM, pOverflow);
478
479     /* Pre-emphasize the input data and store in the data buffer with the appropriate offset */
480     for (i = 0; i < DELAY; i++)
481     {
482         data_buffer[i] = 0;
483     }
484
485     st->pre_emp_mem = shr_r(st->pre_emp_mem, sub(st->last_normb_shift, normb_shift, pOverflow), pOverflow);
486     st->last_normb_shift = normb_shift;
487
488     data_buffer[DELAY] = add(input_buffer[0], mult(PRE_EMP_FAC, st->pre_emp_mem, pOverflow), pOverflow);
489
490     for (i = DELAY + 1, j = 1; i < DELAY + FRM_LEN; i++, j++)
491     {
492         data_buffer[i] = add(input_buffer[j], mult(PRE_EMP_FAC, input_buffer[j-1], pOverflow), pOverflow);
493     }
494     st->pre_emp_mem = input_buffer[FRM_LEN-1];
495
496     for (i = DELAY + FRM_LEN; i < FFT_LEN; i++)
497     {
498         data_buffer[i] = 0;
499     }
500
501
502     /* Perform FFT on the data buffer */
503     r_fft(data_buffer, pOverflow);
504
505
506     /* Use normb_shift factor to determine the scaling of the energy estimates */
507     state_change = 0;
508     if (st->shift_state == 0)
509     {
510         if (normb_shift <= (-FFT_HEADROOM + 2))
511         {
512             state_change = 1;
513             st->shift_state = 1;
514         }
515     }
516     else
517     {
518         if (normb_shift >= (-FFT_HEADROOM + 5))
519         {
520             state_change = 1;
521             st->shift_state = 0;
522         }
523     }
524
525     /* Scale channel energy estimate */
526     if (state_change)
527     {
528         for (i = LO_CHAN; i <= HI_CHAN; i++)
529         {
530             st->Lch_enrg[i] =
531                 L_shr(
532                     st->Lch_enrg[i],
533                     state_change_shift_r[st->shift_state],
534                     pOverflow);
535         }
536     }
537
538
539     /* Estimate the energy in each channel */
540     if (st->Lframe_cnt == 1)
541     {
542         alpha = 32767;
543         one_m_alpha = 0;
544     }
545     else
546     {
547         alpha = CEE_SM_FAC;
548         one_m_alpha = ONE_MINUS_CEE_SM_FAC;
549     }
550
551     for (i = LO_CHAN; i <= HI_CHAN; i++)
552     {
553         Lenrg = 0;
554         j1 = ch_tbl[i][0];
555         j2 = ch_tbl[i][1];
556
557         for (j = j1; j <= j2; j++)
558         {
559             Lenrg = L_mac(
560                         Lenrg,
561                         data_buffer[2 * j],
562                         data_buffer[2 * j],
563                         pOverflow);
564
565             Lenrg = L_mac(
566                         Lenrg,
567                         data_buffer[2 * j + 1],
568                         data_buffer[2 * j + 1],
569                         pOverflow);
570         }
571
572         /* Denorm energy & scale 30,1 according to the state */
573         tmp = shl(normb_shift, 1, pOverflow);
574         tmp = sub(tmp, enrg_norm_shift[st->shift_state], pOverflow);
575         Lenrg = L_shr_r(Lenrg, tmp, pOverflow);
576
577         /* integrate over time:
578          * e[i] = (1-alpha)*e[i] + alpha*enrg/num_bins_in_chan
579          */
580         tmp = mult(alpha, ch_tbl_sh[i], pOverflow);
581         L_Extract(Lenrg, &hi1, &lo1, pOverflow);
582         Ltmp = Mpy_32_16(hi1, lo1, tmp, pOverflow);
583
584         L_Extract(st->Lch_enrg[i], &hi1, &lo1, pOverflow);
585
586         Ltmp1 = Mpy_32_16(hi1, lo1, one_m_alpha, pOverflow);
587         st->Lch_enrg[i] = L_add(Ltmp, Ltmp1, pOverflow);
588
589         if (st->Lch_enrg[i] < min_chan_enrg[st->shift_state])
590         {
591             st->Lch_enrg[i] = min_chan_enrg[st->shift_state];
592         }
593
594     }
595
596
597     /* Compute the total channel energy estimate (Ltce) */
598     Ltce = 0;
599     for (i = LO_CHAN; i <= HI_CHAN; i++)
600     {
601         Ltce =
602             L_add(
603                 Ltce,
604                 st->Lch_enrg[i],
605                 pOverflow);
606     }
607
608
609     /* Calculate spectral peak-to-average ratio, set flag if p2a > 10 dB */
610     Lpeak = 0;
611
612     /* Sine waves not valid for low frequencies */
613     for (i = LO_CHAN + 2; i <= HI_CHAN; i++)
614     {
615         if (L_sub(st->Lch_enrg [i], Lpeak, pOverflow) > 0)
616         {
617             Lpeak = st->Lch_enrg [i];
618         }
619     }
620
621     /* Set p2a_flag if peak (dB) > average channel energy (dB) + 10 dB */
622     /*   Lpeak > Ltce/num_channels * 10^(10/10)                        */
623     /*   Lpeak > (10/16)*Ltce                                          */
624
625     L_Extract(Ltce, &hi1, &lo1, pOverflow);
626     Ltmp = Mpy_32_16(hi1, lo1, 20480, pOverflow);
627     if (L_sub(Lpeak, Ltmp, pOverflow) > 0)
628     {
629         p2a_flag = TRUE;
630     }
631     else
632     {
633         p2a_flag = FALSE;
634     }
635
636
637     /* Initialize channel noise estimate to either the channel energy or fixed level  */
638     /*   Scale the energy appropriately to yield state 0 (22,9) scaling for noise */
639     if (st->Lframe_cnt <= 4)
640     {
641         if (p2a_flag == TRUE)
642         {
643             for (i = LO_CHAN; i <= HI_CHAN; i++)
644             {
645                 st->Lch_noise[i] = INE_NOISE_0;
646             }
647         }
648         else
649         {
650             for (i = LO_CHAN; i <= HI_CHAN; i++)
651             {
652                 if (st->Lch_enrg[i] < ine_noise[st->shift_state])
653                 {
654                     st->Lch_noise[i] = INE_NOISE_0;
655                 }
656                 else
657                 {
658                     if (st->shift_state == 1)
659                     {
660                         st->Lch_noise[i] =
661                             L_shr(
662                                 st->Lch_enrg[i],
663                                 state_change_shift_r[0],
664                                 pOverflow);
665                     }
666                     else
667                     {
668                         st->Lch_noise[i] = st->Lch_enrg[i];
669                     }
670                 }
671             }
672         }
673     }
674
675
676     /* Compute the channel energy (in dB), the channel SNRs, and the sum of voice metrics */
677     vm_sum = 0;
678     for (i = LO_CHAN; i <= HI_CHAN; i++)
679     {
680         ch_enrg_db[i] =
681             fn10Log10(
682                 st->Lch_enrg[i],
683                 fbits[st->shift_state],
684                 pOverflow);
685
686         ch_noise_db =
687             fn10Log10(
688                 st->Lch_noise[i],
689                 FRACTIONAL_BITS_0,
690                 pOverflow);
691
692         ch_snr[i] = sub(ch_enrg_db[i], ch_noise_db, pOverflow);
693
694         /* quantize channel SNR in 3/8 dB steps (scaled 7,8 => 15,0) */
695         /*   ch_snr = pv_round((snr/(3/8))>>8)                          */
696         /*          = pv_round(((0.6667*snr)<<2)>>8)                    */
697         /*          = pv_round((0.6667*snr)>>6)                         */
698
699         tmp = mult(21845, ch_snr[i], pOverflow);
700
701         ch_snrq = shr_r(tmp, 6, pOverflow);
702
703         /* Accumulate the sum of voice metrics  */
704         if (ch_snrq < 89)
705         {
706             if (ch_snrq > 0)
707             {
708                 j = ch_snrq;
709             }
710             else
711             {
712                 j = 0;
713             }
714         }
715         else
716         {
717             j = 89;
718         }
719         vm_sum = add(vm_sum, vm_tbl[j], pOverflow);
720     }
721
722
723     /* Initialize NOMINAL peak voice energy and average noise energy, calculate instantaneous SNR */
724     if (st->Lframe_cnt <= 4 || st->fupdate_flag == TRUE)
725     {
726         /* tce_db = (96 - 22 - 10*log10(64) (due to FFT)) scaled as 7,8 */
727         tce_db = 14320;
728         st->negSNRvar = 0;
729         st->negSNRbias = 0;
730
731         /* Compute the total noise estimate (Ltne) */
732         Ltne = 0;
733         for (i = LO_CHAN; i <= HI_CHAN; i++)
734         {
735             Ltne = L_add(Ltne, st->Lch_noise[i], pOverflow);
736         }
737
738         /* Get total noise in dB */
739         tne_db =
740             fn10Log10(
741                 Ltne,
742                 FRACTIONAL_BITS_0,
743                 pOverflow);
744
745         /* Initialise instantaneous and long-term peak signal-to-noise ratios */
746         xt = sub(tce_db, tne_db, pOverflow);
747         st->tsnr = xt;
748     }
749     else
750     {
751         /* Calculate instantaneous frame signal-to-noise ratio */
752         /* xt = 10*log10( sum(2.^(ch_snr*0.1*log2(10)))/length(ch_snr) ) */
753         Ltmp1 = 0;
754         for (i = LO_CHAN; i <= HI_CHAN; i++)
755         {
756             /* Ltmp2 = ch_snr[i] * 0.1 * log2(10); (ch_snr scaled as 7,8) */
757             Ltmp2 = L_mult(ch_snr[i], 10885, pOverflow);
758             Ltmp2 = L_shr(Ltmp2, 8, pOverflow);
759
760             L_Extract(Ltmp2, &hi1, &lo1, pOverflow);
761             hi1 = add(hi1, 3, pOverflow);  /* 2^3 to compensate for negative SNR */
762
763             Ltmp2 = Pow2(hi1, lo1, pOverflow);
764
765             Ltmp1 = L_add(Ltmp1, Ltmp2, pOverflow);
766         }
767         xt =
768             fn10Log10(
769                 Ltmp1,
770                 4 + 3,
771                 pOverflow);     /* average by 16, inverse compensation 2^3 */
772
773         /* Estimate long-term "peak" SNR */
774         if (xt > st->tsnr)
775         {
776             Ltmp1 = L_mult(29491, st->tsnr, pOverflow);
777             Ltmp2 = L_mult(3277, xt, pOverflow);
778             Ltmp1 = L_add(Ltmp1, Ltmp2, pOverflow);
779
780             /* tsnr = 0.9*tsnr + 0.1*xt; */
781             st->tsnr = pv_round(Ltmp1, pOverflow);
782         }
783         /* else if (xt > 0.625*tsnr) */
784         else
785         {
786             tmp = mult(20480, st->tsnr, pOverflow);
787             tmp = sub(xt, tmp, pOverflow);
788
789             if (tmp > 0)
790             {
791                 /* tsnr = 0.998*tsnr + 0.002*xt; */
792                 Ltmp1 = L_mult(32702, st->tsnr, pOverflow);
793                 Ltmp2 = L_mult(66, xt, pOverflow);
794                 Ltmp1 = L_add(Ltmp1, Ltmp2, pOverflow);
795
796                 st->tsnr = pv_round(Ltmp1, pOverflow);
797             }
798         }
799     }
800
801     /* Quantize the long-term SNR in 3 dB steps, limit to 0 <= tsnrq <= 19 */
802     tmp = mult(st->tsnr, 10923, pOverflow);
803     tsnrq = shr(tmp, 8, pOverflow);
804
805     /* tsnrq = min(19, max(0, tsnrq)); */
806     if (tsnrq > 19)
807     {
808         tsnrq = 19;
809     }
810     else if (tsnrq < 0)
811     {
812         tsnrq = 0;
813     }
814
815     /* Calculate the negative SNR sensitivity bias */
816     if (xt < 0)
817     {
818         /* negSNRvar = 0.99*negSNRvar + 0.01*xt*xt; */
819         /*   xt scaled as 7,8 => xt*xt scaled as 14,17, shift to 7,8 and round */
820         Ltmp1 = L_mult(xt, xt, pOverflow);
821         Ltmp1 = L_shl(Ltmp1, 7, pOverflow);
822         tmp = pv_round(Ltmp1, pOverflow);
823
824         Ltmp1 = L_mult(32440, st->negSNRvar, pOverflow);
825         Ltmp2 = L_mult(328, tmp, pOverflow);
826         Ltmp1 = L_add(Ltmp1, Ltmp2, pOverflow);
827
828         st->negSNRvar = pv_round(Ltmp1, pOverflow);
829
830         /* if (negSNRvar > 4.0) negSNRvar = 4.0;  */
831         if (st->negSNRvar > 1024)
832         {
833             st->negSNRvar = 1024;
834         }
835
836         /* negSNRbias = max(12.0*(negSNRvar - 0.65), 0.0); */
837         tmp = sub(st->negSNRvar, 166, pOverflow);
838         tmp = shl(tmp, 4, pOverflow);
839         tmp = mult_r(tmp, 24576, pOverflow);
840
841         if (tmp < 0)
842         {
843             st->negSNRbias = 0;
844         }
845         else
846         {
847             st->negSNRbias = shr(tmp, 8, pOverflow);
848         }
849     }
850
851
852     /* Determine VAD as a function of the voice metric sum and quantized SNR */
853
854     tmp = add(vm_threshold_table[tsnrq], st->negSNRbias, pOverflow);
855
856     if (vm_sum > tmp)
857     {
858         ivad = 1;
859         st->burstcount = add(st->burstcount, 1, pOverflow);
860         if (st->burstcount > burstcount_table[tsnrq])
861         {
862             st->hangover = hangover_table[tsnrq];
863         }
864     }
865     else
866     {
867         st->burstcount = 0;
868         st->hangover = sub(st->hangover, 1, pOverflow);
869         if (st->hangover <= 0)
870         {
871             ivad = 0;
872             st->hangover = 0;
873         }
874         else
875         {
876             ivad = 1;
877         }
878     }
879
880
881     /* Calculate log spectral deviation */
882     ch_enrg_dev = 0;
883     if (st->Lframe_cnt == 1)
884     {
885         for (i = LO_CHAN; i <= HI_CHAN; i++)
886         {
887             st->ch_enrg_long_db[i] = ch_enrg_db[i];
888         }
889     }
890     else
891     {
892         for (i = LO_CHAN; i <= HI_CHAN; i++)
893         {
894             tmp = sub(st->ch_enrg_long_db[i], ch_enrg_db[i], pOverflow);
895             tmp = abs_s(tmp);
896
897             ch_enrg_dev = add(ch_enrg_dev, tmp, pOverflow);
898         }
899     }
900
901     /*
902      * Calculate long term integration constant as
903      * a function of instantaneous SNR
904      * (i.e., high SNR (tsnr dB) -> slower integration (alpha = HIGH_ALPHA),
905      *         low SNR (0 dB) -> faster integration (alpha = LOW_ALPHA)
906      */
907
908     /* alpha = HIGH_ALPHA - ALPHA_RANGE * (tsnr - xt)
909      * ----------------------------------------------
910      *         tsnr, low <= alpha <= high
911      */
912     tmp = sub(st->tsnr, xt, pOverflow);
913     if (tmp <= 0 || st->tsnr <= 0)
914     {
915         alpha = HIGH_ALPHA;
916         one_m_alpha = 32768L - HIGH_ALPHA;
917     }
918     else if (tmp > st->tsnr)
919     {
920         alpha = LOW_ALPHA;
921         one_m_alpha = 32768L - LOW_ALPHA;
922     }
923     else
924     {
925         tmp = div_s(tmp, st->tsnr);
926         tmp = mult(ALPHA_RANGE, tmp, pOverflow);
927         alpha = sub(HIGH_ALPHA, tmp, pOverflow);
928         one_m_alpha = sub(32767, alpha, pOverflow);
929     }
930
931     /* Calc long term log spectral energy */
932     for (i = LO_CHAN; i <= HI_CHAN; i++)
933     {
934         Ltmp1 = L_mult(one_m_alpha, ch_enrg_db[i], pOverflow);
935         Ltmp2 = L_mult(alpha, st->ch_enrg_long_db[i], pOverflow);
936
937         Ltmp1 = L_add(Ltmp1, Ltmp2, pOverflow);
938         st->ch_enrg_long_db[i] = pv_round(Ltmp1, pOverflow);
939     }
940
941
942     /* Set or clear the noise update flags */
943     update_flag = FALSE;
944     st->fupdate_flag = FALSE;
945     if (vm_sum <= UPDATE_THLD)
946     {
947         if (st->burstcount == 0)
948         {
949             update_flag = TRUE;
950             st->update_cnt = 0;
951         }
952     }
953     else if (L_sub(Ltce, noise_floor_chan[st->shift_state], pOverflow) > 0)
954     {
955         if (ch_enrg_dev < DEV_THLD)
956         {
957             if (p2a_flag == FALSE)
958             {
959                 if (st->LTP_flag == FALSE)
960                 {
961                     st->update_cnt = add(st->update_cnt, 1, pOverflow);
962                     if (st->update_cnt >= UPDATE_CNT_THLD)
963                     {
964                         update_flag = TRUE;
965                         st->fupdate_flag = TRUE;
966                     }
967                 }
968             }
969         }
970     }
971     if (st->update_cnt == st->last_update_cnt)
972     {
973         st->hyster_cnt = add(st->hyster_cnt, 1, pOverflow);
974     }
975     else
976     {
977         st->hyster_cnt = 0;
978     }
979
980     st->last_update_cnt = st->update_cnt;
981
982     if (st->hyster_cnt > HYSTER_CNT_THLD)
983     {
984         st->update_cnt = 0;
985     }
986
987
988     /* Conditionally update the channel noise estimates */
989     if (update_flag == TRUE)
990     {
991         /* Check shift state */
992         if (st->shift_state == 1)
993         {
994             /* get factor to shift ch_enrg[]
995              * from state 1 to 0 (noise always state 0)
996              */
997             tmp = state_change_shift_r[0];
998         }
999         else
1000         {
1001             /* No shift if already state 0 */
1002             tmp = 0;
1003         }
1004
1005         /* Update noise energy estimate */
1006         for (i = LO_CHAN; i <= HI_CHAN; i++)
1007         {
1008             /* integrate over time: en[i] = (1-alpha)*en[i] + alpha*e[n] */
1009             /* (extract with shift compensation for state 1) */
1010
1011             Ltmp1 = L_shr(st->Lch_enrg[i], tmp, pOverflow);
1012             L_Extract(Ltmp1, &hi1, &lo1, pOverflow);
1013
1014             Ltmp = Mpy_32_16(hi1, lo1, CNE_SM_FAC, pOverflow);
1015
1016             L_Extract(st->Lch_noise[i], &hi1, &lo1, pOverflow);
1017
1018             Ltmp1 = Mpy_32_16(hi1, lo1, ONE_MINUS_CNE_SM_FAC, pOverflow);
1019             st->Lch_noise[i] = L_add(Ltmp, Ltmp1, pOverflow);
1020
1021             /* Limit low level noise */
1022             if (st->Lch_noise[i] <= MIN_NOISE_ENRG_0)
1023             {
1024                 st->Lch_noise[i] = MIN_NOISE_ENRG_0;
1025             }
1026         }
1027     }
1028
1029     return(ivad);
1030 }                               /* end of vad2 () */
1031
1032
1033 /*
1034 ------------------------------------------------------------------------------
1035  FUNCTION NAME: vad2_init
1036 ------------------------------------------------------------------------------
1037  INPUT AND OUTPUT DEFINITIONS
1038
1039  Inputs:
1040     state -- double pointer to type vadState2 -- pointer to memory to
1041                                                  be initialized.
1042
1043  Outputs:
1044     state -- points to initalized area in memory.
1045
1046  Returns:
1047     None
1048
1049  Global Variables Used:
1050     None
1051
1052  Local Variables Needed:
1053     None
1054
1055 ------------------------------------------------------------------------------
1056  FUNCTION DESCRIPTION
1057
1058  Allocates state memory and initializes state memory
1059
1060 ------------------------------------------------------------------------------
1061  REQUIREMENTS
1062
1063  None
1064
1065 ------------------------------------------------------------------------------
1066  REFERENCES
1067
1068  vad2.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
1069
1070 ------------------------------------------------------------------------------
1071  PSEUDO-CODE
1072
1073
1074 ------------------------------------------------------------------------------
1075  CAUTION [optional]
1076  [State any special notes, constraints or cautions for users of this function]
1077
1078 ------------------------------------------------------------------------------
1079 */
1080 Word16 vad2_init(vadState2 **state)
1081 {
1082     vadState2* s;
1083
1084     if (state == (vadState2 **) NULL)
1085     {
1086         return -1;
1087     }
1088     *state = NULL;
1089
1090     /* allocate memory */
1091     if ((s = (vadState2 *) oscl_malloc(sizeof(vadState2))) == NULL)
1092     {
1093         return -1;
1094     }
1095
1096     vad2_reset(s);
1097
1098     *state = s;
1099
1100     return 0;
1101 }
1102
1103
1104 /*
1105 ------------------------------------------------------------------------------
1106  FUNCTION NAME: vad2_reset
1107 ------------------------------------------------------------------------------
1108  INPUT AND OUTPUT DEFINITIONS
1109
1110  Inputs:
1111     state -- pointer to type vadState1 --  State struct
1112
1113  Outputs:
1114     state -- pointer to type vadState1 --  State struct
1115
1116  Returns:
1117     None
1118
1119  Global Variables Used:
1120     None
1121
1122  Local Variables Needed:
1123     None
1124
1125 ------------------------------------------------------------------------------
1126  FUNCTION DESCRIPTION
1127
1128  Purpose:    Resets state memory to zero
1129
1130 ------------------------------------------------------------------------------
1131  REQUIREMENTS
1132
1133  None
1134
1135 ------------------------------------------------------------------------------
1136  REFERENCES
1137
1138  vad2.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
1139
1140 ------------------------------------------------------------------------------
1141  PSEUDO-CODE
1142
1143
1144 ------------------------------------------------------------------------------
1145  CAUTION [optional]
1146  [State any special notes, constraints or cautions for users of this function]
1147
1148 ------------------------------------------------------------------------------
1149 */
1150
1151 Word16 vad2_reset(vadState2 * st)
1152 {
1153     Word16  i;
1154     Word16  *ptr;
1155
1156     if (st == (vadState2 *) NULL)
1157     {
1158         return -1;
1159     }
1160     ptr = (Word16 *)st;
1161
1162     for (i = 0; i < sizeof(vadState2) / 2; i++)
1163     {
1164         *ptr++ = 0;
1165     }
1166
1167     return 0;
1168 }                       /* end of vad2_reset () */
1169
1170
1171 /*
1172 ------------------------------------------------------------------------------
1173  FUNCTION NAME: vad2_exit
1174 ------------------------------------------------------------------------------
1175  INPUT AND OUTPUT DEFINITIONS
1176
1177  Inputs:
1178     state -- pointer to type vadState1 --  State struct
1179
1180  Outputs:
1181     None
1182
1183  Returns:
1184     None
1185
1186  Global Variables Used:
1187     None
1188
1189  Local Variables Needed:
1190     None
1191
1192 ------------------------------------------------------------------------------
1193  FUNCTION DESCRIPTION
1194
1195     The memory used for state memory is freed
1196
1197 ------------------------------------------------------------------------------
1198  REQUIREMENTS
1199
1200  None
1201
1202 ------------------------------------------------------------------------------
1203  REFERENCES
1204
1205  vad2.c, UMTS GSM AMR speech codec, R99 - Version 3.2.0, March 2, 2001
1206
1207 ------------------------------------------------------------------------------
1208  PSEUDO-CODE
1209
1210
1211 ------------------------------------------------------------------------------
1212  CAUTION [optional]
1213  [State any special notes, constraints or cautions for users of this function]
1214
1215 ------------------------------------------------------------------------------
1216 */
1217
1218 void vad2_exit(vadState2 **state)
1219 {
1220     if (state == NULL || *state == NULL)
1221     {
1222         return;
1223     }
1224
1225     /* deallocate memory */
1226     oscl_free(*state);
1227     *state = NULL;
1228
1229     return;
1230 }
1231