Coverage Report

Created: 2026-06-07 08:05

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/opus/celt/pitch.c
Line
Count
Source
1
/* Copyright (c) 2007-2008 CSIRO
2
   Copyright (c) 2007-2009 Xiph.Org Foundation
3
   Written by Jean-Marc Valin */
4
/**
5
   @file pitch.c
6
   @brief Pitch analysis
7
 */
8
9
/*
10
   Redistribution and use in source and binary forms, with or without
11
   modification, are permitted provided that the following conditions
12
   are met:
13
14
   - Redistributions of source code must retain the above copyright
15
   notice, this list of conditions and the following disclaimer.
16
17
   - Redistributions in binary form must reproduce the above copyright
18
   notice, this list of conditions and the following disclaimer in the
19
   documentation and/or other materials provided with the distribution.
20
21
   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22
   ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23
   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
24
   A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
25
   OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
26
   EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
27
   PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
28
   PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
29
   LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
30
   NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
31
   SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32
*/
33
34
#ifdef HAVE_CONFIG_H
35
#include "config.h"
36
#endif
37
38
#include "pitch.h"
39
#include "os_support.h"
40
#include "modes.h"
41
#include "stack_alloc.h"
42
#include "mathops.h"
43
#include "celt_lpc.h"
44
45
static void find_best_pitch(opus_val32 *xcorr, opus_val16 *y, int len,
46
                            int max_pitch, int *best_pitch
47
#ifdef FIXED_POINT
48
                            , int yshift, opus_val32 maxcorr
49
#endif
50
                            )
51
491k
{
52
491k
   int i, j;
53
491k
   opus_val32 Syy=1;
54
491k
   opus_val16 best_num[2];
55
491k
   opus_val32 best_den[2];
56
#ifdef FIXED_POINT
57
   int xshift;
58
59
   xshift = celt_ilog2(maxcorr)-14;
60
#endif
61
62
491k
   best_num[0] = -1;
63
491k
   best_num[1] = -1;
64
491k
   best_den[0] = 0;
65
491k
   best_den[1] = 0;
66
491k
   best_pitch[0] = 0;
67
491k
   best_pitch[1] = 1;
68
160M
   for (j=0;j<len;j++)
69
160M
      Syy = ADD32(Syy, SHR32(MULT16_16(y[j],y[j]), yshift));
70
154M
   for (i=0;i<max_pitch;i++)
71
153M
   {
72
153M
      if (xcorr[i]>0)
73
18.1M
      {
74
18.1M
         opus_val16 num;
75
18.1M
         opus_val32 xcorr16;
76
18.1M
         xcorr16 = EXTRACT16(VSHR32(xcorr[i], xshift));
77
#ifndef FIXED_POINT
78
         /* Considering the range of xcorr16, this should avoid both underflows
79
            and overflows (inf) when squaring xcorr16 */
80
         xcorr16 *= 1e-12f;
81
#endif
82
18.1M
         num = MULT16_16_Q15(xcorr16,xcorr16);
83
18.1M
         if (MULT16_32_Q15(num,best_den[1]) > MULT16_32_Q15(best_num[1],Syy))
84
3.81M
         {
85
3.81M
            if (MULT16_32_Q15(num,best_den[0]) > MULT16_32_Q15(best_num[0],Syy))
86
2.69M
            {
87
2.69M
               best_num[1] = best_num[0];
88
2.69M
               best_den[1] = best_den[0];
89
2.69M
               best_pitch[1] = best_pitch[0];
90
2.69M
               best_num[0] = num;
91
2.69M
               best_den[0] = Syy;
92
2.69M
               best_pitch[0] = i;
93
2.69M
            } else {
94
1.12M
               best_num[1] = num;
95
1.12M
               best_den[1] = Syy;
96
1.12M
               best_pitch[1] = i;
97
1.12M
            }
98
3.81M
         }
99
18.1M
      }
100
153M
      Syy += SHR32(MULT16_16(y[i+len],y[i+len]),yshift) - SHR32(MULT16_16(y[i],y[i]),yshift);
101
153M
      Syy = MAX32(1, Syy);
102
153M
   }
103
491k
}
pitch.c:find_best_pitch
Line
Count
Source
51
285k
{
52
285k
   int i, j;
53
285k
   opus_val32 Syy=1;
54
285k
   opus_val16 best_num[2];
55
285k
   opus_val32 best_den[2];
56
285k
#ifdef FIXED_POINT
57
285k
   int xshift;
58
59
285k
   xshift = celt_ilog2(maxcorr)-14;
60
285k
#endif
61
62
285k
   best_num[0] = -1;
63
285k
   best_num[1] = -1;
64
285k
   best_den[0] = 0;
65
285k
   best_den[1] = 0;
66
285k
   best_pitch[0] = 0;
67
285k
   best_pitch[1] = 1;
68
92.8M
   for (j=0;j<len;j++)
69
92.5M
      Syy = ADD32(Syy, SHR32(MULT16_16(y[j],y[j]), yshift));
70
89.8M
   for (i=0;i<max_pitch;i++)
71
89.5M
   {
72
89.5M
      if (xcorr[i]>0)
73
11.2M
      {
74
11.2M
         opus_val16 num;
75
11.2M
         opus_val32 xcorr16;
76
11.2M
         xcorr16 = EXTRACT16(VSHR32(xcorr[i], xshift));
77
#ifndef FIXED_POINT
78
         /* Considering the range of xcorr16, this should avoid both underflows
79
            and overflows (inf) when squaring xcorr16 */
80
         xcorr16 *= 1e-12f;
81
#endif
82
11.2M
         num = MULT16_16_Q15(xcorr16,xcorr16);
83
11.2M
         if (MULT16_32_Q15(num,best_den[1]) > MULT16_32_Q15(best_num[1],Syy))
84
2.26M
         {
85
2.26M
            if (MULT16_32_Q15(num,best_den[0]) > MULT16_32_Q15(best_num[0],Syy))
86
1.58M
            {
87
1.58M
               best_num[1] = best_num[0];
88
1.58M
               best_den[1] = best_den[0];
89
1.58M
               best_pitch[1] = best_pitch[0];
90
1.58M
               best_num[0] = num;
91
1.58M
               best_den[0] = Syy;
92
1.58M
               best_pitch[0] = i;
93
1.58M
            } else {
94
682k
               best_num[1] = num;
95
682k
               best_den[1] = Syy;
96
682k
               best_pitch[1] = i;
97
682k
            }
98
2.26M
         }
99
11.2M
      }
100
89.5M
      Syy += SHR32(MULT16_16(y[i+len],y[i+len]),yshift) - SHR32(MULT16_16(y[i],y[i]),yshift);
101
89.5M
      Syy = MAX32(1, Syy);
102
89.5M
   }
103
285k
}
pitch.c:find_best_pitch
Line
Count
Source
51
206k
{
52
206k
   int i, j;
53
206k
   opus_val32 Syy=1;
54
206k
   opus_val16 best_num[2];
55
206k
   opus_val32 best_den[2];
56
#ifdef FIXED_POINT
57
   int xshift;
58
59
   xshift = celt_ilog2(maxcorr)-14;
60
#endif
61
62
206k
   best_num[0] = -1;
63
206k
   best_num[1] = -1;
64
206k
   best_den[0] = 0;
65
206k
   best_den[1] = 0;
66
206k
   best_pitch[0] = 0;
67
206k
   best_pitch[1] = 1;
68
67.9M
   for (j=0;j<len;j++)
69
67.6M
      Syy = ADD32(Syy, SHR32(MULT16_16(y[j],y[j]), yshift));
70
64.4M
   for (i=0;i<max_pitch;i++)
71
64.2M
   {
72
64.2M
      if (xcorr[i]>0)
73
6.93M
      {
74
6.93M
         opus_val16 num;
75
6.93M
         opus_val32 xcorr16;
76
6.93M
         xcorr16 = EXTRACT16(VSHR32(xcorr[i], xshift));
77
6.93M
#ifndef FIXED_POINT
78
         /* Considering the range of xcorr16, this should avoid both underflows
79
            and overflows (inf) when squaring xcorr16 */
80
6.93M
         xcorr16 *= 1e-12f;
81
6.93M
#endif
82
6.93M
         num = MULT16_16_Q15(xcorr16,xcorr16);
83
6.93M
         if (MULT16_32_Q15(num,best_den[1]) > MULT16_32_Q15(best_num[1],Syy))
84
1.54M
         {
85
1.54M
            if (MULT16_32_Q15(num,best_den[0]) > MULT16_32_Q15(best_num[0],Syy))
86
1.10M
            {
87
1.10M
               best_num[1] = best_num[0];
88
1.10M
               best_den[1] = best_den[0];
89
1.10M
               best_pitch[1] = best_pitch[0];
90
1.10M
               best_num[0] = num;
91
1.10M
               best_den[0] = Syy;
92
1.10M
               best_pitch[0] = i;
93
1.10M
            } else {
94
437k
               best_num[1] = num;
95
437k
               best_den[1] = Syy;
96
437k
               best_pitch[1] = i;
97
437k
            }
98
1.54M
         }
99
6.93M
      }
100
64.2M
      Syy += SHR32(MULT16_16(y[i+len],y[i+len]),yshift) - SHR32(MULT16_16(y[i],y[i]),yshift);
101
64.2M
      Syy = MAX32(1, Syy);
102
64.2M
   }
103
206k
}
104
105
static void celt_fir5(opus_val16 *x,
106
         const opus_val16 *num,
107
         int N)
