Coverage Report

Created: 2026-07-10 06:54

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/speex/libspeex/ltp.c
Line
Count
Source
1
/* Copyright (C) 2002-2006 Jean-Marc Valin
2
   File: ltp.c
3
   Long-Term Prediction functions
4
5
   Redistribution and use in source and binary forms, with or without
6
   modification, are permitted provided that the following conditions
7
   are met:
8
9
   - Redistributions of source code must retain the above copyright
10
   notice, this list of conditions and the following disclaimer.
11
12
   - Redistributions in binary form must reproduce the above copyright
13
   notice, this list of conditions and the following disclaimer in the
14
   documentation and/or other materials provided with the distribution.
15
16
   - Neither the name of the Xiph.org Foundation nor the names of its
17
   contributors may be used to endorse or promote products derived from
18
   this software without specific prior written permission.
19
20
   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21
   ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22
   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
23
   A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR
24
   CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25
   EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
26
   PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
27
   PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
28
   LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
29
   NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
30
   SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31
*/
32
33
#ifdef HAVE_CONFIG_H
34
#include "config.h"
35
#endif
36
37
#include <math.h>
38
#include "ltp.h"
39
#include "stack_alloc.h"
40
#include "filters.h"
41
#include "math_approx.h"
42
#include "os_support.h"
43
44
#ifndef NULL
45
#define NULL 0
46
#endif
47
48
49
#ifdef _USE_SSE
50
#include "ltp_sse.h"
51
#elif defined (ARM4_ASM) || defined(ARM5E_ASM)
52
#include "ltp_arm4.h"
53
#elif defined (BFIN_ASM)
54
#include "ltp_bfin.h"
55
#endif
56
57
#ifndef OVERRIDE_INNER_PROD
58
spx_word32_t inner_prod(const spx_word16_t *x, const spx_word16_t *y, int len)
59
7.08M
{
60
7.08M
   spx_word32_t sum=0;
61
7.08M
   len >>= 2;
62
153M
   while(len--)
63
146M
   {
64
146M
      spx_word32_t part=0;
65
146M
      part = MAC16_16(part,*x++,*y++);
66
146M
      part = MAC16_16(part,*x++,*y++);
67
146M
      part = MAC16_16(part,*x++,*y++);
68
146M
      part = MAC16_16(part,*x++,*y++);
69
      /* HINT: If you had a 40-bit accumulator, you could shift only at the end */
70
146M
      sum = ADD32(sum,SHR32(part,6));
71
146M
   }
72
7.08M
   return sum;
73
7.08M
}
74
#endif
75
76
#ifndef DISABLE_ENCODER
77
78
#ifndef OVERRIDE_PITCH_XCORR
79
#if 0 /* HINT: Enable this for machines with enough registers (i.e. not x86) */
80
static void pitch_xcorr(const spx_word16_t *_x, const spx_word16_t *_y, spx_word32_t *corr, int len, int nb_pitch, char *stack)
81
{
82
   int i,j;
83
   for (i=0;i<nb_pitch;i+=4)
84
   {
85
      /* Compute correlation*/
86
      /*corr[nb_pitch-1-i]=inner_prod(x, _y+i, len);*/
87
      spx_word32_t sum1=0;
88
      spx_word32_t sum2=0;
89
      spx_word32_t sum3=0;
90
      spx_word32_t sum4=0;
91
      const spx_word16_t *y = _y+i;
92
      const spx_word16_t *x = _x;
93
      spx_word16_t y0, y1, y2, y3;
94
      /*y0=y[0];y1=y[1];y2=y[2];y3=y[3];*/
95
      y0=*y++;
96
      y1=*y++;
97
      y2=*y++;
98
      y3=*y++;
99
      for (j=0;j<len;j+=4)
100
      {
101
         spx_word32_t part1;
102
         spx_word32_t part2;
103
         spx_word32_t part3;
104
         spx_word32_t part4;
105
         part1 = MULT16_16(*x,y0);
106
         part2 = MULT16_16(*x,y1);
107
         part3 = MULT16_16(*x,y2);
108
         part4 = MULT16_16(*x,y3);
109
         x++;
110
         y0=*y++;
111
         part1 = MAC16_16(part1,*x,y1);
112
         part2 = MAC16_16(part2,*x,y2);
113
         part3 = MAC16_16(part3,*x,y3);
114
         part4 = MAC16_16(part4,*x,y0);
115
         x++;
116
         y1=*y++;
117
         part1 = MAC16_16(part1,*x,y2);
118
         part2 = MAC16_16(part2,*x,y3);
119
         part3 = MAC16_16(part3,*x,y0);
120
         part4 = MAC16_16(part4,*x,y1);
121
         x++;
122
         y2=*y++;
123
         part1 = MAC16_16(part1,*x,y3);
124
         part2 = MAC16_16(part2,*x,y0);
125
         part3 = MAC16_16(part3,*x,y1);
126
         part4 = MAC16_16(part4,*x,y2);
127
         x++;
128
         y3=*y++;
129
130
         sum1 = ADD32(sum1,SHR32(part1,6));
131
         sum2 = ADD32(sum2,SHR32(part2,6));
132
         sum3 = ADD32(sum3,SHR32(part3,6));
133
         sum4 = ADD32(sum4,SHR32(part4,6));
134
      }
135
      corr[nb_pitch-1-i]=sum1;
136
      corr[nb_pitch-2-i]=sum2;
137
      corr[nb_pitch-3-i]=sum3;
138
      corr[nb_pitch-4-i]=sum4;
139
   }
140
141
}
142
#else
143
static void pitch_xcorr(const spx_word16_t *_x, const spx_word16_t *_y, spx_word32_t *corr, int len, int nb_pitch, char *stack)
144
42.8k
{
145
42.8k
   int i;
146
5.25M
   for (i=0;i<nb_pitch;i++)
147
5.21M
   {
148
      /* Compute correlation*/
149
5.21M
      corr[nb_pitch-1-i]=inner_prod(_x, _y+i, len);
150
5.21M
   }
151
152
42.8k
}
153
#endif
154
#endif
155
156
#ifndef OVERRIDE_COMPUTE_PITCH_ERROR
157
static inline spx_word32_t compute_pitch_error(spx_word16_t *C, spx_word16_t *g, spx_word16_t pitch_control)
158
29.8M
{
159
29.8M
   spx_word32_t sum = 0;
160
29.8M
   sum = ADD32(sum,MULT16_16(MULT16_16_16(g[0],pitch_control),C[0]));
161
29.8M
   sum = ADD32(sum,MULT16_16(MULT16_16_16(g[1],pitch_control),C[1]));
162
29.8M
   sum = ADD32(sum,MULT16_16(MULT16_16_16(g[2],pitch_control),C[2]));
163
29.8M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[0],g[1]),C[3]));
164
29.8M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[2],g[1]),C[4]));
165
29.8M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[2],g[0]),C[5]));
166
29.8M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[0],g[0]),C[6]));
167
29.8M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[1],g[1]),C[7]));
168
29.8M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[2],g[2]),C[8]));
169
29.8M
   return sum;
170
29.8M
}
ltp.c:compute_pitch_error
Line
Count
Source
158
14.9M
{
159
14.9M
   spx_word32_t sum = 0;
160
14.9M
   sum = ADD32(sum,MULT16_16(MULT16_16_16(g[0],pitch_control),C[0]));
161
14.9M
   sum = ADD32(sum,MULT16_16(MULT16_16_16(g[1],pitch_control),C[1]));
162
14.9M
   sum = ADD32(sum,MULT16_16(MULT16_16_16(g[2],pitch_control),C[2]));
163
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[0],g[1]),C[3]));
164
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[2],g[1]),C[4]));
165
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[2],g[0]),C[5]));
166
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[0],g[0]),C[6]));
167
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[1],g[1]),C[7]));
168
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[2],g[2]),C[8]));
169
14.9M
   return sum;
170
14.9M
}
ltp.c:compute_pitch_error
Line
Count
Source
158
14.9M
{
159
14.9M
   spx_word32_t sum = 0;
160
14.9M
   sum = ADD32(sum,MULT16_16(MULT16_16_16(g[0],pitch_control),C[0]));
161
14.9M
   sum = ADD32(sum,MULT16_16(MULT16_16_16(g[1],pitch_control),C[1]));
162
14.9M
   sum = ADD32(sum,MULT16_16(MULT16_16_16(g[2],pitch_control),C[2]));
163
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[0],g[1]),C[3]));
164
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[2],g[1]),C[4]));
165
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[2],g[0]),C[5]));
166
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[0],g[0]),C[6]));
167
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[1],g[1]),C[7]));
168
14.9M
   sum = SUB32(sum,MULT16_16(MULT16_16_16(g[2],g[2]),C[8]));
169
14.9M
   return sum;
