xref: /aosp_15_r20/external/flac/src/libFLAC/lpc.c (revision 600f14f40d737144c998e2ec7a483122d3776fbc)
1*600f14f4SXin Li /* libFLAC - Free Lossless Audio Codec library
2*600f14f4SXin Li  * Copyright (C) 2000-2009  Josh Coalson
3*600f14f4SXin Li  * Copyright (C) 2011-2023  Xiph.Org Foundation
4*600f14f4SXin Li  *
5*600f14f4SXin Li  * Redistribution and use in source and binary forms, with or without
6*600f14f4SXin Li  * modification, are permitted provided that the following conditions
7*600f14f4SXin Li  * are met:
8*600f14f4SXin Li  *
9*600f14f4SXin Li  * - Redistributions of source code must retain the above copyright
10*600f14f4SXin Li  * notice, this list of conditions and the following disclaimer.
11*600f14f4SXin Li  *
12*600f14f4SXin Li  * - Redistributions in binary form must reproduce the above copyright
13*600f14f4SXin Li  * notice, this list of conditions and the following disclaimer in the
14*600f14f4SXin Li  * documentation and/or other materials provided with the distribution.
15*600f14f4SXin Li  *
16*600f14f4SXin Li  * - Neither the name of the Xiph.org Foundation nor the names of its
17*600f14f4SXin Li  * contributors may be used to endorse or promote products derived from
18*600f14f4SXin Li  * this software without specific prior written permission.
19*600f14f4SXin Li  *
20*600f14f4SXin Li  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21*600f14f4SXin Li  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22*600f14f4SXin Li  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
23*600f14f4SXin Li  * A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR
24*600f14f4SXin Li  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25*600f14f4SXin Li  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
26*600f14f4SXin Li  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
27*600f14f4SXin Li  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
28*600f14f4SXin Li  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
29*600f14f4SXin Li  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
30*600f14f4SXin Li  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31*600f14f4SXin Li  */
32*600f14f4SXin Li 
33*600f14f4SXin Li #ifdef HAVE_CONFIG_H
34*600f14f4SXin Li #  include <config.h>
35*600f14f4SXin Li #endif
36*600f14f4SXin Li 
37*600f14f4SXin Li #include <math.h>
38*600f14f4SXin Li #include <stdlib.h>
39*600f14f4SXin Li 
40*600f14f4SXin Li #include "FLAC/assert.h"
41*600f14f4SXin Li #include "FLAC/format.h"
42*600f14f4SXin Li #include "share/compat.h"
43*600f14f4SXin Li #include "private/bitmath.h"
44*600f14f4SXin Li #include "private/lpc.h"
45*600f14f4SXin Li #include "private/macros.h"
46*600f14f4SXin Li 
47*600f14f4SXin Li #if !defined(NDEBUG) || defined FLAC__OVERFLOW_DETECT || defined FLAC__OVERFLOW_DETECT_VERBOSE
48*600f14f4SXin Li #include <stdio.h>
49*600f14f4SXin Li #endif
50*600f14f4SXin Li 
51*600f14f4SXin Li /* OPT: #undef'ing this may improve the speed on some architectures */
52*600f14f4SXin Li #define FLAC__LPC_UNROLLED_FILTER_LOOPS
53*600f14f4SXin Li 
54*600f14f4SXin Li #ifndef FLAC__INTEGER_ONLY_LIBRARY
55*600f14f4SXin Li 
56*600f14f4SXin Li #if defined(_MSC_VER) && (_MSC_VER < 1800)
57*600f14f4SXin Li #include <float.h>
lround(double x)58*600f14f4SXin Li static inline long int lround(double x) {
59*600f14f4SXin Li 	return (long)(x + _copysign(0.5, x));
60*600f14f4SXin Li }
61*600f14f4SXin Li #elif !defined(HAVE_LROUND) && defined(__GNUC__)
lround(double x)62*600f14f4SXin Li static inline long int lround(double x) {
63*600f14f4SXin Li 	return (long)(x + __builtin_copysign(0.5, x));
64*600f14f4SXin Li }
65*600f14f4SXin Li /* If this fails, we are in the presence of a mid 90's compiler, move along... */
66*600f14f4SXin Li #endif
67*600f14f4SXin Li 
FLAC__lpc_window_data(const FLAC__int32 in[],const FLAC__real window[],FLAC__real out[],uint32_t data_len)68*600f14f4SXin Li void FLAC__lpc_window_data(const FLAC__int32 in[], const FLAC__real window[], FLAC__real out[], uint32_t data_len)
69*600f14f4SXin Li {
70*600f14f4SXin Li 	uint32_t i;
71*600f14f4SXin Li 	for(i = 0; i < data_len; i++)
72*600f14f4SXin Li 		out[i] = in[i] * window[i];
73*600f14f4SXin Li }
74*600f14f4SXin Li 
FLAC__lpc_window_data_wide(const FLAC__int64 in[],const FLAC__real window[],FLAC__real out[],uint32_t data_len)75*600f14f4SXin Li void FLAC__lpc_window_data_wide(const FLAC__int64 in[], const FLAC__real window[], FLAC__real out[], uint32_t data_len)
76*600f14f4SXin Li {
77*600f14f4SXin Li 	uint32_t i;
78*600f14f4SXin Li 	for(i = 0; i < data_len; i++)
79*600f14f4SXin Li 		out[i] = in[i] * window[i];
80*600f14f4SXin Li }
81*600f14f4SXin Li 
FLAC__lpc_window_data_partial(const FLAC__int32 in[],const FLAC__real window[],FLAC__real out[],uint32_t data_len,uint32_t part_size,uint32_t data_shift)82*600f14f4SXin Li void FLAC__lpc_window_data_partial(const FLAC__int32 in[], const FLAC__real window[], FLAC__real out[], uint32_t data_len, uint32_t part_size, uint32_t data_shift)
83*600f14f4SXin Li {
84*600f14f4SXin Li 	uint32_t i, j;
85*600f14f4SXin Li 	if((part_size + data_shift) < data_len){
86*600f14f4SXin Li 		for(i = 0; i < part_size; i++)
87*600f14f4SXin Li 			out[i] = in[data_shift+i] * window[i];
88*600f14f4SXin Li 		i = flac_min(i,data_len - part_size - data_shift);
89*600f14f4SXin Li 		for(j = data_len - part_size; j < data_len; i++, j++)
90*600f14f4SXin Li 			out[i] = in[data_shift+i] * window[j];
91*600f14f4SXin Li 		if(i < data_len)
92*600f14f4SXin Li 			out[i] = 0.0f;
93*600f14f4SXin Li 	}
94*600f14f4SXin Li }
95*600f14f4SXin Li 
FLAC__lpc_window_data_partial_wide(const FLAC__int64 in[],const FLAC__real window[],FLAC__real out[],uint32_t data_len,uint32_t part_size,uint32_t data_shift)96*600f14f4SXin Li void FLAC__lpc_window_data_partial_wide(const FLAC__int64 in[], const FLAC__real window[], FLAC__real out[], uint32_t data_len, uint32_t part_size, uint32_t data_shift)
97*600f14f4SXin Li {
98*600f14f4SXin Li 	uint32_t i, j;
99*600f14f4SXin Li 	if((part_size + data_shift) < data_len){
100*600f14f4SXin Li 		for(i = 0; i < part_size; i++)
101*600f14f4SXin Li 			out[i] = in[data_shift+i] * window[i];
102*600f14f4SXin Li 		i = flac_min(i,data_len - part_size - data_shift);
103*600f14f4SXin Li 		for(j = data_len - part_size; j < data_len; i++, j++)
104*600f14f4SXin Li 			out[i] = in[data_shift+i] * window[j];
105*600f14f4SXin Li 		if(i < data_len)
106*600f14f4SXin Li 			out[i] = 0.0f;
107*600f14f4SXin Li 	}
108*600f14f4SXin Li }
109*600f14f4SXin Li 
FLAC__lpc_compute_autocorrelation(const FLAC__real data[],uint32_t data_len,uint32_t lag,double autoc[])110*600f14f4SXin Li void FLAC__lpc_compute_autocorrelation(const FLAC__real data[], uint32_t data_len, uint32_t lag, double autoc[])
111*600f14f4SXin Li {
112*600f14f4SXin Li 	/* a readable, but slower, version */
113*600f14f4SXin Li #if 0
114*600f14f4SXin Li 	double d;
115*600f14f4SXin Li 	uint32_t i;
116*600f14f4SXin Li 
117*600f14f4SXin Li 	FLAC__ASSERT(lag > 0);
118*600f14f4SXin Li 	FLAC__ASSERT(lag <= data_len);
119*600f14f4SXin Li 
120*600f14f4SXin Li 	/*
121*600f14f4SXin Li 	 * Technically we should subtract the mean first like so:
122*600f14f4SXin Li 	 *   for(i = 0; i < data_len; i++)
123*600f14f4SXin Li 	 *     data[i] -= mean;
124*600f14f4SXin Li 	 * but it appears not to make enough of a difference to matter, and
125*600f14f4SXin Li 	 * most signals are already closely centered around zero
126*600f14f4SXin Li 	 */
127*600f14f4SXin Li 	while(lag--) {
128*600f14f4SXin Li 		for(i = lag, d = 0.0; i < data_len; i++)
129*600f14f4SXin Li 			d += data[i] * (double)data[i - lag];
130*600f14f4SXin Li 		autoc[lag] = d;
131*600f14f4SXin Li 	}
132*600f14f4SXin Li #endif
133*600f14f4SXin Li 	if (data_len < FLAC__MAX_LPC_ORDER || lag > 16) {
134*600f14f4SXin Li 		/*
135*600f14f4SXin Li 		 * this version tends to run faster because of better data locality
136*600f14f4SXin Li 		 * ('data_len' is usually much larger than 'lag')
137*600f14f4SXin Li 		 */
138*600f14f4SXin Li 		double d;
139*600f14f4SXin Li 		uint32_t sample, coeff;
140*600f14f4SXin Li 		const uint32_t limit = data_len - lag;
141*600f14f4SXin Li 
142*600f14f4SXin Li 		FLAC__ASSERT(lag > 0);
143*600f14f4SXin Li 		FLAC__ASSERT(lag <= data_len);
144*600f14f4SXin Li 
145*600f14f4SXin Li 		for(coeff = 0; coeff < lag; coeff++)
146*600f14f4SXin Li 			autoc[coeff] = 0.0;
147*600f14f4SXin Li 		for(sample = 0; sample <= limit; sample++) {
148*600f14f4SXin Li 			d = data[sample];
149*600f14f4SXin Li 			for(coeff = 0; coeff < lag; coeff++)
150*600f14f4SXin Li 				autoc[coeff] += d * data[sample+coeff];
151*600f14f4SXin Li 		}
152*600f14f4SXin Li 		for(; sample < data_len; sample++) {
153*600f14f4SXin Li 			d = data[sample];
154*600f14f4SXin Li 			for(coeff = 0; coeff < data_len - sample; coeff++)
155*600f14f4SXin Li 				autoc[coeff] += d * data[sample+coeff];
156*600f14f4SXin Li 		}
157*600f14f4SXin Li 	}
158*600f14f4SXin Li 	else if(lag <= 8) {
159*600f14f4SXin Li 		#undef MAX_LAG
160*600f14f4SXin Li 		#define MAX_LAG 8
161*600f14f4SXin Li 		#include "deduplication/lpc_compute_autocorrelation_intrin.c"
162*600f14f4SXin Li 	}
163*600f14f4SXin Li 	else if(lag <= 12) {
164*600f14f4SXin Li 		#undef MAX_LAG
165*600f14f4SXin Li 		#define MAX_LAG 12
166*600f14f4SXin Li 		#include "deduplication/lpc_compute_autocorrelation_intrin.c"
167*600f14f4SXin Li 	}
168*600f14f4SXin Li 	else if(lag <= 16) {
169*600f14f4SXin Li 		#undef MAX_LAG
170*600f14f4SXin Li 		#define MAX_LAG 16
171*600f14f4SXin Li 		#include "deduplication/lpc_compute_autocorrelation_intrin.c"
172*600f14f4SXin Li 	}
173*600f14f4SXin Li 
174*600f14f4SXin Li }
175*600f14f4SXin Li 
FLAC__lpc_compute_lp_coefficients(const double autoc[],uint32_t * max_order,FLAC__real lp_coeff[][FLAC__MAX_LPC_ORDER],double error[])176*600f14f4SXin Li void FLAC__lpc_compute_lp_coefficients(const double autoc[], uint32_t *max_order, FLAC__real lp_coeff[][FLAC__MAX_LPC_ORDER], double error[])
177*600f14f4SXin Li {
178*600f14f4SXin Li 	uint32_t i, j;
179*600f14f4SXin Li 	double r, err, lpc[FLAC__MAX_LPC_ORDER];
180*600f14f4SXin Li 
181*600f14f4SXin Li 	FLAC__ASSERT(0 != max_order);
182*600f14f4SXin Li 	FLAC__ASSERT(0 < *max_order);
183*600f14f4SXin Li 	FLAC__ASSERT(*max_order <= FLAC__MAX_LPC_ORDER);
184*600f14f4SXin Li 	FLAC__ASSERT(autoc[0] != 0.0);
185*600f14f4SXin Li 
186*600f14f4SXin Li 	err = autoc[0];
187*600f14f4SXin Li 
188*600f14f4SXin Li 	for(i = 0; i < *max_order; i++) {
189*600f14f4SXin Li 		/* Sum up this iteration's reflection coefficient. */
190*600f14f4SXin Li 		r = -autoc[i+1];
191*600f14f4SXin Li 		for(j = 0; j < i; j++)
192*600f14f4SXin Li 			r -= lpc[j] * autoc[i-j];
193*600f14f4SXin Li 		r /= err;
194*600f14f4SXin Li 
195*600f14f4SXin Li 		/* Update LPC coefficients and total error. */
196*600f14f4SXin Li 		lpc[i]=r;
197*600f14f4SXin Li 		for(j = 0; j < (i>>1); j++) {
198*600f14f4SXin Li 			double tmp = lpc[j];
199*600f14f4SXin Li 			lpc[j] += r * lpc[i-1-j];
200*600f14f4SXin Li 			lpc[i-1-j] += r * tmp;
201*600f14f4SXin Li 		}
202*600f14f4SXin Li 		if(i & 1)
203*600f14f4SXin Li 			lpc[j] += lpc[j] * r;
204*600f14f4SXin Li 
205*600f14f4SXin Li 		err *= (1.0 - r * r);
206*600f14f4SXin Li 
207*600f14f4SXin Li 		/* save this order */
208*600f14f4SXin Li 		for(j = 0; j <= i; j++)
209*600f14f4SXin Li 			lp_coeff[i][j] = (FLAC__real)(-lpc[j]); /* negate FIR filter coeff to get predictor coeff */
210*600f14f4SXin Li 		error[i] = err;
211*600f14f4SXin Li 
212*600f14f4SXin Li 		/* see SF bug https://sourceforge.net/p/flac/bugs/234/ */
213*600f14f4SXin Li 		if(err == 0.0) {
214*600f14f4SXin Li 			*max_order = i+1;
215*600f14f4SXin Li 			return;
216*600f14f4SXin Li 		}
217*600f14f4SXin Li 	}
218*600f14f4SXin Li }
219*600f14f4SXin Li 
FLAC__lpc_quantize_coefficients(const FLAC__real lp_coeff[],uint32_t order,uint32_t precision,FLAC__int32 qlp_coeff[],int * shift)220*600f14f4SXin Li int FLAC__lpc_quantize_coefficients(const FLAC__real lp_coeff[], uint32_t order, uint32_t precision, FLAC__int32 qlp_coeff[], int *shift)
221*600f14f4SXin Li {
222*600f14f4SXin Li 	uint32_t i;
223*600f14f4SXin Li 	double cmax;
224*600f14f4SXin Li 	FLAC__int32 qmax, qmin;
225*600f14f4SXin Li 
226*600f14f4SXin Li 	FLAC__ASSERT(precision > 0);
227*600f14f4SXin Li 	FLAC__ASSERT(precision >= FLAC__MIN_QLP_COEFF_PRECISION);
228*600f14f4SXin Li 
229*600f14f4SXin Li 	/* drop one bit for the sign; from here on out we consider only |lp_coeff[i]| */
230*600f14f4SXin Li 	precision--;
231*600f14f4SXin Li 	qmax = 1 << precision;
232*600f14f4SXin Li 	qmin = -qmax;
233*600f14f4SXin Li 	qmax--;
234*600f14f4SXin Li 
235*600f14f4SXin Li 	/* calc cmax = max( |lp_coeff[i]| ) */
236*600f14f4SXin Li 	cmax = 0.0;
237*600f14f4SXin Li 	for(i = 0; i < order; i++) {
238*600f14f4SXin Li 		const double d = fabs(lp_coeff[i]);
239*600f14f4SXin Li 		if(d > cmax)
240*600f14f4SXin Li 			cmax = d;
241*600f14f4SXin Li 	}
242*600f14f4SXin Li 
243*600f14f4SXin Li 	if(cmax <= 0.0) {
244*600f14f4SXin Li 		/* => coefficients are all 0, which means our constant-detect didn't work */
245*600f14f4SXin Li 		return 2;
246*600f14f4SXin Li 	}
247*600f14f4SXin Li 	else {
248*600f14f4SXin Li 		const int max_shiftlimit = (1 << (FLAC__SUBFRAME_LPC_QLP_SHIFT_LEN-1)) - 1;
249*600f14f4SXin Li 		const int min_shiftlimit = -max_shiftlimit - 1;
250*600f14f4SXin Li 		int log2cmax;
251*600f14f4SXin Li 
252*600f14f4SXin Li 		(void)frexp(cmax, &log2cmax);
253*600f14f4SXin Li 		log2cmax--;
254*600f14f4SXin Li 		*shift = (int)precision - log2cmax - 1;
255*600f14f4SXin Li 
256*600f14f4SXin Li 		if(*shift > max_shiftlimit)
257*600f14f4SXin Li 			*shift = max_shiftlimit;
258*600f14f4SXin Li 		else if(*shift < min_shiftlimit)
259*600f14f4SXin Li 			return 1;
260*600f14f4SXin Li 	}
261*600f14f4SXin Li 
262*600f14f4SXin Li 	if(*shift >= 0) {
263*600f14f4SXin Li 		double error = 0.0;
264*600f14f4SXin Li 		FLAC__int32 q;
265*600f14f4SXin Li 		for(i = 0; i < order; i++) {
266*600f14f4SXin Li 			error += lp_coeff[i] * (1 << *shift);
267*600f14f4SXin Li 			q = lround(error);
268*600f14f4SXin Li 
269*600f14f4SXin Li #ifdef FLAC__OVERFLOW_DETECT
270*600f14f4SXin Li 			if(q > qmax+1) /* we expect q==qmax+1 occasionally due to rounding */
271*600f14f4SXin Li 				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]);
272*600f14f4SXin Li 			else if(q < qmin)
273*600f14f4SXin Li 				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]);
274*600f14f4SXin Li #endif
275*600f14f4SXin Li 			if(q > qmax)
276*600f14f4SXin Li 				q = qmax;
277*600f14f4SXin Li 			else if(q < qmin)
278*600f14f4SXin Li 				q = qmin;
279*600f14f4SXin Li 			error -= q;
280*600f14f4SXin Li 			qlp_coeff[i] = q;
281*600f14f4SXin Li 		}
282*600f14f4SXin Li 	}
283*600f14f4SXin Li 	/* negative shift is very rare but due to design flaw, negative shift is
284*600f14f4SXin Li 	 * not allowed in the decoder, so it must be handled specially by scaling
285*600f14f4SXin Li 	 * down coeffs
286*600f14f4SXin Li 	 */
287*600f14f4SXin Li 	else {
288*600f14f4SXin Li 		const int nshift = -(*shift);
289*600f14f4SXin Li 		double error = 0.0;
290*600f14f4SXin Li 		FLAC__int32 q;
291*600f14f4SXin Li #ifndef NDEBUG
292*600f14f4SXin Li 		fprintf(stderr,"FLAC__lpc_quantize_coefficients: negative shift=%d order=%u cmax=%f\n", *shift, order, cmax);
293*600f14f4SXin Li #endif
294*600f14f4SXin Li 		for(i = 0; i < order; i++) {
295*600f14f4SXin Li 			error += lp_coeff[i] / (1 << nshift);
296*600f14f4SXin Li 			q = lround(error);
297*600f14f4SXin Li #ifdef FLAC__OVERFLOW_DETECT
298*600f14f4SXin Li 			if(q > qmax+1) /* we expect q==qmax+1 occasionally due to rounding */
299*600f14f4SXin Li 				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]);
300*600f14f4SXin Li 			else if(q < qmin)
301*600f14f4SXin Li 				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]);
302*600f14f4SXin Li #endif
303*600f14f4SXin Li 			if(q > qmax)
304*600f14f4SXin Li 				q = qmax;
305*600f14f4SXin Li 			else if(q < qmin)
306*600f14f4SXin Li 				q = qmin;
307*600f14f4SXin Li 			error -= q;
308*600f14f4SXin Li 			qlp_coeff[i] = q;
309*600f14f4SXin Li 		}
310*600f14f4SXin Li 		*shift = 0;
311*600f14f4SXin Li 	}
312*600f14f4SXin Li 
313*600f14f4SXin Li 	return 0;
314*600f14f4SXin Li }
315*600f14f4SXin Li 
316*600f14f4SXin Li #if defined(_MSC_VER)
317*600f14f4SXin Li // silence MSVC warnings about __restrict modifier
318*600f14f4SXin Li #pragma warning ( disable : 4028 )
319*600f14f4SXin Li #endif
320*600f14f4SXin Li 
FLAC__lpc_compute_residual_from_qlp_coefficients(const FLAC__int32 * flac_restrict data,uint32_t data_len,const FLAC__int32 * flac_restrict qlp_coeff,uint32_t order,int lp_quantization,FLAC__int32 * flac_restrict residual)321*600f14f4SXin Li void FLAC__lpc_compute_residual_from_qlp_coefficients(const FLAC__int32 * flac_restrict data, uint32_t data_len, const FLAC__int32 * flac_restrict qlp_coeff, uint32_t order, int lp_quantization, FLAC__int32 * flac_restrict residual)
322*600f14f4SXin Li #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS)
323*600f14f4SXin Li {
324*600f14f4SXin Li 	FLAC__int64 sumo;
325*600f14f4SXin Li 	uint32_t i, j;
326*600f14f4SXin Li 	FLAC__int32 sum;
327*600f14f4SXin Li 	const FLAC__int32 *history;
328*600f14f4SXin Li 
329*600f14f4SXin Li #ifdef FLAC__OVERFLOW_DETECT_VERBOSE
330*600f14f4SXin Li 	fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients: data_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization);
331*600f14f4SXin Li 	for(i=0;i<order;i++)
332*600f14f4SXin Li 		fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]);
333*600f14f4SXin Li 	fprintf(stderr,"\n");
334*600f14f4SXin Li #endif
335*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
336*600f14f4SXin Li 
337*600f14f4SXin Li 	for(i = 0; i < data_len; i++) {
338*600f14f4SXin Li 		sumo = 0;
339*600f14f4SXin Li 		sum = 0;
340*600f14f4SXin Li 		history = data;
341*600f14f4SXin Li 		for(j = 0; j < order; j++) {
342*600f14f4SXin Li 			sum += qlp_coeff[j] * (*(--history));
343*600f14f4SXin Li 			sumo += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*history);
344*600f14f4SXin Li 			if(sumo > 2147483647ll || sumo < -2147483648ll)
345*600f14f4SXin Li 				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);
346*600f14f4SXin Li 		}
347*600f14f4SXin Li 		*(residual++) = *(data++) - (sum >> lp_quantization);
348*600f14f4SXin Li 	}
349*600f14f4SXin Li 
350*600f14f4SXin Li 	/* Here's a slower but clearer version:
351*600f14f4SXin Li 	for(i = 0; i < data_len; i++) {
352*600f14f4SXin Li 		sum = 0;
353*600f14f4SXin Li 		for(j = 0; j < order; j++)
354*600f14f4SXin Li 			sum += qlp_coeff[j] * data[i-j-1];
355*600f14f4SXin Li 		residual[i] = data[i] - (sum >> lp_quantization);
356*600f14f4SXin Li 	}
357*600f14f4SXin Li 	*/
358*600f14f4SXin Li }
359*600f14f4SXin Li #else /* fully unrolled version for normal use */
360*600f14f4SXin Li {
361*600f14f4SXin Li 	int i;
362*600f14f4SXin Li 	FLAC__int32 sum;
363*600f14f4SXin Li 
364*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
365*600f14f4SXin Li 	FLAC__ASSERT(order <= 32);
366*600f14f4SXin Li 
367*600f14f4SXin Li 	/*
368*600f14f4SXin Li 	 * We do unique versions up to 12th order since that's the subset limit.
369*600f14f4SXin Li 	 * Also they are roughly ordered to match frequency of occurrence to
370*600f14f4SXin Li 	 * minimize branching.
371*600f14f4SXin Li 	 */
372*600f14f4SXin Li 	if(order <= 12) {
373*600f14f4SXin Li 		if(order > 8) {
374*600f14f4SXin Li 			if(order > 10) {
375*600f14f4SXin Li 				if(order == 12) {
376*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
377*600f14f4SXin Li 						sum = 0;
378*600f14f4SXin Li 						sum += qlp_coeff[11] * data[i-12];
379*600f14f4SXin Li 						sum += qlp_coeff[10] * data[i-11];
380*600f14f4SXin Li 						sum += qlp_coeff[9] * data[i-10];
381*600f14f4SXin Li 						sum += qlp_coeff[8] * data[i-9];
382*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
383*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
384*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
385*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
386*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
387*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
388*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
389*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
390*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
391*600f14f4SXin Li 					}
392*600f14f4SXin Li 				}
393*600f14f4SXin Li 				else { /* order == 11 */
394*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
395*600f14f4SXin Li 						sum = 0;
396*600f14f4SXin Li 						sum += qlp_coeff[10] * data[i-11];
397*600f14f4SXin Li 						sum += qlp_coeff[9] * data[i-10];
398*600f14f4SXin Li 						sum += qlp_coeff[8] * data[i-9];
399*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
400*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
401*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
402*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
403*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
404*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
405*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
406*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
407*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
408*600f14f4SXin Li 					}
409*600f14f4SXin Li 				}
410*600f14f4SXin Li 			}
411*600f14f4SXin Li 			else {
412*600f14f4SXin Li 				if(order == 10) {
413*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
414*600f14f4SXin Li 						sum = 0;
415*600f14f4SXin Li 						sum += qlp_coeff[9] * data[i-10];
416*600f14f4SXin Li 						sum += qlp_coeff[8] * data[i-9];
417*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
418*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
419*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
420*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
421*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
422*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
423*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
424*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
425*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
426*600f14f4SXin Li 					}
427*600f14f4SXin Li 				}
428*600f14f4SXin Li 				else { /* order == 9 */
429*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
430*600f14f4SXin Li 						sum = 0;
431*600f14f4SXin Li 						sum += qlp_coeff[8] * data[i-9];
432*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
433*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
434*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
435*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
436*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
437*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
438*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
439*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
440*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
441*600f14f4SXin Li 					}
442*600f14f4SXin Li 				}
443*600f14f4SXin Li 			}
444*600f14f4SXin Li 		}
445*600f14f4SXin Li 		else if(order > 4) {
446*600f14f4SXin Li 			if(order > 6) {
447*600f14f4SXin Li 				if(order == 8) {
448*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
449*600f14f4SXin Li 						sum = 0;
450*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
451*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
452*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
453*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
454*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
455*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
456*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
457*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
458*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
459*600f14f4SXin Li 					}
460*600f14f4SXin Li 				}
461*600f14f4SXin Li 				else { /* order == 7 */
462*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
463*600f14f4SXin Li 						sum = 0;
464*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
465*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
466*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
467*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
468*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
469*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
470*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
471*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
472*600f14f4SXin Li 					}
473*600f14f4SXin Li 				}
474*600f14f4SXin Li 			}
475*600f14f4SXin Li 			else {
476*600f14f4SXin Li 				if(order == 6) {
477*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
478*600f14f4SXin Li 						sum = 0;
479*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
480*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
481*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
482*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
483*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
484*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
485*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
486*600f14f4SXin Li 					}
487*600f14f4SXin Li 				}
488*600f14f4SXin Li 				else { /* order == 5 */
489*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
490*600f14f4SXin Li 						sum = 0;
491*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
492*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
493*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
494*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
495*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
496*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
497*600f14f4SXin Li 					}
498*600f14f4SXin Li 				}
499*600f14f4SXin Li 			}
500*600f14f4SXin Li 		}
501*600f14f4SXin Li 		else {
502*600f14f4SXin Li 			if(order > 2) {
503*600f14f4SXin Li 				if(order == 4) {
504*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
505*600f14f4SXin Li 						sum = 0;
506*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
507*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
508*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
509*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
510*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
511*600f14f4SXin Li 					}
512*600f14f4SXin Li 				}
513*600f14f4SXin Li 				else { /* order == 3 */
514*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
515*600f14f4SXin Li 						sum = 0;
516*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
517*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
518*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
519*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
520*600f14f4SXin Li 					}
521*600f14f4SXin Li 				}
522*600f14f4SXin Li 			}
523*600f14f4SXin Li 			else {
524*600f14f4SXin Li 				if(order == 2) {
525*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
526*600f14f4SXin Li 						sum = 0;
527*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
528*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
529*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
530*600f14f4SXin Li 					}
531*600f14f4SXin Li 				}
532*600f14f4SXin Li 				else { /* order == 1 */
533*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++)
534*600f14f4SXin Li 						residual[i] = data[i] - ((qlp_coeff[0] * data[i-1]) >> lp_quantization);
535*600f14f4SXin Li 				}
536*600f14f4SXin Li 			}
537*600f14f4SXin Li 		}
538*600f14f4SXin Li 	}
539*600f14f4SXin Li 	else { /* order > 12 */
540*600f14f4SXin Li 		for(i = 0; i < (int)data_len; i++) {
541*600f14f4SXin Li 			sum = 0;
542*600f14f4SXin Li 			switch(order) {
543*600f14f4SXin Li 				case 32: sum += qlp_coeff[31] * data[i-32]; /* Falls through. */
544*600f14f4SXin Li 				case 31: sum += qlp_coeff[30] * data[i-31]; /* Falls through. */
545*600f14f4SXin Li 				case 30: sum += qlp_coeff[29] * data[i-30]; /* Falls through. */
546*600f14f4SXin Li 				case 29: sum += qlp_coeff[28] * data[i-29]; /* Falls through. */
547*600f14f4SXin Li 				case 28: sum += qlp_coeff[27] * data[i-28]; /* Falls through. */
548*600f14f4SXin Li 				case 27: sum += qlp_coeff[26] * data[i-27]; /* Falls through. */
549*600f14f4SXin Li 				case 26: sum += qlp_coeff[25] * data[i-26]; /* Falls through. */
550*600f14f4SXin Li 				case 25: sum += qlp_coeff[24] * data[i-25]; /* Falls through. */
551*600f14f4SXin Li 				case 24: sum += qlp_coeff[23] * data[i-24]; /* Falls through. */
552*600f14f4SXin Li 				case 23: sum += qlp_coeff[22] * data[i-23]; /* Falls through. */
553*600f14f4SXin Li 				case 22: sum += qlp_coeff[21] * data[i-22]; /* Falls through. */
554*600f14f4SXin Li 				case 21: sum += qlp_coeff[20] * data[i-21]; /* Falls through. */
555*600f14f4SXin Li 				case 20: sum += qlp_coeff[19] * data[i-20]; /* Falls through. */
556*600f14f4SXin Li 				case 19: sum += qlp_coeff[18] * data[i-19]; /* Falls through. */
557*600f14f4SXin Li 				case 18: sum += qlp_coeff[17] * data[i-18]; /* Falls through. */
558*600f14f4SXin Li 				case 17: sum += qlp_coeff[16] * data[i-17]; /* Falls through. */
559*600f14f4SXin Li 				case 16: sum += qlp_coeff[15] * data[i-16]; /* Falls through. */
560*600f14f4SXin Li 				case 15: sum += qlp_coeff[14] * data[i-15]; /* Falls through. */
561*600f14f4SXin Li 				case 14: sum += qlp_coeff[13] * data[i-14]; /* Falls through. */
562*600f14f4SXin Li 				case 13: sum += qlp_coeff[12] * data[i-13];
563*600f14f4SXin Li 				         sum += qlp_coeff[11] * data[i-12];
564*600f14f4SXin Li 				         sum += qlp_coeff[10] * data[i-11];
565*600f14f4SXin Li 				         sum += qlp_coeff[ 9] * data[i-10];
566*600f14f4SXin Li 				         sum += qlp_coeff[ 8] * data[i- 9];
567*600f14f4SXin Li 				         sum += qlp_coeff[ 7] * data[i- 8];
568*600f14f4SXin Li 				         sum += qlp_coeff[ 6] * data[i- 7];
569*600f14f4SXin Li 				         sum += qlp_coeff[ 5] * data[i- 6];
570*600f14f4SXin Li 				         sum += qlp_coeff[ 4] * data[i- 5];
571*600f14f4SXin Li 				         sum += qlp_coeff[ 3] * data[i- 4];
572*600f14f4SXin Li 				         sum += qlp_coeff[ 2] * data[i- 3];
573*600f14f4SXin Li 				         sum += qlp_coeff[ 1] * data[i- 2];
574*600f14f4SXin Li 				         sum += qlp_coeff[ 0] * data[i- 1];
575*600f14f4SXin Li 			}
576*600f14f4SXin Li 			residual[i] = data[i] - (sum >> lp_quantization);
577*600f14f4SXin Li 		}
578*600f14f4SXin Li 	}
579*600f14f4SXin Li }
580*600f14f4SXin Li #endif
581*600f14f4SXin Li 
FLAC__lpc_compute_residual_from_qlp_coefficients_wide(const FLAC__int32 * flac_restrict data,uint32_t data_len,const FLAC__int32 * flac_restrict qlp_coeff,uint32_t order,int lp_quantization,FLAC__int32 * flac_restrict residual)582*600f14f4SXin Li void FLAC__lpc_compute_residual_from_qlp_coefficients_wide(const FLAC__int32 * flac_restrict data, uint32_t data_len, const FLAC__int32 * flac_restrict qlp_coeff, uint32_t order, int lp_quantization, FLAC__int32 * flac_restrict residual)
583*600f14f4SXin Li #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS)
584*600f14f4SXin Li {
585*600f14f4SXin Li 	uint32_t i, j;
586*600f14f4SXin Li 	FLAC__int64 sum;
587*600f14f4SXin Li 	const FLAC__int32 *history;
588*600f14f4SXin Li 
589*600f14f4SXin Li #ifdef FLAC__OVERFLOW_DETECT_VERBOSE
590*600f14f4SXin Li 	fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients_wide: data_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization);
591*600f14f4SXin Li 	for(i=0;i<order;i++)
592*600f14f4SXin Li 		fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]);
593*600f14f4SXin Li 	fprintf(stderr,"\n");
594*600f14f4SXin Li #endif
595*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
596*600f14f4SXin Li 
597*600f14f4SXin Li 	for(i = 0; i < data_len; i++) {
598*600f14f4SXin Li 		sum = 0;
599*600f14f4SXin Li 		history = data;
600*600f14f4SXin Li 		for(j = 0; j < order; j++)
601*600f14f4SXin Li 			sum += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*(--history));
602*600f14f4SXin Li 		if(FLAC__bitmath_silog2((FLAC__int64)(*data) - (sum >> lp_quantization)) > 32) {
603*600f14f4SXin Li 			fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients_wide: OVERFLOW, i=%u, data=%d, sum=%" PRId64 ", residual=%" PRId64 "\n", i, *data, (int64_t)(sum >> lp_quantization), ((FLAC__int64)(*data) - (sum >> lp_quantization)));
604*600f14f4SXin Li 			break;
605*600f14f4SXin Li 		}
606*600f14f4SXin Li 		*(residual++) = *(data++) - (FLAC__int32)(sum >> lp_quantization);
607*600f14f4SXin Li 	}
608*600f14f4SXin Li }
609*600f14f4SXin Li #else /* fully unrolled version for normal use */
610*600f14f4SXin Li {
611*600f14f4SXin Li 	int i;
612*600f14f4SXin Li 	FLAC__int64 sum;
613*600f14f4SXin Li 
614*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
615*600f14f4SXin Li 	FLAC__ASSERT(order <= 32);
616*600f14f4SXin Li 
617*600f14f4SXin Li 	/*
618*600f14f4SXin Li 	 * We do unique versions up to 12th order since that's the subset limit.
619*600f14f4SXin Li 	 * Also they are roughly ordered to match frequency of occurrence to
620*600f14f4SXin Li 	 * minimize branching.
621*600f14f4SXin Li 	 */
622*600f14f4SXin Li 	if(order <= 12) {
623*600f14f4SXin Li 		if(order > 8) {
624*600f14f4SXin Li 			if(order > 10) {
625*600f14f4SXin Li 				if(order == 12) {
626*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
627*600f14f4SXin Li 						sum = 0;
628*600f14f4SXin Li 						sum += qlp_coeff[11] * (FLAC__int64)data[i-12];
629*600f14f4SXin Li 						sum += qlp_coeff[10] * (FLAC__int64)data[i-11];
630*600f14f4SXin Li 						sum += qlp_coeff[9] * (FLAC__int64)data[i-10];
631*600f14f4SXin Li 						sum += qlp_coeff[8] * (FLAC__int64)data[i-9];
632*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
633*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
634*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
635*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
636*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
637*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
638*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
639*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
640*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
641*600f14f4SXin Li 					}
642*600f14f4SXin Li 				}
643*600f14f4SXin Li 				else { /* order == 11 */
644*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
645*600f14f4SXin Li 						sum = 0;
646*600f14f4SXin Li 						sum += qlp_coeff[10] * (FLAC__int64)data[i-11];
647*600f14f4SXin Li 						sum += qlp_coeff[9] * (FLAC__int64)data[i-10];
648*600f14f4SXin Li 						sum += qlp_coeff[8] * (FLAC__int64)data[i-9];
649*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
650*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
651*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
652*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
653*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
654*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
655*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
656*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
657*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
658*600f14f4SXin Li 					}
659*600f14f4SXin Li 				}
660*600f14f4SXin Li 			}
661*600f14f4SXin Li 			else {
662*600f14f4SXin Li 				if(order == 10) {
663*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
664*600f14f4SXin Li 						sum = 0;
665*600f14f4SXin Li 						sum += qlp_coeff[9] * (FLAC__int64)data[i-10];
666*600f14f4SXin Li 						sum += qlp_coeff[8] * (FLAC__int64)data[i-9];
667*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
668*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
669*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
670*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
671*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
672*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
673*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
674*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
675*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
676*600f14f4SXin Li 					}
677*600f14f4SXin Li 				}
678*600f14f4SXin Li 				else { /* order == 9 */
679*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
680*600f14f4SXin Li 						sum = 0;
681*600f14f4SXin Li 						sum += qlp_coeff[8] * (FLAC__int64)data[i-9];
682*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
683*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
684*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
685*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
686*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
687*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
688*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
689*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
690*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
691*600f14f4SXin Li 					}
692*600f14f4SXin Li 				}
693*600f14f4SXin Li 			}
694*600f14f4SXin Li 		}
695*600f14f4SXin Li 		else if(order > 4) {
696*600f14f4SXin Li 			if(order > 6) {
697*600f14f4SXin Li 				if(order == 8) {
698*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
699*600f14f4SXin Li 						sum = 0;
700*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
701*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
702*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
703*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
704*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
705*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
706*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
707*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
708*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
709*600f14f4SXin Li 					}
710*600f14f4SXin Li 				}
711*600f14f4SXin Li 				else { /* order == 7 */
712*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
713*600f14f4SXin Li 						sum = 0;
714*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
715*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
716*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
717*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
718*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
719*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
720*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
721*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
722*600f14f4SXin Li 					}
723*600f14f4SXin Li 				}
724*600f14f4SXin Li 			}
725*600f14f4SXin Li 			else {
726*600f14f4SXin Li 				if(order == 6) {
727*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
728*600f14f4SXin Li 						sum = 0;
729*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
730*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
731*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
732*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
733*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
734*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
735*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
736*600f14f4SXin Li 					}
737*600f14f4SXin Li 				}
738*600f14f4SXin Li 				else { /* order == 5 */
739*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
740*600f14f4SXin Li 						sum = 0;
741*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
742*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
743*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
744*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
745*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
746*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
747*600f14f4SXin Li 					}
748*600f14f4SXin Li 				}
749*600f14f4SXin Li 			}
750*600f14f4SXin Li 		}
751*600f14f4SXin Li 		else {
752*600f14f4SXin Li 			if(order > 2) {
753*600f14f4SXin Li 				if(order == 4) {
754*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
755*600f14f4SXin Li 						sum = 0;
756*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
757*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
758*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
759*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
760*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
761*600f14f4SXin Li 					}
762*600f14f4SXin Li 				}
763*600f14f4SXin Li 				else { /* order == 3 */
764*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
765*600f14f4SXin Li 						sum = 0;
766*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
767*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
768*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
769*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
770*600f14f4SXin Li 					}
771*600f14f4SXin Li 				}
772*600f14f4SXin Li 			}
773*600f14f4SXin Li 			else {
774*600f14f4SXin Li 				if(order == 2) {
775*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
776*600f14f4SXin Li 						sum = 0;
777*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
778*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
779*600f14f4SXin Li 						residual[i] = data[i] - (sum >> lp_quantization);
780*600f14f4SXin Li 					}
781*600f14f4SXin Li 				}
782*600f14f4SXin Li 				else { /* order == 1 */
783*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++)
784*600f14f4SXin Li 						residual[i] = data[i] - ((qlp_coeff[0] * (FLAC__int64)data[i-1]) >> lp_quantization);
785*600f14f4SXin Li 				}
786*600f14f4SXin Li 			}
787*600f14f4SXin Li 		}
788*600f14f4SXin Li 	}
789*600f14f4SXin Li 	else { /* order > 12 */
790*600f14f4SXin Li 		for(i = 0; i < (int)data_len; i++) {
791*600f14f4SXin Li 			sum = 0;
792*600f14f4SXin Li 			switch(order) {
793*600f14f4SXin Li 				case 32: sum += qlp_coeff[31] * (FLAC__int64)data[i-32]; /* Falls through. */
794*600f14f4SXin Li 				case 31: sum += qlp_coeff[30] * (FLAC__int64)data[i-31]; /* Falls through. */
795*600f14f4SXin Li 				case 30: sum += qlp_coeff[29] * (FLAC__int64)data[i-30]; /* Falls through. */
796*600f14f4SXin Li 				case 29: sum += qlp_coeff[28] * (FLAC__int64)data[i-29]; /* Falls through. */
797*600f14f4SXin Li 				case 28: sum += qlp_coeff[27] * (FLAC__int64)data[i-28]; /* Falls through. */
798*600f14f4SXin Li 				case 27: sum += qlp_coeff[26] * (FLAC__int64)data[i-27]; /* Falls through. */
799*600f14f4SXin Li 				case 26: sum += qlp_coeff[25] * (FLAC__int64)data[i-26]; /* Falls through. */
800*600f14f4SXin Li 				case 25: sum += qlp_coeff[24] * (FLAC__int64)data[i-25]; /* Falls through. */
801*600f14f4SXin Li 				case 24: sum += qlp_coeff[23] * (FLAC__int64)data[i-24]; /* Falls through. */
802*600f14f4SXin Li 				case 23: sum += qlp_coeff[22] * (FLAC__int64)data[i-23]; /* Falls through. */
803*600f14f4SXin Li 				case 22: sum += qlp_coeff[21] * (FLAC__int64)data[i-22]; /* Falls through. */
804*600f14f4SXin Li 				case 21: sum += qlp_coeff[20] * (FLAC__int64)data[i-21]; /* Falls through. */
805*600f14f4SXin Li 				case 20: sum += qlp_coeff[19] * (FLAC__int64)data[i-20]; /* Falls through. */
806*600f14f4SXin Li 				case 19: sum += qlp_coeff[18] * (FLAC__int64)data[i-19]; /* Falls through. */
807*600f14f4SXin Li 				case 18: sum += qlp_coeff[17] * (FLAC__int64)data[i-18]; /* Falls through. */
808*600f14f4SXin Li 				case 17: sum += qlp_coeff[16] * (FLAC__int64)data[i-17]; /* Falls through. */
809*600f14f4SXin Li 				case 16: sum += qlp_coeff[15] * (FLAC__int64)data[i-16]; /* Falls through. */
810*600f14f4SXin Li 				case 15: sum += qlp_coeff[14] * (FLAC__int64)data[i-15]; /* Falls through. */
811*600f14f4SXin Li 				case 14: sum += qlp_coeff[13] * (FLAC__int64)data[i-14]; /* Falls through. */
812*600f14f4SXin Li 				case 13: sum += qlp_coeff[12] * (FLAC__int64)data[i-13];
813*600f14f4SXin Li 				         sum += qlp_coeff[11] * (FLAC__int64)data[i-12];
814*600f14f4SXin Li 				         sum += qlp_coeff[10] * (FLAC__int64)data[i-11];
815*600f14f4SXin Li 				         sum += qlp_coeff[ 9] * (FLAC__int64)data[i-10];
816*600f14f4SXin Li 				         sum += qlp_coeff[ 8] * (FLAC__int64)data[i- 9];
817*600f14f4SXin Li 				         sum += qlp_coeff[ 7] * (FLAC__int64)data[i- 8];
818*600f14f4SXin Li 				         sum += qlp_coeff[ 6] * (FLAC__int64)data[i- 7];
819*600f14f4SXin Li 				         sum += qlp_coeff[ 5] * (FLAC__int64)data[i- 6];
820*600f14f4SXin Li 				         sum += qlp_coeff[ 4] * (FLAC__int64)data[i- 5];
821*600f14f4SXin Li 				         sum += qlp_coeff[ 3] * (FLAC__int64)data[i- 4];
822*600f14f4SXin Li 				         sum += qlp_coeff[ 2] * (FLAC__int64)data[i- 3];
823*600f14f4SXin Li 				         sum += qlp_coeff[ 1] * (FLAC__int64)data[i- 2];
824*600f14f4SXin Li 				         sum += qlp_coeff[ 0] * (FLAC__int64)data[i- 1];
825*600f14f4SXin Li 			}
826*600f14f4SXin Li 			residual[i] = data[i] - (sum >> lp_quantization);
827*600f14f4SXin Li 		}
828*600f14f4SXin Li 	}
829*600f14f4SXin Li }
830*600f14f4SXin Li #endif
831*600f14f4SXin Li 
FLAC__lpc_compute_residual_from_qlp_coefficients_limit_residual(const FLAC__int32 * flac_restrict data,uint32_t data_len,const FLAC__int32 * flac_restrict qlp_coeff,uint32_t order,int lp_quantization,FLAC__int32 * flac_restrict residual)832*600f14f4SXin Li FLAC__bool FLAC__lpc_compute_residual_from_qlp_coefficients_limit_residual(const FLAC__int32 * flac_restrict data, uint32_t data_len, const FLAC__int32 * flac_restrict qlp_coeff, uint32_t order, int lp_quantization, FLAC__int32 * flac_restrict residual)
833*600f14f4SXin Li {
834*600f14f4SXin Li 	int i;
835*600f14f4SXin Li 	FLAC__int64 sum, residual_to_check;
836*600f14f4SXin Li 
837*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
838*600f14f4SXin Li 	FLAC__ASSERT(order <= 32);
839*600f14f4SXin Li 
840*600f14f4SXin Li 	for(i = 0; i < (int)data_len; i++) {
841*600f14f4SXin Li 		sum = 0;
842*600f14f4SXin Li 		switch(order) {
843*600f14f4SXin Li 			case 32: sum += qlp_coeff[31] * (FLAC__int64)data[i-32]; /* Falls through. */
844*600f14f4SXin Li 			case 31: sum += qlp_coeff[30] * (FLAC__int64)data[i-31]; /* Falls through. */
845*600f14f4SXin Li 			case 30: sum += qlp_coeff[29] * (FLAC__int64)data[i-30]; /* Falls through. */
846*600f14f4SXin Li 			case 29: sum += qlp_coeff[28] * (FLAC__int64)data[i-29]; /* Falls through. */
847*600f14f4SXin Li 			case 28: sum += qlp_coeff[27] * (FLAC__int64)data[i-28]; /* Falls through. */
848*600f14f4SXin Li 			case 27: sum += qlp_coeff[26] * (FLAC__int64)data[i-27]; /* Falls through. */
849*600f14f4SXin Li 			case 26: sum += qlp_coeff[25] * (FLAC__int64)data[i-26]; /* Falls through. */
850*600f14f4SXin Li 			case 25: sum += qlp_coeff[24] * (FLAC__int64)data[i-25]; /* Falls through. */
851*600f14f4SXin Li 			case 24: sum += qlp_coeff[23] * (FLAC__int64)data[i-24]; /* Falls through. */
852*600f14f4SXin Li 			case 23: sum += qlp_coeff[22] * (FLAC__int64)data[i-23]; /* Falls through. */
853*600f14f4SXin Li 			case 22: sum += qlp_coeff[21] * (FLAC__int64)data[i-22]; /* Falls through. */
854*600f14f4SXin Li 			case 21: sum += qlp_coeff[20] * (FLAC__int64)data[i-21]; /* Falls through. */
855*600f14f4SXin Li 			case 20: sum += qlp_coeff[19] * (FLAC__int64)data[i-20]; /* Falls through. */
856*600f14f4SXin Li 			case 19: sum += qlp_coeff[18] * (FLAC__int64)data[i-19]; /* Falls through. */
857*600f14f4SXin Li 			case 18: sum += qlp_coeff[17] * (FLAC__int64)data[i-18]; /* Falls through. */
858*600f14f4SXin Li 			case 17: sum += qlp_coeff[16] * (FLAC__int64)data[i-17]; /* Falls through. */
859*600f14f4SXin Li 			case 16: sum += qlp_coeff[15] * (FLAC__int64)data[i-16]; /* Falls through. */
860*600f14f4SXin Li 			case 15: sum += qlp_coeff[14] * (FLAC__int64)data[i-15]; /* Falls through. */
861*600f14f4SXin Li 			case 14: sum += qlp_coeff[13] * (FLAC__int64)data[i-14]; /* Falls through. */
862*600f14f4SXin Li 			case 13: sum += qlp_coeff[12] * (FLAC__int64)data[i-13]; /* Falls through. */
863*600f14f4SXin Li 			case 12: sum += qlp_coeff[11] * (FLAC__int64)data[i-12]; /* Falls through. */
864*600f14f4SXin Li 			case 11: sum += qlp_coeff[10] * (FLAC__int64)data[i-11]; /* Falls through. */
865*600f14f4SXin Li 			case 10: sum += qlp_coeff[ 9] * (FLAC__int64)data[i-10]; /* Falls through. */
866*600f14f4SXin Li 			case  9: sum += qlp_coeff[ 8] * (FLAC__int64)data[i- 9]; /* Falls through. */
867*600f14f4SXin Li 			case  8: sum += qlp_coeff[ 7] * (FLAC__int64)data[i- 8]; /* Falls through. */
868*600f14f4SXin Li 			case  7: sum += qlp_coeff[ 6] * (FLAC__int64)data[i- 7]; /* Falls through. */
869*600f14f4SXin Li 			case  6: sum += qlp_coeff[ 5] * (FLAC__int64)data[i- 6]; /* Falls through. */
870*600f14f4SXin Li 			case  5: sum += qlp_coeff[ 4] * (FLAC__int64)data[i- 5]; /* Falls through. */
871*600f14f4SXin Li 			case  4: sum += qlp_coeff[ 3] * (FLAC__int64)data[i- 4]; /* Falls through. */
872*600f14f4SXin Li 			case  3: sum += qlp_coeff[ 2] * (FLAC__int64)data[i- 3]; /* Falls through. */
873*600f14f4SXin Li 			case  2: sum += qlp_coeff[ 1] * (FLAC__int64)data[i- 2]; /* Falls through. */
874*600f14f4SXin Li 			case  1: sum += qlp_coeff[ 0] * (FLAC__int64)data[i- 1];
875*600f14f4SXin Li 		}
876*600f14f4SXin Li 		residual_to_check = data[i] - (sum >> lp_quantization);
877*600f14f4SXin Li 		 /* residual must not be INT32_MIN because abs(INT32_MIN) is undefined */
878*600f14f4SXin Li 		if(residual_to_check <= INT32_MIN || residual_to_check > INT32_MAX)
879*600f14f4SXin Li 			return false;
880*600f14f4SXin Li 		else
881*600f14f4SXin Li 			residual[i] = residual_to_check;
882*600f14f4SXin Li 	}
883*600f14f4SXin Li 	return true;
884*600f14f4SXin Li }
885*600f14f4SXin Li 
FLAC__lpc_compute_residual_from_qlp_coefficients_limit_residual_33bit(const FLAC__int64 * flac_restrict data,uint32_t data_len,const FLAC__int32 * flac_restrict qlp_coeff,uint32_t order,int lp_quantization,FLAC__int32 * flac_restrict residual)886*600f14f4SXin Li FLAC__bool FLAC__lpc_compute_residual_from_qlp_coefficients_limit_residual_33bit(const FLAC__int64 * flac_restrict data, uint32_t data_len, const FLAC__int32 * flac_restrict qlp_coeff, uint32_t order, int lp_quantization, FLAC__int32 * flac_restrict residual)
887*600f14f4SXin Li {
888*600f14f4SXin Li 	int i;
889*600f14f4SXin Li 	FLAC__int64 sum, residual_to_check;
890*600f14f4SXin Li 
891*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
892*600f14f4SXin Li 	FLAC__ASSERT(order <= 32);
893*600f14f4SXin Li 
894*600f14f4SXin Li 	for(i = 0; i < (int)data_len; i++) {
895*600f14f4SXin Li 		sum = 0;
896*600f14f4SXin Li 		switch(order) {
897*600f14f4SXin Li 			case 32: sum += qlp_coeff[31] * data[i-32]; /* Falls through. */
898*600f14f4SXin Li 			case 31: sum += qlp_coeff[30] * data[i-31]; /* Falls through. */
899*600f14f4SXin Li 			case 30: sum += qlp_coeff[29] * data[i-30]; /* Falls through. */
900*600f14f4SXin Li 			case 29: sum += qlp_coeff[28] * data[i-29]; /* Falls through. */
901*600f14f4SXin Li 			case 28: sum += qlp_coeff[27] * data[i-28]; /* Falls through. */
902*600f14f4SXin Li 			case 27: sum += qlp_coeff[26] * data[i-27]; /* Falls through. */
903*600f14f4SXin Li 			case 26: sum += qlp_coeff[25] * data[i-26]; /* Falls through. */
904*600f14f4SXin Li 			case 25: sum += qlp_coeff[24] * data[i-25]; /* Falls through. */
905*600f14f4SXin Li 			case 24: sum += qlp_coeff[23] * data[i-24]; /* Falls through. */
906*600f14f4SXin Li 			case 23: sum += qlp_coeff[22] * data[i-23]; /* Falls through. */
907*600f14f4SXin Li 			case 22: sum += qlp_coeff[21] * data[i-22]; /* Falls through. */
908*600f14f4SXin Li 			case 21: sum += qlp_coeff[20] * data[i-21]; /* Falls through. */
909*600f14f4SXin Li 			case 20: sum += qlp_coeff[19] * data[i-20]; /* Falls through. */
910*600f14f4SXin Li 			case 19: sum += qlp_coeff[18] * data[i-19]; /* Falls through. */
911*600f14f4SXin Li 			case 18: sum += qlp_coeff[17] * data[i-18]; /* Falls through. */
912*600f14f4SXin Li 			case 17: sum += qlp_coeff[16] * data[i-17]; /* Falls through. */
913*600f14f4SXin Li 			case 16: sum += qlp_coeff[15] * data[i-16]; /* Falls through. */
914*600f14f4SXin Li 			case 15: sum += qlp_coeff[14] * data[i-15]; /* Falls through. */
915*600f14f4SXin Li 			case 14: sum += qlp_coeff[13] * data[i-14]; /* Falls through. */
916*600f14f4SXin Li 			case 13: sum += qlp_coeff[12] * data[i-13]; /* Falls through. */
917*600f14f4SXin Li 			case 12: sum += qlp_coeff[11] * data[i-12]; /* Falls through. */
918*600f14f4SXin Li 			case 11: sum += qlp_coeff[10] * data[i-11]; /* Falls through. */
919*600f14f4SXin Li 			case 10: sum += qlp_coeff[ 9] * data[i-10]; /* Falls through. */
920*600f14f4SXin Li 			case  9: sum += qlp_coeff[ 8] * data[i- 9]; /* Falls through. */
921*600f14f4SXin Li 			case  8: sum += qlp_coeff[ 7] * data[i- 8]; /* Falls through. */
922*600f14f4SXin Li 			case  7: sum += qlp_coeff[ 6] * data[i- 7]; /* Falls through. */
923*600f14f4SXin Li 			case  6: sum += qlp_coeff[ 5] * data[i- 6]; /* Falls through. */
924*600f14f4SXin Li 			case  5: sum += qlp_coeff[ 4] * data[i- 5]; /* Falls through. */
925*600f14f4SXin Li 			case  4: sum += qlp_coeff[ 3] * data[i- 4]; /* Falls through. */
926*600f14f4SXin Li 			case  3: sum += qlp_coeff[ 2] * data[i- 3]; /* Falls through. */
927*600f14f4SXin Li 			case  2: sum += qlp_coeff[ 1] * data[i- 2]; /* Falls through. */
928*600f14f4SXin Li 			case  1: sum += qlp_coeff[ 0] * data[i- 1];
929*600f14f4SXin Li 		}
930*600f14f4SXin Li 		residual_to_check = data[i] - (sum >> lp_quantization);
931*600f14f4SXin Li 		/* residual must not be INT32_MIN because abs(INT32_MIN) is undefined */
932*600f14f4SXin Li 		if(residual_to_check <= INT32_MIN || residual_to_check > INT32_MAX)
933*600f14f4SXin Li 			return false;
934*600f14f4SXin Li 		else
935*600f14f4SXin Li 			residual[i] = residual_to_check;
936*600f14f4SXin Li 	}
937*600f14f4SXin Li 	return true;
938*600f14f4SXin Li }
939*600f14f4SXin Li 
940*600f14f4SXin Li #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */
941*600f14f4SXin Li 
FLAC__lpc_max_prediction_before_shift_bps(uint32_t subframe_bps,const FLAC__int32 * flac_restrict qlp_coeff,uint32_t order)942*600f14f4SXin Li uint32_t FLAC__lpc_max_prediction_before_shift_bps(uint32_t subframe_bps, const FLAC__int32 * flac_restrict qlp_coeff, uint32_t order)
943*600f14f4SXin Li {
944*600f14f4SXin Li 	/* This used to be subframe_bps + qlp_coeff_precision + FLAC__bitmath_ilog2(order)
945*600f14f4SXin Li 	 * but that treats both the samples as well as the predictor as unknown. The
946*600f14f4SXin Li 	 * predictor is known however, so taking the log2 of the sum of the absolute values
947*600f14f4SXin Li 	 * of all coefficients is a more accurate representation of the predictor */
948*600f14f4SXin Li 	FLAC__int32 abs_sum_of_qlp_coeff = 0;
949*600f14f4SXin Li 	uint32_t i;
950*600f14f4SXin Li 	for(i = 0; i < order; i++)
951*600f14f4SXin Li 		abs_sum_of_qlp_coeff += abs(qlp_coeff[i]);
952*600f14f4SXin Li 	if(abs_sum_of_qlp_coeff == 0)
953*600f14f4SXin Li 		abs_sum_of_qlp_coeff = 1;
954*600f14f4SXin Li 	return subframe_bps + FLAC__bitmath_silog2(abs_sum_of_qlp_coeff);
955*600f14f4SXin Li }
956*600f14f4SXin Li 
957*600f14f4SXin Li 
FLAC__lpc_max_residual_bps(uint32_t subframe_bps,const FLAC__int32 * flac_restrict qlp_coeff,uint32_t order,int lp_quantization)958*600f14f4SXin Li uint32_t FLAC__lpc_max_residual_bps(uint32_t subframe_bps, const FLAC__int32 * flac_restrict qlp_coeff, uint32_t order, int lp_quantization)
959*600f14f4SXin Li {
960*600f14f4SXin Li 	FLAC__int32 predictor_sum_bps = FLAC__lpc_max_prediction_before_shift_bps(subframe_bps, qlp_coeff, order) - lp_quantization;
961*600f14f4SXin Li 	if((int)subframe_bps > predictor_sum_bps)
962*600f14f4SXin Li 		return subframe_bps + 1;
963*600f14f4SXin Li 	else
964*600f14f4SXin Li 		return predictor_sum_bps + 1;
965*600f14f4SXin Li }
966*600f14f4SXin Li 
967*600f14f4SXin Li #if defined(FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION) && !defined(FUZZING_BUILD_MODE_FLAC_SANITIZE_SIGNED_INTEGER_OVERFLOW)
968*600f14f4SXin Li /* The attribute below is to silence the undefined sanitizer of oss-fuzz.
969*600f14f4SXin Li  * Because fuzzing feeds bogus predictors and residual samples to the
970*600f14f4SXin Li  * decoder, having overflows in this section is unavoidable. Also,
971*600f14f4SXin Li  * because the calculated values are audio path only, there is no
972*600f14f4SXin Li  * potential for security problems */
973*600f14f4SXin Li __attribute__((no_sanitize("signed-integer-overflow")))
974*600f14f4SXin Li #endif
FLAC__lpc_restore_signal(const FLAC__int32 * flac_restrict residual,uint32_t data_len,const FLAC__int32 * flac_restrict qlp_coeff,uint32_t order,int lp_quantization,FLAC__int32 * flac_restrict data)975*600f14f4SXin Li void FLAC__lpc_restore_signal(const FLAC__int32 * flac_restrict residual, uint32_t data_len, const FLAC__int32 * flac_restrict qlp_coeff, uint32_t order, int lp_quantization, FLAC__int32 * flac_restrict data)
976*600f14f4SXin Li #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS)
977*600f14f4SXin Li {
978*600f14f4SXin Li 	FLAC__int64 sumo;
979*600f14f4SXin Li 	uint32_t i, j;
980*600f14f4SXin Li 	FLAC__int32 sum;
981*600f14f4SXin Li 	const FLAC__int32 *r = residual, *history;
982*600f14f4SXin Li 
983*600f14f4SXin Li #ifdef FLAC__OVERFLOW_DETECT_VERBOSE
984*600f14f4SXin Li 	fprintf(stderr,"FLAC__lpc_restore_signal: data_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization);
985*600f14f4SXin Li 	for(i=0;i<order;i++)
986*600f14f4SXin Li 		fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]);
987*600f14f4SXin Li 	fprintf(stderr,"\n");
988*600f14f4SXin Li #endif
989*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
990*600f14f4SXin Li 
991*600f14f4SXin Li 	for(i = 0; i < data_len; i++) {
992*600f14f4SXin Li 		sumo = 0;
993*600f14f4SXin Li 		sum = 0;
994*600f14f4SXin Li 		history = data;
995*600f14f4SXin Li 		for(j = 0; j < order; j++) {
996*600f14f4SXin Li 			sum += qlp_coeff[j] * (*(--history));
997*600f14f4SXin Li 			sumo += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*history);
998*600f14f4SXin Li #ifdef FLAC__OVERFLOW_DETECT
999*600f14f4SXin Li 			if(sumo > 2147483647ll || sumo < -2147483648ll)
1000*600f14f4SXin Li 				fprintf(stderr,"FLAC__lpc_restore_signal: OVERFLOW, i=%u, j=%u, c=%d, d=%d, sumo=%" PRId64 "\n",i,j,qlp_coeff[j],*history,sumo);
1001*600f14f4SXin Li #endif
1002*600f14f4SXin Li 		}
1003*600f14f4SXin Li 		*(data++) = *(r++) + (sum >> lp_quantization);
1004*600f14f4SXin Li 	}
1005*600f14f4SXin Li 
1006*600f14f4SXin Li 	/* Here's a slower but clearer version:
1007*600f14f4SXin Li 	for(i = 0; i < data_len; i++) {
1008*600f14f4SXin Li 		sum = 0;
1009*600f14f4SXin Li 		for(j = 0; j < order; j++)
1010*600f14f4SXin Li 			sum += qlp_coeff[j] * data[i-j-1];
1011*600f14f4SXin Li 		data[i] = residual[i] + (sum >> lp_quantization);
1012*600f14f4SXin Li 	}
1013*600f14f4SXin Li 	*/
1014*600f14f4SXin Li }
1015*600f14f4SXin Li #else /* fully unrolled version for normal use */
1016*600f14f4SXin Li {
1017*600f14f4SXin Li 	int i;
1018*600f14f4SXin Li 	FLAC__int32 sum;
1019*600f14f4SXin Li 
1020*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
1021*600f14f4SXin Li 	FLAC__ASSERT(order <= 32);
1022*600f14f4SXin Li 
1023*600f14f4SXin Li 	/*
1024*600f14f4SXin Li 	 * We do unique versions up to 12th order since that's the subset limit.
1025*600f14f4SXin Li 	 * Also they are roughly ordered to match frequency of occurrence to
1026*600f14f4SXin Li 	 * minimize branching.
1027*600f14f4SXin Li 	 */
1028*600f14f4SXin Li 	if(order <= 12) {
1029*600f14f4SXin Li 		if(order > 8) {
1030*600f14f4SXin Li 			if(order > 10) {
1031*600f14f4SXin Li 				if(order == 12) {
1032*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1033*600f14f4SXin Li 						sum = 0;
1034*600f14f4SXin Li 						sum += qlp_coeff[11] * data[i-12];
1035*600f14f4SXin Li 						sum += qlp_coeff[10] * data[i-11];
1036*600f14f4SXin Li 						sum += qlp_coeff[9] * data[i-10];
1037*600f14f4SXin Li 						sum += qlp_coeff[8] * data[i-9];
1038*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
1039*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
1040*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
1041*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
1042*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
1043*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1044*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1045*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1046*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1047*600f14f4SXin Li 					}
1048*600f14f4SXin Li 				}
1049*600f14f4SXin Li 				else { /* order == 11 */
1050*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1051*600f14f4SXin Li 						sum = 0;
1052*600f14f4SXin Li 						sum += qlp_coeff[10] * data[i-11];
1053*600f14f4SXin Li 						sum += qlp_coeff[9] * data[i-10];
1054*600f14f4SXin Li 						sum += qlp_coeff[8] * data[i-9];
1055*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
1056*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
1057*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
1058*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
1059*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
1060*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1061*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1062*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1063*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1064*600f14f4SXin Li 					}
1065*600f14f4SXin Li 				}
1066*600f14f4SXin Li 			}
1067*600f14f4SXin Li 			else {
1068*600f14f4SXin Li 				if(order == 10) {
1069*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1070*600f14f4SXin Li 						sum = 0;
1071*600f14f4SXin Li 						sum += qlp_coeff[9] * data[i-10];
1072*600f14f4SXin Li 						sum += qlp_coeff[8] * data[i-9];
1073*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
1074*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
1075*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
1076*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
1077*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
1078*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1079*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1080*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1081*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1082*600f14f4SXin Li 					}
1083*600f14f4SXin Li 				}
1084*600f14f4SXin Li 				else { /* order == 9 */
1085*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1086*600f14f4SXin Li 						sum = 0;
1087*600f14f4SXin Li 						sum += qlp_coeff[8] * data[i-9];
1088*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
1089*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
1090*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
1091*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
1092*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
1093*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1094*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1095*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1096*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1097*600f14f4SXin Li 					}
1098*600f14f4SXin Li 				}
1099*600f14f4SXin Li 			}
1100*600f14f4SXin Li 		}
1101*600f14f4SXin Li 		else if(order > 4) {
1102*600f14f4SXin Li 			if(order > 6) {
1103*600f14f4SXin Li 				if(order == 8) {
1104*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1105*600f14f4SXin Li 						sum = 0;
1106*600f14f4SXin Li 						sum += qlp_coeff[7] * data[i-8];
1107*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
1108*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
1109*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
1110*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
1111*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1112*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1113*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1114*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1115*600f14f4SXin Li 					}
1116*600f14f4SXin Li 				}
1117*600f14f4SXin Li 				else { /* order == 7 */
1118*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1119*600f14f4SXin Li 						sum = 0;
1120*600f14f4SXin Li 						sum += qlp_coeff[6] * data[i-7];
1121*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
1122*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
1123*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
1124*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1125*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1126*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1127*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1128*600f14f4SXin Li 					}
1129*600f14f4SXin Li 				}
1130*600f14f4SXin Li 			}
1131*600f14f4SXin Li 			else {
1132*600f14f4SXin Li 				if(order == 6) {
1133*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1134*600f14f4SXin Li 						sum = 0;
1135*600f14f4SXin Li 						sum += qlp_coeff[5] * data[i-6];
1136*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
1137*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
1138*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1139*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1140*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1141*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1142*600f14f4SXin Li 					}
1143*600f14f4SXin Li 				}
1144*600f14f4SXin Li 				else { /* order == 5 */
1145*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1146*600f14f4SXin Li 						sum = 0;
1147*600f14f4SXin Li 						sum += qlp_coeff[4] * data[i-5];
1148*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
1149*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1150*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1151*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1152*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1153*600f14f4SXin Li 					}
1154*600f14f4SXin Li 				}
1155*600f14f4SXin Li 			}
1156*600f14f4SXin Li 		}
1157*600f14f4SXin Li 		else {
1158*600f14f4SXin Li 			if(order > 2) {
1159*600f14f4SXin Li 				if(order == 4) {
1160*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1161*600f14f4SXin Li 						sum = 0;
1162*600f14f4SXin Li 						sum += qlp_coeff[3] * data[i-4];
1163*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1164*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1165*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1166*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1167*600f14f4SXin Li 					}
1168*600f14f4SXin Li 				}
1169*600f14f4SXin Li 				else { /* order == 3 */
1170*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1171*600f14f4SXin Li 						sum = 0;
1172*600f14f4SXin Li 						sum += qlp_coeff[2] * data[i-3];
1173*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1174*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1175*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1176*600f14f4SXin Li 					}
1177*600f14f4SXin Li 				}
1178*600f14f4SXin Li 			}
1179*600f14f4SXin Li 			else {
1180*600f14f4SXin Li 				if(order == 2) {
1181*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1182*600f14f4SXin Li 						sum = 0;
1183*600f14f4SXin Li 						sum += qlp_coeff[1] * data[i-2];
1184*600f14f4SXin Li 						sum += qlp_coeff[0] * data[i-1];
1185*600f14f4SXin Li 						data[i] = residual[i] + (sum >> lp_quantization);
1186*600f14f4SXin Li 					}
1187*600f14f4SXin Li 				}
1188*600f14f4SXin Li 				else { /* order == 1 */
1189*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++)
1190*600f14f4SXin Li 						data[i] = residual[i] + ((qlp_coeff[0] * data[i-1]) >> lp_quantization);
1191*600f14f4SXin Li 				}
1192*600f14f4SXin Li 			}
1193*600f14f4SXin Li 		}
1194*600f14f4SXin Li 	}
1195*600f14f4SXin Li 	else { /* order > 12 */
1196*600f14f4SXin Li 		for(i = 0; i < (int)data_len; i++) {
1197*600f14f4SXin Li 			sum = 0;
1198*600f14f4SXin Li 			switch(order) {
1199*600f14f4SXin Li 				case 32: sum += qlp_coeff[31] * data[i-32]; /* Falls through. */
1200*600f14f4SXin Li 				case 31: sum += qlp_coeff[30] * data[i-31]; /* Falls through. */
1201*600f14f4SXin Li 				case 30: sum += qlp_coeff[29] * data[i-30]; /* Falls through. */
1202*600f14f4SXin Li 				case 29: sum += qlp_coeff[28] * data[i-29]; /* Falls through. */
1203*600f14f4SXin Li 				case 28: sum += qlp_coeff[27] * data[i-28]; /* Falls through. */
1204*600f14f4SXin Li 				case 27: sum += qlp_coeff[26] * data[i-27]; /* Falls through. */
1205*600f14f4SXin Li 				case 26: sum += qlp_coeff[25] * data[i-26]; /* Falls through. */
1206*600f14f4SXin Li 				case 25: sum += qlp_coeff[24] * data[i-25]; /* Falls through. */
1207*600f14f4SXin Li 				case 24: sum += qlp_coeff[23] * data[i-24]; /* Falls through. */
1208*600f14f4SXin Li 				case 23: sum += qlp_coeff[22] * data[i-23]; /* Falls through. */
1209*600f14f4SXin Li 				case 22: sum += qlp_coeff[21] * data[i-22]; /* Falls through. */
1210*600f14f4SXin Li 				case 21: sum += qlp_coeff[20] * data[i-21]; /* Falls through. */
1211*600f14f4SXin Li 				case 20: sum += qlp_coeff[19] * data[i-20]; /* Falls through. */
1212*600f14f4SXin Li 				case 19: sum += qlp_coeff[18] * data[i-19]; /* Falls through. */
1213*600f14f4SXin Li 				case 18: sum += qlp_coeff[17] * data[i-18]; /* Falls through. */
1214*600f14f4SXin Li 				case 17: sum += qlp_coeff[16] * data[i-17]; /* Falls through. */
1215*600f14f4SXin Li 				case 16: sum += qlp_coeff[15] * data[i-16]; /* Falls through. */
1216*600f14f4SXin Li 				case 15: sum += qlp_coeff[14] * data[i-15]; /* Falls through. */
1217*600f14f4SXin Li 				case 14: sum += qlp_coeff[13] * data[i-14]; /* Falls through. */
1218*600f14f4SXin Li 				case 13: sum += qlp_coeff[12] * data[i-13];
1219*600f14f4SXin Li 				         sum += qlp_coeff[11] * data[i-12];
1220*600f14f4SXin Li 				         sum += qlp_coeff[10] * data[i-11];
1221*600f14f4SXin Li 				         sum += qlp_coeff[ 9] * data[i-10];
1222*600f14f4SXin Li 				         sum += qlp_coeff[ 8] * data[i- 9];
1223*600f14f4SXin Li 				         sum += qlp_coeff[ 7] * data[i- 8];
1224*600f14f4SXin Li 				         sum += qlp_coeff[ 6] * data[i- 7];
1225*600f14f4SXin Li 				         sum += qlp_coeff[ 5] * data[i- 6];
1226*600f14f4SXin Li 				         sum += qlp_coeff[ 4] * data[i- 5];
1227*600f14f4SXin Li 				         sum += qlp_coeff[ 3] * data[i- 4];
1228*600f14f4SXin Li 				         sum += qlp_coeff[ 2] * data[i- 3];
1229*600f14f4SXin Li 				         sum += qlp_coeff[ 1] * data[i- 2];
1230*600f14f4SXin Li 				         sum += qlp_coeff[ 0] * data[i- 1];
1231*600f14f4SXin Li 			}
1232*600f14f4SXin Li 			data[i] = residual[i] + (sum >> lp_quantization);
1233*600f14f4SXin Li 		}
1234*600f14f4SXin Li 	}
1235*600f14f4SXin Li }
1236*600f14f4SXin Li #endif
1237*600f14f4SXin Li 
FLAC__lpc_restore_signal_wide(const FLAC__int32 * flac_restrict residual,uint32_t data_len,const FLAC__int32 * flac_restrict qlp_coeff,uint32_t order,int lp_quantization,FLAC__int32 * flac_restrict data)1238*600f14f4SXin Li void FLAC__lpc_restore_signal_wide(const FLAC__int32 * flac_restrict residual, uint32_t data_len, const FLAC__int32 * flac_restrict qlp_coeff, uint32_t order, int lp_quantization, FLAC__int32 * flac_restrict data)
1239*600f14f4SXin Li #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS)
1240*600f14f4SXin Li {
1241*600f14f4SXin Li 	uint32_t i, j;
1242*600f14f4SXin Li 	FLAC__int64 sum;
1243*600f14f4SXin Li 	const FLAC__int32 *r = residual, *history;
1244*600f14f4SXin Li 
1245*600f14f4SXin Li #ifdef FLAC__OVERFLOW_DETECT_VERBOSE
1246*600f14f4SXin Li 	fprintf(stderr,"FLAC__lpc_restore_signal_wide: data_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization);
1247*600f14f4SXin Li 	for(i=0;i<order;i++)
1248*600f14f4SXin Li 		fprintf(stderr,", q[%u]=%d",i,qlp_coeff[i]);
1249*600f14f4SXin Li 	fprintf(stderr,"\n");
1250*600f14f4SXin Li #endif
1251*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
1252*600f14f4SXin Li 
1253*600f14f4SXin Li 	for(i = 0; i < data_len; i++) {
1254*600f14f4SXin Li 		sum = 0;
1255*600f14f4SXin Li 		history = data;
1256*600f14f4SXin Li 		for(j = 0; j < order; j++)
1257*600f14f4SXin Li 			sum += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*(--history));
1258*600f14f4SXin Li #ifdef FLAC__OVERFLOW_DETECT
1259*600f14f4SXin Li 		if(FLAC__bitmath_silog2((FLAC__int64)(*r) + (sum >> lp_quantization)) > 32) {
1260*600f14f4SXin Li 			fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW, i=%u, residual=%d, sum=%" PRId64 ", data=%" PRId64 "\n", i, *r, (sum >> lp_quantization), ((FLAC__int64)(*r) + (sum >> lp_quantization)));
1261*600f14f4SXin Li 			break;
1262*600f14f4SXin Li 		}
1263*600f14f4SXin Li #endif
1264*600f14f4SXin Li 		*(data++) = (FLAC__int32)(*(r++) + (sum >> lp_quantization));
1265*600f14f4SXin Li 	}
1266*600f14f4SXin Li }
1267*600f14f4SXin Li #else /* fully unrolled version for normal use */
1268*600f14f4SXin Li {
1269*600f14f4SXin Li 	int i;
1270*600f14f4SXin Li 	FLAC__int64 sum;
1271*600f14f4SXin Li 
1272*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
1273*600f14f4SXin Li 	FLAC__ASSERT(order <= 32);
1274*600f14f4SXin Li 
1275*600f14f4SXin Li 	/*
1276*600f14f4SXin Li 	 * We do unique versions up to 12th order since that's the subset limit.
1277*600f14f4SXin Li 	 * Also they are roughly ordered to match frequency of occurrence to
1278*600f14f4SXin Li 	 * minimize branching.
1279*600f14f4SXin Li 	 */
1280*600f14f4SXin Li 	if(order <= 12) {
1281*600f14f4SXin Li 		if(order > 8) {
1282*600f14f4SXin Li 			if(order > 10) {
1283*600f14f4SXin Li 				if(order == 12) {
1284*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1285*600f14f4SXin Li 						sum = 0;
1286*600f14f4SXin Li 						sum += qlp_coeff[11] * (FLAC__int64)data[i-12];
1287*600f14f4SXin Li 						sum += qlp_coeff[10] * (FLAC__int64)data[i-11];
1288*600f14f4SXin Li 						sum += qlp_coeff[9] * (FLAC__int64)data[i-10];
1289*600f14f4SXin Li 						sum += qlp_coeff[8] * (FLAC__int64)data[i-9];
1290*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
1291*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
1292*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
1293*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
1294*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
1295*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1296*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1297*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1298*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1299*600f14f4SXin Li 					}
1300*600f14f4SXin Li 				}
1301*600f14f4SXin Li 				else { /* order == 11 */
1302*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1303*600f14f4SXin Li 						sum = 0;
1304*600f14f4SXin Li 						sum += qlp_coeff[10] * (FLAC__int64)data[i-11];
1305*600f14f4SXin Li 						sum += qlp_coeff[9] * (FLAC__int64)data[i-10];
1306*600f14f4SXin Li 						sum += qlp_coeff[8] * (FLAC__int64)data[i-9];
1307*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
1308*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
1309*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
1310*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
1311*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
1312*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1313*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1314*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1315*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1316*600f14f4SXin Li 					}
1317*600f14f4SXin Li 				}
1318*600f14f4SXin Li 			}
1319*600f14f4SXin Li 			else {
1320*600f14f4SXin Li 				if(order == 10) {
1321*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1322*600f14f4SXin Li 						sum = 0;
1323*600f14f4SXin Li 						sum += qlp_coeff[9] * (FLAC__int64)data[i-10];
1324*600f14f4SXin Li 						sum += qlp_coeff[8] * (FLAC__int64)data[i-9];
1325*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
1326*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
1327*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
1328*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
1329*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
1330*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1331*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1332*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1333*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1334*600f14f4SXin Li 					}
1335*600f14f4SXin Li 				}
1336*600f14f4SXin Li 				else { /* order == 9 */
1337*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1338*600f14f4SXin Li 						sum = 0;
1339*600f14f4SXin Li 						sum += qlp_coeff[8] * (FLAC__int64)data[i-9];
1340*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
1341*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
1342*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
1343*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
1344*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
1345*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1346*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1347*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1348*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1349*600f14f4SXin Li 					}
1350*600f14f4SXin Li 				}
1351*600f14f4SXin Li 			}
1352*600f14f4SXin Li 		}
1353*600f14f4SXin Li 		else if(order > 4) {
1354*600f14f4SXin Li 			if(order > 6) {
1355*600f14f4SXin Li 				if(order == 8) {
1356*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1357*600f14f4SXin Li 						sum = 0;
1358*600f14f4SXin Li 						sum += qlp_coeff[7] * (FLAC__int64)data[i-8];
1359*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
1360*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
1361*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
1362*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
1363*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1364*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1365*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1366*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1367*600f14f4SXin Li 					}
1368*600f14f4SXin Li 				}
1369*600f14f4SXin Li 				else { /* order == 7 */
1370*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1371*600f14f4SXin Li 						sum = 0;
1372*600f14f4SXin Li 						sum += qlp_coeff[6] * (FLAC__int64)data[i-7];
1373*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
1374*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
1375*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
1376*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1377*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1378*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1379*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1380*600f14f4SXin Li 					}
1381*600f14f4SXin Li 				}
1382*600f14f4SXin Li 			}
1383*600f14f4SXin Li 			else {
1384*600f14f4SXin Li 				if(order == 6) {
1385*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1386*600f14f4SXin Li 						sum = 0;
1387*600f14f4SXin Li 						sum += qlp_coeff[5] * (FLAC__int64)data[i-6];
1388*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
1389*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
1390*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1391*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1392*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1393*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1394*600f14f4SXin Li 					}
1395*600f14f4SXin Li 				}
1396*600f14f4SXin Li 				else { /* order == 5 */
1397*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1398*600f14f4SXin Li 						sum = 0;
1399*600f14f4SXin Li 						sum += qlp_coeff[4] * (FLAC__int64)data[i-5];
1400*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
1401*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1402*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1403*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1404*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1405*600f14f4SXin Li 					}
1406*600f14f4SXin Li 				}
1407*600f14f4SXin Li 			}
1408*600f14f4SXin Li 		}
1409*600f14f4SXin Li 		else {
1410*600f14f4SXin Li 			if(order > 2) {
1411*600f14f4SXin Li 				if(order == 4) {
1412*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1413*600f14f4SXin Li 						sum = 0;
1414*600f14f4SXin Li 						sum += qlp_coeff[3] * (FLAC__int64)data[i-4];
1415*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1416*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1417*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1418*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1419*600f14f4SXin Li 					}
1420*600f14f4SXin Li 				}
1421*600f14f4SXin Li 				else { /* order == 3 */
1422*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1423*600f14f4SXin Li 						sum = 0;
1424*600f14f4SXin Li 						sum += qlp_coeff[2] * (FLAC__int64)data[i-3];
1425*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1426*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1427*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1428*600f14f4SXin Li 					}
1429*600f14f4SXin Li 				}
1430*600f14f4SXin Li 			}
1431*600f14f4SXin Li 			else {
1432*600f14f4SXin Li 				if(order == 2) {
1433*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++) {
1434*600f14f4SXin Li 						sum = 0;
1435*600f14f4SXin Li 						sum += qlp_coeff[1] * (FLAC__int64)data[i-2];
1436*600f14f4SXin Li 						sum += qlp_coeff[0] * (FLAC__int64)data[i-1];
1437*600f14f4SXin Li 						data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1438*600f14f4SXin Li 					}
1439*600f14f4SXin Li 				}
1440*600f14f4SXin Li 				else { /* order == 1 */
1441*600f14f4SXin Li 					for(i = 0; i < (int)data_len; i++)
1442*600f14f4SXin Li 						data[i] = (FLAC__int32)(residual[i] + ((qlp_coeff[0] * (FLAC__int64)data[i-1]) >> lp_quantization));
1443*600f14f4SXin Li 				}
1444*600f14f4SXin Li 			}
1445*600f14f4SXin Li 		}
1446*600f14f4SXin Li 	}
1447*600f14f4SXin Li 	else { /* order > 12 */
1448*600f14f4SXin Li 		for(i = 0; i < (int)data_len; i++) {
1449*600f14f4SXin Li 			sum = 0;
1450*600f14f4SXin Li 			switch(order) {
1451*600f14f4SXin Li 				case 32: sum += qlp_coeff[31] * (FLAC__int64)data[i-32]; /* Falls through. */
1452*600f14f4SXin Li 				case 31: sum += qlp_coeff[30] * (FLAC__int64)data[i-31]; /* Falls through. */
1453*600f14f4SXin Li 				case 30: sum += qlp_coeff[29] * (FLAC__int64)data[i-30]; /* Falls through. */
1454*600f14f4SXin Li 				case 29: sum += qlp_coeff[28] * (FLAC__int64)data[i-29]; /* Falls through. */
1455*600f14f4SXin Li 				case 28: sum += qlp_coeff[27] * (FLAC__int64)data[i-28]; /* Falls through. */
1456*600f14f4SXin Li 				case 27: sum += qlp_coeff[26] * (FLAC__int64)data[i-27]; /* Falls through. */
1457*600f14f4SXin Li 				case 26: sum += qlp_coeff[25] * (FLAC__int64)data[i-26]; /* Falls through. */
1458*600f14f4SXin Li 				case 25: sum += qlp_coeff[24] * (FLAC__int64)data[i-25]; /* Falls through. */
1459*600f14f4SXin Li 				case 24: sum += qlp_coeff[23] * (FLAC__int64)data[i-24]; /* Falls through. */
1460*600f14f4SXin Li 				case 23: sum += qlp_coeff[22] * (FLAC__int64)data[i-23]; /* Falls through. */
1461*600f14f4SXin Li 				case 22: sum += qlp_coeff[21] * (FLAC__int64)data[i-22]; /* Falls through. */
1462*600f14f4SXin Li 				case 21: sum += qlp_coeff[20] * (FLAC__int64)data[i-21]; /* Falls through. */
1463*600f14f4SXin Li 				case 20: sum += qlp_coeff[19] * (FLAC__int64)data[i-20]; /* Falls through. */
1464*600f14f4SXin Li 				case 19: sum += qlp_coeff[18] * (FLAC__int64)data[i-19]; /* Falls through. */
1465*600f14f4SXin Li 				case 18: sum += qlp_coeff[17] * (FLAC__int64)data[i-18]; /* Falls through. */
1466*600f14f4SXin Li 				case 17: sum += qlp_coeff[16] * (FLAC__int64)data[i-17]; /* Falls through. */
1467*600f14f4SXin Li 				case 16: sum += qlp_coeff[15] * (FLAC__int64)data[i-16]; /* Falls through. */
1468*600f14f4SXin Li 				case 15: sum += qlp_coeff[14] * (FLAC__int64)data[i-15]; /* Falls through. */
1469*600f14f4SXin Li 				case 14: sum += qlp_coeff[13] * (FLAC__int64)data[i-14]; /* Falls through. */
1470*600f14f4SXin Li 				case 13: sum += qlp_coeff[12] * (FLAC__int64)data[i-13];
1471*600f14f4SXin Li 				         sum += qlp_coeff[11] * (FLAC__int64)data[i-12];
1472*600f14f4SXin Li 				         sum += qlp_coeff[10] * (FLAC__int64)data[i-11];
1473*600f14f4SXin Li 				         sum += qlp_coeff[ 9] * (FLAC__int64)data[i-10];
1474*600f14f4SXin Li 				         sum += qlp_coeff[ 8] * (FLAC__int64)data[i- 9];
1475*600f14f4SXin Li 				         sum += qlp_coeff[ 7] * (FLAC__int64)data[i- 8];
1476*600f14f4SXin Li 				         sum += qlp_coeff[ 6] * (FLAC__int64)data[i- 7];
1477*600f14f4SXin Li 				         sum += qlp_coeff[ 5] * (FLAC__int64)data[i- 6];
1478*600f14f4SXin Li 				         sum += qlp_coeff[ 4] * (FLAC__int64)data[i- 5];
1479*600f14f4SXin Li 				         sum += qlp_coeff[ 3] * (FLAC__int64)data[i- 4];
1480*600f14f4SXin Li 				         sum += qlp_coeff[ 2] * (FLAC__int64)data[i- 3];
1481*600f14f4SXin Li 				         sum += qlp_coeff[ 1] * (FLAC__int64)data[i- 2];
1482*600f14f4SXin Li 				         sum += qlp_coeff[ 0] * (FLAC__int64)data[i- 1];
1483*600f14f4SXin Li 			}
1484*600f14f4SXin Li 			data[i] = (FLAC__int32) (residual[i] + (sum >> lp_quantization));
1485*600f14f4SXin Li 		}
1486*600f14f4SXin Li 	}
1487*600f14f4SXin Li }
1488*600f14f4SXin Li #endif
1489*600f14f4SXin Li 
1490*600f14f4SXin Li #if defined(FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION) && !defined(FUZZING_BUILD_MODE_FLAC_SANITIZE_SIGNED_INTEGER_OVERFLOW)
1491*600f14f4SXin Li /* The attribute below is to silence the undefined sanitizer of oss-fuzz.
1492*600f14f4SXin Li  * Because fuzzing feeds bogus predictors and residual samples to the
1493*600f14f4SXin Li  * decoder, having overflows in this section is unavoidable. Also,
1494*600f14f4SXin Li  * because the calculated values are audio path only, there is no
1495*600f14f4SXin Li  * potential for security problems */
1496*600f14f4SXin Li __attribute__((no_sanitize("signed-integer-overflow")))
1497*600f14f4SXin Li #endif
FLAC__lpc_restore_signal_wide_33bit(const FLAC__int32 * flac_restrict residual,uint32_t data_len,const FLAC__int32 * flac_restrict qlp_coeff,uint32_t order,int lp_quantization,FLAC__int64 * flac_restrict data)1498*600f14f4SXin Li void FLAC__lpc_restore_signal_wide_33bit(const FLAC__int32 * flac_restrict residual, uint32_t data_len, const FLAC__int32 * flac_restrict qlp_coeff, uint32_t order, int lp_quantization, FLAC__int64 * flac_restrict data)
1499*600f14f4SXin Li #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS)
1500*600f14f4SXin Li {
1501*600f14f4SXin Li 	uint32_t i, j;
1502*600f14f4SXin Li 	FLAC__int64 sum;
1503*600f14f4SXin Li 	const FLAC__int32 *r = residual;
1504*600f14f4SXin Li 	const FLAC__int64 *history;
1505*600f14f4SXin Li 
1506*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
1507*600f14f4SXin Li 
1508*600f14f4SXin Li 	for(i = 0; i < data_len; i++) {
1509*600f14f4SXin Li 		sum = 0;
1510*600f14f4SXin Li 		history = data;
1511*600f14f4SXin Li 		for(j = 0; j < order; j++)
1512*600f14f4SXin Li 			sum += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*(--history));
1513*600f14f4SXin Li #ifdef FLAC__OVERFLOW_DETECT
1514*600f14f4SXin Li 		if(FLAC__bitmath_silog2((FLAC__int64)(*r) + (sum >> lp_quantization)) > 33) {
1515*600f14f4SXin Li 			fprintf(stderr,"FLAC__lpc_restore_signal_33bit: OVERFLOW, i=%u, residual=%d, sum=%" PRId64 ", data=%" PRId64 "\n", i, *r, (sum >> lp_quantization), ((FLAC__int64)(*r) + (sum >> lp_quantization)));
1516*600f14f4SXin Li 			break;
1517*600f14f4SXin Li 		}
1518*600f14f4SXin Li #endif
1519*600f14f4SXin Li 		*(data++) = (FLAC__int64)(*(r++)) + (sum >> lp_quantization);
1520*600f14f4SXin Li 	}
1521*600f14f4SXin Li }
1522*600f14f4SXin Li #else /* unrolled version for normal use */
1523*600f14f4SXin Li {
1524*600f14f4SXin Li 	int i;
1525*600f14f4SXin Li 	FLAC__int64 sum;
1526*600f14f4SXin Li 
1527*600f14f4SXin Li 	FLAC__ASSERT(order > 0);
1528*600f14f4SXin Li 	FLAC__ASSERT(order <= 32);
1529*600f14f4SXin Li 
1530*600f14f4SXin Li 	for(i = 0; i < (int)data_len; i++) {
1531*600f14f4SXin Li 		sum = 0;
1532*600f14f4SXin Li 		switch(order) {
1533*600f14f4SXin Li 			case 32: sum += qlp_coeff[31] * data[i-32]; /* Falls through. */
1534*600f14f4SXin Li 			case 31: sum += qlp_coeff[30] * data[i-31]; /* Falls through. */
1535*600f14f4SXin Li 			case 30: sum += qlp_coeff[29] * data[i-30]; /* Falls through. */
1536*600f14f4SXin Li 			case 29: sum += qlp_coeff[28] * data[i-29]; /* Falls through. */
1537*600f14f4SXin Li 			case 28: sum += qlp_coeff[27] * data[i-28]; /* Falls through. */
1538*600f14f4SXin Li 			case 27: sum += qlp_coeff[26] * data[i-27]; /* Falls through. */
1539*600f14f4SXin Li 			case 26: sum += qlp_coeff[25] * data[i-26]; /* Falls through. */
1540*600f14f4SXin Li 			case 25: sum += qlp_coeff[24] * data[i-25]; /* Falls through. */
1541*600f14f4SXin Li 			case 24: sum += qlp_coeff[23] * data[i-24]; /* Falls through. */
1542*600f14f4SXin Li 			case 23: sum += qlp_coeff[22] * data[i-23]; /* Falls through. */
1543*600f14f4SXin Li 			case 22: sum += qlp_coeff[21] * data[i-22]; /* Falls through. */
1544*600f14f4SXin Li 			case 21: sum += qlp_coeff[20] * data[i-21]; /* Falls through. */
1545*600f14f4SXin Li 			case 20: sum += qlp_coeff[19] * data[i-20]; /* Falls through. */
1546*600f14f4SXin Li 			case 19: sum += qlp_coeff[18] * data[i-19]; /* Falls through. */
1547*600f14f4SXin Li 			case 18: sum += qlp_coeff[17] * data[i-18]; /* Falls through. */
1548*600f14f4SXin Li 			case 17: sum += qlp_coeff[16] * data[i-17]; /* Falls through. */
1549*600f14f4SXin Li 			case 16: sum += qlp_coeff[15] * data[i-16]; /* Falls through. */
1550*600f14f4SXin Li 			case 15: sum += qlp_coeff[14] * data[i-15]; /* Falls through. */
1551*600f14f4SXin Li 			case 14: sum += qlp_coeff[13] * data[i-14]; /* Falls through. */
1552*600f14f4SXin Li 			case 13: sum += qlp_coeff[12] * data[i-13]; /* Falls through. */
1553*600f14f4SXin Li 			case 12: sum += qlp_coeff[11] * data[i-12]; /* Falls through. */
1554*600f14f4SXin Li 			case 11: sum += qlp_coeff[10] * data[i-11]; /* Falls through. */
1555*600f14f4SXin Li 			case 10: sum += qlp_coeff[ 9] * data[i-10]; /* Falls through. */
1556*600f14f4SXin Li 			case  9: sum += qlp_coeff[ 8] * data[i- 9]; /* Falls through. */
1557*600f14f4SXin Li 			case  8: sum += qlp_coeff[ 7] * data[i- 8]; /* Falls through. */
1558*600f14f4SXin Li 			case  7: sum += qlp_coeff[ 6] * data[i- 7]; /* Falls through. */
1559*600f14f4SXin Li 			case  6: sum += qlp_coeff[ 5] * data[i- 6]; /* Falls through. */
1560*600f14f4SXin Li 			case  5: sum += qlp_coeff[ 4] * data[i- 5]; /* Falls through. */
1561*600f14f4SXin Li 			case  4: sum += qlp_coeff[ 3] * data[i- 4]; /* Falls through. */
1562*600f14f4SXin Li 			case  3: sum += qlp_coeff[ 2] * data[i- 3]; /* Falls through. */
1563*600f14f4SXin Li 			case  2: sum += qlp_coeff[ 1] * data[i- 2]; /* Falls through. */
1564*600f14f4SXin Li 			case  1: sum += qlp_coeff[ 0] * data[i- 1];
1565*600f14f4SXin Li 		}
1566*600f14f4SXin Li 		data[i] = residual[i] + (sum >> lp_quantization);
1567*600f14f4SXin Li 	}
1568*600f14f4SXin Li }
1569*600f14f4SXin Li #endif
1570*600f14f4SXin Li 
1571*600f14f4SXin Li #if defined(_MSC_VER)
1572*600f14f4SXin Li #pragma warning ( default : 4028 )
1573*600f14f4SXin Li #endif
1574*600f14f4SXin Li 
1575*600f14f4SXin Li #ifndef FLAC__INTEGER_ONLY_LIBRARY
1576*600f14f4SXin Li 
FLAC__lpc_compute_expected_bits_per_residual_sample(double lpc_error,uint32_t total_samples)1577*600f14f4SXin Li double FLAC__lpc_compute_expected_bits_per_residual_sample(double lpc_error, uint32_t total_samples)
1578*600f14f4SXin Li {
1579*600f14f4SXin Li 	double error_scale;
1580*600f14f4SXin Li 
1581*600f14f4SXin Li 	FLAC__ASSERT(total_samples > 0);
1582*600f14f4SXin Li 
1583*600f14f4SXin Li 	error_scale = 0.5 / (double)total_samples;
1584*600f14f4SXin Li 
1585*600f14f4SXin Li 	return FLAC__lpc_compute_expected_bits_per_residual_sample_with_error_scale(lpc_error, error_scale);
1586*600f14f4SXin Li }
1587*600f14f4SXin Li 
FLAC__lpc_compute_expected_bits_per_residual_sample_with_error_scale(double lpc_error,double error_scale)1588*600f14f4SXin Li double FLAC__lpc_compute_expected_bits_per_residual_sample_with_error_scale(double lpc_error, double error_scale)
1589*600f14f4SXin Li {
1590*600f14f4SXin Li 	if(lpc_error > 0.0) {
1591*600f14f4SXin Li 		double bps = (double)0.5 * log(error_scale * lpc_error) / M_LN2;
1592*600f14f4SXin Li 		if(bps >= 0.0)
1593*600f14f4SXin Li 			return bps;
1594*600f14f4SXin Li 		else
1595*600f14f4SXin Li 			return 0.0;
1596*600f14f4SXin Li 	}
1597*600f14f4SXin Li 	else if(lpc_error < 0.0) { /* error should not be negative but can happen due to inadequate floating-point resolution */
1598*600f14f4SXin Li 		return 1e32;
1599*600f14f4SXin Li 	}
1600*600f14f4SXin Li 	else {
1601*600f14f4SXin Li 		return 0.0;
1602*600f14f4SXin Li 	}
1603*600f14f4SXin Li }
1604*600f14f4SXin Li 
FLAC__lpc_compute_best_order(const double lpc_error[],uint32_t max_order,uint32_t total_samples,uint32_t overhead_bits_per_order)1605*600f14f4SXin Li uint32_t FLAC__lpc_compute_best_order(const double lpc_error[], uint32_t max_order, uint32_t total_samples, uint32_t overhead_bits_per_order)
1606*600f14f4SXin Li {
1607*600f14f4SXin Li 	uint32_t order, indx, 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 */
1608*600f14f4SXin Li 	double bits, best_bits, error_scale;
1609*600f14f4SXin Li 
1610*600f14f4SXin Li 	FLAC__ASSERT(max_order > 0);
1611*600f14f4SXin Li 	FLAC__ASSERT(total_samples > 0);
1612*600f14f4SXin Li 
1613*600f14f4SXin Li 	error_scale = 0.5 / (double)total_samples;
1614*600f14f4SXin Li 
1615*600f14f4SXin Li 	best_index = 0;
1616*600f14f4SXin Li 	best_bits = (uint32_t)(-1);
1617*600f14f4SXin Li 
1618*600f14f4SXin Li 	for(indx = 0, order = 1; indx < max_order; indx++, order++) {
1619*600f14f4SXin Li 		bits = FLAC__lpc_compute_expected_bits_per_residual_sample_with_error_scale(lpc_error[indx], error_scale) * (double)(total_samples - order) + (double)(order * overhead_bits_per_order);
1620*600f14f4SXin Li 		if(bits < best_bits) {
1621*600f14f4SXin Li 			best_index = indx;
1622*600f14f4SXin Li 			best_bits = bits;
1623*600f14f4SXin Li 		}
1624*600f14f4SXin Li 	}
1625*600f14f4SXin Li 
1626*600f14f4SXin Li 	return best_index+1; /* +1 since indx of lpc_error[] is order-1 */
1627*600f14f4SXin Li }
1628*600f14f4SXin Li 
1629*600f14f4SXin Li #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */
1630