Varlength arrays fix for C89
[opus.git] / libcelt / plc.c
1
2
3
4
5 celt_word32 _celt_lpc(
6 celt_word16       *lpc, /* out: [0...p-1] LPC coefficients      */
7 const celt_word16 *ac,  /* in:  [0...p] autocorrelation values  */
8 int          p
9 )
10 {
11    int i, j;  
12    celt_word16 r;
13    celt_word16 error = ac[0];
14
15    if (ac[0] == 0)
16    {
17       for (i = 0; i < p; i++)
18          lpc[i] = 0;
19       return 0;
20    }
21    
22    for (i = 0; i < p; i++) {
23       
24       /* Sum up this iteration's reflection coefficient */
25       celt_word32 rr = NEG32(SHL32(EXTEND32(ac[i + 1]),13));
26       for (j = 0; j < i; j++) 
27          rr = SUB32(rr,MULT16_16(lpc[j],ac[i - j]));
28 #ifdef FIXED_POINT
29       r = DIV32_16(rr+PSHR32(error,1),ADD16(error,8));
30 #else
31       r = rr/(error+.003*ac[0]);
32 #endif
33       /*  Update LPC coefficients and total error */
34       lpc[i] = r;
35       for (j = 0; j < i>>1; j++) 
36       {
37          celt_word16 tmp  = lpc[j];
38          lpc[j]     = MAC16_16_P13(lpc[j],r,lpc[i-1-j]);
39          lpc[i-1-j] = MAC16_16_P13(lpc[i-1-j],r,tmp);
40       }
41       if (i & 1) 
42          lpc[j] = MAC16_16_P13(lpc[j],lpc[j],r);
43       
44       error = SUB16(error,MULT16_16_Q13(r,MULT16_16_Q13(error,r)));
45    }
46    return error;
47 }
48
49 void fir(const celt_word16 *x,
50          const celt_word16 *num,
51          celt_word16 *y,
52          int N,
53          int ord,
54          celt_word32 *mem)
55 {
56    int i,j;
57
58    for (i=0;i<N;i++)
59    {
60       float sum = x[i];
61       for (j=0;j<ord;j++)
62       {
63          sum += num[j]*mem[j];
64       }
65       for (j=ord-1;j>=1;j--)
66       {
67          mem[j]=mem[j-1];
68       }
69       mem[0] = x[i];
70       y[i] = sum;
71    }
72 }
73
74 void iir(const celt_word16 *x,
75          const celt_word16 *den,
76          celt_word16 *y,
77          int N,
78          int ord,
79          celt_word32 *mem)
80 {
81    int i,j;
82    for (i=0;i<N;i++)
83    {
84       float sum = x[i];
85       for (j=0;j<ord;j++)
86       {
87          sum -= den[j]*mem[j];
88       }
89       for (j=ord-1;j>=1;j--)
90       {
91          mem[j]=mem[j-1];
92       }
93       mem[0] = sum;
94       y[i] = sum;
95    }
96 }
97
98 void _celt_autocorr(
99                    const celt_word16 *x,   /*  in: [0...n-1] samples x   */
100                    float       *ac,  /* out: [0...lag-1] ac values */
101                    const float       *window,
102                    int          overlap,
103                    int          lag, 
104                    int          n
105                   )
106 {
107    float d;
108    int i;
109    VARDECL(float, xx);
110    SAVE_STACK;
111    ALLOC(xx, n, float);
112    for (i=0;i<n;i++)
113       xx[i] = x[i];
114    for (i=0;i<overlap;i++)
115    {
116       xx[i] *= window[i];
117       xx[n-i-1] *= window[i];
118    }
119    while (lag>=0)
120    {
121       for (i = lag, d = 0; i < n; i++) 
122          d += x[i] * x[i-lag];
123       ac[lag] = d;
124       lag--;
125    }
126    ac[0] += 10;
127    RESTORE_STACK;
128 }