170
14.9M
}
171
#endif
172
173
#ifndef OVERRIDE_OPEN_LOOP_NBEST_PITCH
174
void open_loop_nbest_pitch(spx_word16_t *sw, int start, int end, int len, int *pitch, spx_word16_t *gain, int N, char *stack)
175
59.5k
{
176
59.5k
   int i,j,k;
177
59.5k
   VARDECL(spx_word32_t *best_score);
178
59.5k
   VARDECL(spx_word32_t *best_ener);
179
59.5k
   spx_word32_t e0;
180
59.5k
   VARDECL(spx_word32_t *corr);
181
#ifdef FIXED_POINT
182
   /* In fixed-point, we need only one (temporary) array of 32-bit values and two (corr16, ener16)
183
      arrays for (normalized) 16-bit values */
184
   VARDECL(spx_word16_t *corr16);
185
   VARDECL(spx_word16_t *ener16);
186
   spx_word32_t *energy;
187
   int cshift=0, eshift=0;
188
   int scaledown = 0;
189
42.8k
   ALLOC(corr16, end-start+1, spx_word16_t);
190
42.8k
   ALLOC(ener16, end-start+1, spx_word16_t);
191
42.8k
   ALLOC(corr, end-start+1, spx_word32_t);
192
   energy = corr;
193
#else
194
   /* In floating-point, we need to float arrays and no normalized copies */
195
   VARDECL(spx_word32_t *energy);
196
   spx_word16_t *corr16;
197
   spx_word16_t *ener16;
198
16.6k
   ALLOC(energy, end-start+2, spx_word32_t);
199
16.6k
   ALLOC(corr, end-start+1, spx_word32_t);
200
   corr16 = corr;
201
   ener16 = energy;
202
#endif
203
204
59.5k
   ALLOC(best_score, N, spx_word32_t);
205
59.5k
   ALLOC(best_ener, N, spx_word32_t);
206
399k
   for (i=0;i<N;i++)
207
339k
   {
208
339k
        best_score[i]=-1;
209
339k
        best_ener[i]=0;
210
339k
        pitch[i]=start;
211
339k
   }
212
213
#ifdef FIXED_POINT
214
7.94M
   for (i=-end;i<len;i++)
215
7.91M
   {
216
7.91M
      if (ABS16(sw[i])>16383)
217
12.0k
      {
218
12.0k
         scaledown=1;
219
12.0k
         break;
220
12.0k
      }
221
7.91M
   }
222
   /* If the weighted input is close to saturation, then we scale it down */
223
42.8k
   if (scaledown)
224
12.0k
   {
225
2.78M
      for (i=-end;i<len;i++)
226
2.77M
      {
227
2.77M
         sw[i]=SHR16(sw[i],1);
228
2.77M
      }
229
12.0k
   }
230
#endif
231
59.5k
   energy[0]=inner_prod(sw-start, sw-start, len);
232
59.5k
   e0=inner_prod(sw, sw, len);
233
7.22M
   for (i=start;i<end;i++)
234
7.16M
   {
235
      /* Update energy for next pitch*/
236
7.16M
      energy[i-start+1] = SUB32(ADD32(energy[i-start],SHR32(MULT16_16(sw[-i-1],sw[-i-1]),6)), SHR32(MULT16_16(sw[-i+len-1],sw[-i+len-1]),6));
237
7.16M
      if (energy[i-start+1] < 0)
238
6.82k
         energy[i-start+1] = 0;
239
7.16M
   }
240
241
#ifdef FIXED_POINT
242
   eshift = normalize16(energy, ener16, 32766, end-start+1);
243
#endif
244
245
   /* In fixed-point, this actually overrites the energy array (aliased to corr) */
246
59.5k
   pitch_xcorr(sw, sw-end, corr, len, end-start+1, stack);
247
248
#ifdef FIXED_POINT
249
   /* Normalize to 180 so we can square it and it still fits in 16 bits */
250
   cshift = normalize16(corr, corr16, 180, end-start+1);
251
   /* If we scaled weighted input down, we need to scale it up again (OK, so we've just lost the LSB, who cares?) */
252
42.8k
   if (scaledown)
253
12.0k
   {
254
2.78M
      for (i=-end;i<len;i++)
255
2.77M
      {
256
2.77M
         sw[i]=SHL16(sw[i],1);
257
2.77M
      }
258
12.0k
   }
259
#endif
260
261
   /* Search for the best pitch prediction gain */
262
7.28M
   for (i=start;i<=end;i++)
263
7.22M
   {
264
7.22M
      spx_word16_t tmp = MULT16_16_16(corr16[i-start],corr16[i-start]);
265
      /* Instead of dividing the tmp by the energy, we multiply on the other side */
266
7.22M
      if (MULT16_16(tmp,best_ener[N-1])>MULT16_16(best_score[N-1],ADD16(1,ener16[i-start])))
267
1.16M
      {
268
         /* We can safely put it last and then check */
269
1.16M
         best_score[N-1]=tmp;
270
1.16M
         best_ener[N-1]=ener16[i-start]+1;
271
1.16M
         pitch[N-1]=i;
272
         /* Check if it comes in front of others */
273
3.66M
         for (j=0;j<N-1;j++)
274
3.48M
         {
275
3.48M
            if (MULT16_16(tmp,best_ener[j])>MULT16_16(best_score[j],ADD16(1,ener16[i-start])))
276
994k
            {
277
4.88M
               for (k=N-1;k>j;k--)
278
3.89M
               {
279
3.89M
                  best_score[k]=best_score[k-1];
280
3.89M
                  best_ener[k]=best_ener[k-1];
281
3.89M
                  pitch[k]=pitch[k-1];
282
3.89M
               }
283
994k
               best_score[j]=tmp;
284
994k
               best_ener[j]=ener16[i-start]+1;
285
994k
               pitch[j]=i;
286
994k
               break;
287
994k
            }
288
3.48M
         }
289
1.16M
      }
290
7.22M
   }
291
292
   /* Compute open-loop gain if necessary */
293
59.5k
   if (gain)
294
26.3k
   {
295
184k
      for (j=0;j<N;j++)
296
157k
      {
297
157k
         spx_word16_t g;
298
157k
         i=pitch[j];
299
157k
         g = DIV32(SHL32(EXTEND32(corr16[i-start]),cshift), 10+SHR32(MULT16_16(spx_sqrt(e0),spx_sqrt(SHL32(EXTEND32(ener16[i-start]),eshift))),6));
300
         /* FIXME: g = max(g,corr/energy) */
301
157k
         if (g<0)
302
58.6k
            g = 0;
303
157k
         gain[j]=g;
304
157k
      }
305
26.3k
   }
306
307
308
59.5k
}
open_loop_nbest_pitch
Line
Count
Source
175
16.6k
{
176
16.6k
   int i,j,k;
177
16.6k
   VARDECL(spx_word32_t *best_score);
178
16.6k
   VARDECL(spx_word32_t *best_ener);
179
16.6k
   spx_word32_t e0;
180
16.6k
   VARDECL(spx_word32_t *corr);
181
#ifdef FIXED_POINT
182
   /* In fixed-point, we need only one (temporary) array of 32-bit values and two (corr16, ener16)
183
      arrays for (normalized) 16-bit values */
184
   VARDECL(spx_word16_t *corr16);
185
   VARDECL(spx_word16_t *ener16);
186
   spx_word32_t *energy;
187
   int cshift=0, eshift=0;
188
   int scaledown = 0;
189
   ALLOC(corr16, end-start+1, spx_word16_t);
190
   ALLOC(ener16, end-start+1, spx_word16_t);
191
   ALLOC(corr, end-start+1, spx_word32_t);
192
   energy = corr;
193
#else
194
   /* In floating-point, we need to float arrays and no normalized copies */
195
16.6k
   VARDECL(spx_word32_t *energy);
196
16.6k
   spx_word16_t *corr16;
197
16.6k
   spx_word16_t *ener16;
198
16.6k
   ALLOC(energy, end-start+2, spx_word32_t);
199
16.6k
   ALLOC(corr, end-start+1, spx_word32_t);
200
16.6k
   corr16 = corr;
201
16.6k
   ener16 = energy;
202
16.6k
#endif
203
204
16.6k
   ALLOC(best_score, N, spx_word32_t);
205
16.6k
   ALLOC(best_ener, N, spx_word32_t);
206
113k
   for (i=0;i<N;i++)
207
97.2k
   {
208
97.2k
        best_score[i]=-1;
209
97.2k
        best_ener[i]=0;
210
97.2k
        pitch[i]=start;
211
97.2k
   }
212
213
#ifdef FIXED_POINT
214
   for (i=-end;i<len;i++)
215
   {
216
      if (ABS16(sw[i])>16383)
217
      {
218
         scaledown=1;
219
         break;
220
      }
221
   }
222
   /* If the weighted input is close to saturation, then we scale it down */
223
   if (scaledown)
224
   {
225
      for (i=-end;i<len;i++)
226
      {
227
         sw[i]=SHR16(sw[i],1);
228
      }
229
   }
230
#endif
231
16.6k
   energy[0]=inner_prod(sw-start, sw-start, len);
232
16.6k
   e0=inner_prod(sw, sw, len);
233
2.00M
   for (i=start;i<end;i++)
234
1.99M
   {
235
      /* Update energy for next pitch*/
236
1.99M
      energy[i-start+1] = SUB32(ADD32(energy[i-start],SHR32(MULT16_16(sw[-i-1],sw[-i-1]),6)), SHR32(MULT16_16(sw[-i+len-1],sw[-i+len-1]),6));
237
1.99M
      if (energy[i-start+1] < 0)
238
6.82k
         energy[i-start+1] = 0;
239
1.99M
   }
240
241
#ifdef FIXED_POINT
242
   eshift = normalize16(energy, ener16, 32766, end-start+1);
243
#endif
244
245
   /* In fixed-point, this actually overrites the energy array (aliased to corr) */
246
16.6k
   pitch_xcorr(sw, sw-end, corr, len, end-start+1, stack);
247
248
#ifdef FIXED_POINT
249
   /* Normalize to 180 so we can square it and it still fits in 16 bits */
250
   cshift = normalize16(corr, corr16, 180, end-start+1);
251
   /* If we scaled weighted input down, we need to scale it up again (OK, so we've just lost the LSB, who cares?) */
252
   if (scaledown)
253
   {
254
      for (i=-end;i<len;i++)
255
      {
256
         sw[i]=SHL16(sw[i],1);
257
      }
258
   }
259
#endif
260
261
   /* Search for the best pitch prediction gain */
262
2.02M
   for (i=start;i<=end;i++)
263
2.00M
   {
264
2.00M
      spx_word16_t tmp = MULT16_16_16(corr16[i-start],corr16[i-start]);
265
      /* Instead of dividing the tmp by the energy, we multiply on the other side */
266
2.00M
      if (MULT16_16(tmp,best_ener[N-1])>MULT16_16(best_score[N-1],ADD16(1,ener16[i-start])))
267
351k
      {
268
         /* We can safely put it last and then check */
269
351k
         best_score[N-1]=tmp;
270
351k
         best_ener[N-1]=ener16[i-start]+1;
271
351k
         pitch[N-1]=i;
272
         /* Check if it comes in front of others */
273
950k
         for (j=0;j<N-1;j++)
274
905k
         {
275
905k
            if (MULT16_16(tmp,best_ener[j])>MULT16_16(best_score[j],ADD16(1,ener16[i-start])))
276
306k
            {
277
1.65M
               for (k=N-1;k>j;k--)
278
1.34M
               {
279
1.34M
                  best_score[k]=best_score[k-1];
280
1.34M
                  best_ener[k]=best_ener[k-1];
281
1.34M
                  pitch[k]=pitch[k-1];
282
1.34M
               }
283
306k
               best_score[j]=tmp;
284
306k
               best_ener[j]=ener16[i-start]+1;
285
306k
               pitch[j]=i;
286
306k
               break;
287
306k
            }
288
905k
         }
289
351k
      }
290
2.00M
   }
291
292
   /* Compute open-loop gain if necessary */
293
16.6k
   if (gain)
294
7.91k
   {
295
55.3k
      for (j=0;j<N;j++)
296
47.4k
      {
297
47.4k
         spx_word16_t g;
298
47.4k
         i=pitch[j];
299
47.4k
         g = DIV32(SHL32(EXTEND32(corr16[i-start]),cshift), 10+SHR32(MULT16_16(spx_sqrt(e0),spx_sqrt(SHL32(EXTEND32(ener16[i-start]),eshift))),6));
300
         /* FIXME: g = max(g,corr/energy) */
301
47.4k
         if (g<0)
302
13.8k
            g = 0;
303
47.4k
         gain[j]=g;
304
47.4k
      }
305
7.91k
   }
306
307
308
16.6k
}
open_loop_nbest_pitch
Line
Count
Source
175
42.8k
{
176
42.8k
   int i,j,k;
177
42.8k
   VARDECL(spx_word32_t *best_score);
178
42.8k
   VARDECL(spx_word32_t *best_ener);
179
42.8k
   spx_word32_t e0;
180
42.8k
   VARDECL(spx_word32_t *corr);
181
42.8k
#ifdef FIXED_POINT
182
   /* In fixed-point, we need only one (temporary) array of 32-bit values and two (corr16, ener16)
183
      arrays for (normalized) 16-bit values */
184
42.8k
   VARDECL(spx_word16_t *corr16);
185
42.8k
   VARDECL(spx_word16_t *ener16);
186
42.8k
   spx_word32_t *energy;
187
42.8k
   int cshift=0, eshift=0;
188
42.8k
   int scaledown = 0;
189
42.8k
   ALLOC(corr16, end-start+1, spx_word16_t);
190
42.8k
   ALLOC(ener16, end-start+1, spx_word16_t);
191
42.8k
   ALLOC(corr, end-start+1, spx_word32_t);
192
42.8k
   energy = corr;
193
#else
194
   /* In floating-point, we need to float arrays and no normalized copies */
195
   VARDECL(spx_word32_t *energy);
196
   spx_word16_t *corr16;
197
   spx_word16_t *ener16;
198
   ALLOC(energy, end-start+2, spx_word32_t);
199
   ALLOC(corr, end-start+1, spx_word32_t);
200
   corr16 = corr;
201
   ener16 = energy;
202
#endif
203
204
42.8k
   ALLOC(best_score, N, spx_word32_t);
205
42.8k
   ALLOC(best_ener, N, spx_word32_t);
206
285k
   for (i=0;i<N;i++)
207
242k
   {
208
242k
        best_score[i]=-1;
209
242k
        best_ener[i]=0;
210
242k
        pitch[i]=start;
211
242k
   }
212
213
42.8k
#ifdef FIXED_POINT
214
7.94M
   for (i=-end;i<len;i++)
215
7.91M
   {
216
7.91M
      if (ABS16(sw[i])>16383)
217
12.0k
      {
218
12.0k
         scaledown=1;
219
12.0k
         break;
220
12.0k
      }
221
7.91M
   }
222
   /* If the weighted input is close to saturation, then we scale it down */
223
42.8k
   if (scaledown)
224
12.0k
   {
225
2.78M
      for (i=-end;i<len;i++)
226
2.77M
      {
227
2.77M
         sw[i]=SHR16(sw[i],1);
228
2.77M
      }
229
12.0k
   }
230
42.8k
#endif
231
42.8k
   energy[0]=inner_prod(sw-start, sw-start, len);
232
42.8k
   e0=inner_prod(sw, sw, len);
233
5.21M
   for (i=start;i<end;i++)
234
5.16M
   {
235
      /* Update energy for next pitch*/
236
5.16M
      energy[i-start+1] = SUB32(ADD32(energy[i-start],SHR32(MULT16_16(sw[-i-1],sw[-i-1]),6)), SHR32(MULT16_16(sw[-i+len-1],sw[-i+len-1]),6));
237
5.16M
      if (energy[i-start+1] < 0)
238
0
         energy[i-start+1] = 0;
239
5.16M
   }
240
241
42.8k
#ifdef FIXED_POINT
242
42.8k
   eshift = normalize16(energy, ener16, 32766, end-start+1);
243
42.8k
#endif
244
245
   /* In fixed-point, this actually overrites the energy array (aliased to corr) */
246
42.8k
   pitch_xcorr(sw, sw-end, corr, len, end-start+1, stack);
247
248
42.8k
#ifdef FIXED_POINT
249
   /* Normalize to 180 so we can square it and it still fits in 16 bits */
250
42.8k
   cshift = normalize16(corr, corr16, 180, end-start+1);
251
   /* If we scaled weighted input down, we need to scale it up again (OK, so we've just lost the LSB, who cares?) */
252
42.8k
   if (scaledown)
253
12.0k
   {
254
2.78M
      for (i=-end;i<len;i++)
255
2.77M
      {
256
2.77M
         sw[i]=SHL16(sw[i],1);
257
2.77M
      }
258
12.0k
   }
259
42.8k
#endif
260
261
   /* Search for the best pitch prediction gain */
262
5.25M
   for (i=start;i<=end;i++)
263
5.21M
   {
264
5.21M
      spx_word16_t tmp = MULT16_16_16(corr16[i-start],corr16[i-start]);
265
      /* Instead of dividing the tmp by the energy, we multiply on the other side */
266
5.21M
      if (MULT16_16(tmp,best_ener[N-1])>MULT16_16(best_score[N-1],ADD16(1,ener16[i-start])))
267
816k
      {
268
         /* We can safely put it last and then check */
269
816k
         best_score[N-1]=tmp;
270
816k
         best_ener[N-1]=ener16[i-start]+1;
271
816k
         pitch[N-1]=i;
272
         /* Check if it comes in front of others */
273
2.71M
         for (j=0;j<N-1;j++)
274
2.58M
         {
275
2.58M
            if (MULT16_16(tmp,best_ener[j])>MULT16_16(best_score[j],ADD16(1,ener16[i-start])))
276
688k
            {
277
3.23M
               for (k=N-1;k>j;k--)
278
2.54M
               {
279
2.54M
                  best_score[k]=best_score[k-1];
280
2.54M
                  best_ener[k]=best_ener[k-1];
281
2.54M
                  pitch[k]=pitch[k-1];
282
2.54M
               }
283
688k
               best_score[j]=tmp;
284
688k
               best_ener[j]=ener16[i-start]+1;
285
688k
               pitch[j]=i;
286
688k
               break;
287
688k
            }
288
2.58M
         }
289
816k
      }
290
5.21M
   }
291
292
   /* Compute open-loop gain if necessary */
293
42.8k
   if (gain)
294
18.3k
   {
295
128k
      for (j=0;j<N;j++)
296
110k
      {
297
110k
         spx_word16_t g;
298
110k
         i=pitch[j];
299
110k
         g = DIV32(SHL32(EXTEND32(corr16[i-start]),cshift), 10+SHR32(MULT16_16(spx_sqrt(e0),spx_sqrt(SHL32(EXTEND32(ener16[i-start]),eshift))),6));
300
         /* FIXME: g = max(g,corr/energy) */
301
110k
         if (g<0)
302
44.7k
            g = 0;
303
110k
         gain[j]=g;
304
110k
      }
305
18.3k
   }
306
307
308
42.8k
}
309
#endif
310
311
#ifndef OVERRIDE_PITCH_GAIN_SEARCH_3TAP_VQ
312
static int pitch_gain_search_3tap_vq(
313
  const signed char *gain_cdbk,
314
  int                gain_cdbk_size,
315
  spx_word16_t      *C16,
316
  spx_word16_t       max_gain
317
)
318
375k
{
319
375k
  const signed char *ptr=gain_cdbk;
320
375k
  int                best_cdbk=0;
321
375k
  spx_word32_t       best_sum=-VERY_LARGE32;
322
375k
  spx_word32_t       sum=0;
323
375k
  spx_word16_t       g[3];
324
375k
  spx_word16_t       pitch_control=64;
325
375k
  spx_word16_t       gain_sum;
326
375k
  int                i;
327
328
30.2M
  for (i=0;i<gain_cdbk_size;i++) {
329
330
29.8M
    ptr = gain_cdbk+4*i;
331
29.8M
    g[0]=ADD16((spx_word16_t)ptr[0],32);
332
29.8M
    g[1]=ADD16((spx_word16_t)ptr[1],32);
333
29.8M
    g[2]=ADD16((spx_word16_t)ptr[2],32);
334
29.8M
    gain_sum = (spx_word16_t)ptr[3];
335
336
29.8M
    sum = compute_pitch_error(C16, g, pitch_control);
337
338
29.8M
    if (sum>best_sum && gain_sum<=max_gain) {
339
1.15M
      best_sum=sum;
340
1.15M
      best_cdbk=i;
341
1.15M
    }
342
29.8M
  }
343
344
375k
  return best_cdbk;
345
375k
}
ltp.c:pitch_gain_search_3tap_vq
Line
Count
Source
318
187k
{
319
187k
  const signed char *ptr=gain_cdbk;
320
187k
  int                best_cdbk=0;
321
187k
  spx_word32_t       best_sum=-VERY_LARGE32;
322
187k
  spx_word32_t       sum=0;
323
187k
  spx_word16_t       g[3];
324
187k
  spx_word16_t       pitch_control=64;
325
187k
  spx_word16_t       gain_sum;
326
187k
  int                i;
327
328
15.1M
  for (i=0;i<gain_cdbk_size;i++) {
329
330
14.9M
    ptr = gain_cdbk+4*i;
331
14.9M
    g[0]=ADD16((spx_word16_t)ptr[0],32);
332
14.9M
    g[1]=ADD16((spx_word16_t)ptr[1],32);
333
14.9M
    g[2]=ADD16((spx_word16_t)ptr[2],32);
334
14.9M
    gain_sum = (spx_word16_t)ptr[3];
335
336
14.9M
    sum = compute_pitch_error(C16, g, pitch_control);
337
338
14.9M
    if (sum>best_sum && gain_sum<=max_gain) {
339
577k
      best_sum=sum;
340
577k
      best_cdbk=i;
341
577k
    }
342
14.9M
  }
343
344
187k
  return best_cdbk;
345
187k
}
ltp.c:pitch_gain_search_3tap_vq
Line
Count
Source
318
187k
{
319
187k
  const signed char *ptr=gain_cdbk;
320
187k
  int                best_cdbk=0;
321
187k
  spx_word32_t       best_sum=-VERY_LARGE32;
322
187k
  spx_word32_t       sum=0;
323
187k
  spx_word16_t       g[3];
324
187k
  spx_word16_t       pitch_control=64;
325
187k
  spx_word16_t       gain_sum;
326
187k
  int                i;
327
328
15.1M
  for (i=0;i<gain_cdbk_size;i++) {
329
330
14.9M
    ptr = gain_cdbk+4*i;
331
14.9M
    g[0]=ADD16((spx_word16_t)ptr[0],32);
332
14.9M
    g[1]=ADD16((spx_word16_t)ptr[1],32);
333
14.9M
    g[2]=ADD16((spx_word16_t)ptr[2],32);
334
14.9M
    gain_sum = (spx_word16_t)ptr[3];
335
336
14.9M
    sum = compute_pitch_error(C16, g, pitch_control);
337
338
14.9M
    if (sum>best_sum && gain_sum<=max_gain) {
339
577k
      best_sum=sum;
340
577k
      best_cdbk=i;
341
577k
    }
342
14.9M
  }
343
344
187k
  return best_cdbk;
345
187k
}
346
#endif
347
348
/** Finds the best quantized 3-tap pitch predictor by analysis by synthesis */
349
static spx_word32_t pitch_gain_search_3tap(
350
const spx_word16_t target[],       /* Target vector */
351
const spx_coef_t ak[],          /* LPCs for this subframe */
352
const spx_coef_t awk1[],        /* Weighted LPCs #1 for this subframe */
353
const spx_coef_t awk2[],        /* Weighted LPCs #2 for this subframe */
354
spx_sig_t exc[],                /* Excitation */
355
const signed char *gain_cdbk,
356
int gain_cdbk_size,
357
int   pitch,                    /* Pitch value */
358
int   p,                        /* Number of LPC coeffs */
359
int   nsf,                      /* Number of samples in subframe */
360
SpeexBits *bits,
361
char *stack,
362
const spx_word16_t *exc2,
363
const spx_word16_t *r,
364
spx_word16_t *new_target,
365
int  *cdbk_index,
366
int plc_tuning,
367
spx_word32_t cumul_gain,
368
int scaledown
369
)
370
187k
{
371
187k
   int i,j;
372
187k
   VARDECL(spx_word16_t *tmp1);
373
187k
   VARDECL(spx_word16_t *e);
374
187k
   spx_word16_t *x[3];
375
187k
   spx_word32_t corr[3];
376
187k
   spx_word32_t A[3][3];
377
187k
   spx_word16_t gain[3];
378
187k
   spx_word32_t err;
379
187k
   spx_word16_t max_gain=128;
380
187k
   int          best_cdbk=0;
381
382
187k
   ALLOC(tmp1, 3*nsf, spx_word16_t);
383
187k
   ALLOC(e, nsf, spx_word16_t);
384
385
187k
   if (cumul_gain > 262144)
386
965
      max_gain = 31;
387
388
187k
   x[0]=tmp1;
389
187k
   x[1]=tmp1+nsf;
390
187k
   x[2]=tmp1+2*nsf;
391
392
7.70M
   for (j=0;j<nsf;j++)
393
7.51M
      new_target[j] = target[j];
394
395
187k
   {
396
187k
      int bound;
397
187k
      VARDECL(spx_mem_t *mm);
398
187k
      int pp=pitch-1;
399
187k
      ALLOC(mm, p, spx_mem_t);
400
187k
      bound = nsf;
401
187k
      if (nsf-pp>0)
402
76.4k
         bound = pp;
403
6.47M
      for (j=0;j<bound;j++)
404
6.29M
         e[j]=exc2[j-pp];
405
187k
      bound = nsf;
406
187k
      if (nsf-pp-pitch>0)
407
27.4k
         bound = pp+pitch;
408
1.29M
      for (;j<bound;j++)
409
1.10M
         e[j]=exc2[j-pp-pitch];
410
308k
      for (;j<nsf;j++)
411
120k
         e[j]=0;
412
#ifdef FIXED_POINT
413
      /* Scale target and excitation down if needed (avoiding overflow) */
414
136k
      if (scaledown)
415
34.5k
      {
416
1.41M
         for (j=0;j<nsf;j++)
417
1.38M
            e[j] = SHR16(e[j],1);
418
1.41M
         for (j=0;j<nsf;j++)
419
1.38M
            new_target[j] = SHR16(new_target[j],1);
420
34.5k
      }
421
#endif
422
2.06M
      for (j=0;j<p;j++)
423
1.87M
         mm[j] = 0;
424
187k
      iir_mem16(e, ak, e, nsf, p, mm, stack);
425
2.06M
      for (j=0;j<p;j++)
426
1.87M
         mm[j] = 0;
427
187k
      filter10(e, awk1, awk2, e, nsf, mm, stack);
428
7.70M
      for (j=0;j<nsf;j++)
429
7.51M
         x[2][j] = e[j];
430
187k
   }
431
563k
   for (i=1;i>=0;i--)
432
375k
   {
433
375k
      spx_word16_t e0=exc2[-pitch-1+i];
434
#ifdef FIXED_POINT
435
      /* Scale excitation down if needed (avoiding overflow) */
436
272k
      if (scaledown)
437
69.0k
         e0 = SHR16(e0,1);
438
#endif
439
375k
      x[i][0]=MULT16_16_Q14(r[0], e0);
440
15.0M
      for (j=0;j<nsf-1;j++)
441
14.6M
         x[i][j+1]=ADD32(x[i+1][j],MULT16_16_P14(r[j+1], e0));
442
375k
   }
443
444
751k
   for (i=0;i<3;i++)
445
563k
      corr[i]=inner_prod(x[i],new_target,nsf);
446
751k
   for (i=0;i<3;i++)
447
1.69M
      for (j=0;j<=i;j++)
448
1.12M
         A[i][j]=A[j][i]=inner_prod(x[i],x[j],nsf);
449
450
187k
   {
451
187k
      spx_word32_t C[9];
452
#ifdef FIXED_POINT
453
      spx_word16_t C16[9];
454
#else
455
      spx_word16_t *C16=C;
456
#endif
457
187k
      C[0]=corr[2];
458
187k
      C[1]=corr[1];
459
187k
      C[2]=corr[0];
460
187k
      C[3]=A[1][2];
461
187k
      C[4]=A[0][1];
462
187k
      C[5]=A[0][2];
463
187k
      C[6]=A[2][2];
464
187k
      C[7]=A[1][1];
465
187k
      C[8]=A[0][0];
466
467
      /*plc_tuning *= 2;*/
468
187k
      if (plc_tuning<2)
469
0
         plc_tuning=2;
470
187k
      if (plc_tuning>30)
471
0
         plc_tuning=30;
472
#ifdef FIXED_POINT
473
136k
      C[0] = SHL32(C[0],1);
474
136k
      C[1] = SHL32(C[1],1);
475
136k
      C[2] = SHL32(C[2],1);
476
136k
      C[3] = SHL32(C[3],1);
477
136k
      C[4] = SHL32(C[4],1);
478
136k
      C[5] = SHL32(C[5],1);
479
136k
      C[6] = MAC16_32_Q15(C[6],MULT16_16_16(plc_tuning,655),C[6]);
480
136k
      C[7] = MAC16_32_Q15(C[7],MULT16_16_16(plc_tuning,655),C[7]);
481
136k
      C[8] = MAC16_32_Q15(C[8],MULT16_16_16(plc_tuning,655),C[8]);
482
      normalize16(C, C16, 32767, 9);
483
#else
484
      C[6]*=.5*(1+.02*plc_tuning);
485
      C[7]*=.5*(1+.02*plc_tuning);
486
      C[8]*=.5*(1+.02*plc_tuning);
487
#endif
488
489
187k
      best_cdbk = pitch_gain_search_3tap_vq(gain_cdbk, gain_cdbk_size, C16, max_gain);
490
491
#ifdef FIXED_POINT
492
136k
      gain[0] = ADD16(32,(spx_word16_t)gain_cdbk[best_cdbk*4]);
493
136k
      gain[1] = ADD16(32,(spx_word16_t)gain_cdbk[best_cdbk*4+1]);
494
136k
      gain[2] = ADD16(32,(spx_word16_t)gain_cdbk[best_cdbk*4+2]);
495
      /*printf ("%d %d %d %d\n",gain[0],gain[1],gain[2], best_cdbk);*/
496
#else
497
      gain[0] = 0.015625*gain_cdbk[best_cdbk*4]  + .5;
498
      gain[1] = 0.015625*gain_cdbk[best_cdbk*4+1]+ .5;
499
      gain[2] = 0.015625*gain_cdbk[best_cdbk*4+2]+ .5;
500
#endif
501
187k
      *cdbk_index=best_cdbk;
502
187k
   }
503
504
187k
   SPEEX_MEMSET(exc, 0, nsf);
505
751k
   for (i=0;i<3;i++)
506
563k
   {
507
563k
      int j;
508
563k
      int tmp1, tmp3;
509
563k
      int pp=pitch+1-i;
510
563k
      tmp1=nsf;
511
563k
      if (tmp1>pp)
512
222k
         tmp1=pp;
513
19.6M
      for (j=0;j<tmp1;j++)
514
19.0M
         exc[j]=MAC16_16(exc[j],SHL16(gain[2-i],7),exc2[j-pp]);
515
563k
      tmp3=nsf;
516
563k
      if (tmp3>pp+pitch)
517
70.7k
         tmp3=pp+pitch;
518
3.72M
      for (j=tmp1;j<tmp3;j++)
519
3.15M
         exc[j]=MAC16_16(exc[j],SHL16(gain[2-i],7),exc2[j-pp-pitch]);
520
563k
   }
521
7.70M
   for (i=0;i<nsf;i++)
522
7.51M
   {
523
7.51M
      spx_word32_t tmp = ADD32(ADD32(MULT16_16(gain[0],x[2][i]),MULT16_16(gain[1],x[1][i])),
524
7.51M
                            MULT16_16(gain[2],x[0][i]));
525
7.51M
      new_target[i] = SUB16(new_target[i], EXTRACT16(PSHR32(tmp,6)));
526
7.51M
   }
527
187k
   err = inner_prod(new_target, new_target, nsf);
528
529
187k
   return err;
530
187k
}
ltp.c:pitch_gain_search_3tap
Line
Count
Source
370
51.3k
{
371
51.3k
   int i,j;
372
51.3k
   VARDECL(spx_word16_t *tmp1);
373
51.3k
   VARDECL(spx_word16_t *e);
374
51.3k
   spx_word16_t *x[3];
375
51.3k
   spx_word32_t corr[3];
376
51.3k
   spx_word32_t A[3][3];
377
51.3k
   spx_word16_t gain[3];
378
51.3k
   spx_word32_t err;
379
51.3k
   spx_word16_t max_gain=128;
380
51.3k
   int          best_cdbk=0;
381
382
51.3k
   ALLOC(tmp1, 3*nsf, spx_word16_t);
383
51.3k
   ALLOC(e, nsf, spx_word16_t);
384
385
51.3k
   if (cumul_gain > 262144)
386
483
      max_gain = 31;
387
388
51.3k
   x[0]=tmp1;
389
51.3k
   x[1]=tmp1+nsf;
390
51.3k
   x[2]=tmp1+2*nsf;
391
392
2.10M
   for (j=0;j<nsf;j++)
393
2.05M
      new_target[j] = target[j];
394
395
51.3k
   {
396
51.3k
      int bound;
397
51.3k
      VARDECL(spx_mem_t *mm);
398
51.3k
      int pp=pitch-1;
399
51.3k
      ALLOC(mm, p, spx_mem_t);
400
51.3k
      bound = nsf;
401
51.3k
      if (nsf-pp>0)
402
25.8k
         bound = pp;
403
1.67M
      for (j=0;j<bound;j++)
404
1.62M
         e[j]=exc2[j-pp];
405
51.3k
      bound = nsf;
406
51.3k
      if (nsf-pp-pitch>0)
407
9.80k
         bound = pp+pitch;
408
438k
      for (;j<bound;j++)
409
386k
         e[j]=exc2[j-pp-pitch];
410
96.7k
      for (;j<nsf;j++)
411
45.3k
         e[j]=0;
412
#ifdef FIXED_POINT
413
      /* Scale target and excitation down if needed (avoiding overflow) */
414
      if (scaledown)
415
      {
416
         for (j=0;j<nsf;j++)
417
            e[j] = SHR16(e[j],1);
418
         for (j=0;j<nsf;j++)
419
            new_target[j] = SHR16(new_target[j],1);
420
      }
421
#endif
422
565k
      for (j=0;j<p;j++)
423
513k
         mm[j] = 0;
424
51.3k
      iir_mem16(e, ak, e, nsf, p, mm, stack);
425
565k
      for (j=0;j<p;j++)
426
513k
         mm[j] = 0;
427
51.3k
      filter10(e, awk1, awk2, e, nsf, mm, stack);
428
2.10M
      for (j=0;j<nsf;j++)
429
2.05M
         x[2][j] = e[j];
430
51.3k
   }
431
154k
   for (i=1;i>=0;i--)
432
102k
   {
433
102k
      spx_word16_t e0=exc2[-pitch-1+i];
434
#ifdef FIXED_POINT
435
      /* Scale excitation down if needed (avoiding overflow) */
436
      if (scaledown)
437
         e0 = SHR16(e0,1);
438
#endif
439
102k
      x[i][0]=MULT16_16_Q14(r[0], e0);
440
4.11M
      for (j=0;j<nsf-1;j++)
441
4.00M
         x[i][j+1]=ADD32(x[i+1][j],MULT16_16_P14(r[j+1], e0));
442
102k
   }
443
444
205k
   for (i=0;i<3;i++)
445
154k
      corr[i]=inner_prod(x[i],new_target,nsf);
446
205k
   for (i=0;i<3;i++)
447
462k
      for (j=0;j<=i;j++)
448
308k
         A[i][j]=A[j][i]=inner_prod(x[i],x[j],nsf);
449
450
51.3k
   {
451
51.3k
      spx_word32_t C[9];
452
#ifdef FIXED_POINT
453
      spx_word16_t C16[9];
454
#else
455
51.3k
      spx_word16_t *C16=C;
456
51.3k
#endif
457
51.3k
      C[0]=corr[2];
458
51.3k
      C[1]=corr[1];
459
51.3k
      C[2]=corr[0];
460
51.3k
      C[3]=A[1][2];
461
51.3k
      C[4]=A[0][1];
462
51.3k
      C[5]=A[0][2];
463
51.3k
      C[6]=A[2][2];
464
51.3k
      C[7]=A[1][1];
465
51.3k
      C[8]=A[0][0];
466
467
      /*plc_tuning *= 2;*/
468
51.3k
      if (plc_tuning<2)
469
0
         plc_tuning=2;
470
51.3k
      if (plc_tuning>30)
471
0
         plc_tuning=30;
472
#ifdef FIXED_POINT
473
      C[0] = SHL32(C[0],1);
474
      C[1] = SHL32(C[1],1);
475
      C[2] = SHL32(C[2],1);
476
      C[3] = SHL32(C[3],1);
477
      C[4] = SHL32(C[4],1);
478
      C[5] = SHL32(C[5],1);
479
      C[6] = MAC16_32_Q15(C[6],MULT16_16_16(plc_tuning,655),C[6]);
480
      C[7] = MAC16_32_Q15(C[7],MULT16_16_16(plc_tuning,655),C[7]);
481
      C[8] = MAC16_32_Q15(C[8],MULT16_16_16(plc_tuning,655),C[8]);
482
      normalize16(C, C16, 32767, 9);
483
#else
484
51.3k
      C[6]*=.5*(1+.02*plc_tuning);
485
51.3k
      C[7]*=.5*(1+.02*plc_tuning);
486
51.3k
      C[8]*=.5*(1+.02*plc_tuning);
487
51.3k
#endif
488
489
51.3k
      best_cdbk = pitch_gain_search_3tap_vq(gain_cdbk, gain_cdbk_size, C16, max_gain);
490
491
#ifdef FIXED_POINT
492
      gain[0] = ADD16(32,(spx_word16_t)gain_cdbk[best_cdbk*4]);
493
      gain[1] = ADD16(32,(spx_word16_t)gain_cdbk[best_cdbk*4+1]);
494
      gain[2] = ADD16(32,(spx_word16_t)gain_cdbk[best_cdbk*4+2]);
495
      /*printf ("%d %d %d %d\n",gain[0],gain[1],gain[2], best_cdbk);*/
496
#else
497
51.3k
      gain[0] = 0.015625*gain_cdbk[best_cdbk*4]  + .5;
498
51.3k
      gain[1] = 0.015625*gain_cdbk[best_cdbk*4+1]+ .5;
499
51.3k
      gain[2] = 0.015625*gain_cdbk[best_cdbk*4+2]+ .5;
500
51.3k
#endif
501
51.3k
      *cdbk_index=best_cdbk;
502
51.3k
   }
503
504
51.3k
   SPEEX_MEMSET(exc, 0, nsf);
505
205k
   for (i=0;i<3;i++)
506
154k
   {
507
154k
      int j;
508
154k
      int tmp1, tmp3;
509
154k
      int pp=pitch+1-i;
510
154k
      tmp1=nsf;
511
154k
      if (tmp1>pp)
512
76.4k
         tmp1=pp;
513
5.10M
      for (j=0;j<tmp1;j++)
514
4.94M
         exc[j]=MAC16_16(exc[j],SHL16(gain[2-i],7),exc2[j-pp]);
515
154k
      tmp3=nsf;
516
154k
      if (tmp3>pp+pitch)
517
26.0k
         tmp3=pp+pitch;
518
1.26M
      for (j=tmp1;j<tmp3;j++)
519
1.11M
         exc[j]=MAC16_16(exc[j],SHL16(gain[2-i],7),exc2[j-pp-pitch]);
520
154k
   }
521
2.10M
   for (i=0;i<nsf;i++)
522
2.05M
   {
523
2.05M
      spx_word32_t tmp = ADD32(ADD32(MULT16_16(gain[0],x[2][i]),MULT16_16(gain[1],x[1][i])),
524
2.05M
                            MULT16_16(gain[2],x[0][i]));
525
2.05M
      new_target[i] = SUB16(new_target[i], EXTRACT16(PSHR32(tmp,6)));
526
2.05M
   }
527
51.3k
   err = inner_prod(new_target, new_target, nsf);
528
529
51.3k
   return err;
530
51.3k
}
ltp.c:pitch_gain_search_3tap
Line
Count
Source
370
136k
{
371
136k
   int i,j;
372
136k
   VARDECL(spx_word16_t *tmp1);
373
136k
   VARDECL(spx_word16_t *e);
374
136k
   spx_word16_t *x[3];
375
136k
   spx_word32_t corr[3];
376
136k
   spx_word32_t A[3][3];
377
136k
   spx_word16_t gain[3];
378
136k
   spx_word32_t err;
379
136k
   spx_word16_t max_gain=128;
380
136k
   int          best_cdbk=0;
381
382
136k
   ALLOC(tmp1, 3*nsf, spx_word16_t);
383
136k
   ALLOC(e, nsf, spx_word16_t);
384
385
136k
   if (cumul_gain > 262144)
386
482
      max_gain = 31;
387
388
136k
   x[0]=tmp1;
389
136k
   x[1]=tmp1+nsf;
390
136k
   x[2]=tmp1+2*nsf;
391
392
5.59M
   for (j=0;j<nsf;j++)
393
5.45M
      new_target[j] = target[j];
394
395
136k
   {
396
136k
      int bound;
397
136k
      VARDECL(spx_mem_t *mm);
398
136k
      int pp=pitch-1;
399
136k
      ALLOC(mm, p, spx_mem_t);
400
136k
      bound = nsf;
401
136k
      if (nsf-pp>0)
402
50.6k
         bound = pp;
403
4.80M
      for (j=0;j<bound;j++)
404
4.66M
         e[j]=exc2[j-pp];
405
136k
      bound = nsf;
406
136k
      if (nsf-pp-pitch>0)
407
17.6k
         bound = pp+pitch;
408
852k
      for (;j<bound;j++)
409
715k
         e[j]=exc2[j-pp-pitch];
410
211k
      for (;j<nsf;j++)
411
74.8k
         e[j]=0;
412
136k
#ifdef FIXED_POINT
413
      /* Scale target and excitation down if needed (avoiding overflow) */
414
136k
      if (scaledown)
415
34.5k
      {
416
1.41M
         for (j=0;j<nsf;j++)
417
1.38M
            e[j] = SHR16(e[j],1);
418
1.41M
         for (j=0;j<nsf;j++)
419
1.38M
            new_target[j] = SHR16(new_target[j],1);
420
34.5k
      }
421
136k
#endif
422
1.50M
      for (j=0;j<p;j++)
423
1.36M
         mm[j] = 0;
424
136k
      iir_mem16(e, ak, e, nsf, p, mm, stack);
425
1.50M
      for (j=0;j<p;j++)
426
1.36M
         mm[j] = 0;
427
136k
      filter10(e, awk1, awk2, e, nsf, mm, stack);
428
5.59M
      for (j=0;j<nsf;j++)
429
5.45M
         x[2][j] = e[j];
430
136k
   }
431
409k
   for (i=1;i>=0;i--)
432
272k
   {
433
272k
      spx_word16_t e0=exc2[-pitch-1+i];
434
272k
#ifdef FIXED_POINT
435
      /* Scale excitation down if needed (avoiding overflow) */
436
272k
      if (scaledown)
437
69.0k
         e0 = SHR16(e0,1);
438
272k
#endif
439
272k
      x[i][0]=MULT16_16_Q14(r[0], e0);
440
10.9M
      for (j=0;j<nsf-1;j++)
441
10.6M
         x[i][j+1]=ADD32(x[i+1][j],MULT16_16_P14(r[j+1], e0));
442
272k
   }
443
444
545k
   for (i=0;i<3;i++)
445
409k
      corr[i]=inner_prod(x[i],new_target,nsf);
446
545k
   for (i=0;i<3;i++)
447
1.22M
      for (j=0;j<=i;j++)
448
818k
         A[i][j]=A[j][i]=inner_prod(x[i],x[j],nsf);
449
450
136k
   {
451
136k
      spx_word32_t C[9];
452
136k
#ifdef FIXED_POINT
453
136k
      spx_word16_t C16[9];
454
#else
455
      spx_word16_t *C16=C;
456
#endif
457
136k
      C[0]=corr[2];
458
136k
      C[1]=corr[1];
459
136k
      C[2]=corr[0];
460
136k
      C[3]=A[1][2];
461
136k
      C[4]=A[0][1];
462
136k
      C[5]=A[0][2];
463
136k
      C[6]=A[2][2];
464
136k
      C[7]=A[1][1];
465
136k
      C[8]=A[0][0];
466
467
      /*plc_tuning *= 2;*/
468
136k
      if (plc_tuning<2)
469
0
         plc_tuning=2;
470
136k
      if (plc_tuning>30)
471
0
         plc_tuning=30;
472
136k
#ifdef FIXED_POINT
473
136k
      C[0] = SHL32(C[0],1);
474
136k
      C[1] = SHL32(C[1],1);
475
136k
      C[2] = SHL32(C[2],1);
476
136k
      C[3] = SHL32(C[3],1);
477
136k
      C[4] = SHL32(C[4],1);
478
136k
      C[5] = SHL32(C[5],1);
479
136k
      C[6] = MAC16_32_Q15(C[6],MULT16_16_16(plc_tuning,655),C[6]);
480
136k
      C[7] = MAC16_32_Q15(C[7],MULT16_16_16(plc_tuning,655),C[7]);
481
136k
      C[8] = MAC16_32_Q15(C[8],MULT16_16_16(plc_tuning,655),C[8]);
482
136k
      normalize16(C, C16, 32767, 9);
483
#else
484
      C[6]*=.5*(1+.02*plc_tuning);
485
      C[7]*=.5*(1+.02*plc_tuning);
486
      C[8]*=.5*(1+.02*plc_tuning);
487
#endif
488
489
136k
      best_cdbk = pitch_gain_search_3tap_vq(gain_cdbk, gain_cdbk_size, C16, max_gain);
490
491
136k
#ifdef FIXED_POINT
492
136k
      gain[0] = ADD16(32,(spx_word16_t)gain_cdbk[best_cdbk*4]);
493
136k
      gain[1] = ADD16(32,(spx_word16_t)gain_cdbk[best_cdbk*4+1]);
494
136k
      gain[2] = ADD16(32,(spx_word16_t)gain_cdbk[best_cdbk*4+2]);
495
      /*printf ("%d %d %d %d\n",gain[0],gain[1],gain[2], best_cdbk);*/
496
#else
497
      gain[0] = 0.015625*gain_cdbk[best_cdbk*4]  + .5;
498
      gain[1] = 0.015625*gain_cdbk[best_cdbk*4+1]+ .5;
499
      gain[2] = 0.015625*gain_cdbk[best_cdbk*4+2]+ .5;
500
#endif
501
136k
      *cdbk_index=best_cdbk;
502
136k
   }
503
504
136k
   SPEEX_MEMSET(exc, 0, nsf);
505
545k
   for (i=0;i<3;i++)
506
409k
   {
507
409k
      int j;
508
409k
      int tmp1, tmp3;
509
409k
      int pp=pitch+1-i;
510
409k
      tmp1=nsf;
511
409k
      if (tmp1>pp)
512
146k
         tmp1=pp;
513
14.5M
      for (j=0;j<tmp1;j++)
514
14.1M
         exc[j]=MAC16_16(exc[j],SHL16(gain[2-i],7),exc2[j-pp]);
515
409k
      tmp3=nsf;
516
409k
      if (tmp3>pp+pitch)
517
44.6k
         tmp3=pp+pitch;
518
2.45M
      for (j=tmp1;j<tmp3;j++)
519
2.04M
         exc[j]=MAC16_16(exc[j],SHL16(gain[2-i],7),exc2[j-pp-pitch]);
520
409k
   }
521
5.59M
   for (i=0;i<nsf;i++)
522
5.45M
   {
523
5.45M
      spx_word32_t tmp = ADD32(ADD32(MULT16_16(gain[0],x[2][i]),MULT16_16(gain[1],x[1][i])),
524
5.45M
                            MULT16_16(gain[2],x[0][i]));
525
5.45M
      new_target[i] = SUB16(new_target[i], EXTRACT16(PSHR32(tmp,6)));
526
5.45M
   }
527
136k
   err = inner_prod(new_target, new_target, nsf);
528
529
136k
   return err;
530
136k
}
531
532
/** Finds the best quantized 3-tap pitch predictor by analysis by synthesis */
533
int pitch_search_3tap(
534
spx_word16_t target[],                 /* Target vector */
535
spx_word16_t *sw,
536
spx_coef_t ak[],                     /* LPCs for this subframe */
537
spx_coef_t awk1[],                   /* Weighted LPCs #1 for this subframe */
538
spx_coef_t awk2[],                   /* Weighted LPCs #2 for this subframe */
539
spx_sig_t exc[],                    /* Excitation */
540
const void *par,
541
int   start,                    /* Smallest pitch value allowed */
542
int   end,                      /* Largest pitch value allowed */
543
spx_word16_t pitch_coef,               /* Voicing (pitch) coefficient */
544
int   p,                        /* Number of LPC coeffs */
545
int   nsf,                      /* Number of samples in subframe */
546
SpeexBits *bits,
547
char *stack,
548
spx_word16_t *exc2,
549
spx_word16_t *r,
550
int complexity,
551
int cdbk_offset,
552
int plc_tuning,
553
spx_word32_t *cumul_gain
554
)
555
41.5k
{
556
41.5k
   int i;
557
41.5k
   int cdbk_index, pitch=0, best_gain_index=0;
558
41.5k
   VARDECL(spx_sig_t *best_exc);
559
41.5k
   VARDECL(spx_word16_t *new_target);
560
41.5k
   VARDECL(spx_word16_t *best_target);
561
41.5k
   int best_pitch=0;
562
41.5k
   spx_word32_t err, best_err=-1;
563
41.5k
   int N;
564
41.5k
   const ltp_params *params;
565
41.5k
   const signed char *gain_cdbk;
566
41.5k
   int   gain_cdbk_size;
567
41.5k
   int scaledown=0;
568
569
41.5k
   VARDECL(int *nbest);
570
571
41.5k
   params = (const ltp_params*) par;
572
41.5k
   gain_cdbk_size = 1<<params->gain_bits;
573
41.5k
   gain_cdbk = params->gain_cdbk + 4*gain_cdbk_size*cdbk_offset;
574
575
41.5k
   N=complexity;
576
41.5k
   if (N>10)
577
0
      N=10;
578
41.5k
   if (N<1)
579
6.32k
      N=1;
580
581
41.5k
   ALLOC(nbest, N, int);
582
41.5k
   params = (const ltp_params*) par;
583
584
41.5k
   if (end<start)
585
2.45k
   {
586
2.45k
      speex_bits_pack(bits, 0, params->pitch_bits);
587
2.45k
      speex_bits_pack(bits, 0, params->gain_bits);
588
2.45k
      SPEEX_MEMSET(exc, 0, nsf);
589
2.45k
      return start;
590
2.45k
   }
591
592
#ifdef FIXED_POINT
593
   /* Check if we need to scale everything down in the pitch search to avoid overflows */
594
1.01M
   for (i=0;i<nsf;i++)
595
992k
   {
596
992k
      if (ABS16(target[i])>16383)
597
5.14k
      {
598
5.14k
         scaledown=1;
599
5.14k
         break;
600
5.14k
      }
601
992k
   }
602
3.03M
   for (i=-end;i<0;i++)
603
3.00M
   {
604
3.00M
      if (ABS16(exc2[i])>16383)
605
4.87k
      {
606
4.87k
         scaledown=1;
607
4.87k
         break;
608
4.87k
      }
609
3.00M
   }
610
#endif
611
39.0k
   if (N>end-start+1)
612
4.68k
      N=end-start+1;
613
39.0k
   if (end != start)
614
33.2k
      open_loop_nbest_pitch(sw, start, end, nsf, nbest, NULL, N, stack);
615
5.81k
   else
616
5.81k
      nbest[0] = start;
617
618
39.0k
   ALLOC(best_exc, nsf, spx_sig_t);
619
39.0k
   ALLOC(new_target, nsf, spx_word16_t);
620
39.0k
   ALLOC(best_target, nsf, spx_word16_t);
621
622
226k
   for (i=0;i<N;i++)
623
187k
   {
624
187k
      pitch=nbest[i];
625
187k
      SPEEX_MEMSET(exc, 0, nsf);
626
187k
      err=pitch_gain_search_3tap(target, ak, awk1, awk2, exc, gain_cdbk, gain_cdbk_size, pitch, p, nsf,
627
187k
                                 bits, stack, exc2, r, new_target, &cdbk_index, plc_tuning, *cumul_gain, scaledown);
628
187k
      if (err<best_err || best_err<0)
629
52.3k
      {
630
52.3k
         SPEEX_COPY(best_exc, exc, nsf);
631
52.3k
         SPEEX_COPY(best_target, new_target, nsf);
632
52.3k
         best_err=err;
633
52.3k
         best_pitch=pitch;
634
52.3k
         best_gain_index=cdbk_index;
635
52.3k
      }
636
187k
   }
637
   /*printf ("pitch: %d %d\n", best_pitch, best_gain_index);*/
638
10.3k
   speex_bits_pack(bits, best_pitch-start, params->pitch_bits);
639
10.3k
   speex_bits_pack(bits, best_gain_index, params->gain_bits);
640
#ifdef FIXED_POINT
641
28.7k
   *cumul_gain = MULT16_32_Q13(SHL16(params->gain_cdbk[4*best_gain_index+3],8), MAX32(1024,*cumul_gain));
642
#else
643
10.3k
   *cumul_gain = 0.03125*MAX32(1024,*cumul_gain)*params->gain_cdbk[4*best_gain_index+3];
644
#endif
645
   /*printf ("%f\n", cumul_gain);*/
646
   /*printf ("encode pitch: %d %d\n", best_pitch, best_gain_index);*/
647
39.0k
   SPEEX_COPY(exc, best_exc, nsf);
648
39.0k
   SPEEX_COPY(target, best_target, nsf);
649
#ifdef FIXED_POINT
650
   /* Scale target back up if needed */
651
28.7k
   if (scaledown)
652
6.85k
   {
653
280k
      for (i=0;i<nsf;i++)
654
274k
         target[i]=SHL16(target[i],1);
655
6.85k
   }
656
#endif
657
10.3k
   return pitch;
658
41.5k
}
pitch_search_3tap
Line
Count
Source
555
11.1k
{
556
11.1k
   int i;
557
11.1k
   int cdbk_index, pitch=0, best_gain_index=0;
558
11.1k
   VARDECL(spx_sig_t *best_exc);
559
11.1k
   VARDECL(spx_word16_t *new_target);
560
11.1k
   VARDECL(spx_word16_t *best_target);
561
11.1k
   int best_pitch=0;
562
11.1k
   spx_word32_t err, best_err=-1;
563
11.1k
   int N;
564
11.1k
   const ltp_params *params;
565
11.1k
   const signed char *gain_cdbk;
566
11.1k
   int   gain_cdbk_size;
567
11.1k
   int scaledown=0;
568
569
11.1k
   VARDECL(int *nbest);
570
571
11.1k
   params = (const ltp_params*) par;
572
11.1k
   gain_cdbk_size = 1<<params->gain_bits;
573
11.1k
   gain_cdbk = params->gain_cdbk + 4*gain_cdbk_size*cdbk_offset;
574
575
11.1k
   N=complexity;
576
11.1k
   if (N>10)
577
0
      N=10;
578
11.1k
   if (N<1)
579
1.73k
      N=1;
580
581
11.1k
   ALLOC(nbest, N, int);
582
11.1k
   params = (const ltp_params*) par;
583
584
11.1k
   if (end<start)
585
793
   {
586
793
      speex_bits_pack(bits, 0, params->pitch_bits);
587
793
      speex_bits_pack(bits, 0, params->gain_bits);
588
793
      SPEEX_MEMSET(exc, 0, nsf);
589
793
      return start;
590
793
   }
591
592
#ifdef FIXED_POINT
593
   /* Check if we need to scale everything down in the pitch search to avoid overflows */
594
   for (i=0;i<nsf;i++)
595
   {
596
      if (ABS16(target[i])>16383)
597
      {
598
         scaledown=1;
599
         break;
600
      }
601
   }
602
   for (i=-end;i<0;i++)
603
   {
604
      if (ABS16(exc2[i])>16383)
605
      {
606
         scaledown=1;
607
         break;
608
      }
609
   }
610
#endif
611
10.3k
   if (N>end-start+1)
612
1.15k
      N=end-start+1;
613
10.3k
   if (end != start)
614
8.76k
      open_loop_nbest_pitch(sw, start, end, nsf, nbest, NULL, N, stack);
615
1.56k
   else
616
1.56k
      nbest[0] = start;
617
618
10.3k
   ALLOC(best_exc, nsf, spx_sig_t);
619
10.3k
   ALLOC(new_target, nsf, spx_word16_t);
620
10.3k
   ALLOC(best_target, nsf, spx_word16_t);
621
622
61.7k
   for (i=0;i<N;i++)
623
51.3k
   {
624
51.3k
      pitch=nbest[i];
625
51.3k
      SPEEX_MEMSET(exc, 0, nsf);
626
51.3k
      err=pitch_gain_search_3tap(target, ak, awk1, awk2, exc, gain_cdbk, gain_cdbk_size, pitch, p, nsf,
627
51.3k
                                 bits, stack, exc2, r, new_target, &cdbk_index, plc_tuning, *cumul_gain, scaledown);
628
51.3k
      if (err<best_err || best_err<0)
629
12.7k
      {
630
12.7k
         SPEEX_COPY(best_exc, exc, nsf);
631
12.7k
         SPEEX_COPY(best_target, new_target, nsf);
632
12.7k
         best_err=err;
633
12.7k
         best_pitch=pitch;
634
12.7k
         best_gain_index=cdbk_index;
635
12.7k
      }
636
51.3k
   }
637
   /*printf ("pitch: %d %d\n", best_pitch, best_gain_index);*/
638
10.3k
   speex_bits_pack(bits, best_pitch-start, params->pitch_bits);
639
10.3k
   speex_bits_pack(bits, best_gain_index, params->gain_bits);
640
#ifdef FIXED_POINT
641
   *cumul_gain = MULT16_32_Q13(SHL16(params->gain_cdbk[4*best_gain_index+3],8), MAX32(1024,*cumul_gain));
642
#else
643
10.3k
   *cumul_gain = 0.03125*MAX32(1024,*cumul_gain)*params->gain_cdbk[4*best_gain_index+3];
644
10.3k
#endif
645
   /*printf ("%f\n", cumul_gain);*/
646
   /*printf ("encode pitch: %d %d\n", best_pitch, best_gain_index);*/
647
10.3k
   SPEEX_COPY(exc, best_exc, nsf);
648
10.3k
   SPEEX_COPY(target, best_target, nsf);
649
#ifdef FIXED_POINT
650
   /* Scale target back up if needed */
651
   if (scaledown)
652
   {
653
      for (i=0;i<nsf;i++)
654
         target[i]=SHL16(target[i],1);
655
   }
656
#endif
657
10.3k
   return pitch;
658
11.1k
}
pitch_search_3tap
Line
Count
Source
555
30.4k
{
556
30.4k
   int i;
557
30.4k
   int cdbk_index, pitch=0, best_gain_index=0;
558
30.4k
   VARDECL(spx_sig_t *best_exc);
559
30.4k
   VARDECL(spx_word16_t *new_target);
560
30.4k
   VARDECL(spx_word16_t *best_target);
561
30.4k
   int best_pitch=0;
562
30.4k
   spx_word32_t err, best_err=-1;
563
30.4k
   int N;
564
30.4k
   const ltp_params *params;
565
30.4k
   const signed char *gain_cdbk;
566
30.4k
   int   gain_cdbk_size;
567
30.4k
   int scaledown=0;
568
569
30.4k
   VARDECL(int *nbest);
570
571
30.4k
   params = (const ltp_params*) par;
572
30.4k
   gain_cdbk_size = 1<<params->gain_bits;
573
30.4k
   gain_cdbk = params->gain_cdbk + 4*gain_cdbk_size*cdbk_offset;
574
575
30.4k
   N=complexity;
576
30.4k
   if (N>10)
577
0
      N=10;
578
30.4k
   if (N<1)
579
4.58k
      N=1;
580
581
30.4k
   ALLOC(nbest, N, int);
582
30.4k
   params = (const ltp_params*) par;
583
584
30.4k
   if (end<start)
585
1.66k
   {
586
1.66k
      speex_bits_pack(bits, 0, params->pitch_bits);
587
1.66k
      speex_bits_pack(bits, 0, params->gain_bits);
588
1.66k
      SPEEX_MEMSET(exc, 0, nsf);
589
1.66k
      return start;
590
1.66k
   }
591
592
28.7k
#ifdef FIXED_POINT
593
   /* Check if we need to scale everything down in the pitch search to avoid overflows */
594
1.01M
   for (i=0;i<nsf;i++)
595
992k
   {
596
992k
      if (ABS16(target[i])>16383)
597
5.14k
      {
598
5.14k
         scaledown=1;
599
5.14k
         break;
600
5.14k
      }
601
992k
   }
602
3.03M
   for (i=-end;i<0;i++)
603
3.00M
   {
604
3.00M
      if (ABS16(exc2[i])>16383)
605
4.87k
      {
606
4.87k
         scaledown=1;
607
4.87k
         break;
608
4.87k
      }
609
3.00M
   }
610
28.7k
#endif
611
28.7k
   if (N>end-start+1)
612
3.53k
      N=end-start+1;
613
28.7k
   if (end != start)
614
24.5k
      open_loop_nbest_pitch(sw, start, end, nsf, nbest, NULL, N, stack);
615
4.24k
   else
616
4.24k
      nbest[0] = start;
617
618
28.7k
   ALLOC(best_exc, nsf, spx_sig_t);
619
28.7k
   ALLOC(new_target, nsf, spx_word16_t);
620
28.7k
   ALLOC(best_target, nsf, spx_word16_t);
621
622
165k
   for (i=0;i<N;i++)
623
136k
   {
624
136k
      pitch=nbest[i];
625
136k
      SPEEX_MEMSET(exc, 0, nsf);
626
136k
      err=pitch_gain_search_3tap(target, ak, awk1, awk2, exc, gain_cdbk, gain_cdbk_size, pitch, p, nsf,
627
136k
                                 bits, stack, exc2, r, new_target, &cdbk_index, plc_tuning, *cumul_gain, scaledown);
628
136k
      if (err<best_err || best_err<0)
629
39.6k
      {
630
39.6k
         SPEEX_COPY(best_exc, exc, nsf);
631
39.6k
         SPEEX_COPY(best_target, new_target, nsf);
632
39.6k
         best_err=err;
633
39.6k
         best_pitch=pitch;
634
39.6k
         best_gain_index=cdbk_index;
635
39.6k
      }
636
136k
   }
637
   /*printf ("pitch: %d %d\n", best_pitch, best_gain_index);*/
638
28.7k
   speex_bits_pack(bits, best_pitch-start, params->pitch_bits);
639
28.7k
   speex_bits_pack(bits, best_gain_index, params->gain_bits);
640
28.7k
#ifdef FIXED_POINT
641
28.7k
   *cumul_gain = MULT16_32_Q13(SHL16(params->gain_cdbk[4*best_gain_index+3],8), MAX32(1024,*cumul_gain));
642
#else
643
   *cumul_gain = 0.03125*MAX32(1024,*cumul_gain)*params->gain_cdbk[4*best_gain_index+3];
644
#endif
645
   /*printf ("%f\n", cumul_gain);*/
646
   /*printf ("encode pitch: %d %d\n", best_pitch, best_gain_index);*/
647
28.7k
   SPEEX_COPY(exc, best_exc, nsf);
648
28.7k
   SPEEX_COPY(target, best_target, nsf);
649
28.7k
#ifdef FIXED_POINT
650
   /* Scale target back up if needed */
651
28.7k
   if (scaledown)
652
6.85k
   {
653
280k
      for (i=0;i<nsf;i++)
654
274k
         target[i]=SHL16(target[i],1);
655
6.85k
   }
656
28.7k
#endif
657
28.7k
   return pitch;
658
30.4k
}
659
#endif /* DISABLE_ENCODER */
660
661
#ifndef DISABLE_DECODER
662
void pitch_unquant_3tap(
663
spx_word16_t exc[],             /* Input excitation */
664
spx_word32_t exc_out[],         /* Output excitation */
665
int   start,                    /* Smallest pitch value allowed */
666
int   end,                      /* Largest pitch value allowed */
667
spx_word16_t pitch_coef,        /* Voicing (pitch) coefficient */
668
const void *par,
669
int   nsf,                      /* Number of samples in subframe */
670
int *pitch_val,
671
spx_word16_t *gain_val,
672
SpeexBits *bits,
673
char *stack,
674
int count_lost,
675
int subframe_offset,
676
spx_word16_t last_pitch_gain,
677
int cdbk_offset
678
)
679
136k
{
680
136k
   int i;
681
136k
   int pitch;
682
136k
   int gain_index;
683
136k
   spx_word16_t gain[3];
684
136k
   const signed char *gain_cdbk;
685
136k
   int gain_cdbk_size;
686
136k
   const ltp_params *params;
687
688
136k
   params = (const ltp_params*) par;
689
136k
   gain_cdbk_size = 1<<params->gain_bits;
690
136k
   gain_cdbk = params->gain_cdbk + 4*gain_cdbk_size*cdbk_offset;
691
692
136k
   pitch = speex_bits_unpack_unsigned(bits, params->pitch_bits);
693
136k
   pitch += start;
694
136k
   gain_index = speex_bits_unpack_unsigned(bits, params->gain_bits);
695
   /*printf ("decode pitch: %d %d\n", pitch, gain_index);*/
696
#ifdef FIXED_POINT
697
68.2k
   gain[0] = ADD16(32,(spx_word16_t)gain_cdbk[gain_index*4]);
698
68.2k
   gain[1] = ADD16(32,(spx_word16_t)gain_cdbk[gain_index*4+1]);
699
68.2k
   gain[2] = ADD16(32,(spx_word16_t)gain_cdbk[gain_index*4+2]);
700
#else
701
   gain[0] = 0.015625*gain_cdbk[gain_index*4]+.5;
702
   gain[1] = 0.015625*gain_cdbk[gain_index*4+1]+.5;
703
   gain[2] = 0.015625*gain_cdbk[gain_index*4+2]+.5;
704
#endif
705
706
136k
   if (count_lost && pitch > subframe_offset)
707
0
   {
708
0
      spx_word16_t gain_sum;
709
0
      if (1) {
710
#ifdef FIXED_POINT
711
0
         spx_word16_t tmp = count_lost < 4 ? last_pitch_gain : SHR16(last_pitch_gain,1);
712
0
         if (tmp>62)
713
0
            tmp=62;
714
#else
715
0
         spx_word16_t tmp = count_lost < 4 ? last_pitch_gain : 0.5 * last_pitch_gain;
716
0
         if (tmp>.95)
717
0
            tmp=.95;
718
#endif
719
0
         gain_sum = gain_3tap_to_1tap(gain);
720
721
0
         if (gain_sum > tmp)
722
0
         {
723
0
            spx_word16_t fact = DIV32_16(SHL32(EXTEND32(tmp),14),gain_sum);
724
0
            for (i=0;i<3;i++)
725
0
               gain[i]=MULT16_16_Q14(fact,gain[i]);
726
0
         }
727
728
0
      }
729
730
0
   }
731
732
136k
   *pitch_val = pitch;
733
136k
   gain_val[0]=gain[0];
734
136k
   gain_val[1]=gain[1];
735
136k
   gain_val[2]=gain[2];
736
136k
   gain[0] = SHL16(gain[0],7);
737
136k
   gain[1] = SHL16(gain[1],7);
738
136k
   gain[2] = SHL16(gain[2],7);
739
136k
   SPEEX_MEMSET(exc_out, 0, nsf);
740
545k
   for (i=0;i<3;i++)
741
409k
   {
742
409k
      int j;
743
409k
      int tmp1, tmp3;
744
409k
      int pp=pitch+1-i;
745
409k
      tmp1=nsf;
746
409k
      if (tmp1>pp)
747
332k
         tmp1=pp;
748
9.41M
      for (j=0;j<tmp1;j++)
749
9.01M
         exc_out[j]=MAC16_16(exc_out[j],gain[2-i],exc[j-pp]);
750
409k
      tmp3=nsf;
751
409k
      if (tmp3>pp+pitch)
752
305k
         tmp3=pp+pitch;
753
5.95M
      for (j=tmp1;j<tmp3;j++)
754
5.54M
         exc_out[j]=MAC16_16(exc_out[j],gain[2-i],exc[j-pp-pitch]);
755
409k
   }
756
   /*for (i=0;i<nsf;i++)
757
   exc[i]=PSHR32(exc32[i],13);*/
758
136k
}
pitch_unquant_3tap
Line
Count
Source
679
68.2k
{
680
68.2k
   int i;
681
68.2k
   int pitch;
682
68.2k
   int gain_index;
683
68.2k
   spx_word16_t gain[3];
684
68.2k
   const signed char *gain_cdbk;
685
68.2k
   int gain_cdbk_size;
686
68.2k
   const ltp_params *params;
687
688
68.2k
   params = (const ltp_params*) par;
689
68.2k
   gain_cdbk_size = 1<<params->gain_bits;
690
68.2k
   gain_cdbk = params->gain_cdbk + 4*gain_cdbk_size*cdbk_offset;
691
692
68.2k
   pitch = speex_bits_unpack_unsigned(bits, params->pitch_bits);
693
68.2k
   pitch += start;
694
68.2k
   gain_index = speex_bits_unpack_unsigned(bits, params->gain_bits);
695
   /*printf ("decode pitch: %d %d\n", pitch, gain_index);*/
696
#ifdef FIXED_POINT
697
   gain[0] = ADD16(32,(spx_word16_t)gain_cdbk[gain_index*4]);
698
   gain[1] = ADD16(32,(spx_word16_t)gain_cdbk[gain_index*4+1]);
699
   gain[2] = ADD16(32,(spx_word16_t)gain_cdbk[gain_index*4+2]);
700
#else
701
68.2k
   gain[0] = 0.015625*gain_cdbk[gain_index*4]+.5;
702
68.2k
   gain[1] = 0.015625*gain_cdbk[gain_index*4+1]+.5;
703
68.2k
   gain[2] = 0.015625*gain_cdbk[gain_index*4+2]+.5;
704
68.2k
#endif
705
706
68.2k
   if (count_lost && pitch > subframe_offset)
707
0
   {
708
0
      spx_word16_t gain_sum;
709
0
      if (1) {
710
#ifdef FIXED_POINT
711
         spx_word16_t tmp = count_lost < 4 ? last_pitch_gain : SHR16(last_pitch_gain,1);
712
         if (tmp>62)
713
            tmp=62;
714
#else
715
0
         spx_word16_t tmp = count_lost < 4 ? last_pitch_gain : 0.5 * last_pitch_gain;
716
0
         if (tmp>.95)
717
0
            tmp=.95;
718
0
#endif
719
0
         gain_sum = gain_3tap_to_1tap(gain);
720
721
0
         if (gain_sum > tmp)
722
0
         {
723
0
            spx_word16_t fact = DIV32_16(SHL32(EXTEND32(tmp),14),gain_sum);
724
0
            for (i=0;i<3;i++)
725
0
               gain[i]=MULT16_16_Q14(fact,gain[i]);
726
0
         }
727
728
0
      }
729
730
0
   }
731
732
68.2k
   *pitch_val = pitch;
733
68.2k
   gain_val[0]=gain[0];
734
68.2k
   gain_val[1]=gain[1];
735
68.2k
   gain_val[2]=gain[2];
736
68.2k
   gain[0] = SHL16(gain[0],7);
737
68.2k
   gain[1] = SHL16(gain[1],7);
738
68.2k
   gain[2] = SHL16(gain[2],7);
739
68.2k
   SPEEX_MEMSET(exc_out, 0, nsf);
740
272k
   for (i=0;i<3;i++)
741
204k
   {
742
204k
      int j;
743
204k
      int tmp1, tmp3;
744
204k
      int pp=pitch+1-i;
745
204k
      tmp1=nsf;
746
204k
      if (tmp1>pp)
747
166k
         tmp1=pp;
748
4.70M
      for (j=0;j<tmp1;j++)
749
4.50M
         exc_out[j]=MAC16_16(exc_out[j],gain[2-i],exc[j-pp]);
750
204k
      tmp3=nsf;
751
204k
      if (tmp3>pp+pitch)
752
152k
         tmp3=pp+pitch;
753
2.97M
      for (j=tmp1;j<tmp3;j++)
754
2.77M
         exc_out[j]=MAC16_16(exc_out[j],gain[2-i],exc[j-pp-pitch]);
755
204k
   }
756
   /*for (i=0;i<nsf;i++)
757
   exc[i]=PSHR32(exc32[i],13);*/
758
68.2k
}
pitch_unquant_3tap
Line
Count
Source
679
68.2k
{
680
68.2k
   int i;
681
68.2k
   int pitch;
682
68.2k
   int gain_index;
683
68.2k
   spx_word16_t gain[3];
684
68.2k
   const signed char *gain_cdbk;
685
68.2k
   int gain_cdbk_size;
686
68.2k
   const ltp_params *params;
687
688
68.2k
   params = (const ltp_params*) par;
689
68.2k
   gain_cdbk_size = 1<<params->gain_bits;
690
68.2k
   gain_cdbk = params->gain_cdbk + 4*gain_cdbk_size*cdbk_offset;
691
692
68.2k
   pitch = speex_bits_unpack_unsigned(bits, params->pitch_bits);
693
68.2k
   pitch += start;
694
68.2k
   gain_index = speex_bits_unpack_unsigned(bits, params->gain_bits);
695
   /*printf ("decode pitch: %d %d\n", pitch, gain_index);*/
696
68.2k
#ifdef FIXED_POINT
697
68.2k
   gain[0] = ADD16(32,(spx_word16_t)gain_cdbk[gain_index*4]);
698
68.2k
   gain[1] = ADD16(32,(spx_word16_t)gain_cdbk[gain_index*4+1]);
699
68.2k
   gain[2] = ADD16(32,(spx_word16_t)gain_cdbk[gain_index*4+2]);
700
#else
701
   gain[0] = 0.015625*gain_cdbk[gain_index*4]+.5;
702
   gain[1] = 0.015625*gain_cdbk[gain_index*4+1]+.5;
703
   gain[2] = 0.015625*gain_cdbk[gain_index*4+2]+.5;
704
#endif
705
706
68.2k
   if (count_lost && pitch > subframe_offset)
707
0
   {
708
0
      spx_word16_t gain_sum;
709
0
      if (1) {
710
0
#ifdef FIXED_POINT
711
0
         spx_word16_t tmp = count_lost < 4 ? last_pitch_gain : SHR16(last_pitch_gain,1);
712
0
         if (tmp>62)
713
0
            tmp=62;
714
#else
715
         spx_word16_t tmp = count_lost < 4 ? last_pitch_gain : 0.5 * last_pitch_gain;
716
         if (tmp>.95)
717
            tmp=.95;
718
#endif
719
0
         gain_sum = gain_3tap_to_1tap(gain);
720
721
0
         if (gain_sum > tmp)
722
0
         {
723
0
            spx_word16_t fact = DIV32_16(SHL32(EXTEND32(tmp),14),gain_sum);
724
0
            for (i=0;i<3;i++)
725
0
               gain[i]=MULT16_16_Q14(fact,gain[i]);
726
0
         }
727
728
0
      }
729
730
0
   }
731
732
68.2k
   *pitch_val = pitch;
733
68.2k
   gain_val[0]=gain[0];
734
68.2k
   gain_val[1]=gain[1];
735
68.2k
   gain_val[2]=gain[2];
736
68.2k
   gain[0] = SHL16(gain[0],7);
737
68.2k
   gain[1] = SHL16(gain[1],7);
738
68.2k
   gain[2] = SHL16(gain[2],7);
739
68.2k
   SPEEX_MEMSET(exc_out, 0, nsf);
740
272k
   for (i=0;i<3;i++)
741
204k
   {
742
204k
      int j;
743
204k
      int tmp1, tmp3;
744
204k
      int pp=pitch+1-i;
745
204k
      tmp1=nsf;
746
204k
      if (tmp1>pp)
747
166k
         tmp1=pp;
748
4.70M
      for (j=0;j<tmp1;j++)
749
4.50M
         exc_out[j]=MAC16_16(exc_out[j],gain[2-i],exc[j-pp]);
750
204k
      tmp3=nsf;
751
204k
      if (tmp3>pp+pitch)
752
152k
         tmp3=pp+pitch;
753
2.97M
      for (j=tmp1;j<tmp3;j++)
754
2.77M
         exc_out[j]=MAC16_16(exc_out[j],gain[2-i],exc[j-pp-pitch]);
755
204k
   }
756
   /*for (i=0;i<nsf;i++)
757
   exc[i]=PSHR32(exc32[i],13);*/
758
68.2k
}
759
#endif /* DISABLE_DECODER */
760
761
#ifndef DISABLE_ENCODER
762
/** Forced pitch delay and gain */
763
int forced_pitch_quant(
764
spx_word16_t target[],                 /* Target vector */
765
spx_word16_t *sw,
766
spx_coef_t ak[],                     /* LPCs for this subframe */
767
spx_coef_t awk1[],                   /* Weighted LPCs #1 for this subframe */
768
spx_coef_t awk2[],                   /* Weighted LPCs #2 for this subframe */
769
spx_sig_t exc[],                    /* Excitation */
770
const void *par,
771
int   start,                    /* Smallest pitch value allowed */
772
int   end,                      /* Largest pitch value allowed */
773
spx_word16_t pitch_coef,               /* Voicing (pitch) coefficient */
774
int   p,                        /* Number of LPC coeffs */
775
int   nsf,                      /* Number of samples in subframe */
776
SpeexBits *bits,
777
char *stack,
778
spx_word16_t *exc2,
779
spx_word16_t *r,
780
int complexity,
781
int cdbk_offset,
782
int plc_tuning,
783
spx_word32_t *cumul_gain
784
)
785
63.2k
{
786
63.2k
   int i;
787
63.2k
   VARDECL(spx_word16_t *res);
788
63.2k
   ALLOC(res, nsf, spx_word16_t);
789
#ifdef FIXED_POINT
790
45.0k
   if (pitch_coef>63)
791
352
      pitch_coef=63;
792
#else
793
18.2k
   if (pitch_coef>.99)
794
144
      pitch_coef=.99;
795
#endif
796
2.00M
   for (i=0;i<nsf&&i<start;i++)
797
1.93M
   {
798
1.93M
      exc[i]=MULT16_16(SHL16(pitch_coef, 7),exc2[i-start]);
799
1.93M
   }
800
656k
   for (;i<nsf;i++)
801
593k
   {
802
593k
      exc[i]=MULT16_32_Q15(SHL16(pitch_coef, 9),exc[i-start]);
803
593k
   }
804
2.59M
   for (i=0;i<nsf;i++)
805
2.53M
      res[i] = EXTRACT16(PSHR32(exc[i], SIG_SHIFT-1));
806
63.2k
   syn_percep_zero16(res, ak, awk1, awk2, res, nsf, p, stack);
807
2.59M
   for (i=0;i<nsf;i++)
808
2.53M
      target[i]=EXTRACT16(SATURATE(SUB32(EXTEND32(target[i]),EXTEND32(res[i])),32700));
809
63.2k
   return start;
810
63.2k
}
forced_pitch_quant
Line
Count
Source
785
18.2k
{
786
18.2k
   int i;
787
18.2k
   VARDECL(spx_word16_t *res);
788
18.2k
   ALLOC(res, nsf, spx_word16_t);
789
#ifdef FIXED_POINT
790
   if (pitch_coef>63)
791
      pitch_coef=63;
792
#else
793
18.2k
   if (pitch_coef>.99)
794
144
      pitch_coef=.99;
795
18.2k
#endif
796
503k
   for (i=0;i<nsf&&i<start;i++)
797
484k
   {
798
484k
      exc[i]=MULT16_16(SHL16(pitch_coef, 7),exc2[i-start]);
799
484k
   }
800
263k
   for (;i<nsf;i++)
801
245k
   {
802
245k
      exc[i]=MULT16_32_Q15(SHL16(pitch_coef, 9),exc[i-start]);
803
245k
   }
804
748k
   for (i=0;i<nsf;i++)
805
730k
      res[i] = EXTRACT16(PSHR32(exc[i], SIG_SHIFT-1));
806
18.2k
   syn_percep_zero16(res, ak, awk1, awk2, res, nsf, p, stack);
807
748k
   for (i=0;i<nsf;i++)
808
730k
      target[i]=EXTRACT16(SATURATE(SUB32(EXTEND32(target[i]),EXTEND32(res[i])),32700));
809
18.2k
   return start;
810
18.2k
}
forced_pitch_quant
Line
Count
Source
785
45.0k
{
786
45.0k
   int i;
787
45.0k
   VARDECL(spx_word16_t *res);
788
45.0k
   ALLOC(res, nsf, spx_word16_t);
789
45.0k
#ifdef FIXED_POINT
790
45.0k
   if (pitch_coef>63)
791
352
      pitch_coef=63;
792
#else
793
   if (pitch_coef>.99)
794
      pitch_coef=.99;
795
#endif
796
1.49M
   for (i=0;i<nsf&&i<start;i++)
797
1.45M
   {
798
1.45M
      exc[i]=MULT16_16(SHL16(pitch_coef, 7),exc2[i-start]);
799
1.45M
   }
800
393k
   for (;i<nsf;i++)
801
348k
   {
802
348k
      exc[i]=MULT16_32_Q15(SHL16(pitch_coef, 9),exc[i-start]);
803
348k
   }
804
1.84M
   for (i=0;i<nsf;i++)
805
1.80M
      res[i] = EXTRACT16(PSHR32(exc[i], SIG_SHIFT-1));
806
45.0k
   syn_percep_zero16(res, ak, awk1, awk2, res, nsf, p, stack);
807
1.84M
   for (i=0;i<nsf;i++)
808
1.80M
      target[i]=EXTRACT16(SATURATE(SUB32(EXTEND32(target[i]),EXTEND32(res[i])),32700));
809
45.0k
   return start;
810
45.0k
}
811
#endif /* DISABLE_ENCODER */
812
813
#ifndef DISABLE_DECODER
814
/** Unquantize forced pitch delay and gain */
815
void forced_pitch_unquant(
816
spx_word16_t exc[],             /* Input excitation */
817
spx_word32_t exc_out[],         /* Output excitation */
818
int   start,                    /* Smallest pitch value allowed */
819
int   end,                      /* Largest pitch value allowed */
820
spx_word16_t pitch_coef,        /* Voicing (pitch) coefficient */
821
const void *par,
822
int   nsf,                      /* Number of samples in subframe */
823
int *pitch_val,
824
spx_word16_t *gain_val,
825
SpeexBits *bits,
826
char *stack,
827
int count_lost,
828
int subframe_offset,
829
spx_word16_t last_pitch_gain,
830
int cdbk_offset
831
)
832
71.7k
{
833
71.7k
   int i;
834
#ifdef FIXED_POINT
835
35.8k
   if (pitch_coef>63)
836
4.78k
      pitch_coef=63;
837
#else
838
35.8k
   if (pitch_coef>.99)
839
4.78k
      pitch_coef=.99;
840
#endif
841
2.94M
   for (i=0;i<nsf;i++)
842
2.86M
   {
843
2.86M
      exc_out[i]=MULT16_16(exc[i-start],SHL16(pitch_coef,7));
844
2.86M
      exc[i] = EXTRACT16(PSHR32(exc_out[i],13));
845
2.86M
   }
846
71.7k
   *pitch_val = start;
847
71.7k
   gain_val[0]=gain_val[2]=0;
848
71.7k
   gain_val[1] = pitch_coef;
849
71.7k
}
forced_pitch_unquant
Line
Count
Source
832
35.8k
{
833
35.8k
   int i;
834
#ifdef FIXED_POINT
835
   if (pitch_coef>63)
836
      pitch_coef=63;
837
#else
838
35.8k
   if (pitch_coef>.99)
839
4.78k
      pitch_coef=.99;
840
35.8k
#endif
841
1.47M
   for (i=0;i<nsf;i++)
842
1.43M
   {
843
1.43M
      exc_out[i]=MULT16_16(exc[i-start],SHL16(pitch_coef,7));
844
1.43M
      exc[i] = EXTRACT16(PSHR32(exc_out[i],13));
845
1.43M
   }
846
35.8k
   *pitch_val = start;
847
35.8k
   gain_val[0]=gain_val[2]=0;
848
35.8k
   gain_val[1] = pitch_coef;
849
35.8k
}
forced_pitch_unquant
Line
Count
Source
832
35.8k
{
833
35.8k
   int i;
834
35.8k
#ifdef FIXED_POINT
835
35.8k
   if (pitch_coef>63)
836
4.78k
      pitch_coef=63;
837
#else
838
   if (pitch_coef>.99)
839
      pitch_coef=.99;
840
#endif
841
1.47M
   for (i=0;i<nsf;i++)
842
1.43M
   {
843
1.43M
      exc_out[i]=MULT16_16(exc[i-start],SHL16(pitch_coef,7));
844
1.43M
      exc[i] = EXTRACT16(PSHR32(exc_out[i],13));
845
1.43M
   }
846
35.8k
   *pitch_val = start;
847
35.8k
   gain_val[0]=gain_val[2]=0;
848
35.8k
   gain_val[1] = pitch_coef;
849
35.8k
}
850
#endif /* DISABLE_DECODER */