108
491k
{
109
491k
   int i;
110
491k
   opus_val16 num0, num1, num2, num3, num4;
111
491k
   opus_val32 mem0, mem1, mem2, mem3, mem4;
112
491k
   num0=num[0];
113
491k
   num1=num[1];
114
491k
   num2=num[2];
115
491k
   num3=num[3];
116
491k
   num4=num[4];
117
491k
   mem0=0;
118
491k
   mem1=0;
119
491k
   mem2=0;
120
491k
   mem3=0;
121
491k
   mem4=0;
122
436M
   for (i=0;i<N;i++)
123
435M
   {
124
435M
      opus_val32 sum = SHL32(EXTEND32(x[i]), SIG_SHIFT);
125
435M
      sum = MAC16_16(sum,num0,mem0);
126
435M
      sum = MAC16_16(sum,num1,mem1);
127
435M
      sum = MAC16_16(sum,num2,mem2);
128
435M
      sum = MAC16_16(sum,num3,mem3);
129
435M
      sum = MAC16_16(sum,num4,mem4);
130
435M
      mem4 = mem3;
131
435M
      mem3 = mem2;
132
435M
      mem2 = mem1;
133
435M
      mem1 = mem0;
134
435M
      mem0 = x[i];
135
435M
      x[i] = ROUND16(sum, SIG_SHIFT);
136
435M
   }
137
491k
}
pitch.c:celt_fir5
Line
Count
Source
108
245k
{
109
245k
   int i;
110
245k
   opus_val16 num0, num1, num2, num3, num4;
111
245k
   opus_val32 mem0, mem1, mem2, mem3, mem4;
112
245k
   num0=num[0];
113
245k
   num1=num[1];
114
245k
   num2=num[2];
115
245k
   num3=num[3];
116
245k
   num4=num[4];
117
245k
   mem0=0;
118
245k
   mem1=0;
119
245k
   mem2=0;
120
245k
   mem3=0;
121
245k
   mem4=0;
122
218M
   for (i=0;i<N;i++)
123
217M
   {
124
217M
      opus_val32 sum = SHL32(EXTEND32(x[i]), SIG_SHIFT);
125
217M
      sum = MAC16_16(sum,num0,mem0);
126
217M
      sum = MAC16_16(sum,num1,mem1);
127
217M
      sum = MAC16_16(sum,num2,mem2);
128
217M
      sum = MAC16_16(sum,num3,mem3);
129
217M
      sum = MAC16_16(sum,num4,mem4);
130
217M
      mem4 = mem3;
131
217M
      mem3 = mem2;
132
217M
      mem2 = mem1;
133
217M
      mem1 = mem0;
134
217M
      mem0 = x[i];
135
217M
      x[i] = ROUND16(sum, SIG_SHIFT);
136
217M
   }
137
245k
}
pitch.c:celt_fir5
Line
Count
Source
108
245k
{
109
245k
   int i;
110
245k
   opus_val16 num0, num1, num2, num3, num4;
111
245k
   opus_val32 mem0, mem1, mem2, mem3, mem4;
112
245k
   num0=num[0];
113
245k
   num1=num[1];
114
245k
   num2=num[2];
115
245k
   num3=num[3];
116
245k
   num4=num[4];
117
245k
   mem0=0;
118
245k
   mem1=0;
119
245k
   mem2=0;
120
245k
   mem3=0;
121
245k
   mem4=0;
122
218M
   for (i=0;i<N;i++)
123
217M
   {
124
217M
      opus_val32 sum = SHL32(EXTEND32(x[i]), SIG_SHIFT);
125
217M
      sum = MAC16_16(sum,num0,mem0);
126
217M
      sum = MAC16_16(sum,num1,mem1);
127
217M
      sum = MAC16_16(sum,num2,mem2);
128
217M
      sum = MAC16_16(sum,num3,mem3);
129
217M
      sum = MAC16_16(sum,num4,mem4);
130
217M
      mem4 = mem3;
131
217M
      mem3 = mem2;
132
217M
      mem2 = mem1;
133
217M
      mem1 = mem0;
134
217M
      mem0 = x[i];
135
217M
      x[i] = ROUND16(sum, SIG_SHIFT);
136
217M
   }
137
245k
}
138
139
140
void pitch_downsample(celt_sig * OPUS_RESTRICT x[], opus_val16 * OPUS_RESTRICT x_lp,
141
      int len, int C, int factor, int arch)
