34#if !defined(_SPANDSP_FIR_H_)
35#define _SPANDSP_FIR_H_
37#if defined(USE_MMX) || defined(USE_SSE2)
49 const int16_t *coeffs;
62 const int32_t *coeffs;
78#if defined(__cplusplus)
83static __inline__
const int16_t *fir16_create(
fir16_state_t *fir,
84 const int16_t *coeffs,
88 fir->curr_pos = taps - 1;
90#if defined(USE_MMX) || defined(USE_SSE2)
91 if ((fir->history = malloc(2*taps*
sizeof(int16_t))))
92 memset(fir->history, 0, 2*taps*
sizeof(int16_t));
94 if ((fir->history = (int16_t *) malloc(taps*
sizeof(int16_t))))
95 memset(fir->history, 0, taps*
sizeof(int16_t));
103#if defined(USE_MMX) || defined(USE_SSE2)
104 memset(fir->history, 0, 2*fir->taps*
sizeof(int16_t));
106 memset(fir->history, 0, fir->taps*
sizeof(int16_t));
117static __inline__ int16_t fir16(
fir16_state_t *fir, int16_t sample)
125 fir->history[fir->curr_pos] = sample;
126 fir->history[fir->curr_pos + fir->taps] = sample;
128 mmx_coeffs = (mmx_t *) fir->coeffs;
129 mmx_hist = (mmx_t *) &fir->history[fir->curr_pos];
135 movq_m2r(mmx_coeffs[0], mm0);
136 movq_m2r(mmx_coeffs[1], mm2);
137 movq_m2r(mmx_hist[0], mm1);
138 movq_m2r(mmx_hist[1], mm3);
141 pmaddwd_r2r(mm1, mm0);
142 pmaddwd_r2r(mm3, mm2);
152#elif defined(USE_SSE2)
156 fir->history[fir->curr_pos] = sample;
157 fir->history[fir->curr_pos + fir->taps] = sample;
159 xmm_coeffs = (xmm_t *) fir->coeffs;
160 xmm_hist = (xmm_t *) &fir->history[fir->curr_pos];
162 pxor_r2r(xmm4, xmm4);
166 movdqu_m2r(xmm_coeffs[0], xmm0);
167 movdqu_m2r(xmm_coeffs[1], xmm2);
168 movdqu_m2r(xmm_hist[0], xmm1);
169 movdqu_m2r(xmm_hist[1], xmm3);
172 pmaddwd_r2r(xmm1, xmm0);
173 pmaddwd_r2r(xmm3, xmm2);
174 paddd_r2r(xmm0, xmm4);
175 paddd_r2r(xmm2, xmm4);
178 movdqa_r2r(xmm4, xmm0);
180 paddd_r2r(xmm0, xmm4);
181 movdqa_r2r(xmm4, xmm0);
183 paddd_r2r(xmm0, xmm4);
189 fir->history[fir->curr_pos] = sample;
191 offset2 = fir->curr_pos;
192 offset1 = fir->taps - offset2;
194 for (i = fir->taps - 1; i >= offset1; i--)
195 y += fir->coeffs[i]*fir->history[i - offset1];
197 y += fir->coeffs[i]*fir->history[i + offset2];
199 if (fir->curr_pos <= 0)
200 fir->curr_pos = fir->taps;
202 return (int16_t) (y >> 15);
206static __inline__
const int16_t *fir32_create(
fir32_state_t *fir,
207 const int32_t *coeffs,
211 fir->curr_pos = taps - 1;
212 fir->coeffs = coeffs;
213 fir->history = (int16_t *) malloc(taps*
sizeof(int16_t));
215 memset(fir->history,
'\0', taps*
sizeof(int16_t));
222 memset(fir->history, 0, fir->taps*
sizeof(int16_t));
232static __inline__ int16_t fir32(
fir32_state_t *fir, int16_t sample)
239 fir->history[fir->curr_pos] = sample;
240 offset2 = fir->curr_pos;
241 offset1 = fir->taps - offset2;
243 for (i = fir->taps - 1; i >= offset1; i--)
244 y += fir->coeffs[i]*fir->history[i - offset1];
246 y += fir->coeffs[i]*fir->history[i + offset2];
247 if (fir->curr_pos <= 0)
248 fir->curr_pos = fir->taps;
250 return (int16_t) (y >> 15);
259 fir->curr_pos = taps - 1;
260 fir->coeffs = coeffs;
261 fir->history = (
float *) malloc(taps*
sizeof(
float));
263 memset(fir->history,
'\0', taps*
sizeof(
float));
281 fir->history[fir->curr_pos] = sample;
283 offset2 = fir->curr_pos;
284 offset1 = fir->taps - offset2;
286 for (i = fir->taps - 1; i >= offset1; i--)
287 y += fir->coeffs[i]*fir->history[i - offset1];
289 y += fir->coeffs[i]*fir->history[i + offset2];
290 if (fir->curr_pos <= 0)
291 fir->curr_pos = fir->taps;
297#if defined(__cplusplus)