OLD | NEW |
1 /* libFLAC - Free Lossless Audio Codec library | 1 /* libFLAC - Free Lossless Audio Codec library |
2 * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson | 2 * Copyright (C) 2000-2009 Josh Coalson |
| 3 * Copyright (C) 2011-2014 Xiph.Org Foundation |
3 * | 4 * |
4 * Redistribution and use in source and binary forms, with or without | 5 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions | 6 * modification, are permitted provided that the following conditions |
6 * are met: | 7 * are met: |
7 * | 8 * |
8 * - Redistributions of source code must retain the above copyright | 9 * - Redistributions of source code must retain the above copyright |
9 * notice, this list of conditions and the following disclaimer. | 10 * notice, this list of conditions and the following disclaimer. |
10 * | 11 * |
11 * - Redistributions in binary form must reproduce the above copyright | 12 * - Redistributions in binary form must reproduce the above copyright |
12 * notice, this list of conditions and the following disclaimer in the | 13 * notice, this list of conditions and the following disclaimer in the |
13 * documentation and/or other materials provided with the distribution. | 14 * documentation and/or other materials provided with the distribution. |
14 * | 15 * |
15 * - Neither the name of the Xiph.org Foundation nor the names of its | 16 * - Neither the name of the Xiph.org Foundation nor the names of its |
16 * contributors may be used to endorse or promote products derived from | 17 * contributors may be used to endorse or promote products derived from |
17 * this software without specific prior written permission. | 18 * this software without specific prior written permission. |
18 * | 19 * |
19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | 20 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | 21 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |
21 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR | 22 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |
22 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR | 23 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR |
23 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, | 24 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, |
24 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, | 25 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, |
25 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR | 26 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR |
26 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF | 27 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF |
27 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING | 28 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING |
28 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | 29 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS |
29 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | 30 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
30 */ | 31 */ |
31 | 32 |
32 #if HAVE_CONFIG_H | 33 #ifdef HAVE_CONFIG_H |
33 # include <config.h> | 34 # include <config.h> |
34 #endif | 35 #endif |
35 | 36 |
36 #include <math.h> | 37 #include <math.h> |
| 38 |
37 #include "FLAC/assert.h" | 39 #include "FLAC/assert.h" |
38 #include "FLAC/format.h" | 40 #include "FLAC/format.h" |
| 41 #include "share/compat.h" |
39 #include "private/bitmath.h" | 42 #include "private/bitmath.h" |
40 #include "private/lpc.h" | 43 #include "private/lpc.h" |
| 44 #include "private/macros.h" |
41 #if defined DEBUG || defined FLAC__OVERFLOW_DETECT || defined FLAC__OVERFLOW_DET
ECT_VERBOSE | 45 #if defined DEBUG || defined FLAC__OVERFLOW_DETECT || defined FLAC__OVERFLOW_DET
ECT_VERBOSE |
42 #include <stdio.h> | 46 #include <stdio.h> |
43 #endif | 47 #endif |
44 | 48 |
45 #ifndef FLAC__INTEGER_ONLY_LIBRARY | |
46 | |
47 #ifndef M_LN2 | |
48 /* math.h in VC++ doesn't seem to have this (how Microsoft is that?) */ | |
49 #define M_LN2 0.69314718055994530942 | |
50 #endif | |
51 | |
52 /* OPT: #undef'ing this may improve the speed on some architectures */ | 49 /* OPT: #undef'ing this may improve the speed on some architectures */ |
53 #define FLAC__LPC_UNROLLED_FILTER_LOOPS | 50 #define FLAC__LPC_UNROLLED_FILTER_LOOPS |
54 | 51 |
| 52 #ifndef FLAC__INTEGER_ONLY_LIBRARY |
| 53 |
| 54 #if !defined(HAVE_LROUND) |
| 55 #if defined(_MSC_VER) |
| 56 #include <float.h> |
| 57 #define copysign _copysign |
| 58 #elif defined(__GNUC__) |
| 59 #define copysign __builtin_copysign |
| 60 #endif |
| 61 static inline long int lround(double x) { |
| 62 return (long)(x + copysign (0.5, x)); |
| 63 } |
| 64 /* If this fails, we are in the presence of a mid 90's compiler, move along... *
/ |
| 65 #endif |
55 | 66 |
56 void FLAC__lpc_window_data(const FLAC__int32 in[], const FLAC__real window[], FL
AC__real out[], unsigned data_len) | 67 void FLAC__lpc_window_data(const FLAC__int32 in[], const FLAC__real window[], FL
AC__real out[], unsigned data_len) |
57 { | 68 { |
58 unsigned i; | 69 unsigned i; |
59 for(i = 0; i < data_len; i++) | 70 for(i = 0; i < data_len; i++) |
60 out[i] = in[i] * window[i]; | 71 out[i] = in[i] * window[i]; |
61 } | 72 } |
62 | 73 |
63 void FLAC__lpc_compute_autocorrelation(const FLAC__real data[], unsigned data_le
n, unsigned lag, FLAC__real autoc[]) | 74 void FLAC__lpc_compute_autocorrelation(const FLAC__real data[], unsigned data_le
n, unsigned lag, FLAC__real autoc[]) |
64 { | 75 { |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
105 for(; sample < data_len; sample++) { | 116 for(; sample < data_len; sample++) { |
106 d = data[sample]; | 117 d = data[sample]; |
107 for(coeff = 0; coeff < data_len - sample; coeff++) | 118 for(coeff = 0; coeff < data_len - sample; coeff++) |
108 autoc[coeff] += d * data[sample+coeff]; | 119 autoc[coeff] += d * data[sample+coeff]; |
109 } | 120 } |
110 } | 121 } |
111 | 122 |
112 void FLAC__lpc_compute_lp_coefficients(const FLAC__real autoc[], unsigned *max_o
rder, FLAC__real lp_coeff[][FLAC__MAX_LPC_ORDER], FLAC__double error[]) | 123 void FLAC__lpc_compute_lp_coefficients(const FLAC__real autoc[], unsigned *max_o
rder, FLAC__real lp_coeff[][FLAC__MAX_LPC_ORDER], FLAC__double error[]) |
113 { | 124 { |
114 unsigned i, j; | 125 unsigned i, j; |
115 » FLAC__double r, err, ref[FLAC__MAX_LPC_ORDER], lpc[FLAC__MAX_LPC_ORDER]; | 126 » FLAC__double r, err, lpc[FLAC__MAX_LPC_ORDER]; |
116 | 127 |
117 FLAC__ASSERT(0 != max_order); | 128 FLAC__ASSERT(0 != max_order); |
118 FLAC__ASSERT(0 < *max_order); | 129 FLAC__ASSERT(0 < *max_order); |
119 FLAC__ASSERT(*max_order <= FLAC__MAX_LPC_ORDER); | 130 FLAC__ASSERT(*max_order <= FLAC__MAX_LPC_ORDER); |
120 FLAC__ASSERT(autoc[0] != 0.0); | 131 FLAC__ASSERT(autoc[0] != 0.0); |
121 | 132 |
122 err = autoc[0]; | 133 err = autoc[0]; |
123 | 134 |
124 for(i = 0; i < *max_order; i++) { | 135 for(i = 0; i < *max_order; i++) { |
125 /* Sum up this iteration's reflection coefficient. */ | 136 /* Sum up this iteration's reflection coefficient. */ |
126 r = -autoc[i+1]; | 137 r = -autoc[i+1]; |
127 for(j = 0; j < i; j++) | 138 for(j = 0; j < i; j++) |
128 r -= lpc[j] * autoc[i-j]; | 139 r -= lpc[j] * autoc[i-j]; |
129 » » ref[i] = (r/=err); | 140 » » r /= err; |
130 | 141 |
131 /* Update LPC coefficients and total error. */ | 142 /* Update LPC coefficients and total error. */ |
132 lpc[i]=r; | 143 lpc[i]=r; |
133 for(j = 0; j < (i>>1); j++) { | 144 for(j = 0; j < (i>>1); j++) { |
134 FLAC__double tmp = lpc[j]; | 145 FLAC__double tmp = lpc[j]; |
135 lpc[j] += r * lpc[i-1-j]; | 146 lpc[j] += r * lpc[i-1-j]; |
136 lpc[i-1-j] += r * tmp; | 147 lpc[i-1-j] += r * tmp; |
137 } | 148 } |
138 if(i & 1) | 149 if(i & 1) |
139 lpc[j] += lpc[j] * r; | 150 lpc[j] += lpc[j] * r; |
140 | 151 |
141 err *= (1.0 - r * r); | 152 err *= (1.0 - r * r); |
142 | 153 |
143 /* save this order */ | 154 /* save this order */ |
144 for(j = 0; j <= i; j++) | 155 for(j = 0; j <= i; j++) |
145 lp_coeff[i][j] = (FLAC__real)(-lpc[j]); /* negate FIR fi
lter coeff to get predictor coeff */ | 156 lp_coeff[i][j] = (FLAC__real)(-lpc[j]); /* negate FIR fi
lter coeff to get predictor coeff */ |
146 error[i] = err; | 157 error[i] = err; |
147 | 158 |
148 » » /* see SF bug #1601812 http://sourceforge.net/tracker/index.php?
func=detail&aid=1601812&group_id=13478&atid=113478 */ | 159 » » /* see SF bug https://sourceforge.net/p/flac/bugs/234/ */ |
149 if(err == 0.0) { | 160 if(err == 0.0) { |
150 *max_order = i+1; | 161 *max_order = i+1; |
151 return; | 162 return; |
152 } | 163 } |
153 } | 164 } |
154 } | 165 } |
155 | 166 |
156 int FLAC__lpc_quantize_coefficients(const FLAC__real lp_coeff[], unsigned order,
unsigned precision, FLAC__int32 qlp_coeff[], int *shift) | 167 int FLAC__lpc_quantize_coefficients(const FLAC__real lp_coeff[], unsigned order,
unsigned precision, FLAC__int32 qlp_coeff[], int *shift) |
157 { | 168 { |
158 unsigned i; | 169 unsigned i; |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
193 *shift = max_shiftlimit; | 204 *shift = max_shiftlimit; |
194 else if(*shift < min_shiftlimit) | 205 else if(*shift < min_shiftlimit) |
195 return 1; | 206 return 1; |
196 } | 207 } |
197 | 208 |
198 if(*shift >= 0) { | 209 if(*shift >= 0) { |
199 FLAC__double error = 0.0; | 210 FLAC__double error = 0.0; |
200 FLAC__int32 q; | 211 FLAC__int32 q; |
201 for(i = 0; i < order; i++) { | 212 for(i = 0; i < order; i++) { |
202 error += lp_coeff[i] * (1 << *shift); | 213 error += lp_coeff[i] * (1 << *shift); |
203 #if 1 /* unfortunately lround() is C99 */ | |
204 if(error >= 0.0) | |
205 q = (FLAC__int32)(error + 0.5); | |
206 else | |
207 q = (FLAC__int32)(error - 0.5); | |
208 #else | |
209 q = lround(error); | 214 q = lround(error); |
210 #endif | 215 |
211 #ifdef FLAC__OVERFLOW_DETECT | 216 #ifdef FLAC__OVERFLOW_DETECT |
212 if(q > qmax+1) /* we expect q==qmax+1 occasionally due t
o rounding */ | 217 if(q > qmax+1) /* we expect q==qmax+1 occasionally due t
o rounding */ |
213 fprintf(stderr,"FLAC__lpc_quantize_coefficients:
quantizer overflow: q>qmax %d>%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,
qmax,*shift,cmax,precision+1,i,lp_coeff[i]); | 218 fprintf(stderr,"FLAC__lpc_quantize_coefficients:
quantizer overflow: q>qmax %d>%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,
qmax,*shift,cmax,precision+1,i,lp_coeff[i]); |
214 else if(q < qmin) | 219 else if(q < qmin) |
215 fprintf(stderr,"FLAC__lpc_quantize_coefficients:
quantizer overflow: q<qmin %d<%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,
qmin,*shift,cmax,precision+1,i,lp_coeff[i]); | 220 fprintf(stderr,"FLAC__lpc_quantize_coefficients:
quantizer overflow: q<qmin %d<%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,
qmin,*shift,cmax,precision+1,i,lp_coeff[i]); |
216 #endif | 221 #endif |
217 if(q > qmax) | 222 if(q > qmax) |
218 q = qmax; | 223 q = qmax; |
219 else if(q < qmin) | 224 else if(q < qmin) |
220 q = qmin; | 225 q = qmin; |
221 error -= q; | 226 error -= q; |
222 qlp_coeff[i] = q; | 227 qlp_coeff[i] = q; |
223 } | 228 } |
224 } | 229 } |
225 /* negative shift is very rare but due to design flaw, negative shift is | 230 /* negative shift is very rare but due to design flaw, negative shift is |
226 * a NOP in the decoder, so it must be handled specially by scaling down | 231 * a NOP in the decoder, so it must be handled specially by scaling down |
227 * coeffs | 232 * coeffs |
228 */ | 233 */ |
229 else { | 234 else { |
230 const int nshift = -(*shift); | 235 const int nshift = -(*shift); |
231 FLAC__double error = 0.0; | 236 FLAC__double error = 0.0; |
232 FLAC__int32 q; | 237 FLAC__int32 q; |
233 #ifdef DEBUG | 238 #ifdef DEBUG |
234 fprintf(stderr,"FLAC__lpc_quantize_coefficients: negative shift=
%d order=%u cmax=%f\n", *shift, order, cmax); | 239 fprintf(stderr,"FLAC__lpc_quantize_coefficients: negative shift=
%d order=%u cmax=%f\n", *shift, order, cmax); |
235 #endif | 240 #endif |
236 for(i = 0; i < order; i++) { | 241 for(i = 0; i < order; i++) { |
237 error += lp_coeff[i] / (1 << nshift); | 242 error += lp_coeff[i] / (1 << nshift); |
238 #if 1 /* unfortunately lround() is C99 */ | |
239 if(error >= 0.0) | |
240 q = (FLAC__int32)(error + 0.5); | |
241 else | |
242 q = (FLAC__int32)(error - 0.5); | |
243 #else | |
244 q = lround(error); | 243 q = lround(error); |
245 #endif | |
246 #ifdef FLAC__OVERFLOW_DETECT | 244 #ifdef FLAC__OVERFLOW_DETECT |
247 if(q > qmax+1) /* we expect q==qmax+1 occasionally due t
o rounding */ | 245 if(q > qmax+1) /* we expect q==qmax+1 occasionally due t
o rounding */ |
248 fprintf(stderr,"FLAC__lpc_quantize_coefficients:
quantizer overflow: q>qmax %d>%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,
qmax,*shift,cmax,precision+1,i,lp_coeff[i]); | 246 fprintf(stderr,"FLAC__lpc_quantize_coefficients:
quantizer overflow: q>qmax %d>%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,
qmax,*shift,cmax,precision+1,i,lp_coeff[i]); |
249 else if(q < qmin) | 247 else if(q < qmin) |
250 fprintf(stderr,"FLAC__lpc_quantize_coefficients:
quantizer overflow: q<qmin %d<%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,
qmin,*shift,cmax,precision+1,i,lp_coeff[i]); | 248 fprintf(stderr,"FLAC__lpc_quantize_coefficients:
quantizer overflow: q<qmin %d<%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,
qmin,*shift,cmax,precision+1,i,lp_coeff[i]); |
251 #endif | 249 #endif |
252 if(q > qmax) | 250 if(q > qmax) |
253 q = qmax; | 251 q = qmax; |
254 else if(q < qmin) | 252 else if(q < qmin) |
255 q = qmin; | 253 q = qmin; |
256 error -= q; | 254 error -= q; |
257 qlp_coeff[i] = q; | 255 qlp_coeff[i] = q; |
258 } | 256 } |
259 *shift = 0; | 257 *shift = 0; |
260 } | 258 } |
261 | 259 |
262 return 0; | 260 return 0; |
263 } | 261 } |
264 | 262 |
265 void FLAC__lpc_compute_residual_from_qlp_coefficients(const FLAC__int32 *data, u
nsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantiza
tion, FLAC__int32 residual[]) | 263 #if defined(_MSC_VER) |
| 264 // silence MSVC warnings about __restrict modifier |
| 265 #pragma warning ( disable : 4028 ) |
| 266 #endif |
| 267 |
| 268 void FLAC__lpc_compute_residual_from_qlp_coefficients(const FLAC__int32 * flac_r
estrict data, unsigned data_len, const FLAC__int32 * flac_restrict qlp_coeff, un
signed order, int lp_quantization, FLAC__int32 * flac_restrict residual) |
266 #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) | 269 #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) |
267 { | 270 { |
268 FLAC__int64 sumo; | 271 FLAC__int64 sumo; |
269 unsigned i, j; | 272 unsigned i, j; |
270 FLAC__int32 sum; | 273 FLAC__int32 sum; |
271 const FLAC__int32 *history; | 274 const FLAC__int32 *history; |
272 | 275 |
273 #ifdef FLAC__OVERFLOW_DETECT_VERBOSE | 276 #ifdef FLAC__OVERFLOW_DETECT_VERBOSE |
274 fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients: data_l
en=%d, order=%u, lpq=%d",data_len,order,lp_quantization); | 277 fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients: data_l
en=%d, order=%u, lpq=%d",data_len,order,lp_quantization); |
275 for(i=0;i<order;i++) | 278 for(i=0;i<order;i++) |
276 fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]); | 279 fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]); |
277 fprintf(stderr,"\n"); | 280 fprintf(stderr,"\n"); |
278 #endif | 281 #endif |
279 FLAC__ASSERT(order > 0); | 282 FLAC__ASSERT(order > 0); |
280 | 283 |
281 for(i = 0; i < data_len; i++) { | 284 for(i = 0; i < data_len; i++) { |
282 sumo = 0; | 285 sumo = 0; |
283 sum = 0; | 286 sum = 0; |
284 history = data; | 287 history = data; |
285 for(j = 0; j < order; j++) { | 288 for(j = 0; j < order; j++) { |
286 sum += qlp_coeff[j] * (*(--history)); | 289 sum += qlp_coeff[j] * (*(--history)); |
287 sumo += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*histo
ry); | 290 sumo += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*histo
ry); |
288 #if defined _MSC_VER | 291 » » » » fprintf(stderr,"FLAC__lpc_compute_residual_from_
qlp_coefficients: OVERFLOW, i=%u, j=%u, c=%d, d=%d, sumo=%" PRId64 "\n",i,j,qlp_
coeff[j],*history,sumo); |
289 » » » if(sumo > 2147483647I64 || sumo < -2147483648I64) | |
290 » » » » fprintf(stderr,"FLAC__lpc_compute_residual_from_
qlp_coefficients: OVERFLOW, i=%u, j=%u, c=%d, d=%d, sumo=%I64d\n",i,j,qlp_coeff[
j],*history,sumo); | |
291 #else | |
292 » » » if(sumo > 2147483647ll || sumo < -2147483648ll) | |
293 » » » » fprintf(stderr,"FLAC__lpc_compute_residual_from_
qlp_coefficients: OVERFLOW, i=%u, j=%u, c=%d, d=%d, sumo=%lld\n",i,j,qlp_coeff[j
],*history,(long long)sumo); | |
294 #endif | |
295 } | 292 } |
296 *(residual++) = *(data++) - (sum >> lp_quantization); | 293 *(residual++) = *(data++) - (sum >> lp_quantization); |
297 } | 294 } |
298 | 295 |
299 /* Here's a slower but clearer version: | 296 /* Here's a slower but clearer version: |
300 for(i = 0; i < data_len; i++) { | 297 for(i = 0; i < data_len; i++) { |
301 sum = 0; | 298 sum = 0; |
302 for(j = 0; j < order; j++) | 299 for(j = 0; j < order; j++) |
303 sum += qlp_coeff[j] * data[i-j-1]; | 300 sum += qlp_coeff[j] * data[i-j-1]; |
304 residual[i] = data[i] - (sum >> lp_quantization); | 301 residual[i] = data[i] - (sum >> lp_quantization); |
(...skipping 216 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
521 sum += qlp_coeff[ 2] * data[i- 3]; | 518 sum += qlp_coeff[ 2] * data[i- 3]; |
522 sum += qlp_coeff[ 1] * data[i- 2]; | 519 sum += qlp_coeff[ 1] * data[i- 2]; |
523 sum += qlp_coeff[ 0] * data[i- 1]; | 520 sum += qlp_coeff[ 0] * data[i- 1]; |
524 } | 521 } |
525 residual[i] = data[i] - (sum >> lp_quantization); | 522 residual[i] = data[i] - (sum >> lp_quantization); |
526 } | 523 } |
527 } | 524 } |
528 } | 525 } |
529 #endif | 526 #endif |
530 | 527 |
531 void FLAC__lpc_compute_residual_from_qlp_coefficients_wide(const FLAC__int32 *da
ta, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_qua
ntization, FLAC__int32 residual[]) | 528 void FLAC__lpc_compute_residual_from_qlp_coefficients_wide(const FLAC__int32 * f
lac_restrict data, unsigned data_len, const FLAC__int32 * flac_restrict qlp_coef
f, unsigned order, int lp_quantization, FLAC__int32 * flac_restrict residual) |
532 #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) | 529 #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) |
533 { | 530 { |
534 unsigned i, j; | 531 unsigned i, j; |
535 FLAC__int64 sum; | 532 FLAC__int64 sum; |
536 const FLAC__int32 *history; | 533 const FLAC__int32 *history; |
537 | 534 |
538 #ifdef FLAC__OVERFLOW_DETECT_VERBOSE | 535 #ifdef FLAC__OVERFLOW_DETECT_VERBOSE |
539 fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients_wide: d
ata_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization); | 536 fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients_wide: d
ata_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization); |
540 for(i=0;i<order;i++) | 537 for(i=0;i<order;i++) |
541 fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]); | 538 fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]); |
542 fprintf(stderr,"\n"); | 539 fprintf(stderr,"\n"); |
543 #endif | 540 #endif |
544 FLAC__ASSERT(order > 0); | 541 FLAC__ASSERT(order > 0); |
545 | 542 |
546 for(i = 0; i < data_len; i++) { | 543 for(i = 0; i < data_len; i++) { |
547 sum = 0; | 544 sum = 0; |
548 history = data; | 545 history = data; |
549 for(j = 0; j < order; j++) | 546 for(j = 0; j < order; j++) |
550 sum += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*(--his
tory)); | 547 sum += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*(--his
tory)); |
551 if(FLAC__bitmath_silog2_wide(sum >> lp_quantization) > 32) { | 548 if(FLAC__bitmath_silog2_wide(sum >> lp_quantization) > 32) { |
552 #if defined _MSC_VER | 549 » » » fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coef
ficients_wide: OVERFLOW, i=%u, sum=%" PRId64 "\n", i, (sum >> lp_quantization)); |
553 » » » fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coef
ficients_wide: OVERFLOW, i=%u, sum=%I64d\n", i, sum >> lp_quantization); | |
554 #else | |
555 » » » fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coef
ficients_wide: OVERFLOW, i=%u, sum=%lld\n", i, (long long)(sum >> lp_quantizatio
n)); | |
556 #endif | |
557 break; | 550 break; |
558 } | 551 } |
559 if(FLAC__bitmath_silog2_wide((FLAC__int64)(*data) - (sum >> lp_q
uantization)) > 32) { | 552 if(FLAC__bitmath_silog2_wide((FLAC__int64)(*data) - (sum >> lp_q
uantization)) > 32) { |
560 #if defined _MSC_VER | 553 » » » fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coef
ficients_wide: OVERFLOW, i=%u, data=%d, sum=%" PRId64 ", residual=%" PRId64 "\n"
, i, *data, (int64_t)(sum >> lp_quantization), ((FLAC__int64)(*data) - (sum >> l
p_quantization))); |
561 » » » fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coef
ficients_wide: OVERFLOW, i=%u, data=%d, sum=%I64d, residual=%I64d\n", i, *data,
sum >> lp_quantization, (FLAC__int64)(*data) - (sum >> lp_quantization)); | |
562 #else | |
563 » » » fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coef
ficients_wide: OVERFLOW, i=%u, data=%d, sum=%lld, residual=%lld\n", i, *data, (l
ong long)(sum >> lp_quantization), (long long)((FLAC__int64)(*data) - (sum >> lp
_quantization))); | |
564 #endif | |
565 break; | 554 break; |
566 } | 555 } |
567 *(residual++) = *(data++) - (FLAC__int32)(sum >> lp_quantization
); | 556 *(residual++) = *(data++) - (FLAC__int32)(sum >> lp_quantization
); |
568 } | 557 } |
569 } | 558 } |
570 #else /* fully unrolled version for normal use */ | 559 #else /* fully unrolled version for normal use */ |
571 { | 560 { |
572 int i; | 561 int i; |
573 FLAC__int64 sum; | 562 FLAC__int64 sum; |
574 | 563 |
(...skipping 210 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
785 sum += qlp_coeff[ 0] * (FLAC__int64)dat
a[i- 1]; | 774 sum += qlp_coeff[ 0] * (FLAC__int64)dat
a[i- 1]; |
786 } | 775 } |
787 residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantiza
tion); | 776 residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantiza
tion); |
788 } | 777 } |
789 } | 778 } |
790 } | 779 } |
791 #endif | 780 #endif |
792 | 781 |
793 #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ | 782 #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ |
794 | 783 |
795 void FLAC__lpc_restore_signal(const FLAC__int32 residual[], unsigned data_len, c
onst FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 d
ata[]) | 784 void FLAC__lpc_restore_signal(const FLAC__int32 * flac_restrict residual, unsign
ed data_len, const FLAC__int32 * flac_restrict qlp_coeff, unsigned order, int lp
_quantization, FLAC__int32 * flac_restrict data) |
796 #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) | 785 #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) |
797 { | 786 { |
798 FLAC__int64 sumo; | 787 FLAC__int64 sumo; |
799 unsigned i, j; | 788 unsigned i, j; |
800 FLAC__int32 sum; | 789 FLAC__int32 sum; |
801 const FLAC__int32 *r = residual, *history; | 790 const FLAC__int32 *r = residual, *history; |
802 | 791 |
803 #ifdef FLAC__OVERFLOW_DETECT_VERBOSE | 792 #ifdef FLAC__OVERFLOW_DETECT_VERBOSE |
804 fprintf(stderr,"FLAC__lpc_restore_signal: data_len=%d, order=%u, lpq=%d"
,data_len,order,lp_quantization); | 793 fprintf(stderr,"FLAC__lpc_restore_signal: data_len=%d, order=%u, lpq=%d"
,data_len,order,lp_quantization); |
805 for(i=0;i<order;i++) | 794 for(i=0;i<order;i++) |
806 fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]); | 795 fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]); |
807 fprintf(stderr,"\n"); | 796 fprintf(stderr,"\n"); |
808 #endif | 797 #endif |
809 FLAC__ASSERT(order > 0); | 798 FLAC__ASSERT(order > 0); |
810 | 799 |
811 for(i = 0; i < data_len; i++) { | 800 for(i = 0; i < data_len; i++) { |
812 sumo = 0; | 801 sumo = 0; |
813 sum = 0; | 802 sum = 0; |
814 history = data; | 803 history = data; |
815 for(j = 0; j < order; j++) { | 804 for(j = 0; j < order; j++) { |
816 sum += qlp_coeff[j] * (*(--history)); | 805 sum += qlp_coeff[j] * (*(--history)); |
817 sumo += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*histo
ry); | 806 sumo += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*histo
ry); |
818 #if defined _MSC_VER | |
819 if(sumo > 2147483647I64 || sumo < -2147483648I64) | |
820 fprintf(stderr,"FLAC__lpc_restore_signal: OVERFL
OW, i=%u, j=%u, c=%d, d=%d, sumo=%I64d\n",i,j,qlp_coeff[j],*history,sumo); | |
821 #else | |
822 if(sumo > 2147483647ll || sumo < -2147483648ll) | 807 if(sumo > 2147483647ll || sumo < -2147483648ll) |
823 » » » » fprintf(stderr,"FLAC__lpc_restore_signal: OVERFL
OW, i=%u, j=%u, c=%d, d=%d, sumo=%lld\n",i,j,qlp_coeff[j],*history,(long long)su
mo); | 808 » » » » fprintf(stderr,"FLAC__lpc_restore_signal: OVERFL
OW, i=%u, j=%u, c=%d, d=%d, sumo=%" PRId64 "\n",i,j,qlp_coeff[j],*history,sumo); |
824 #endif | |
825 } | 809 } |
826 *(data++) = *(r++) + (sum >> lp_quantization); | 810 *(data++) = *(r++) + (sum >> lp_quantization); |
827 } | 811 } |
828 | 812 |
829 /* Here's a slower but clearer version: | 813 /* Here's a slower but clearer version: |
830 for(i = 0; i < data_len; i++) { | 814 for(i = 0; i < data_len; i++) { |
831 sum = 0; | 815 sum = 0; |
832 for(j = 0; j < order; j++) | 816 for(j = 0; j < order; j++) |
833 sum += qlp_coeff[j] * data[i-j-1]; | 817 sum += qlp_coeff[j] * data[i-j-1]; |
834 data[i] = residual[i] + (sum >> lp_quantization); | 818 data[i] = residual[i] + (sum >> lp_quantization); |
(...skipping 216 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1051 sum += qlp_coeff[ 2] * data[i- 3]; | 1035 sum += qlp_coeff[ 2] * data[i- 3]; |
1052 sum += qlp_coeff[ 1] * data[i- 2]; | 1036 sum += qlp_coeff[ 1] * data[i- 2]; |
1053 sum += qlp_coeff[ 0] * data[i- 1]; | 1037 sum += qlp_coeff[ 0] * data[i- 1]; |
1054 } | 1038 } |
1055 data[i] = residual[i] + (sum >> lp_quantization); | 1039 data[i] = residual[i] + (sum >> lp_quantization); |
1056 } | 1040 } |
1057 } | 1041 } |
1058 } | 1042 } |
1059 #endif | 1043 #endif |
1060 | 1044 |
1061 void FLAC__lpc_restore_signal_wide(const FLAC__int32 residual[], unsigned data_l
en, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__in
t32 data[]) | 1045 void FLAC__lpc_restore_signal_wide(const FLAC__int32 * flac_restrict residual, u
nsigned data_len, const FLAC__int32 * flac_restrict qlp_coeff, unsigned order, i
nt lp_quantization, FLAC__int32 * flac_restrict data) |
1062 #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) | 1046 #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) |
1063 { | 1047 { |
1064 unsigned i, j; | 1048 unsigned i, j; |
1065 FLAC__int64 sum; | 1049 FLAC__int64 sum; |
1066 const FLAC__int32 *r = residual, *history; | 1050 const FLAC__int32 *r = residual, *history; |
1067 | 1051 |
1068 #ifdef FLAC__OVERFLOW_DETECT_VERBOSE | 1052 #ifdef FLAC__OVERFLOW_DETECT_VERBOSE |
1069 fprintf(stderr,"FLAC__lpc_restore_signal_wide: data_len=%d, order=%u, lp
q=%d",data_len,order,lp_quantization); | 1053 fprintf(stderr,"FLAC__lpc_restore_signal_wide: data_len=%d, order=%u, lp
q=%d",data_len,order,lp_quantization); |
1070 for(i=0;i<order;i++) | 1054 for(i=0;i<order;i++) |
1071 fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]); | 1055 fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]); |
1072 fprintf(stderr,"\n"); | 1056 fprintf(stderr,"\n"); |
1073 #endif | 1057 #endif |
1074 FLAC__ASSERT(order > 0); | 1058 FLAC__ASSERT(order > 0); |
1075 | 1059 |
1076 for(i = 0; i < data_len; i++) { | 1060 for(i = 0; i < data_len; i++) { |
1077 sum = 0; | 1061 sum = 0; |
1078 history = data; | 1062 history = data; |
1079 for(j = 0; j < order; j++) | 1063 for(j = 0; j < order; j++) |
1080 sum += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*(--his
tory)); | 1064 sum += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*(--his
tory)); |
1081 if(FLAC__bitmath_silog2_wide(sum >> lp_quantization) > 32) { | 1065 if(FLAC__bitmath_silog2_wide(sum >> lp_quantization) > 32) { |
1082 #ifdef _MSC_VER | 1066 » » » fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW,
i=%u, sum=%" PRId64 "\n", i, (sum >> lp_quantization)); |
1083 » » » fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW,
i=%u, sum=%I64d\n", i, sum >> lp_quantization); | |
1084 #else | |
1085 » » » fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW,
i=%u, sum=%lld\n", i, (long long)(sum >> lp_quantization)); | |
1086 #endif | |
1087 break; | 1067 break; |
1088 } | 1068 } |
1089 if(FLAC__bitmath_silog2_wide((FLAC__int64)(*r) + (sum >> lp_quan
tization)) > 32) { | 1069 if(FLAC__bitmath_silog2_wide((FLAC__int64)(*r) + (sum >> lp_quan
tization)) > 32) { |
1090 #ifdef _MSC_VER | 1070 » » » fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW,
i=%u, residual=%d, sum=%" PRId64 ", data=%" PRId64 "\n", i, *r, (sum >> lp_quan
tization), ((FLAC__int64)(*r) + (sum >> lp_quantization))); |
1091 » » » fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW,
i=%u, residual=%d, sum=%I64d, data=%I64d\n", i, *r, sum >> lp_quantization, (FL
AC__int64)(*r) + (sum >> lp_quantization)); | |
1092 #else | |
1093 » » » fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW,
i=%u, residual=%d, sum=%lld, data=%lld\n", i, *r, (long long)(sum >> lp_quantiz
ation), (long long)((FLAC__int64)(*r) + (sum >> lp_quantization))); | |
1094 #endif | |
1095 break; | 1071 break; |
1096 } | 1072 } |
1097 *(data++) = *(r++) + (FLAC__int32)(sum >> lp_quantization); | 1073 *(data++) = *(r++) + (FLAC__int32)(sum >> lp_quantization); |
1098 } | 1074 } |
1099 } | 1075 } |
1100 #else /* fully unrolled version for normal use */ | 1076 #else /* fully unrolled version for normal use */ |
1101 { | 1077 { |
1102 int i; | 1078 int i; |
1103 FLAC__int64 sum; | 1079 FLAC__int64 sum; |
1104 | 1080 |
(...skipping 208 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1313 sum += qlp_coeff[ 2] * (FLAC__int64)dat
a[i- 3]; | 1289 sum += qlp_coeff[ 2] * (FLAC__int64)dat
a[i- 3]; |
1314 sum += qlp_coeff[ 1] * (FLAC__int64)dat
a[i- 2]; | 1290 sum += qlp_coeff[ 1] * (FLAC__int64)dat
a[i- 2]; |
1315 sum += qlp_coeff[ 0] * (FLAC__int64)dat
a[i- 1]; | 1291 sum += qlp_coeff[ 0] * (FLAC__int64)dat
a[i- 1]; |
1316 } | 1292 } |
1317 data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantiza
tion); | 1293 data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantiza
tion); |
1318 } | 1294 } |
1319 } | 1295 } |
1320 } | 1296 } |
1321 #endif | 1297 #endif |
1322 | 1298 |
| 1299 #if defined(_MSC_VER) |
| 1300 #pragma warning ( default : 4028 ) |
| 1301 #endif |
| 1302 |
1323 #ifndef FLAC__INTEGER_ONLY_LIBRARY | 1303 #ifndef FLAC__INTEGER_ONLY_LIBRARY |
1324 | 1304 |
1325 FLAC__double FLAC__lpc_compute_expected_bits_per_residual_sample(FLAC__double lp
c_error, unsigned total_samples) | 1305 FLAC__double FLAC__lpc_compute_expected_bits_per_residual_sample(FLAC__double lp
c_error, unsigned total_samples) |
1326 { | 1306 { |
1327 FLAC__double error_scale; | 1307 FLAC__double error_scale; |
1328 | 1308 |
1329 FLAC__ASSERT(total_samples > 0); | 1309 FLAC__ASSERT(total_samples > 0); |
1330 | 1310 |
1331 error_scale = 0.5 * M_LN2 * M_LN2 / (FLAC__double)total_samples; | 1311 error_scale = 0.5 * M_LN2 * M_LN2 / (FLAC__double)total_samples; |
1332 | 1312 |
(...skipping 12 matching lines...) Expand all Loading... |
1345 else if(lpc_error < 0.0) { /* error should not be negative but can happe
n due to inadequate floating-point resolution */ | 1325 else if(lpc_error < 0.0) { /* error should not be negative but can happe
n due to inadequate floating-point resolution */ |
1346 return 1e32; | 1326 return 1e32; |
1347 } | 1327 } |
1348 else { | 1328 else { |
1349 return 0.0; | 1329 return 0.0; |
1350 } | 1330 } |
1351 } | 1331 } |
1352 | 1332 |
1353 unsigned FLAC__lpc_compute_best_order(const FLAC__double lpc_error[], unsigned m
ax_order, unsigned total_samples, unsigned overhead_bits_per_order) | 1333 unsigned FLAC__lpc_compute_best_order(const FLAC__double lpc_error[], unsigned m
ax_order, unsigned total_samples, unsigned overhead_bits_per_order) |
1354 { | 1334 { |
1355 » unsigned order, index, best_index; /* 'index' the index into lpc_error;
index==order-1 since lpc_error[0] is for order==1, lpc_error[1] is for order==2,
etc */ | 1335 » unsigned order, indx, best_index; /* 'index' the index into lpc_error; i
ndex==order-1 since lpc_error[0] is for order==1, lpc_error[1] is for order==2,
etc */ |
1356 FLAC__double bits, best_bits, error_scale; | 1336 FLAC__double bits, best_bits, error_scale; |
1357 | 1337 |
1358 FLAC__ASSERT(max_order > 0); | 1338 FLAC__ASSERT(max_order > 0); |
1359 FLAC__ASSERT(total_samples > 0); | 1339 FLAC__ASSERT(total_samples > 0); |
1360 | 1340 |
1361 error_scale = 0.5 * M_LN2 * M_LN2 / (FLAC__double)total_samples; | 1341 error_scale = 0.5 * M_LN2 * M_LN2 / (FLAC__double)total_samples; |
1362 | 1342 |
1363 best_index = 0; | 1343 best_index = 0; |
1364 best_bits = (unsigned)(-1); | 1344 best_bits = (unsigned)(-1); |
1365 | 1345 |
1366 » for(index = 0, order = 1; index < max_order; index++, order++) { | 1346 » for(indx = 0, order = 1; indx < max_order; indx++, order++) { |
1367 » » bits = FLAC__lpc_compute_expected_bits_per_residual_sample_with_
error_scale(lpc_error[index], error_scale) * (FLAC__double)(total_samples - orde
r) + (FLAC__double)(order * overhead_bits_per_order); | 1347 » » bits = FLAC__lpc_compute_expected_bits_per_residual_sample_with_
error_scale(lpc_error[indx], error_scale) * (FLAC__double)(total_samples - order
) + (FLAC__double)(order * overhead_bits_per_order); |
1368 if(bits < best_bits) { | 1348 if(bits < best_bits) { |
1369 » » » best_index = index; | 1349 » » » best_index = indx; |
1370 best_bits = bits; | 1350 best_bits = bits; |
1371 } | 1351 } |
1372 } | 1352 } |
1373 | 1353 |
1374 » return best_index+1; /* +1 since index of lpc_error[] is order-1 */ | 1354 » return best_index+1; /* +1 since indx of lpc_error[] is order-1 */ |
1375 } | 1355 } |
1376 | 1356 |
1377 #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ | 1357 #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ |
OLD | NEW |