142
245k
{
143
245k
   int i;
144
245k
   opus_val32 ac[5];
145
245k
   opus_val16 tmp=Q15ONE;
146
245k
   opus_val16 lpc[4];
147
245k
   opus_val16 lpc2[5];
148
245k
   opus_val16 c1 = QCONST16(.8f,15);
149
245k
   int offset;
150
#ifdef FIXED_POINT
151
   int shift;
152
   opus_val32 maxabs;
153
#endif
154
245k
   offset = factor/2;
155
#ifdef FIXED_POINT
156
   maxabs = celt_maxabs32(x[0], len*factor);
157
142k
   if (C==2)
158
74.9k
   {
159
74.9k
      opus_val32 maxabs_1 = celt_maxabs32(x[1], len*factor);
160
74.9k
      maxabs = MAX32(maxabs, maxabs_1);
161
74.9k
   }
162
142k
   if (maxabs<1)
163
1.44k
      maxabs=1;
164
   shift = celt_ilog2(maxabs)-10;
165
142k
   if (shift<0)
166
3.85k
      shift=0;
167
142k
   if (C==2)
168
74.9k
      shift++;
169
126M
   for (i=1;i<len;i++)
170
126M
      x_lp[i] = SHR32(x[0][(factor*i-offset)], shift+2) + SHR32(x[0][(factor*i+offset)], shift+2) + SHR32(x[0][factor*i], shift+1);
171
142k
   x_lp[0] = SHR32(x[0][offset], shift+2) + SHR32(x[0][0], shift+1);
172
142k
   if (C==2)
173
74.9k
   {
174
68.2M
      for (i=1;i<len;i++)
175
68.1M
         x_lp[i] += SHR32(x[1][(factor*i-offset)], shift+2) + SHR32(x[1][(factor*i+offset)], shift+2) + SHR32(x[1][factor*i], shift+1);
176
74.9k
      x_lp[0] += SHR32(x[1][offset], shift+2) + SHR32(x[1][0], shift+1);
177
74.9k
   }
178
#else
179
91.5M
   for (i=1;i<len;i++)
180
91.4M
      x_lp[i] = .25f*x[0][(factor*i-offset)] + .25f*x[0][(factor*i+offset)] + .5f*x[0][factor*i];
181
   x_lp[0] = .25f*x[0][offset] + .5f*x[0][0];
182
103k
   if (C==2)
183
53.1k
   {
184
49.7M
      for (i=1;i<len;i++)
185
49.6M
         x_lp[i] += .25f*x[1][(factor*i-offset)] + .25f*x[1][(factor*i+offset)] + .5f*x[1][factor*i];
186
53.1k
      x_lp[0] += .25f*x[1][offset] + .5f*x[1][0];
187
53.1k
   }
188
#endif
189
245k
   _celt_autocorr(x_lp, ac, NULL, 0,
190
245k
                  4, len, arch);
191
192
   /* Noise floor -40 dB */
193
#ifdef FIXED_POINT
194
142k
   ac[0] += SHR32(ac[0],13);
195
#else
196
   ac[0] *= 1.0001f;
197
#endif
198
   /* Lag windowing */
199
1.22M
   for (i=1;i<=4;i++)
200
982k
   {
201
      /*ac[i] *= exp(-.5*(2*M_PI*.002*i)*(2*M_PI*.002*i));*/
202
#ifdef FIXED_POINT
203
570k
      ac[i] -= MULT16_32_Q15(2*i*i, ac[i]);
204
#else
205
      ac[i] -= ac[i]*(.008f*i)*(.008f*i);
206
#endif
207
982k
   }
208
209
245k
   _celt_lpc(lpc, ac, 4);
210
1.22M
   for (i=0;i<4;i++)
211
982k
   {
212
982k
      tmp = MULT16_16_Q15(QCONST16(.9f,15), tmp);
213
982k
      lpc[i] = MULT16_16_Q15(lpc[i], tmp);
214
982k
   }
215
   /* Add a zero */
216
245k
   lpc2[0] = lpc[0] + QCONST16(.8f,SIG_SHIFT);
217
245k
   lpc2[1] = lpc[1] + MULT16_16_Q15(c1,lpc[0]);
218
245k
   lpc2[2] = lpc[2] + MULT16_16_Q15(c1,lpc[1]);
219
245k
   lpc2[3] = lpc[3] + MULT16_16_Q15(c1,lpc[2]);
220
245k
   lpc2[4] = MULT16_16_Q15(c1,lpc[3]);
221
245k
   celt_fir5(x_lp, lpc2, len);
222
245k
}
pitch_downsample
Line
Count
Source
142
142k
{
143
142k
   int i;
144
142k
   opus_val32 ac[5];
145
142k
   opus_val16 tmp=Q15ONE;
146
142k
   opus_val16 lpc[4];
147
142k
   opus_val16 lpc2[5];
148
142k
   opus_val16 c1 = QCONST16(.8f,15);
149
142k
   int offset;
150
142k
#ifdef FIXED_POINT
151
142k
   int shift;
152
142k
   opus_val32 maxabs;
153
142k
#endif
154
142k
   offset = factor/2;
155
142k
#ifdef FIXED_POINT
156
142k
   maxabs = celt_maxabs32(x[0], len*factor);
157
142k
   if (C==2)
158
74.9k
   {
159
74.9k
      opus_val32 maxabs_1 = celt_maxabs32(x[1], len*factor);
160
74.9k
      maxabs = MAX32(maxabs, maxabs_1);
161
74.9k
   }
162
142k
   if (maxabs<1)
163
1.44k
      maxabs=1;
164
142k
   shift = celt_ilog2(maxabs)-10;
165
142k
   if (shift<0)
166
3.85k
      shift=0;
167
142k
   if (C==2)
168
74.9k
      shift++;
169
126M
   for (i=1;i<len;i++)
170
126M
      x_lp[i] = SHR32(x[0][(factor*i-offset)], shift+2) + SHR32(x[0][(factor*i+offset)], shift+2) + SHR32(x[0][factor*i], shift+1);
171
142k
   x_lp[0] = SHR32(x[0][offset], shift+2) + SHR32(x[0][0], shift+1);
172
142k
   if (C==2)
173
74.9k
   {
174
68.2M
      for (i=1;i<len;i++)
175
68.1M
         x_lp[i] += SHR32(x[1][(factor*i-offset)], shift+2) + SHR32(x[1][(factor*i+offset)], shift+2) + SHR32(x[1][factor*i], shift+1);
176
74.9k
      x_lp[0] += SHR32(x[1][offset], shift+2) + SHR32(x[1][0], shift+1);
177
74.9k
   }
178
#else
179
   for (i=1;i<len;i++)
180
      x_lp[i] = .25f*x[0][(factor*i-offset)] + .25f*x[0][(factor*i+offset)] + .5f*x[0][factor*i];
181
   x_lp[0] = .25f*x[0][offset] + .5f*x[0][0];
182
   if (C==2)
183
   {
184
      for (i=1;i<len;i++)
185
         x_lp[i] += .25f*x[1][(factor*i-offset)] + .25f*x[1][(factor*i+offset)] + .5f*x[1][factor*i];
186
      x_lp[0] += .25f*x[1][offset] + .5f*x[1][0];
187
   }
188
#endif
189
142k
   _celt_autocorr(x_lp, ac, NULL, 0,
190
142k
                  4, len, arch);
191
192
   /* Noise floor -40 dB */
193
142k
#ifdef FIXED_POINT
194
142k
   ac[0] += SHR32(ac[0],13);
195
#else
196
   ac[0] *= 1.0001f;
197
#endif
198
   /* Lag windowing */
199
712k
   for (i=1;i<=4;i++)
200
570k
   {
201
      /*ac[i] *= exp(-.5*(2*M_PI*.002*i)*(2*M_PI*.002*i));*/
202
570k
#ifdef FIXED_POINT
203
570k
      ac[i] -= MULT16_32_Q15(2*i*i, ac[i]);
204
#else
205
      ac[i] -= ac[i]*(.008f*i)*(.008f*i);
206
#endif
207
570k
   }
208
209
142k
   _celt_lpc(lpc, ac, 4);
210
712k
   for (i=0;i<4;i++)
211
570k
   {
212
570k
      tmp = MULT16_16_Q15(QCONST16(.9f,15), tmp);
213
570k
      lpc[i] = MULT16_16_Q15(lpc[i], tmp);
214
570k
   }
215
   /* Add a zero */
216
142k
   lpc2[0] = lpc[0] + QCONST16(.8f,SIG_SHIFT);
217
142k
   lpc2[1] = lpc[1] + MULT16_16_Q15(c1,lpc[0]);
218
142k
   lpc2[2] = lpc[2] + MULT16_16_Q15(c1,lpc[1]);
219
142k
   lpc2[3] = lpc[3] + MULT16_16_Q15(c1,lpc[2]);
220
142k
   lpc2[4] = MULT16_16_Q15(c1,lpc[3]);
221
142k
   celt_fir5(x_lp, lpc2, len);
222
142k
}
pitch_downsample
Line
Count
Source
142
103k
{
143
103k
   int i;
144
103k
   opus_val32 ac[5];
145
103k
   opus_val16 tmp=Q15ONE;
146
103k
   opus_val16 lpc[4];
147
103k
   opus_val16 lpc2[5];
148
103k
   opus_val16 c1 = QCONST16(.8f,15);
149
103k
   int offset;
150
#ifdef FIXED_POINT
151
   int shift;
152
   opus_val32 maxabs;
153
#endif
154
103k
   offset = factor/2;
155
#ifdef FIXED_POINT
156
   maxabs = celt_maxabs32(x[0], len*factor);
157
   if (C==2)
158
   {
159
      opus_val32 maxabs_1 = celt_maxabs32(x[1], len*factor);
160
      maxabs = MAX32(maxabs, maxabs_1);
161
   }
162
   if (maxabs<1)
163
      maxabs=1;
164
   shift = celt_ilog2(maxabs)-10;
165
   if (shift<0)
166
      shift=0;
167
   if (C==2)
168
      shift++;
169
   for (i=1;i<len;i++)
170
      x_lp[i] = SHR32(x[0][(factor*i-offset)], shift+2) + SHR32(x[0][(factor*i+offset)], shift+2) + SHR32(x[0][factor*i], shift+1);
171
   x_lp[0] = SHR32(x[0][offset], shift+2) + SHR32(x[0][0], shift+1);
172
   if (C==2)
173
   {
174
      for (i=1;i<len;i++)
175
         x_lp[i] += SHR32(x[1][(factor*i-offset)], shift+2) + SHR32(x[1][(factor*i+offset)], shift+2) + SHR32(x[1][factor*i], shift+1);
176
      x_lp[0] += SHR32(x[1][offset], shift+2) + SHR32(x[1][0], shift+1);
177
   }
178
#else
179
91.5M
   for (i=1;i<len;i++)
180
91.4M
      x_lp[i] = .25f*x[0][(factor*i-offset)] + .25f*x[0][(factor*i+offset)] + .5f*x[0][factor*i];
181
103k
   x_lp[0] = .25f*x[0][offset] + .5f*x[0][0];
182
103k
   if (C==2)
183
53.1k
   {
184
49.7M
      for (i=1;i<len;i++)
185
49.6M
         x_lp[i] += .25f*x[1][(factor*i-offset)] + .25f*x[1][(factor*i+offset)] + .5f*x[1][factor*i];
186
53.1k
      x_lp[0] += .25f*x[1][offset] + .5f*x[1][0];
187
53.1k
   }
188
103k
#endif
189
103k
   _celt_autocorr(x_lp, ac, NULL, 0,
190
103k
                  4, len, arch);
191
192
   /* Noise floor -40 dB */
193
#ifdef FIXED_POINT
194
   ac[0] += SHR32(ac[0],13);
195
#else
196
103k
   ac[0] *= 1.0001f;
197
103k
#endif
198
   /* Lag windowing */
199
515k
   for (i=1;i<=4;i++)
200
412k
   {
201
      /*ac[i] *= exp(-.5*(2*M_PI*.002*i)*(2*M_PI*.002*i));*/
202
#ifdef FIXED_POINT
203
      ac[i] -= MULT16_32_Q15(2*i*i, ac[i]);
204
#else
205
412k
      ac[i] -= ac[i]*(.008f*i)*(.008f*i);
206
412k
#endif
207
412k
   }
208
209
103k
   _celt_lpc(lpc, ac, 4);
210
515k
   for (i=0;i<4;i++)
211
412k
   {
212
412k
      tmp = MULT16_16_Q15(QCONST16(.9f,15), tmp);
213
412k
      lpc[i] = MULT16_16_Q15(lpc[i], tmp);
214
412k
   }
215
   /* Add a zero */
216
103k
   lpc2[0] = lpc[0] + QCONST16(.8f,SIG_SHIFT);
217
103k
   lpc2[1] = lpc[1] + MULT16_16_Q15(c1,lpc[0]);
218
103k
   lpc2[2] = lpc[2] + MULT16_16_Q15(c1,lpc[1]);
219
103k
   lpc2[3] = lpc[3] + MULT16_16_Q15(c1,lpc[2]);
220
103k
   lpc2[4] = MULT16_16_Q15(c1,lpc[3]);
221
103k
   celt_fir5(x_lp, lpc2, len);
222
103k
}
223
224
/* Pure C implementation. */
225
#ifdef FIXED_POINT
226
opus_val32
227
#else
228
void
229
#endif
230
celt_pitch_xcorr_c(const opus_val16 *_x, const opus_val16 *_y,
231
      opus_val32 *xcorr, int len, int max_pitch, int arch)
