webrtcvad 0.1.0 → 0.2.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/ext/webrtcvad/extconf.rb +29 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/division_operations.c +141 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/dot_product_with_scale.h +40 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/energy.c +39 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/get_scaling_square.c +46 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/include/signal_processing_library.h +1605 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/include/spl_inl.h +153 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/resample_48khz.c +186 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/resample_by_2_internal.c +689 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/resample_by_2_internal.h +60 -0
- data/ext/webrtcvad/webrtc/common_audio/signal_processing/resample_fractional.c +239 -0
- data/ext/webrtcvad/webrtc/common_audio/third_party/spl_sqrt_floor/spl_sqrt_floor.c +77 -0
- data/ext/webrtcvad/webrtc/common_audio/third_party/spl_sqrt_floor/spl_sqrt_floor.h +29 -0
- data/ext/webrtcvad/webrtc/common_audio/third_party/spl_sqrt_floor/spl_sqrt_floor_mips.c +207 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/include/webrtc_vad.h +87 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/vad_core.c +685 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/vad_core.h +114 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/vad_filterbank.c +329 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/vad_filterbank.h +45 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/vad_gmm.c +82 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/vad_gmm.h +39 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/vad_sp.c +176 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/vad_sp.h +54 -0
- data/ext/webrtcvad/webrtc/common_audio/vad/webrtc_vad.c +114 -0
- data/ext/webrtcvad/webrtc/rtc_base/checks.cc +207 -0
- data/ext/webrtcvad/webrtc/rtc_base/checks.h +400 -0
- data/ext/webrtcvad/webrtc/rtc_base/compile_assert_c.h +25 -0
- data/ext/webrtcvad/webrtc/rtc_base/numerics/safe_compare.h +176 -0
- data/ext/webrtcvad/webrtc/rtc_base/sanitizer.h +144 -0
- data/ext/webrtcvad/webrtc/rtc_base/system/inline.h +31 -0
- data/ext/webrtcvad/webrtc/rtc_base/system/rtc_export.h +43 -0
- data/ext/webrtcvad/webrtc/rtc_base/type_traits.h +140 -0
- data/ext/webrtcvad/webrtcvad.c +112 -0
- metadata +37 -3
@@ -0,0 +1,60 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright (c) 2011 The WebRTC project authors. All Rights Reserved.
|
3
|
+
*
|
4
|
+
* Use of this source code is governed by a BSD-style license
|
5
|
+
* that can be found in the LICENSE file in the root of the source
|
6
|
+
* tree. An additional intellectual property rights grant can be found
|
7
|
+
* in the file PATENTS. All contributing project authors may
|
8
|
+
* be found in the AUTHORS file in the root of the source tree.
|
9
|
+
*/
|
10
|
+
|
11
|
+
/*
|
12
|
+
* This header file contains some internal resampling functions.
|
13
|
+
*
|
14
|
+
*/
|
15
|
+
|
16
|
+
#ifndef COMMON_AUDIO_SIGNAL_PROCESSING_RESAMPLE_BY_2_INTERNAL_H_
|
17
|
+
#define COMMON_AUDIO_SIGNAL_PROCESSING_RESAMPLE_BY_2_INTERNAL_H_
|
18
|
+
|
19
|
+
#include <stdint.h>
|
20
|
+
|
21
|
+
/*******************************************************************
|
22
|
+
* resample_by_2_fast.c
|
23
|
+
* Functions for internal use in the other resample functions
|
24
|
+
******************************************************************/
|
25
|
+
void WebRtcSpl_DownBy2IntToShort(int32_t* in,
|
26
|
+
int32_t len,
|
27
|
+
int16_t* out,
|
28
|
+
int32_t* state);
|
29
|
+
|
30
|
+
void WebRtcSpl_DownBy2ShortToInt(const int16_t* in,
|
31
|
+
int32_t len,
|
32
|
+
int32_t* out,
|
33
|
+
int32_t* state);
|
34
|
+
|
35
|
+
void WebRtcSpl_UpBy2ShortToInt(const int16_t* in,
|
36
|
+
int32_t len,
|
37
|
+
int32_t* out,
|
38
|
+
int32_t* state);
|
39
|
+
|
40
|
+
void WebRtcSpl_UpBy2IntToInt(const int32_t* in,
|
41
|
+
int32_t len,
|
42
|
+
int32_t* out,
|
43
|
+
int32_t* state);
|
44
|
+
|
45
|
+
void WebRtcSpl_UpBy2IntToShort(const int32_t* in,
|
46
|
+
int32_t len,
|
47
|
+
int16_t* out,
|
48
|
+
int32_t* state);
|
49
|
+
|
50
|
+
void WebRtcSpl_LPBy2ShortToInt(const int16_t* in,
|
51
|
+
int32_t len,
|
52
|
+
int32_t* out,
|
53
|
+
int32_t* state);
|
54
|
+
|
55
|
+
void WebRtcSpl_LPBy2IntToInt(const int32_t* in,
|
56
|
+
int32_t len,
|
57
|
+
int32_t* out,
|
58
|
+
int32_t* state);
|
59
|
+
|
60
|
+
#endif // COMMON_AUDIO_SIGNAL_PROCESSING_RESAMPLE_BY_2_INTERNAL_H_
|
@@ -0,0 +1,239 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright (c) 2011 The WebRTC project authors. All Rights Reserved.
|
3
|
+
*
|
4
|
+
* Use of this source code is governed by a BSD-style license
|
5
|
+
* that can be found in the LICENSE file in the root of the source
|
6
|
+
* tree. An additional intellectual property rights grant can be found
|
7
|
+
* in the file PATENTS. All contributing project authors may
|
8
|
+
* be found in the AUTHORS file in the root of the source tree.
|
9
|
+
*/
|
10
|
+
|
11
|
+
|
12
|
+
/*
|
13
|
+
* This file contains the resampling functions between 48, 44, 32 and 24 kHz.
|
14
|
+
* The description headers can be found in signal_processing_library.h
|
15
|
+
*
|
16
|
+
*/
|
17
|
+
|
18
|
+
#include "common_audio/signal_processing/include/signal_processing_library.h"
|
19
|
+
|
20
|
+
// interpolation coefficients
|
21
|
+
static const int16_t kCoefficients48To32[2][8] = {
|
22
|
+
{778, -2050, 1087, 23285, 12903, -3783, 441, 222},
|
23
|
+
{222, 441, -3783, 12903, 23285, 1087, -2050, 778}
|
24
|
+
};
|
25
|
+
|
26
|
+
static const int16_t kCoefficients32To24[3][8] = {
|
27
|
+
{767, -2362, 2434, 24406, 10620, -3838, 721, 90},
|
28
|
+
{386, -381, -2646, 19062, 19062, -2646, -381, 386},
|
29
|
+
{90, 721, -3838, 10620, 24406, 2434, -2362, 767}
|
30
|
+
};
|
31
|
+
|
32
|
+
static const int16_t kCoefficients44To32[4][9] = {
|
33
|
+
{117, -669, 2245, -6183, 26267, 13529, -3245, 845, -138},
|
34
|
+
{-101, 612, -2283, 8532, 29790, -5138, 1789, -524, 91},
|
35
|
+
{50, -292, 1016, -3064, 32010, 3933, -1147, 315, -53},
|
36
|
+
{-156, 974, -3863, 18603, 21691, -6246, 2353, -712, 126}
|
37
|
+
};
|
38
|
+
|
39
|
+
// Resampling ratio: 2/3
|
40
|
+
// input: int32_t (normalized, not saturated) :: size 3 * K
|
41
|
+
// output: int32_t (shifted 15 positions to the left, + offset 16384) :: size 2 * K
|
42
|
+
// K: number of blocks
|
43
|
+
|
44
|
+
void WebRtcSpl_Resample48khzTo32khz(const int32_t *In, int32_t *Out, size_t K)
|
45
|
+
{
|
46
|
+
/////////////////////////////////////////////////////////////
|
47
|
+
// Filter operation:
|
48
|
+
//
|
49
|
+
// Perform resampling (3 input samples -> 2 output samples);
|
50
|
+
// process in sub blocks of size 3 samples.
|
51
|
+
int32_t tmp;
|
52
|
+
size_t m;
|
53
|
+
|
54
|
+
for (m = 0; m < K; m++)
|
55
|
+
{
|
56
|
+
tmp = 1 << 14;
|
57
|
+
tmp += kCoefficients48To32[0][0] * In[0];
|
58
|
+
tmp += kCoefficients48To32[0][1] * In[1];
|
59
|
+
tmp += kCoefficients48To32[0][2] * In[2];
|
60
|
+
tmp += kCoefficients48To32[0][3] * In[3];
|
61
|
+
tmp += kCoefficients48To32[0][4] * In[4];
|
62
|
+
tmp += kCoefficients48To32[0][5] * In[5];
|
63
|
+
tmp += kCoefficients48To32[0][6] * In[6];
|
64
|
+
tmp += kCoefficients48To32[0][7] * In[7];
|
65
|
+
Out[0] = tmp;
|
66
|
+
|
67
|
+
tmp = 1 << 14;
|
68
|
+
tmp += kCoefficients48To32[1][0] * In[1];
|
69
|
+
tmp += kCoefficients48To32[1][1] * In[2];
|
70
|
+
tmp += kCoefficients48To32[1][2] * In[3];
|
71
|
+
tmp += kCoefficients48To32[1][3] * In[4];
|
72
|
+
tmp += kCoefficients48To32[1][4] * In[5];
|
73
|
+
tmp += kCoefficients48To32[1][5] * In[6];
|
74
|
+
tmp += kCoefficients48To32[1][6] * In[7];
|
75
|
+
tmp += kCoefficients48To32[1][7] * In[8];
|
76
|
+
Out[1] = tmp;
|
77
|
+
|
78
|
+
// update pointers
|
79
|
+
In += 3;
|
80
|
+
Out += 2;
|
81
|
+
}
|
82
|
+
}
|
83
|
+
|
84
|
+
// Resampling ratio: 3/4
|
85
|
+
// input: int32_t (normalized, not saturated) :: size 4 * K
|
86
|
+
// output: int32_t (shifted 15 positions to the left, + offset 16384) :: size 3 * K
|
87
|
+
// K: number of blocks
|
88
|
+
|
89
|
+
void WebRtcSpl_Resample32khzTo24khz(const int32_t *In, int32_t *Out, size_t K)
|
90
|
+
{
|
91
|
+
/////////////////////////////////////////////////////////////
|
92
|
+
// Filter operation:
|
93
|
+
//
|
94
|
+
// Perform resampling (4 input samples -> 3 output samples);
|
95
|
+
// process in sub blocks of size 4 samples.
|
96
|
+
size_t m;
|
97
|
+
int32_t tmp;
|
98
|
+
|
99
|
+
for (m = 0; m < K; m++)
|
100
|
+
{
|
101
|
+
tmp = 1 << 14;
|
102
|
+
tmp += kCoefficients32To24[0][0] * In[0];
|
103
|
+
tmp += kCoefficients32To24[0][1] * In[1];
|
104
|
+
tmp += kCoefficients32To24[0][2] * In[2];
|
105
|
+
tmp += kCoefficients32To24[0][3] * In[3];
|
106
|
+
tmp += kCoefficients32To24[0][4] * In[4];
|
107
|
+
tmp += kCoefficients32To24[0][5] * In[5];
|
108
|
+
tmp += kCoefficients32To24[0][6] * In[6];
|
109
|
+
tmp += kCoefficients32To24[0][7] * In[7];
|
110
|
+
Out[0] = tmp;
|
111
|
+
|
112
|
+
tmp = 1 << 14;
|
113
|
+
tmp += kCoefficients32To24[1][0] * In[1];
|
114
|
+
tmp += kCoefficients32To24[1][1] * In[2];
|
115
|
+
tmp += kCoefficients32To24[1][2] * In[3];
|
116
|
+
tmp += kCoefficients32To24[1][3] * In[4];
|
117
|
+
tmp += kCoefficients32To24[1][4] * In[5];
|
118
|
+
tmp += kCoefficients32To24[1][5] * In[6];
|
119
|
+
tmp += kCoefficients32To24[1][6] * In[7];
|
120
|
+
tmp += kCoefficients32To24[1][7] * In[8];
|
121
|
+
Out[1] = tmp;
|
122
|
+
|
123
|
+
tmp = 1 << 14;
|
124
|
+
tmp += kCoefficients32To24[2][0] * In[2];
|
125
|
+
tmp += kCoefficients32To24[2][1] * In[3];
|
126
|
+
tmp += kCoefficients32To24[2][2] * In[4];
|
127
|
+
tmp += kCoefficients32To24[2][3] * In[5];
|
128
|
+
tmp += kCoefficients32To24[2][4] * In[6];
|
129
|
+
tmp += kCoefficients32To24[2][5] * In[7];
|
130
|
+
tmp += kCoefficients32To24[2][6] * In[8];
|
131
|
+
tmp += kCoefficients32To24[2][7] * In[9];
|
132
|
+
Out[2] = tmp;
|
133
|
+
|
134
|
+
// update pointers
|
135
|
+
In += 4;
|
136
|
+
Out += 3;
|
137
|
+
}
|
138
|
+
}
|
139
|
+
|
140
|
+
//
|
141
|
+
// fractional resampling filters
|
142
|
+
// Fout = 11/16 * Fin
|
143
|
+
// Fout = 8/11 * Fin
|
144
|
+
//
|
145
|
+
|
146
|
+
// compute two inner-products and store them to output array
|
147
|
+
static void WebRtcSpl_ResampDotProduct(const int32_t *in1, const int32_t *in2,
|
148
|
+
const int16_t *coef_ptr, int32_t *out1,
|
149
|
+
int32_t *out2)
|
150
|
+
{
|
151
|
+
int32_t tmp1 = 16384;
|
152
|
+
int32_t tmp2 = 16384;
|
153
|
+
int16_t coef;
|
154
|
+
|
155
|
+
coef = coef_ptr[0];
|
156
|
+
tmp1 += coef * in1[0];
|
157
|
+
tmp2 += coef * in2[-0];
|
158
|
+
|
159
|
+
coef = coef_ptr[1];
|
160
|
+
tmp1 += coef * in1[1];
|
161
|
+
tmp2 += coef * in2[-1];
|
162
|
+
|
163
|
+
coef = coef_ptr[2];
|
164
|
+
tmp1 += coef * in1[2];
|
165
|
+
tmp2 += coef * in2[-2];
|
166
|
+
|
167
|
+
coef = coef_ptr[3];
|
168
|
+
tmp1 += coef * in1[3];
|
169
|
+
tmp2 += coef * in2[-3];
|
170
|
+
|
171
|
+
coef = coef_ptr[4];
|
172
|
+
tmp1 += coef * in1[4];
|
173
|
+
tmp2 += coef * in2[-4];
|
174
|
+
|
175
|
+
coef = coef_ptr[5];
|
176
|
+
tmp1 += coef * in1[5];
|
177
|
+
tmp2 += coef * in2[-5];
|
178
|
+
|
179
|
+
coef = coef_ptr[6];
|
180
|
+
tmp1 += coef * in1[6];
|
181
|
+
tmp2 += coef * in2[-6];
|
182
|
+
|
183
|
+
coef = coef_ptr[7];
|
184
|
+
tmp1 += coef * in1[7];
|
185
|
+
tmp2 += coef * in2[-7];
|
186
|
+
|
187
|
+
coef = coef_ptr[8];
|
188
|
+
*out1 = tmp1 + coef * in1[8];
|
189
|
+
*out2 = tmp2 + coef * in2[-8];
|
190
|
+
}
|
191
|
+
|
192
|
+
// Resampling ratio: 8/11
|
193
|
+
// input: int32_t (normalized, not saturated) :: size 11 * K
|
194
|
+
// output: int32_t (shifted 15 positions to the left, + offset 16384) :: size 8 * K
|
195
|
+
// K: number of blocks
|
196
|
+
|
197
|
+
void WebRtcSpl_Resample44khzTo32khz(const int32_t *In, int32_t *Out, size_t K)
|
198
|
+
{
|
199
|
+
/////////////////////////////////////////////////////////////
|
200
|
+
// Filter operation:
|
201
|
+
//
|
202
|
+
// Perform resampling (11 input samples -> 8 output samples);
|
203
|
+
// process in sub blocks of size 11 samples.
|
204
|
+
int32_t tmp;
|
205
|
+
size_t m;
|
206
|
+
|
207
|
+
for (m = 0; m < K; m++)
|
208
|
+
{
|
209
|
+
tmp = 1 << 14;
|
210
|
+
|
211
|
+
// first output sample
|
212
|
+
Out[0] = ((int32_t)In[3] << 15) + tmp;
|
213
|
+
|
214
|
+
// sum and accumulate filter coefficients and input samples
|
215
|
+
tmp += kCoefficients44To32[3][0] * In[5];
|
216
|
+
tmp += kCoefficients44To32[3][1] * In[6];
|
217
|
+
tmp += kCoefficients44To32[3][2] * In[7];
|
218
|
+
tmp += kCoefficients44To32[3][3] * In[8];
|
219
|
+
tmp += kCoefficients44To32[3][4] * In[9];
|
220
|
+
tmp += kCoefficients44To32[3][5] * In[10];
|
221
|
+
tmp += kCoefficients44To32[3][6] * In[11];
|
222
|
+
tmp += kCoefficients44To32[3][7] * In[12];
|
223
|
+
tmp += kCoefficients44To32[3][8] * In[13];
|
224
|
+
Out[4] = tmp;
|
225
|
+
|
226
|
+
// sum and accumulate filter coefficients and input samples
|
227
|
+
WebRtcSpl_ResampDotProduct(&In[0], &In[17], kCoefficients44To32[0], &Out[1], &Out[7]);
|
228
|
+
|
229
|
+
// sum and accumulate filter coefficients and input samples
|
230
|
+
WebRtcSpl_ResampDotProduct(&In[2], &In[15], kCoefficients44To32[1], &Out[2], &Out[6]);
|
231
|
+
|
232
|
+
// sum and accumulate filter coefficients and input samples
|
233
|
+
WebRtcSpl_ResampDotProduct(&In[3], &In[14], kCoefficients44To32[2], &Out[3], &Out[5]);
|
234
|
+
|
235
|
+
// update pointers
|
236
|
+
In += 11;
|
237
|
+
Out += 8;
|
238
|
+
}
|
239
|
+
}
|
@@ -0,0 +1,77 @@
|
|
1
|
+
/*
|
2
|
+
* Written by Wilco Dijkstra, 1996. The following email exchange establishes the
|
3
|
+
* license.
|
4
|
+
*
|
5
|
+
* From: Wilco Dijkstra <Wilco.Dijkstra@ntlworld.com>
|
6
|
+
* Date: Fri, Jun 24, 2011 at 3:20 AM
|
7
|
+
* Subject: Re: sqrt routine
|
8
|
+
* To: Kevin Ma <kma@google.com>
|
9
|
+
* Hi Kevin,
|
10
|
+
* Thanks for asking. Those routines are public domain (originally posted to
|
11
|
+
* comp.sys.arm a long time ago), so you can use them freely for any purpose.
|
12
|
+
* Cheers,
|
13
|
+
* Wilco
|
14
|
+
*
|
15
|
+
* ----- Original Message -----
|
16
|
+
* From: "Kevin Ma" <kma@google.com>
|
17
|
+
* To: <Wilco.Dijkstra@ntlworld.com>
|
18
|
+
* Sent: Thursday, June 23, 2011 11:44 PM
|
19
|
+
* Subject: Fwd: sqrt routine
|
20
|
+
* Hi Wilco,
|
21
|
+
* I saw your sqrt routine from several web sites, including
|
22
|
+
* http://www.finesse.demon.co.uk/steven/sqrt.html.
|
23
|
+
* Just wonder if there's any copyright information with your Successive
|
24
|
+
* approximation routines, or if I can freely use it for any purpose.
|
25
|
+
* Thanks.
|
26
|
+
* Kevin
|
27
|
+
*/
|
28
|
+
|
29
|
+
// Minor modifications in code style for WebRTC, 2012.
|
30
|
+
|
31
|
+
#include "common_audio/third_party/spl_sqrt_floor/spl_sqrt_floor.h"
|
32
|
+
|
33
|
+
/*
|
34
|
+
* Algorithm:
|
35
|
+
* Successive approximation of the equation (root + delta) ^ 2 = N
|
36
|
+
* until delta < 1. If delta < 1 we have the integer part of SQRT (N).
|
37
|
+
* Use delta = 2^i for i = 15 .. 0.
|
38
|
+
*
|
39
|
+
* Output precision is 16 bits. Note for large input values (close to
|
40
|
+
* 0x7FFFFFFF), bit 15 (the highest bit of the low 16-bit half word)
|
41
|
+
* contains the MSB information (a non-sign value). Do with caution
|
42
|
+
* if you need to cast the output to int16_t type.
|
43
|
+
*
|
44
|
+
* If the input value is negative, it returns 0.
|
45
|
+
*/
|
46
|
+
|
47
|
+
#define WEBRTC_SPL_SQRT_ITER(N) \
|
48
|
+
try1 = root + (1 << (N)); \
|
49
|
+
if (value >= try1 << (N)) \
|
50
|
+
{ \
|
51
|
+
value -= try1 << (N); \
|
52
|
+
root |= 2 << (N); \
|
53
|
+
}
|
54
|
+
|
55
|
+
int32_t WebRtcSpl_SqrtFloor(int32_t value)
|
56
|
+
{
|
57
|
+
int32_t root = 0, try1;
|
58
|
+
|
59
|
+
WEBRTC_SPL_SQRT_ITER (15);
|
60
|
+
WEBRTC_SPL_SQRT_ITER (14);
|
61
|
+
WEBRTC_SPL_SQRT_ITER (13);
|
62
|
+
WEBRTC_SPL_SQRT_ITER (12);
|
63
|
+
WEBRTC_SPL_SQRT_ITER (11);
|
64
|
+
WEBRTC_SPL_SQRT_ITER (10);
|
65
|
+
WEBRTC_SPL_SQRT_ITER ( 9);
|
66
|
+
WEBRTC_SPL_SQRT_ITER ( 8);
|
67
|
+
WEBRTC_SPL_SQRT_ITER ( 7);
|
68
|
+
WEBRTC_SPL_SQRT_ITER ( 6);
|
69
|
+
WEBRTC_SPL_SQRT_ITER ( 5);
|
70
|
+
WEBRTC_SPL_SQRT_ITER ( 4);
|
71
|
+
WEBRTC_SPL_SQRT_ITER ( 3);
|
72
|
+
WEBRTC_SPL_SQRT_ITER ( 2);
|
73
|
+
WEBRTC_SPL_SQRT_ITER ( 1);
|
74
|
+
WEBRTC_SPL_SQRT_ITER ( 0);
|
75
|
+
|
76
|
+
return root >> 1;
|
77
|
+
}
|
@@ -0,0 +1,29 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright (c) 2018 The WebRTC project authors. All Rights Reserved.
|
3
|
+
*
|
4
|
+
* Use of this source code is governed by a BSD-style license
|
5
|
+
* that can be found in the LICENSE file in the root of the source
|
6
|
+
* tree. An additional intellectual property rights grant can be found
|
7
|
+
* in the file PATENTS. All contributing project authors may
|
8
|
+
* be found in the AUTHORS file in the root of the source tree.
|
9
|
+
*/
|
10
|
+
|
11
|
+
#include <stdint.h>
|
12
|
+
|
13
|
+
//
|
14
|
+
// WebRtcSpl_SqrtFloor(...)
|
15
|
+
//
|
16
|
+
// Returns the square root of the input value |value|. The precision of this
|
17
|
+
// function is rounding down integer precision, i.e., sqrt(8) gives 2 as answer.
|
18
|
+
// If |value| is a negative number then 0 is returned.
|
19
|
+
//
|
20
|
+
// Algorithm:
|
21
|
+
//
|
22
|
+
// An iterative 4 cylce/bit routine
|
23
|
+
//
|
24
|
+
// Input:
|
25
|
+
// - value : Value to calculate sqrt of
|
26
|
+
//
|
27
|
+
// Return value : Result of the sqrt calculation
|
28
|
+
//
|
29
|
+
int32_t WebRtcSpl_SqrtFloor(int32_t value);
|
@@ -0,0 +1,207 @@
|
|
1
|
+
/*
|
2
|
+
* Written by Wilco Dijkstra, 1996. The following email exchange establishes the
|
3
|
+
* license.
|
4
|
+
*
|
5
|
+
* From: Wilco Dijkstra <Wilco.Dijkstra@ntlworld.com>
|
6
|
+
* Date: Fri, Jun 24, 2011 at 3:20 AM
|
7
|
+
* Subject: Re: sqrt routine
|
8
|
+
* To: Kevin Ma <kma@google.com>
|
9
|
+
* Hi Kevin,
|
10
|
+
* Thanks for asking. Those routines are public domain (originally posted to
|
11
|
+
* comp.sys.arm a long time ago), so you can use them freely for any purpose.
|
12
|
+
* Cheers,
|
13
|
+
* Wilco
|
14
|
+
*
|
15
|
+
* ----- Original Message -----
|
16
|
+
* From: "Kevin Ma" <kma@google.com>
|
17
|
+
* To: <Wilco.Dijkstra@ntlworld.com>
|
18
|
+
* Sent: Thursday, June 23, 2011 11:44 PM
|
19
|
+
* Subject: Fwd: sqrt routine
|
20
|
+
* Hi Wilco,
|
21
|
+
* I saw your sqrt routine from several web sites, including
|
22
|
+
* http://www.finesse.demon.co.uk/steven/sqrt.html.
|
23
|
+
* Just wonder if there's any copyright information with your Successive
|
24
|
+
* approximation routines, or if I can freely use it for any purpose.
|
25
|
+
* Thanks.
|
26
|
+
* Kevin
|
27
|
+
*/
|
28
|
+
|
29
|
+
// Minor modifications in code style for WebRTC, 2012.
|
30
|
+
// Code optimizations for MIPS, 2013.
|
31
|
+
|
32
|
+
#include "common_audio/third_party/spl_sqrt_floor/spl_sqrt_floor.h"
|
33
|
+
|
34
|
+
/*
|
35
|
+
* Algorithm:
|
36
|
+
* Successive approximation of the equation (root + delta) ^ 2 = N
|
37
|
+
* until delta < 1. If delta < 1 we have the integer part of SQRT (N).
|
38
|
+
* Use delta = 2^i for i = 15 .. 0.
|
39
|
+
*
|
40
|
+
* Output precision is 16 bits. Note for large input values (close to
|
41
|
+
* 0x7FFFFFFF), bit 15 (the highest bit of the low 16-bit half word)
|
42
|
+
* contains the MSB information (a non-sign value). Do with caution
|
43
|
+
* if you need to cast the output to int16_t type.
|
44
|
+
*
|
45
|
+
* If the input value is negative, it returns 0.
|
46
|
+
*/
|
47
|
+
|
48
|
+
|
49
|
+
int32_t WebRtcSpl_SqrtFloor(int32_t value)
|
50
|
+
{
|
51
|
+
int32_t root = 0, tmp1, tmp2, tmp3, tmp4;
|
52
|
+
|
53
|
+
__asm __volatile(
|
54
|
+
".set push \n\t"
|
55
|
+
".set noreorder \n\t"
|
56
|
+
|
57
|
+
"lui %[tmp1], 0x4000 \n\t"
|
58
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
59
|
+
"sub %[tmp3], %[value], %[tmp1] \n\t"
|
60
|
+
"lui %[tmp1], 0x1 \n\t"
|
61
|
+
"or %[tmp4], %[root], %[tmp1] \n\t"
|
62
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
63
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
64
|
+
|
65
|
+
"addiu %[tmp1], $0, 0x4000 \n\t"
|
66
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
67
|
+
"sll %[tmp1], 14 \n\t"
|
68
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
69
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
70
|
+
"ori %[tmp4], %[root], 0x8000 \n\t"
|
71
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
72
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
73
|
+
|
74
|
+
"addiu %[tmp1], $0, 0x2000 \n\t"
|
75
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
76
|
+
"sll %[tmp1], 13 \n\t"
|
77
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
78
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
79
|
+
"ori %[tmp4], %[root], 0x4000 \n\t"
|
80
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
81
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
82
|
+
|
83
|
+
"addiu %[tmp1], $0, 0x1000 \n\t"
|
84
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
85
|
+
"sll %[tmp1], 12 \n\t"
|
86
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
87
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
88
|
+
"ori %[tmp4], %[root], 0x2000 \n\t"
|
89
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
90
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
91
|
+
|
92
|
+
"addiu %[tmp1], $0, 0x800 \n\t"
|
93
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
94
|
+
"sll %[tmp1], 11 \n\t"
|
95
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
96
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
97
|
+
"ori %[tmp4], %[root], 0x1000 \n\t"
|
98
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
99
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
100
|
+
|
101
|
+
"addiu %[tmp1], $0, 0x400 \n\t"
|
102
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
103
|
+
"sll %[tmp1], 10 \n\t"
|
104
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
105
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
106
|
+
"ori %[tmp4], %[root], 0x800 \n\t"
|
107
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
108
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
109
|
+
|
110
|
+
"addiu %[tmp1], $0, 0x200 \n\t"
|
111
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
112
|
+
"sll %[tmp1], 9 \n\t"
|
113
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
114
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
115
|
+
"ori %[tmp4], %[root], 0x400 \n\t"
|
116
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
117
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
118
|
+
|
119
|
+
"addiu %[tmp1], $0, 0x100 \n\t"
|
120
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
121
|
+
"sll %[tmp1], 8 \n\t"
|
122
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
123
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
124
|
+
"ori %[tmp4], %[root], 0x200 \n\t"
|
125
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
126
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
127
|
+
|
128
|
+
"addiu %[tmp1], $0, 0x80 \n\t"
|
129
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
130
|
+
"sll %[tmp1], 7 \n\t"
|
131
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
132
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
133
|
+
"ori %[tmp4], %[root], 0x100 \n\t"
|
134
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
135
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
136
|
+
|
137
|
+
"addiu %[tmp1], $0, 0x40 \n\t"
|
138
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
139
|
+
"sll %[tmp1], 6 \n\t"
|
140
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
141
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
142
|
+
"ori %[tmp4], %[root], 0x80 \n\t"
|
143
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
144
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
145
|
+
|
146
|
+
"addiu %[tmp1], $0, 0x20 \n\t"
|
147
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
148
|
+
"sll %[tmp1], 5 \n\t"
|
149
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
150
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
151
|
+
"ori %[tmp4], %[root], 0x40 \n\t"
|
152
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
153
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
154
|
+
|
155
|
+
"addiu %[tmp1], $0, 0x10 \n\t"
|
156
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
157
|
+
"sll %[tmp1], 4 \n\t"
|
158
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
159
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
160
|
+
"ori %[tmp4], %[root], 0x20 \n\t"
|
161
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
162
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
163
|
+
|
164
|
+
"addiu %[tmp1], $0, 0x8 \n\t"
|
165
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
166
|
+
"sll %[tmp1], 3 \n\t"
|
167
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
168
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
169
|
+
"ori %[tmp4], %[root], 0x10 \n\t"
|
170
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
171
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
172
|
+
|
173
|
+
"addiu %[tmp1], $0, 0x4 \n\t"
|
174
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
175
|
+
"sll %[tmp1], 2 \n\t"
|
176
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
177
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
178
|
+
"ori %[tmp4], %[root], 0x8 \n\t"
|
179
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
180
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
181
|
+
|
182
|
+
"addiu %[tmp1], $0, 0x2 \n\t"
|
183
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
184
|
+
"sll %[tmp1], 1 \n\t"
|
185
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
186
|
+
"subu %[tmp3], %[value], %[tmp1] \n\t"
|
187
|
+
"ori %[tmp4], %[root], 0x4 \n\t"
|
188
|
+
"movz %[value], %[tmp3], %[tmp2] \n\t"
|
189
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
190
|
+
|
191
|
+
"addiu %[tmp1], $0, 0x1 \n\t"
|
192
|
+
"addu %[tmp1], %[tmp1], %[root] \n\t"
|
193
|
+
"slt %[tmp2], %[value], %[tmp1] \n\t"
|
194
|
+
"ori %[tmp4], %[root], 0x2 \n\t"
|
195
|
+
"movz %[root], %[tmp4], %[tmp2] \n\t"
|
196
|
+
|
197
|
+
".set pop \n\t"
|
198
|
+
|
199
|
+
: [root] "+r" (root), [value] "+r" (value),
|
200
|
+
[tmp1] "=&r" (tmp1), [tmp2] "=&r" (tmp2),
|
201
|
+
[tmp3] "=&r" (tmp3), [tmp4] "=&r" (tmp4)
|
202
|
+
:
|
203
|
+
);
|
204
|
+
|
205
|
+
return root >> 1;
|
206
|
+
}
|
207
|
+
|