1/*
2 ** Copyright 2003-2010, VisualOn, Inc.
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 express or implied.
13 ** See the License for the specific language governing permissions and
14 ** limitations under the License.
15 */
16
17
18/***********************************************************************
19*       File: autocorr.c                                               *
20*                                                                      *
21*       Description:Compute autocorrelations of signal with windowing  *
22*                                                                      *
23************************************************************************/
24
25#include "typedef.h"
26#include "basic_op.h"
27#include "oper_32b.h"
28#include "acelp.h"
29#include "ham_wind.tab"
30
31#define UNUSED(x) (void)(x)
32
33void Autocorr(
34		Word16 x[],                           /* (i)    : Input signal                      */
35		Word16 m,                             /* (i)    : LPC order                         */
36		Word16 r_h[],                         /* (o) Q15: Autocorrelations  (msb)           */
37		Word16 r_l[]                          /* (o)    : Autocorrelations  (lsb)           */
38	     )
39{
40	Word32 i, norm, shift;
41	Word16 y[L_WINDOW];
42	Word32 L_sum, L_sum1, L_tmp, F_LEN;
43	Word16 *p1,*p2,*p3;
44	const Word16 *p4;
45        UNUSED(m);
46
47	/* Windowing of signal */
48	p1 = x;
49	p4 = vo_window;
50	p3 = y;
51
52	for (i = 0; i < L_WINDOW; i+=4)
53	{
54		*p3++ = vo_mult_r((*p1++), (*p4++));
55		*p3++ = vo_mult_r((*p1++), (*p4++));
56		*p3++ = vo_mult_r((*p1++), (*p4++));
57		*p3++ = vo_mult_r((*p1++), (*p4++));
58	}
59
60	/* calculate energy of signal */
61	L_sum = vo_L_deposit_h(16);               /* sqrt(256), avoid overflow after rounding */
62	for (i = 0; i < L_WINDOW; i++)
63	{
64		L_tmp = vo_L_mult(y[i], y[i]);
65		L_tmp = (L_tmp >> 8);
66		L_sum += L_tmp;
67	}
68
69	/* scale signal to avoid overflow in autocorrelation */
70	norm = norm_l(L_sum);
71	shift = 4 - (norm >> 1);
72	if(shift > 0)
73	{
74		p1 = y;
75		for (i = 0; i < L_WINDOW; i+=4)
76		{
77			*p1 = vo_shr_r(*p1, shift);
78			p1++;
79			*p1 = vo_shr_r(*p1, shift);
80			p1++;
81			*p1 = vo_shr_r(*p1, shift);
82			p1++;
83			*p1 = vo_shr_r(*p1, shift);
84			p1++;
85		}
86	}
87
88	/* Compute and normalize r[0] */
89	L_sum = 1;
90	for (i = 0; i < L_WINDOW; i+=4)
91	{
92		L_sum += vo_L_mult(y[i], y[i]);
93		L_sum += vo_L_mult(y[i+1], y[i+1]);
94		L_sum += vo_L_mult(y[i+2], y[i+2]);
95		L_sum += vo_L_mult(y[i+3], y[i+3]);
96	}
97
98	norm = norm_l(L_sum);
99	L_sum = (L_sum << norm);
100
101	r_h[0] = L_sum >> 16;
102	r_l[0] = (L_sum & 0xffff)>>1;
103
104	/* Compute r[1] to r[m] */
105	for (i = 1; i <= 8; i++)
106	{
107		L_sum1 = 0;
108		L_sum = 0;
109		F_LEN = (Word32)(L_WINDOW - 2*i);
110		p1 = y;
111		p2 = y + (2*i)-1;
112		do{
113			L_sum1 += *p1 * *p2++;
114			L_sum += *p1++ * *p2;
115		}while(--F_LEN!=0);
116
117		L_sum1 += *p1 * *p2++;
118
119		L_sum1 = L_sum1<<norm;
120		L_sum = L_sum<<norm;
121
122		r_h[(2*i)-1] = L_sum1 >> 15;
123		r_l[(2*i)-1] = L_sum1 & 0x00007fff;
124		r_h[(2*i)] = L_sum >> 15;
125		r_l[(2*i)] = L_sum & 0x00007fff;
126	}
127	return;
128}
129
130
131
132