232
2.88M
{
233
234
#if 0 /* This is a simple version of the pitch correlation that should work
235
         well on DSPs like Blackfin and TI C5x/C6x */
236
   int i, j;
237
#ifdef FIXED_POINT
238
   opus_val32 maxcorr=1;
239
#endif
240
#if !defined(OVERRIDE_PITCH_XCORR)
241
   (void)arch;
242
#endif
243
   for (i=0;i<max_pitch;i++)
244
   {
245
      opus_val32 sum = 0;
246
      for (j=0;j<len;j++)
247
         sum = MAC16_16(sum, _x[j], _y[i+j]);
248
      xcorr[i] = sum;
249
#ifdef FIXED_POINT
250
      maxcorr = MAX32(maxcorr, sum);
251
#endif
252
   }
253
#ifdef FIXED_POINT
254
   return maxcorr;
255
#endif
256
257
#else /* Unrolled version of the pitch correlation -- runs faster on x86 and ARM */
258
2.88M
   int i;
259
   /*The EDSP version requires that max_pitch is at least 1, and that _x is
260
      32-bit aligned.
261
     Since it's hard to put asserts in assembly, put them here.*/
262
#ifdef FIXED_POINT
263
   opus_val32 maxcorr=1;
264
#endif
265
2.88M
   celt_assert(max_pitch>0);
266
2.88M
   celt_sig_assert(((size_t)_x&3)==0);
267
19.2M
   for (i=0;i<max_pitch-3;i+=4)
268
16.3M
   {
269
16.3M
      opus_val32 sum[4]={0,0,0,0};
270
#if defined(OPUS_CHECK_ASM) && defined(FIXED_POINT)
271
      {
272
         opus_val32 sum_c[4]={0,0,0,0};
273
         xcorr_kernel_c(_x, _y+i, sum_c, len);
274
#endif
275
16.3M
         xcorr_kernel(_x, _y+i, sum, len, arch);
276
#if defined(OPUS_CHECK_ASM) && defined(FIXED_POINT)
277
16.3M
         celt_assert(memcmp(sum, sum_c, sizeof(sum)) == 0);
278
16.3M
      }
279
0
#endif
280
0
      xcorr[i]=sum[0];
281
16.3M
      xcorr[i+1]=sum[1];
282
16.3M
      xcorr[i+2]=sum[2];
283
16.3M
      xcorr[i+3]=sum[3];
284
#ifdef FIXED_POINT
285
16.3M
      sum[0] = MAX32(sum[0], sum[1]);
286
16.3M
      sum[2] = MAX32(sum[2], sum[3]);
287
16.3M
      sum[0] = MAX32(sum[0], sum[2]);
288
16.3M
      maxcorr = MAX32(maxcorr, sum[0]);
289
#endif
290
16.3M
   }
291
   /* In case max_pitch isn't a multiple of 4, do non-unrolled version. */
292
7.51M
   for (;i<max_pitch;i++)
293
4.63M
   {
294
4.63M
      opus_val32 sum;
295
4.63M
      sum = celt_inner_prod(_x, _y+i, len, arch);
296
4.63M
      xcorr[i] = sum;
297
#ifdef FIXED_POINT
298
4.63M
      maxcorr = MAX32(maxcorr, sum);
299
#endif
300
4.63M
   }
301
#ifdef FIXED_POINT
302
   return maxcorr;
303
#endif
304
2.88M
#endif
305
2.88M
}
celt_pitch_xcorr_c
Line
Count
Source
232
2.88M
{
233
234
#if 0 /* This is a simple version of the pitch correlation that should work
235
         well on DSPs like Blackfin and TI C5x/C6x */
236
   int i, j;
237
#ifdef FIXED_POINT
238
   opus_val32 maxcorr=1;
239
#endif
240
#if !defined(OVERRIDE_PITCH_XCORR)
241
   (void)arch;
242
#endif
243
   for (i=0;i<max_pitch;i++)
244
   {
245
      opus_val32 sum = 0;
246
      for (j=0;j<len;j++)
247
         sum = MAC16_16(sum, _x[j], _y[i+j]);
248
      xcorr[i] = sum;
249
#ifdef FIXED_POINT
250
      maxcorr = MAX32(maxcorr, sum);
251
#endif
252
   }
253
#ifdef FIXED_POINT
254
   return maxcorr;
255
#endif
256
257
#else /* Unrolled version of the pitch correlation -- runs faster on x86 and ARM */
258
2.88M
   int i;
259
   /*The EDSP version requires that max_pitch is at least 1, and that _x is
260
      32-bit aligned.
261
     Since it's hard to put asserts in assembly, put them here.*/
262
2.88M
#ifdef FIXED_POINT
263
2.88M
   opus_val32 maxcorr=1;
264
2.88M
#endif
265
2.88M
   celt_assert(max_pitch>0);
266
2.88M
   celt_sig_assert(((size_t)_x&3)==0);
267
19.2M
   for (i=0;i<max_pitch-3;i+=4)
268
16.3M
   {
269
16.3M
      opus_val32 sum[4]={0,0,0,0};
270
16.3M
#if defined(OPUS_CHECK_ASM) && defined(FIXED_POINT)
271
16.3M
      {
272
16.3M
         opus_val32 sum_c[4]={0,0,0,0};
273
16.3M
         xcorr_kernel_c(_x, _y+i, sum_c, len);
274
16.3M
#endif
275
16.3M
         xcorr_kernel(_x, _y+i, sum, len, arch);
276
16.3M
#if defined(OPUS_CHECK_ASM) && defined(FIXED_POINT)
277
16.3M
         celt_assert(memcmp(sum, sum_c, sizeof(sum)) == 0);
278
16.3M
      }
279
0
#endif
280
0
      xcorr[i]=sum[0];
281
16.3M
      xcorr[i+1]=sum[1];
282
16.3M
      xcorr[i+2]=sum[2];
283
16.3M
      xcorr[i+3]=sum[3];
284
16.3M
#ifdef FIXED_POINT
285
16.3M
      sum[0] = MAX32(sum[0], sum[1]);
286
16.3M
      sum[2] = MAX32(sum[2], sum[3]);
287
16.3M
      sum[0] = MAX32(sum[0], sum[2]);
288
16.3M
      maxcorr = MAX32(maxcorr, sum[0]);
289
16.3M
#endif
290
16.3M
   }
291
   /* In case max_pitch isn't a multiple of 4, do non-unrolled version. */
292
7.51M
   for (;i<max_pitch;i++)
293
4.63M
   {
294
4.63M
      opus_val32 sum;
295
4.63M
      sum = celt_inner_prod(_x, _y+i, len, arch);
296
4.63M
      xcorr[i] = sum;
297
4.63M
#ifdef FIXED_POINT
298
4.63M
      maxcorr = MAX32(maxcorr, sum);
299
4.63M
#endif
300
4.63M
   }
301
2.88M
#ifdef FIXED_POINT
302
2.88M
   return maxcorr;
303
2.88M
#endif
304
2.88M
#endif
305
2.88M
}
Unexecuted instantiation: celt_pitch_xcorr_c
306
307
void pitch_search(const opus_val16 * OPUS_RESTRICT x_lp, opus_val16 * OPUS_RESTRICT y,
308
                  int len, int max_pitch, int *pitch, int arch)
