1/*
2 *  Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
3 *
4 *  Use of this source code is governed by a BSD-style license
5 *  that can be found in the LICENSE file in the root of the source
6 *  tree. An additional intellectual property rights grant can be found
7 *  in the file PATENTS.  All contributing project authors may
8 *  be found in the AUTHORS file in the root of the source tree.
9 */
10
11/*
12 * filterbanks.c
13 *
14 * This file contains function
15 * WebRtcIsacfix_SplitAndFilter, and WebRtcIsacfix_FilterAndCombine
16 * which implement filterbanks that produce decimated lowpass and
17 * highpass versions of a signal, and performs reconstruction.
18 *
19 */
20
21#include "filterbank_internal.h"
22
23#include <assert.h>
24
25#include "codec.h"
26#include "filterbank_tables.h"
27#include "settings.h"
28
29// Declare a function pointer.
30AllpassFilter2FixDec16 WebRtcIsacfix_AllpassFilter2FixDec16;
31
32void WebRtcIsacfix_AllpassFilter2FixDec16C(
33    int16_t *data_ch1,  // Input and output in channel 1, in Q0
34    int16_t *data_ch2,  // Input and output in channel 2, in Q0
35    const int16_t *factor_ch1,  // Scaling factor for channel 1, in Q15
36    const int16_t *factor_ch2,  // Scaling factor for channel 2, in Q15
37    const int length,  // Length of the data buffers
38    int32_t *filter_state_ch1,  // Filter state for channel 1, in Q16
39    int32_t *filter_state_ch2) {  // Filter state for channel 2, in Q16
40  int n = 0;
41  int32_t state0_ch1 = filter_state_ch1[0], state1_ch1 = filter_state_ch1[1];
42  int32_t state0_ch2 = filter_state_ch2[0], state1_ch2 = filter_state_ch2[1];
43  int16_t in_out = 0;
44  int32_t a = 0, b = 0;
45
46  // Assembly file assumption.
47  assert(length % 2 == 0);
48
49  for (n = 0; n < length; n++) {
50    // Process channel 1:
51    in_out = data_ch1[n];
52    a = factor_ch1[0] * in_out;  // Q15 * Q0 = Q15
53    a <<= 1;  // Q15 -> Q16
54    b = WebRtcSpl_AddSatW32(a, state0_ch1);
55    a = -factor_ch1[0] * (int16_t)(b >> 16);  // Q15
56    state0_ch1 = WebRtcSpl_AddSatW32(a << 1, (uint32_t)in_out << 16);  // Q16
57    in_out = (int16_t) (b >> 16);  // Save as Q0
58
59    a = factor_ch1[1] * in_out;  // Q15 * Q0 = Q15
60    a <<= 1; // Q15 -> Q16
61    b = WebRtcSpl_AddSatW32(a, state1_ch1);  // Q16
62    a = -factor_ch1[1] * (int16_t)(b >> 16);  // Q15
63    state1_ch1 = WebRtcSpl_AddSatW32(a << 1, (uint32_t)in_out << 16);  // Q16
64    data_ch1[n] = (int16_t) (b >> 16);  // Save as Q0
65
66    // Process channel 2:
67    in_out = data_ch2[n];
68    a = factor_ch2[0] * in_out;  // Q15 * Q0 = Q15
69    a <<= 1;  // Q15 -> Q16
70    b = WebRtcSpl_AddSatW32(a, state0_ch2);  // Q16
71    a = -factor_ch2[0] * (int16_t)(b >> 16);  // Q15
72    state0_ch2 = WebRtcSpl_AddSatW32(a << 1, (uint32_t)in_out << 16);  // Q16
73    in_out = (int16_t) (b >> 16);  // Save as Q0
74
75    a = factor_ch2[1] * in_out;  // Q15 * Q0 = Q15
76    a <<= 1;  // Q15 -> Q16
77    b = WebRtcSpl_AddSatW32(a, state1_ch2);  // Q16
78    a = -factor_ch2[1] * (int16_t)(b >> 16);  // Q15
79    state1_ch2 = WebRtcSpl_AddSatW32(a << 1, (uint32_t)in_out << 16);  // Q16
80    data_ch2[n] = (int16_t) (b >> 16);  // Save as Q0
81  }
82
83  filter_state_ch1[0] = state0_ch1;
84  filter_state_ch1[1] = state1_ch1;
85  filter_state_ch2[0] = state0_ch2;
86  filter_state_ch2[1] = state1_ch2;
87}
88
89// Declare a function pointer.
90HighpassFilterFixDec32 WebRtcIsacfix_HighpassFilterFixDec32;
91
92void WebRtcIsacfix_HighpassFilterFixDec32C(int16_t *io,
93                                           int16_t len,
94                                           const int16_t *coefficient,
95                                           int32_t *state)
96{
97  int k;
98  int32_t a1 = 0, b1 = 0, c = 0, in = 0;
99  int32_t a2 = 0, b2 = 0;
100  int32_t state0 = state[0];
101  int32_t state1 = state[1];
102
103  for (k=0; k<len; k++) {
104    in = (int32_t)io[k];
105
106#ifdef WEBRTC_ARCH_ARM_V7
107    {
108      register int tmp_coeff0;
109      register int tmp_coeff1;
110      __asm __volatile(
111        "ldr %[tmp_coeff0], [%[coeff]]\n\t"
112        "ldr %[tmp_coeff1], [%[coeff], #4]\n\t"
113        "smmulr %[a2], %[tmp_coeff0], %[state0]\n\t"
114        "smmulr %[b2], %[tmp_coeff1], %[state1]\n\t"
115        "ldr %[tmp_coeff0], [%[coeff], #8]\n\t"
116        "ldr %[tmp_coeff1], [%[coeff], #12]\n\t"
117        "smmulr %[a1], %[tmp_coeff0], %[state0]\n\t"
118        "smmulr %[b1], %[tmp_coeff1], %[state1]\n\t"
119        :[a2]"=&r"(a2),
120         [b2]"=&r"(b2),
121         [a1]"=&r"(a1),
122         [b1]"=r"(b1),
123         [tmp_coeff0]"=&r"(tmp_coeff0),
124         [tmp_coeff1]"=&r"(tmp_coeff1)
125        :[coeff]"r"(coefficient),
126         [state0]"r"(state0),
127         [state1]"r"(state1)
128      );
129    }
130#else
131    /* Q35 * Q4 = Q39 ; shift 32 bit => Q7 */
132    a1 = WEBRTC_SPL_MUL_16_32_RSFT16(coefficient[5], state0) +
133        (WEBRTC_SPL_MUL_16_32_RSFT16(coefficient[4], state0) >> 16);
134    b1 = WEBRTC_SPL_MUL_16_32_RSFT16(coefficient[7], state1) +
135        (WEBRTC_SPL_MUL_16_32_RSFT16(coefficient[6], state1) >> 16);
136
137    /* Q30 * Q4 = Q34 ; shift 32 bit => Q2 */
138    a2 = WEBRTC_SPL_MUL_16_32_RSFT16(coefficient[1], state0) +
139        (WEBRTC_SPL_MUL_16_32_RSFT16(coefficient[0], state0) >> 16);
140    b2 = WEBRTC_SPL_MUL_16_32_RSFT16(coefficient[3], state1) +
141        (WEBRTC_SPL_MUL_16_32_RSFT16(coefficient[2], state1) >> 16);
142#endif
143
144    c = in + ((a1 + b1) >> 7);  // Q0.
145    io[k] = (int16_t)WebRtcSpl_SatW32ToW16(c);  // Write output as Q0.
146
147    c = (in << 2) - a2 - b2;  // In Q2.
148    c = (int32_t)WEBRTC_SPL_SAT(536870911, c, -536870912);
149
150    state1 = state0;
151    state0 = c << 2;  // Write state as Q4
152  }
153  state[0] = state0;
154  state[1] = state1;
155}
156
157
158void WebRtcIsacfix_SplitAndFilter1(int16_t *pin,
159                                   int16_t *LP16,
160                                   int16_t *HP16,
161                                   PreFiltBankstr *prefiltdata)
162{
163  /* Function WebRtcIsacfix_SplitAndFilter */
164  /* This function creates low-pass and high-pass decimated versions of part of
165     the input signal, and part of the signal in the input 'lookahead buffer'. */
166
167  int k;
168
169  int16_t tempin_ch1[FRAMESAMPLES/2 + QLOOKAHEAD];
170  int16_t tempin_ch2[FRAMESAMPLES/2 + QLOOKAHEAD];
171  int32_t tmpState_ch1[2 * (QORDER-1)]; /* 4 */
172  int32_t tmpState_ch2[2 * (QORDER-1)]; /* 4 */
173
174  /* High pass filter */
175  WebRtcIsacfix_HighpassFilterFixDec32(pin, FRAMESAMPLES, WebRtcIsacfix_kHpStCoeffInQ30, prefiltdata->HPstates_fix);
176
177
178  /* First Channel */
179  for (k=0;k<FRAMESAMPLES/2;k++) {
180    tempin_ch1[QLOOKAHEAD + k] = pin[1 + 2 * k];
181  }
182  for (k=0;k<QLOOKAHEAD;k++) {
183    tempin_ch1[k]=prefiltdata->INLABUF1_fix[k];
184    prefiltdata->INLABUF1_fix[k] = pin[FRAMESAMPLES + 1 - 2 * (QLOOKAHEAD - k)];
185  }
186
187  /* Second Channel.  This is exactly like the first channel, except that the
188     even samples are now filtered instead (lower channel). */
189  for (k=0;k<FRAMESAMPLES/2;k++) {
190    tempin_ch2[QLOOKAHEAD + k] = pin[2 * k];
191  }
192  for (k=0;k<QLOOKAHEAD;k++) {
193    tempin_ch2[k]=prefiltdata->INLABUF2_fix[k];
194    prefiltdata->INLABUF2_fix[k] = pin[FRAMESAMPLES - 2 * (QLOOKAHEAD - k)];
195  }
196
197
198  /*obtain polyphase components by forward all-pass filtering through each channel */
199  /* The all pass filtering automatically updates the filter states which are exported in the
200     prefiltdata structure */
201  WebRtcIsacfix_AllpassFilter2FixDec16(tempin_ch1,
202                                       tempin_ch2,
203                                       WebRtcIsacfix_kUpperApFactorsQ15,
204                                       WebRtcIsacfix_kLowerApFactorsQ15,
205                                       FRAMESAMPLES/2,
206                                       prefiltdata->INSTAT1_fix,
207                                       prefiltdata->INSTAT2_fix);
208
209  for (k = 0; k < 2 * (QORDER - 1); k++) {
210    tmpState_ch1[k] = prefiltdata->INSTAT1_fix[k];
211    tmpState_ch2[k] = prefiltdata->INSTAT2_fix[k];
212  }
213  WebRtcIsacfix_AllpassFilter2FixDec16(tempin_ch1 + FRAMESAMPLES/2,
214                                       tempin_ch2 + FRAMESAMPLES/2,
215                                       WebRtcIsacfix_kUpperApFactorsQ15,
216                                       WebRtcIsacfix_kLowerApFactorsQ15,
217                                       QLOOKAHEAD,
218                                       tmpState_ch1,
219                                       tmpState_ch2);
220
221  /* Now Construct low-pass and high-pass signals as combinations of polyphase components */
222  for (k=0; k<FRAMESAMPLES/2 + QLOOKAHEAD; k++) {
223    int32_t tmp1, tmp2, tmp3;
224    tmp1 = (int32_t)tempin_ch1[k]; // Q0 -> Q0
225    tmp2 = (int32_t)tempin_ch2[k]; // Q0 -> Q0
226    tmp3 = (tmp1 + tmp2) >> 1;  /* Low pass signal. */
227    LP16[k] = (int16_t)WebRtcSpl_SatW32ToW16(tmp3); /*low pass */
228    tmp3 = (tmp1 - tmp2) >> 1;  /* High pass signal. */
229    HP16[k] = (int16_t)WebRtcSpl_SatW32ToW16(tmp3); /*high pass */
230  }
231
232}/*end of WebRtcIsacfix_SplitAndFilter */
233
234
235#ifdef WEBRTC_ISAC_FIX_NB_CALLS_ENABLED
236
237/* Without lookahead */
238void WebRtcIsacfix_SplitAndFilter2(int16_t *pin,
239                                   int16_t *LP16,
240                                   int16_t *HP16,
241                                   PreFiltBankstr *prefiltdata)
242{
243  /* Function WebRtcIsacfix_SplitAndFilter2 */
244  /* This function creates low-pass and high-pass decimated versions of part of
245     the input signal. */
246
247  int k;
248
249  int16_t tempin_ch1[FRAMESAMPLES/2];
250  int16_t tempin_ch2[FRAMESAMPLES/2];
251
252
253  /* High pass filter */
254  WebRtcIsacfix_HighpassFilterFixDec32(pin, FRAMESAMPLES, WebRtcIsacfix_kHpStCoeffInQ30, prefiltdata->HPstates_fix);
255
256
257  /* First Channel */
258  for (k=0;k<FRAMESAMPLES/2;k++) {
259    tempin_ch1[k] = pin[1 + 2 * k];
260  }
261
262  /* Second Channel.  This is exactly like the first channel, except that the
263     even samples are now filtered instead (lower channel). */
264  for (k=0;k<FRAMESAMPLES/2;k++) {
265    tempin_ch2[k] = pin[2 * k];
266  }
267
268
269  /*obtain polyphase components by forward all-pass filtering through each channel */
270  /* The all pass filtering automatically updates the filter states which are exported in the
271     prefiltdata structure */
272  WebRtcIsacfix_AllpassFilter2FixDec16(tempin_ch1,
273                                       tempin_ch2,
274                                       WebRtcIsacfix_kUpperApFactorsQ15,
275                                       WebRtcIsacfix_kLowerApFactorsQ15,
276                                       FRAMESAMPLES/2,
277                                       prefiltdata->INSTAT1_fix,
278                                       prefiltdata->INSTAT2_fix);
279
280  /* Now Construct low-pass and high-pass signals as combinations of polyphase components */
281  for (k=0; k<FRAMESAMPLES/2; k++) {
282    int32_t tmp1, tmp2, tmp3;
283    tmp1 = (int32_t)tempin_ch1[k]; // Q0 -> Q0
284    tmp2 = (int32_t)tempin_ch2[k]; // Q0 -> Q0
285    tmp3 = (tmp1 + tmp2) >> 1;  /* Low pass signal. */
286    LP16[k] = (int16_t)WebRtcSpl_SatW32ToW16(tmp3); /*low pass */
287    tmp3 = (tmp1 - tmp2) >> 1;  /* High pass signal. */
288    HP16[k] = (int16_t)WebRtcSpl_SatW32ToW16(tmp3); /*high pass */
289  }
290
291}/*end of WebRtcIsacfix_SplitAndFilter */
292
293#endif
294
295
296
297//////////////////////////////////////////////////////////
298////////// Combining
299/* Function WebRtcIsacfix_FilterAndCombine */
300/* This is a decoder function that takes the decimated
301   length FRAMESAMPLES/2 input low-pass and
302   high-pass signals and creates a reconstructed fullband
303   output signal of length FRAMESAMPLES. WebRtcIsacfix_FilterAndCombine
304   is the sibling function of WebRtcIsacfix_SplitAndFilter */
305/* INPUTS:
306   inLP: a length FRAMESAMPLES/2 array of input low-pass
307   samples.
308   inHP: a length FRAMESAMPLES/2 array of input high-pass
309   samples.
310   postfiltdata: input data structure containing the filterbank
311   states from the previous decoding iteration.
312   OUTPUTS:
313   Out: a length FRAMESAMPLES array of output reconstructed
314   samples (fullband) based on the input low-pass and
315   high-pass signals.
316   postfiltdata: the input data structure containing the filterbank
317   states is updated for the next decoding iteration */
318void WebRtcIsacfix_FilterAndCombine1(int16_t *tempin_ch1,
319                                     int16_t *tempin_ch2,
320                                     int16_t *out16,
321                                     PostFiltBankstr *postfiltdata)
322{
323  int k;
324  int16_t in[FRAMESAMPLES];
325
326  /* all-pass filter the new upper and lower channel signal.
327     For upper channel, use the all-pass filter factors that were used as a
328     lower channel at the encoding side. So at the decoder, the corresponding
329     all-pass filter factors for each channel are swapped.
330     For lower channel signal, since all-pass filter factors at the decoder are
331     swapped from the ones at the encoder, the 'upper' channel all-pass filter
332     factors (kUpperApFactors) are used to filter this new lower channel signal.
333  */
334  WebRtcIsacfix_AllpassFilter2FixDec16(tempin_ch1,
335                                       tempin_ch2,
336                                       WebRtcIsacfix_kLowerApFactorsQ15,
337                                       WebRtcIsacfix_kUpperApFactorsQ15,
338                                       FRAMESAMPLES/2,
339                                       postfiltdata->STATE_0_UPPER_fix,
340                                       postfiltdata->STATE_0_LOWER_fix);
341
342  /* Merge outputs to form the full length output signal.*/
343  for (k=0;k<FRAMESAMPLES/2;k++) {
344    in[2 * k] = tempin_ch2[k];
345    in[2 * k + 1] = tempin_ch1[k];
346  }
347
348  /* High pass filter */
349  WebRtcIsacfix_HighpassFilterFixDec32(in, FRAMESAMPLES, WebRtcIsacfix_kHPStCoeffOut1Q30, postfiltdata->HPstates1_fix);
350  WebRtcIsacfix_HighpassFilterFixDec32(in, FRAMESAMPLES, WebRtcIsacfix_kHPStCoeffOut2Q30, postfiltdata->HPstates2_fix);
351
352  for (k=0;k<FRAMESAMPLES;k++) {
353    out16[k] = in[k];
354  }
355}
356
357
358#ifdef WEBRTC_ISAC_FIX_NB_CALLS_ENABLED
359/* Function WebRtcIsacfix_FilterAndCombine */
360/* This is a decoder function that takes the decimated
361   length len/2 input low-pass and
362   high-pass signals and creates a reconstructed fullband
363   output signal of length len. WebRtcIsacfix_FilterAndCombine
364   is the sibling function of WebRtcIsacfix_SplitAndFilter */
365/* INPUTS:
366   inLP: a length len/2 array of input low-pass
367   samples.
368   inHP: a length len/2 array of input high-pass
369   samples.
370   postfiltdata: input data structure containing the filterbank
371   states from the previous decoding iteration.
372   OUTPUTS:
373   Out: a length len array of output reconstructed
374   samples (fullband) based on the input low-pass and
375   high-pass signals.
376   postfiltdata: the input data structure containing the filterbank
377   states is updated for the next decoding iteration */
378void WebRtcIsacfix_FilterAndCombine2(int16_t *tempin_ch1,
379                                     int16_t *tempin_ch2,
380                                     int16_t *out16,
381                                     PostFiltBankstr *postfiltdata,
382                                     int16_t len)
383{
384  int k;
385  int16_t in[FRAMESAMPLES];
386
387  /* all-pass filter the new upper and lower channel signal.
388     For upper channel, use the all-pass filter factors that were used as a
389     lower channel at the encoding side. So at the decoder, the corresponding
390     all-pass filter factors for each channel are swapped.
391     For lower channel signal, since all-pass filter factors at the decoder are
392     swapped from the ones at the encoder, the 'upper' channel all-pass filter
393     factors (kUpperApFactors) are used to filter this new lower channel signal.
394  */
395  WebRtcIsacfix_AllpassFilter2FixDec16(tempin_ch1,
396                                       tempin_ch2,
397                                       WebRtcIsacfix_kLowerApFactorsQ15,
398                                       WebRtcIsacfix_kUpperApFactorsQ15,
399                                       len / 2,
400                                       postfiltdata->STATE_0_UPPER_fix,
401                                       postfiltdata->STATE_0_LOWER_fix);
402
403  /* Merge outputs to form the full length output signal.*/
404  for (k=0;k<len/2;k++) {
405    in[2 * k] = tempin_ch2[k];
406    in[2 * k + 1] = tempin_ch1[k];
407  }
408
409  /* High pass filter */
410  WebRtcIsacfix_HighpassFilterFixDec32(in, len, WebRtcIsacfix_kHPStCoeffOut1Q30, postfiltdata->HPstates1_fix);
411  WebRtcIsacfix_HighpassFilterFixDec32(in, len, WebRtcIsacfix_kHPStCoeffOut2Q30, postfiltdata->HPstates2_fix);
412
413  for (k=0;k<len;k++) {
414    out16[k] = in[k];
415  }
416}
417
418#endif
419