309
245k
{
310
245k
   int i, j;
311
245k
   int lag;
312
245k
   int best_pitch[2]={0,0};
313
245k
   VARDECL(opus_val16, x_lp4);
314
245k
   VARDECL(opus_val16, y_lp4);
315
245k
   VARDECL(opus_val32, xcorr);
316
#ifdef FIXED_POINT
317
   opus_val32 maxcorr;
318
   opus_val32 xmax, ymax;
319
   int shift=0;
320
#endif
321
245k
   int offset;
322
323
245k
   SAVE_STACK;
324
325
245k
   celt_assert(len>0);
326
245k
   celt_assert(max_pitch>0);
327
245k
   lag = len+max_pitch;
328
329
245k
   ALLOC(x_lp4, len>>2, opus_val16);
330
245k
   ALLOC(y_lp4, lag>>2, opus_val16);
331
245k
   ALLOC(xcorr, max_pitch>>1, opus_val32);
332
333
   /* Downsample by 2 again */
334
53.6M
   for (j=0;j<len>>2;j++)
335
53.4M
      x_lp4[j] = x_lp[2*j];
336
104M
   for (j=0;j<lag>>2;j++)
337
104M
      y_lp4[j] = y[2*j];
338
339
#ifdef FIXED_POINT
340
   xmax = celt_maxabs16(x_lp4, len>>2);
341
   ymax = celt_maxabs16(y_lp4, lag>>2);
342
142k
   shift = celt_ilog2(MAX32(1, MAX32(xmax, ymax))) - 14 + celt_ilog2(len)/2;
343
142k
   if (shift>0)
344
5.26k
   {
345
1.75M
      for (j=0;j<len>>2;j++)
346
1.75M
         x_lp4[j] = SHR16(x_lp4[j], shift);
347
2.59M
      for (j=0;j<lag>>2;j++)
348
2.58M
         y_lp4[j] = SHR16(y_lp4[j], shift);
349
      /* Use double the shift for a MAC */
350
5.26k
      shift *= 2;
351
137k
   } else {
352
137k
      shift = 0;
353
137k
   }
354
#endif
355
356
   /* Coarse search with 4x decimation */
357
358
#ifdef FIXED_POINT
359
   maxcorr =
360
#endif
361
245k
   celt_pitch_xcorr(x_lp4, y_lp4, xcorr, len>>2, max_pitch>>2, arch);
362
363
245k
   find_best_pitch(xcorr, y_lp4, len>>2, max_pitch>>2, best_pitch
364
#ifdef FIXED_POINT
365
                   , 0, maxcorr
366
#endif
367
245k
                   );
368
369
   /* Finer search with 2x decimation */
370
#ifdef FIXED_POINT
371
   maxcorr=1;
372
#endif
373
102M
   for (i=0;i<max_pitch>>1;i++)
374
102M
   {
375
102M
      opus_val32 sum;
376
102M
      xcorr[i] = 0;
377
102M
      if (abs(i-2*best_pitch[0])>2 && abs(i-2*best_pitch[1])>2)
378
100M
         continue;
379
#ifdef FIXED_POINT
380
1.23M
      sum = 0;
381
539M
      for (j=0;j<len>>1;j++)
382
537M
         sum += SHR32(MULT16_16(x_lp[j],y[i+j]), shift);
383
#else
384
907k
      sum = celt_inner_prod(x_lp, y+i, len>>1, arch);
385
#endif
386
2.14M
      xcorr[i] = MAX32(-1, sum);
387
#ifdef FIXED_POINT
388
1.23M
      maxcorr = MAX32(maxcorr, sum);
389
#endif
390
907k
   }
391
245k
   find_best_pitch(xcorr, y, len>>1, max_pitch>>1, best_pitch
392
#ifdef FIXED_POINT
393
                   , shift+1, maxcorr
394
#endif
395
245k
                   );
396
397
   /* Refine by pseudo-interpolation */
398
245k
   if (best_pitch[0]>0 && best_pitch[0]<(max_pitch>>1)-1)
399
210k
   {
400
210k
      opus_val32 a, b, c;
401
210k
      a = xcorr[best_pitch[0]-1];
402
210k
      b = xcorr[best_pitch[0]];
403
210k
      c = xcorr[best_pitch[0]+1];
404
210k
      if ((c-a) > MULT16_32_Q15(QCONST16(.7f,15),b-a))
405
37.5k
         offset = 1;
406
173k
      else if ((a-c) > MULT16_32_Q15(QCONST16(.7f,15),b-c))
407
20.1k
         offset = -1;
408
153k
      else
409
153k
         offset = 0;
410
210k
   } else {
411
34.6k
      offset = 0;
412
34.6k
   }
413
245k
   *pitch = 2*best_pitch[0]-offset;
414
415
245k
   RESTORE_STACK;
416
245k
}
pitch_search
Line
Count
Source
309
142k
{
310
142k
   int i, j;
311
142k
   int lag;
312
142k
   int best_pitch[2]={0,0};
313
142k
   VARDECL(opus_val16, x_lp4);
314
142k
   VARDECL(opus_val16, y_lp4);
315
142k
   VARDECL(opus_val32, xcorr);
316
142k
#ifdef FIXED_POINT
317
142k
   opus_val32 maxcorr;
318
142k
   opus_val32 xmax, ymax;
319
142k
   int shift=0;
320
142k
#endif
321
142k
   int offset;
322
323
142k
   SAVE_STACK;
324
325
142k
   celt_assert(len>0);
326
142k
   celt_assert(max_pitch>0);
327
142k
   lag = len+max_pitch;
328
329
142k
   ALLOC(x_lp4, len>>2, opus_val16);
330
142k
   ALLOC(y_lp4, lag>>2, opus_val16);
331
142k
   ALLOC(xcorr, max_pitch>>1, opus_val32);
332
333
   /* Downsample by 2 again */
334
30.9M
   for (j=0;j<len>>2;j++)
335
30.8M
      x_lp4[j] = x_lp[2*j];
336
60.7M
   for (j=0;j<lag>>2;j++)
337
60.6M
      y_lp4[j] = y[2*j];
338
339
142k
#ifdef FIXED_POINT
340
142k
   xmax = celt_maxabs16(x_lp4, len>>2);
341
142k
   ymax = celt_maxabs16(y_lp4, lag>>2);
342
142k
   shift = celt_ilog2(MAX32(1, MAX32(xmax, ymax))) - 14 + celt_ilog2(len)/2;
343
142k
   if (shift>0)
344
5.26k
   {
345
1.75M
      for (j=0;j<len>>2;j++)
346
1.75M
         x_lp4[j] = SHR16(x_lp4[j], shift);
347
2.59M
      for (j=0;j<lag>>2;j++)
348
2.58M
         y_lp4[j] = SHR16(y_lp4[j], shift);
349
      /* Use double the shift for a MAC */
350
5.26k
      shift *= 2;
351
137k
   } else {
352
137k
      shift = 0;
353
137k
   }
354
142k
#endif
355
356
   /* Coarse search with 4x decimation */
357
358
142k
#ifdef FIXED_POINT
359
142k
   maxcorr =
360
142k
#endif
361
142k
   celt_pitch_xcorr(x_lp4, y_lp4, xcorr, len>>2, max_pitch>>2, arch);
362
363
142k
   find_best_pitch(xcorr, y_lp4, len>>2, max_pitch>>2, best_pitch
364
142k
#ifdef FIXED_POINT
365
142k
                   , 0, maxcorr
366
142k
#endif
367
142k
                   );
368
369
   /* Finer search with 2x decimation */
370
142k
#ifdef FIXED_POINT
371
142k
   maxcorr=1;
372
142k
#endif
373
59.8M
   for (i=0;i<max_pitch>>1;i++)
374
59.7M
   {
375
59.7M
      opus_val32 sum;
376
59.7M
      xcorr[i] = 0;
377
59.7M
      if (abs(i-2*best_pitch[0])>2 && abs(i-2*best_pitch[1])>2)
378
58.4M
         continue;
379
1.23M
#ifdef FIXED_POINT
380
1.23M
      sum = 0;
381
539M
      for (j=0;j<len>>1;j++)
382
537M
         sum += SHR32(MULT16_16(x_lp[j],y[i+j]), shift);
383
#else
384
      sum = celt_inner_prod(x_lp, y+i, len>>1, arch);
385
#endif
386
1.23M
      xcorr[i] = MAX32(-1, sum);
387
1.23M
#ifdef FIXED_POINT
388
1.23M
      maxcorr = MAX32(maxcorr, sum);
389
1.23M
#endif
390
1.23M
   }
391
142k
   find_best_pitch(xcorr, y, len>>1, max_pitch>>1, best_pitch
392
142k
#ifdef FIXED_POINT
393
142k
                   , shift+1, maxcorr
394
142k
#endif
395
142k
                   );
396
397
   /* Refine by pseudo-interpolation */
398
142k
   if (best_pitch[0]>0 && best_pitch[0]<(max_pitch>>1)-1)
399
122k
   {
400
122k
      opus_val32 a, b, c;
401
122k
      a = xcorr[best_pitch[0]-1];
402
122k
      b = xcorr[best_pitch[0]];
403
122k
      c = xcorr[best_pitch[0]+1];
404
122k
      if ((c-a) > MULT16_32_Q15(QCONST16(.7f,15),b-a))
405
25.0k
         offset = 1;
406
97.2k
      else if ((a-c) > MULT16_32_Q15(QCONST16(.7f,15),b-c))
407
12.5k
         offset = -1;
408
84.7k
      else
409
84.7k
         offset = 0;
410
122k
   } else {
411
20.1k
      offset = 0;
412
20.1k
   }
413
142k
   *pitch = 2*best_pitch[0]-offset;
414
415
142k
   RESTORE_STACK;
416
142k
}
pitch_search
Line
Count
Source
309
103k
{
310
103k
   int i, j;
311
103k
   int lag;
312
103k
   int best_pitch[2]={0,0};
313
103k
   VARDECL(opus_val16, x_lp4);
314
103k
   VARDECL(opus_val16, y_lp4);
315
103k
   VARDECL(opus_val32, xcorr);
316
#ifdef FIXED_POINT
317
   opus_val32 maxcorr;
318
   opus_val32 xmax, ymax;
319
   int shift=0;
320
#endif
321
103k
   int offset;
322
323
103k
   SAVE_STACK;
324
325
103k
   celt_assert(len>0);
326
103k
   celt_assert(max_pitch>0);
327
103k
   lag = len+max_pitch;
328
329
103k
   ALLOC(x_lp4, len>>2, opus_val16);
330
103k
   ALLOC(y_lp4, lag>>2, opus_val16);
331
103k
   ALLOC(xcorr, max_pitch>>1, opus_val32);
332
333
   /* Downsample by 2 again */
334
22.6M
   for (j=0;j<len>>2;j++)
335
22.5M
      x_lp4[j] = x_lp[2*j];
336
44.0M
   for (j=0;j<lag>>2;j++)
337
43.9M
      y_lp4[j] = y[2*j];
338
339
#ifdef FIXED_POINT
340
   xmax = celt_maxabs16(x_lp4, len>>2);
341
   ymax = celt_maxabs16(y_lp4, lag>>2);
342
   shift = celt_ilog2(MAX32(1, MAX32(xmax, ymax))) - 14 + celt_ilog2(len)/2;
343
   if (shift>0)
344
   {
345
      for (j=0;j<len>>2;j++)
346
         x_lp4[j] = SHR16(x_lp4[j], shift);
347
      for (j=0;j<lag>>2;j++)
348
         y_lp4[j] = SHR16(y_lp4[j], shift);
349
      /* Use double the shift for a MAC */
350
      shift *= 2;
351
   } else {
352
      shift = 0;
353
   }
354
#endif
355
356
   /* Coarse search with 4x decimation */
357
358
#ifdef FIXED_POINT
359
   maxcorr =
360
#endif
361
103k
   celt_pitch_xcorr(x_lp4, y_lp4, xcorr, len>>2, max_pitch>>2, arch);
362
363
103k
   find_best_pitch(xcorr, y_lp4, len>>2, max_pitch>>2, best_pitch
364
#ifdef FIXED_POINT
365
                   , 0, maxcorr
366
#endif
367
103k
                   );
368
369
   /* Finer search with 2x decimation */
370
#ifdef FIXED_POINT
371
   maxcorr=1;
372
#endif
373
42.9M
   for (i=0;i<max_pitch>>1;i++)
374
42.8M
   {
375
42.8M
      opus_val32 sum;
376
42.8M
      xcorr[i] = 0;
377
42.8M
      if (abs(i-2*best_pitch[0])>2 && abs(i-2*best_pitch[1])>2)
378
41.9M
         continue;
379
#ifdef FIXED_POINT
380
      sum = 0;
381
      for (j=0;j<len>>1;j++)
382
         sum += SHR32(MULT16_16(x_lp[j],y[i+j]), shift);
383
#else
384
907k
      sum = celt_inner_prod(x_lp, y+i, len>>1, arch);
385
907k
#endif
386
907k
      xcorr[i] = MAX32(-1, sum);
387
#ifdef FIXED_POINT
388
      maxcorr = MAX32(maxcorr, sum);
389
#endif
390
907k
   }
391
103k
   find_best_pitch(xcorr, y, len>>1, max_pitch>>1, best_pitch
392
#ifdef FIXED_POINT
393
                   , shift+1, maxcorr
394
#endif
395
103k
                   );
396
397
   /* Refine by pseudo-interpolation */
398
103k
   if (best_pitch[0]>0 && best_pitch[0]<(max_pitch>>1)-1)
399
88.6k
   {
400
88.6k
      opus_val32 a, b, c;
401
88.6k
      a = xcorr[best_pitch[0]-1];
402
88.6k
      b = xcorr[best_pitch[0]];
403
88.6k
      c = xcorr[best_pitch[0]+1];
404
88.6k
      if ((c-a) > MULT16_32_Q15(QCONST16(.7f,15),b-a))
405
12.4k
         offset = 1;
406
76.1k
      else if ((a-c) > MULT16_32_Q15(QCONST16(.7f,15),b-c))
407
7.54k
         offset = -1;
408
68.6k
      else
409
68.6k
         offset = 0;
410
88.6k
   } else {
411
14.4k
      offset = 0;
412
14.4k
   }
413
103k
   *pitch = 2*best_pitch[0]-offset;
414
415
103k
   RESTORE_STACK;
416
103k
}
417
418
#ifdef FIXED_POINT
419
static opus_val16 compute_pitch_gain(opus_val32 xy, opus_val32 xx, opus_val32 yy)
420
803k
{
421
803k
   opus_val32 x2y2;
422
803k
   int sx, sy, shift;
423
803k
   opus_val32 g;
424
803k
   opus_val16 den;
425
803k
   if (xy == 0 || xx == 0 || yy == 0)
426
136k
      return 0;
427
667k
   sx = celt_ilog2(xx)-14;
428
667k
   sy = celt_ilog2(yy)-14;
429
667k
   shift = sx + sy;
430
667k
   x2y2 = SHR32(MULT16_16(VSHR32(xx, sx), VSHR32(yy, sy)), 14);
431
667k
   if (shift & 1) {
432
192k
      if (x2y2 < 32768)
433
99.3k
      {
434
99.3k
         x2y2 <<= 1;
435
99.3k
         shift--;
436
99.3k
      } else {
437
92.7k
         x2y2 >>= 1;
438
92.7k
         shift++;
439
92.7k
      }
440
192k
   }
441
667k
   den = celt_rsqrt_norm(x2y2);
442
667k
   g = MULT16_32_Q15(den, xy);
443
667k
   g = VSHR32(g, (shift>>1)-1);
444
667k
   return EXTRACT16(MAX32(-Q15ONE, MIN32(g, Q15ONE)));
445
803k
}
446
#else
447
static opus_val16 compute_pitch_gain(opus_val32 xy, opus_val32 xx, opus_val32 yy)
448
582k
{
449
582k
   return xy/celt_sqrt(1+xx*yy);
450
582k
}
451
#endif
452
453
static const int second_check[16] = {0, 0, 3, 2, 3, 2, 5, 2, 3, 2, 3, 2, 5, 2, 3, 2};
454
opus_val16 remove_doubling(opus_val16 *x, int maxperiod, int minperiod,
455
      int N, int *T0_, int prev_period, opus_val16 prev_gain, int arch)
456
282k
{
457
282k
   int k, i, T, T0;
458
282k
   opus_val16 g, g0;
459
282k
   opus_val16 pg;
460
282k
   opus_val32 xy,xx,yy,xy2;
461
282k
   opus_val32 xcorr[3];
462
282k
   opus_val32 best_xy, best_yy;
463
282k
   int offset;
464
282k
   int minperiod0;
465
282k
   VARDECL(opus_val32, yy_lookup);
466
282k
   SAVE_STACK;
467
468
282k
   minperiod0 = minperiod;
469
282k
   maxperiod /= 2;
470
282k
   minperiod /= 2;
471
282k
   *T0_ /= 2;
472
282k
   prev_period /= 2;
473
282k
   N /= 2;
474
282k
   x += maxperiod;
475
282k
   if (*T0_>=maxperiod)
476
32.8k
      *T0_=maxperiod-1;
477
478
282k
   T = T0 = *T0_;
479
282k
   ALLOC(yy_lookup, maxperiod+1, opus_val32);
480
282k
   dual_inner_prod(x, x, x-T0, N, &xx, &xy, arch);
481
282k
   yy_lookup[0] = xx;
482
282k
   yy=xx;
483
147M
   for (i=1;i<=maxperiod;i++)
484
147M
   {
485
147M
      yy = yy+MULT16_16(x[-i],x[-i])-MULT16_16(x[N-i],x[N-i]);
486
147M
      yy_lookup[i] = MAX32(0, yy);
487
147M
   }
488
282k
   yy = yy_lookup[T0];
489
282k
   best_xy = xy;
490
282k
   best_yy = yy;
491
282k
   g = g0 = compute_pitch_gain(xy, xx, yy);
492
   /* Look for any pitch at T/k */
493
2.77M
   for (k=2;k<=15;k++)
494
2.65M
   {
495
2.65M
      int T1, T1b;
496
2.65M
      opus_val16 g1;
497
2.65M
      opus_val16 cont=0;
498
2.65M
      opus_val16 thresh;
499
2.65M
      T1 = celt_udiv(2*T0+k, 2*k);
500
2.65M
      if (T1 < minperiod)
501
169k
         break;
502
      /* Look for another strong correlation at T1b */
503
2.48M
      if (k==2)
504
282k
      {
505
282k
         if (T1+T0>maxperiod)
506
61.1k
            T1b = T0;
507
221k
         else
508
221k
            T1b = T0+T1;
509
282k
      } else
510
2.20M
      {
511
2.20M
         T1b = celt_udiv(2*second_check[k]*T0+k, 2*k);
512
2.20M
      }
513
2.48M
      dual_inner_prod(x, &x[-T1], &x[-T1b], N, &xy, &xy2, arch);
514
2.48M
      xy = HALF32(xy + xy2);
515
2.48M
      yy = HALF32(yy_lookup[T1] + yy_lookup[T1b]);
516
2.48M
      g1 = compute_pitch_gain(xy, xx, yy);
517
2.48M
      if (abs(T1-prev_period)<=1)
518
33.7k
         cont = prev_gain;
519
2.45M
      else if (abs(T1-prev_period)<=2 && 5*k*k < T0)
520
2.15k
         cont = HALF16(prev_gain);
521
2.45M
      else
522
2.45M
         cont = 0;
523
2.48M
      thresh = MAX16(QCONST16(.3f,15), MULT16_16_Q15(QCONST16(.7f,15),g0)-cont);
524
      /* Bias against very high pitch (very short period) to avoid false-positives
525
         due to short-term correlation */
526
2.48M
      if (T1<3*minperiod)
527
1.10M
         thresh = MAX16(QCONST16(.4f,15), MULT16_16_Q15(QCONST16(.85f,15),g0)-cont);
528
1.38M
      else if (T1<2*minperiod)
529
0
         thresh = MAX16(QCONST16(.5f,15), MULT16_16_Q15(QCONST16(.9f,15),g0)-cont);
530
2.48M
      if (g1 > thresh)
531
223k
      {
532
223k
         best_xy = xy;
533
223k
         best_yy = yy;
534
223k
         T = T1;
535
223k
         g = g1;
536
223k
      }
537
2.48M
   }
538
282k
   best_xy = MAX32(0, best_xy);
539
282k
   if (best_yy <= best_xy)
540
94.7k
      pg = Q15ONE;
541
187k
   else
542
187k
      pg = SHR32(frac_div32(best_xy,best_yy+1),16);
543
544
1.13M
   for (k=0;k<3;k++)
545
848k
      xcorr[k] = celt_inner_prod(x, x-(T+k-1), N, arch);
546
282k
   if ((xcorr[2]-xcorr[0]) > MULT16_32_Q15(QCONST16(.7f,15),xcorr[1]-xcorr[0]))
547
25.4k
      offset = 1;
548
257k
   else if ((xcorr[0]-xcorr[2]) > MULT16_32_Q15(QCONST16(.7f,15),xcorr[1]-xcorr[2]))
549
43.2k
      offset = -1;
550
214k
   else
551
214k
      offset = 0;
552
282k
   if (pg > g)
553
222k
      pg = g;
554
282k
   *T0_ = 2*T+offset;
555
556
282k
   if (*T0_<minperiod0)
557
4.79k
      *T0_=minperiod0;
558
282k
   RESTORE_STACK;
559
282k
   return pg;
560
282k
}
remove_doubling
Line
Count
Source
456
141k
{
457
141k
   int k, i, T, T0;
458
141k
   opus_val16 g, g0;
459
141k
   opus_val16 pg;
460
141k
   opus_val32 xy,xx,yy,xy2;
461
141k
   opus_val32 xcorr[3];
462
141k
   opus_val32 best_xy, best_yy;
463
141k
   int offset;
464
141k
   int minperiod0;
465
141k
   VARDECL(opus_val32, yy_lookup);
466
141k
   SAVE_STACK;
467
468
141k
   minperiod0 = minperiod;
469
141k
   maxperiod /= 2;
470
141k
   minperiod /= 2;
471
141k
   *T0_ /= 2;
472
141k
   prev_period /= 2;
473
141k
   N /= 2;
474
141k
   x += maxperiod;
475
141k
   if (*T0_>=maxperiod)
476
16.4k
      *T0_=maxperiod-1;
477
478
141k
   T = T0 = *T0_;
479
141k
   ALLOC(yy_lookup, maxperiod+1, opus_val32);
480
141k
   dual_inner_prod(x, x, x-T0, N, &xx, &xy, arch);
481
141k
   yy_lookup[0] = xx;
482
141k
   yy=xx;
483
73.7M
   for (i=1;i<=maxperiod;i++)
484
73.5M
   {
485
73.5M
      yy = yy+MULT16_16(x[-i],x[-i])-MULT16_16(x[N-i],x[N-i]);
486
73.5M
      yy_lookup[i] = MAX32(0, yy);
487
73.5M
   }
488
141k
   yy = yy_lookup[T0];
489
141k
   best_xy = xy;
490
141k
   best_yy = yy;
491
141k
   g = g0 = compute_pitch_gain(xy, xx, yy);
492
   /* Look for any pitch at T/k */
493
1.38M
   for (k=2;k<=15;k++)
494
1.32M
   {
495
1.32M
      int T1, T1b;
496
1.32M
      opus_val16 g1;
497
1.32M
      opus_val16 cont=0;
498
1.32M
      opus_val16 thresh;
499
1.32M
      T1 = celt_udiv(2*T0+k, 2*k);
500
1.32M
      if (T1 < minperiod)
501
84.7k
         break;
502
      /* Look for another strong correlation at T1b */
503
1.24M
      if (k==2)
504
141k
      {
505
141k
         if (T1+T0>maxperiod)
506
30.5k
            T1b = T0;
507
110k
         else
508
110k
            T1b = T0+T1;
509
141k
      } else
510
1.10M
      {
511
1.10M
         T1b = celt_udiv(2*second_check[k]*T0+k, 2*k);
512
1.10M
      }
513
1.24M
      dual_inner_prod(x, &x[-T1], &x[-T1b], N, &xy, &xy2, arch);
514
1.24M
      xy = HALF32(xy + xy2);
515
1.24M
      yy = HALF32(yy_lookup[T1] + yy_lookup[T1b]);
516
1.24M
      g1 = compute_pitch_gain(xy, xx, yy);
517
1.24M
      if (abs(T1-prev_period)<=1)
518
16.8k
         cont = prev_gain;
519
1.22M
      else if (abs(T1-prev_period)<=2 && 5*k*k < T0)
520
1.07k
         cont = HALF16(prev_gain);
521
1.22M
      else
522
1.22M
         cont = 0;
523
1.24M
      thresh = MAX16(QCONST16(.3f,15), MULT16_16_Q15(QCONST16(.7f,15),g0)-cont);
524
      /* Bias against very high pitch (very short period) to avoid false-positives
525
         due to short-term correlation */
526
1.24M
      if (T1<3*minperiod)
527
554k
         thresh = MAX16(QCONST16(.4f,15), MULT16_16_Q15(QCONST16(.85f,15),g0)-cont);
528
690k
      else if (T1<2*minperiod)
529
0
         thresh = MAX16(QCONST16(.5f,15), MULT16_16_Q15(QCONST16(.9f,15),g0)-cont);
530
1.24M
      if (g1 > thresh)
531
111k
      {
532
111k
         best_xy = xy;
533
111k
         best_yy = yy;
534
111k
         T = T1;
535
111k
         g = g1;
536
111k
      }
537
1.24M
   }
538
141k
   best_xy = MAX32(0, best_xy);
539
141k
   if (best_yy <= best_xy)
540
47.3k
      pg = Q15ONE;
541
93.9k
   else
542
93.9k
      pg = SHR32(frac_div32(best_xy,best_yy+1),16);
543
544
565k
   for (k=0;k<3;k++)
545
424k
      xcorr[k] = celt_inner_prod(x, x-(T+k-1), N, arch);
546
141k
   if ((xcorr[2]-xcorr[0]) > MULT16_32_Q15(QCONST16(.7f,15),xcorr[1]-xcorr[0]))
547
12.7k
      offset = 1;
548
128k
   else if ((xcorr[0]-xcorr[2]) > MULT16_32_Q15(QCONST16(.7f,15),xcorr[1]-xcorr[2]))
549
21.6k
      offset = -1;
550
107k
   else
551
107k
      offset = 0;
552
141k
   if (pg > g)
553
111k
      pg = g;
554
141k
   *T0_ = 2*T+offset;
555
556
141k
   if (*T0_<minperiod0)
557
2.39k
      *T0_=minperiod0;
558
141k
   RESTORE_STACK;
559
141k
   return pg;
560
141k
}
remove_doubling
Line
Count
Source
456
141k
{
457
141k
   int k, i, T, T0;
458
141k
   opus_val16 g, g0;
459
141k
   opus_val16 pg;
460
141k
   opus_val32 xy,xx,yy,xy2;
461
141k
   opus_val32 xcorr[3];
462
141k
   opus_val32 best_xy, best_yy;
463
141k
   int offset;
464
141k
   int minperiod0;
465
141k
   VARDECL(opus_val32, yy_lookup);
466
141k
   SAVE_STACK;
467
468
141k
   minperiod0 = minperiod;
469
141k
   maxperiod /= 2;
470
141k
   minperiod /= 2;
471
141k
   *T0_ /= 2;
472
141k
   prev_period /= 2;
473
141k
   N /= 2;
474
141k
   x += maxperiod;
475
141k
   if (*T0_>=maxperiod)
476
16.4k
      *T0_=maxperiod-1;
477
478
141k
   T = T0 = *T0_;
479
141k
   ALLOC(yy_lookup, maxperiod+1, opus_val32);
480
141k
   dual_inner_prod(x, x, x-T0, N, &xx, &xy, arch);
481
141k
   yy_lookup[0] = xx;
482
141k
   yy=xx;
483
73.7M
   for (i=1;i<=maxperiod;i++)
484
73.5M
   {
485
73.5M
      yy = yy+MULT16_16(x[-i],x[-i])-MULT16_16(x[N-i],x[N-i]);
486
73.5M
      yy_lookup[i] = MAX32(0, yy);
487
73.5M
   }
488
141k
   yy = yy_lookup[T0];
489
141k
   best_xy = xy;
490
141k
   best_yy = yy;
491
141k
   g = g0 = compute_pitch_gain(xy, xx, yy);
492
   /* Look for any pitch at T/k */
493
1.38M
   for (k=2;k<=15;k++)
494
1.32M
   {
495
1.32M
      int T1, T1b;
496
1.32M
      opus_val16 g1;
497
1.32M
      opus_val16 cont=0;
498
1.32M
      opus_val16 thresh;
499
1.32M
      T1 = celt_udiv(2*T0+k, 2*k);
500
1.32M
      if (T1 < minperiod)
501
84.7k
         break;
502
      /* Look for another strong correlation at T1b */
503
1.24M
      if (k==2)
504
141k
      {
505
141k
         if (T1+T0>maxperiod)
506
30.5k
            T1b = T0;
507
110k
         else
508
110k
            T1b = T0+T1;
509
141k
      } else
510
1.10M
      {
511
1.10M
         T1b = celt_udiv(2*second_check[k]*T0+k, 2*k);
512
1.10M
      }
513
1.24M
      dual_inner_prod(x, &x[-T1], &x[-T1b], N, &xy, &xy2, arch);
514
1.24M
      xy = HALF32(xy + xy2);
515
1.24M
      yy = HALF32(yy_lookup[T1] + yy_lookup[T1b]);
516
1.24M
      g1 = compute_pitch_gain(xy, xx, yy);
517
1.24M
      if (abs(T1-prev_period)<=1)
518
16.8k
         cont = prev_gain;
519
1.22M
      else if (abs(T1-prev_period)<=2 && 5*k*k < T0)
520
1.07k
         cont = HALF16(prev_gain);
521
1.22M
      else
522
1.22M
         cont = 0;
523
1.24M
      thresh = MAX16(QCONST16(.3f,15), MULT16_16_Q15(QCONST16(.7f,15),g0)-cont);
524
      /* Bias against very high pitch (very short period) to avoid false-positives
525
         due to short-term correlation */
526
1.24M
      if (T1<3*minperiod)
527
554k
         thresh = MAX16(QCONST16(.4f,15), MULT16_16_Q15(QCONST16(.85f,15),g0)-cont);
528
690k
      else if (T1<2*minperiod)
529
0
         thresh = MAX16(QCONST16(.5f,15), MULT16_16_Q15(QCONST16(.9f,15),g0)-cont);
530
1.24M
      if (g1 > thresh)
531
111k
      {
532
111k
         best_xy = xy;
533
111k
         best_yy = yy;
534
111k
         T = T1;
535
111k
         g = g1;
536
111k
      }
537
1.24M
   }
538
141k
   best_xy = MAX32(0, best_xy);
539
141k
   if (best_yy <= best_xy)
540
47.3k
      pg = Q15ONE;
541
93.9k
   else
542
93.9k
      pg = SHR32(frac_div32(best_xy,best_yy+1),16);
543
544
565k
   for (k=0;k<3;k++)
545
424k
      xcorr[k] = celt_inner_prod(x, x-(T+k-1), N, arch);
546
141k
   if ((xcorr[2]-xcorr[0]) > MULT16_32_Q15(QCONST16(.7f,15),xcorr[1]-xcorr[0]))
547
12.7k
      offset = 1;
548
128k
   else if ((xcorr[0]-xcorr[2]) > MULT16_32_Q15(QCONST16(.7f,15),xcorr[1]-xcorr[2]))
549
21.6k
      offset = -1;
550
107k
   else
551
107k
      offset = 0;
552
141k
   if (pg > g)
553
111k
      pg = g;
554
141k
   *T0_ = 2*T+offset;
555
556
141k
   if (*T0_<minperiod0)
557
2.39k
      *T0_=minperiod0;
558
141k
   RESTORE_STACK;
559
141k
   return pg;
560
141k
}