• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /******************************************************************************
2  *                                                                            *
3  * Copyright (C) 2018 The Android Open Source Project
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at:
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  *
17  *****************************************************************************
18  * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19 */
20 #include <string.h>
21 #include "ixheaacd_sbr_common.h"
22 #include <ixheaacd_type_def.h>
23 
24 #include "ixheaacd_constants.h"
25 #include <ixheaacd_basic_ops32.h>
26 #include <ixheaacd_basic_ops16.h>
27 #include <ixheaacd_basic_ops40.h>
28 #include "ixheaacd_basic_ops_arr.h"
29 #include "ixheaacd_basic_ops.h"
30 
31 #include "ixheaacd_defines.h"
32 #include <ixheaacd_basic_op.h>
33 #include "ixheaacd_intrinsics.h"
34 #include "ixheaacd_common_rom.h"
35 #include "ixheaacd_basic_funcs.h"
36 #include "ixheaacd_bitbuffer.h"
37 #include "ixheaacd_sbrdecsettings.h"
38 #include "ixheaacd_defines.h"
39 
40 #include "ixheaacd_pns.h"
41 
42 #include <ixheaacd_aac_rom.h>
43 #include "ixheaacd_pulsedata.h"
44 
45 #include "ixheaacd_drc_data_struct.h"
46 #include "ixheaacd_lt_predict.h"
47 #include "ixheaacd_channelinfo.h"
48 #include "ixheaacd_drc_dec.h"
49 
50 #include "ixheaacd_sbrdecoder.h"
51 #include "ixheaacd_sbr_scale.h"
52 #include "ixheaacd_lpp_tran.h"
53 #include "ixheaacd_env_extr_part.h"
54 #include <ixheaacd_sbr_rom.h>
55 
56 #include "ixheaacd_hybrid.h"
57 #include "ixheaacd_ps_dec.h"
58 
59 #include "ixheaacd_env_extr.h"
60 
61 #include "ixheaacd_ps_dec.h"
62 
63 #include "ixheaacd_qmf_dec.h"
64 #include "ixheaacd_env_calc.h"
65 #include "ixheaacd_sbr_const.h"
66 
67 #include "ixheaacd_pvc_dec.h"
68 #include "ixheaacd_sbr_dec.h"
69 #include "ixheaacd_function_selector.h"
70 
ixheaacd_shl16_saturate(WORD16 op1,WORD16 shift)71 static PLATFORM_INLINE WORD16 ixheaacd_shl16_saturate(WORD16 op1,
72                                                       WORD16 shift) {
73   WORD16 var_out;
74   WORD32 temp;
75 
76   temp = (WORD32)(op1 << shift);
77   var_out = ixheaacd_sat16(temp);
78   return (var_out);
79 }
80 
ixheaacd_shl16_arr_saturate(WORD16 * word16_arr,WORD16 shift,WORD n)81 static PLATFORM_INLINE VOID ixheaacd_shl16_arr_saturate(WORD16 *word16_arr,
82                                                         WORD16 shift, WORD n) {
83   WORD i;
84 
85   for (i = n - 1; i >= 0; i--) {
86     *word16_arr = ixheaacd_shl16_saturate(*word16_arr, shift);
87     word16_arr++;
88   }
89 
90   return;
91 }
92 
ixheaacd_scale_short_vec_left(WORD16 * word16_arr,WORD32 n,WORD16 shift)93 VOID ixheaacd_scale_short_vec_left(WORD16 *word16_arr, WORD32 n, WORD16 shift) {
94   ixheaacd_shl16_arr_saturate(word16_arr, shift, n);
95 }
96 
ixheaacd_scale_int_vec_left(WORD32 * word32_arr,WORD32 n,WORD16 shift)97 VOID ixheaacd_scale_int_vec_left(WORD32 *word32_arr, WORD32 n, WORD16 shift) {
98   ixheaacd_shl32_arr_sat(word32_arr, shift, n);
99 }
100 
ixheaacd_scale_int_vec_right(WORD32 * word32_arr,WORD32 n,WORD16 shift)101 VOID ixheaacd_scale_int_vec_right(WORD32 *word32_arr, WORD32 n, WORD16 shift) {
102   ixheaacd_shr32_arr(word32_arr, shift, n);
103 }
104 
ixheaacd_scale_short_vec_right(WORD16 * word16_arr,WORD32 n,WORD16 shift)105 VOID ixheaacd_scale_short_vec_right(WORD16 *word16_arr, WORD32 n,
106                                     WORD16 shift) {
107   ixheaacd_shr16_arr(word16_arr, shift, n);
108 }
109 
ixheaacd_calc_max(WORD16 * array,WORD32 size)110 WORD32 ixheaacd_calc_max(WORD16 *array, WORD32 size) {
111   WORD n;
112   WORD32 max_val = 0;
113   WORD16 temp1, temp2;
114 
115   for (n = size; n != 0; n--) {
116     temp1 = *array++;
117     temp2 = *array++;
118 
119     max_val = max_val | ixheaacd_abs32_nrm(temp1);
120     max_val = max_val | ixheaacd_abs32_nrm(temp2);
121   }
122 
123   return max_val;
124 }
125 
ixheaacd_get_ps_scale(ia_ps_dec_struct * ptr_ps_dec)126 static WORD ixheaacd_get_ps_scale(ia_ps_dec_struct *ptr_ps_dec) {
127   WORD i, m, n, len;
128   WORD32 max_val = 0;
129   WORD16 *ptr_re;
130   WORD32 *ptr_re_temp, *ptr_im;
131 
132   for (m = 0; m < 2; m++) {
133     ptr_re = &ptr_ps_dec->delay_buf_qmf_ap_re_im[m][2 * 3];
134     max_val |=
135         ixheaacd_calc_max(ptr_re, NUM_OF_QUAD_MIRROR_FILTER_ALL_PASS_CHNLS);
136   }
137 
138   ptr_re = (WORD16 *)ptr_ps_dec->delay_buf_qmf_ld_re_im;
139 
140   max_val |= ixheaacd_calc_max(ptr_re, HIGH_DEL * SMALL_DEL_STRT);
141 
142   ptr_re = (WORD16 *)ptr_ps_dec->delay_buf_qmf_sd_re_im;
143 
144   max_val |= ixheaacd_calc_max(
145       ptr_re, (SMALL_DEL *
146                (NUM_OF_QUAD_MIRROR_FILTER_ICC_CHNLS -
147                 (NUM_OF_QUAD_MIRROR_FILTER_ALL_PASS_CHNLS + SMALL_DEL_STRT))));
148 
149   ptr_re = (WORD16 *)ptr_ps_dec->delay_buf_qmf_sub_re_im;
150 
151   max_val |= ixheaacd_calc_max(ptr_re, 16 * DEL_ALL_PASS);
152 
153   for (i = 0; i < NUM_SER_AP_LINKS; i++) {
154     for (m = 0; m < ptr_ps_dec->delay_sample_ser[i]; m++) {
155       ptr_re = &ptr_ps_dec->delay_buf_qmf_ser_re_im[m][i][2 * 3];
156 
157       max_val |=
158           ixheaacd_calc_max(ptr_re, NUM_OF_QUAD_MIRROR_FILTER_ALL_PASS_CHNLS);
159     }
160   }
161 
162   ptr_re = (WORD16 *)ptr_ps_dec->delay_buf_qmf_sub_ser_re_im;
163   max_val |= ixheaacd_calc_max(ptr_re, NUM_SER_AP_LINKS * 5 * 16);
164 
165   max_val = max_val << 16;
166 
167   len = ptr_ps_dec->str_hybrid.ptr_qmf_buf;
168 
169   for (i = 0; i < NO_QMF_CHANNELS_IN_HYBRID; i++) {
170     ptr_re_temp = &ptr_ps_dec->str_hybrid.ptr_qmf_buf_re[i][0];
171     ptr_im = &ptr_ps_dec->str_hybrid.ptr_qmf_buf_im[i][0];
172 
173     for (n = len; n != 0; n--) {
174       WORD32 temp3 = *ptr_re_temp++;
175       WORD32 temp4 = *ptr_im++;
176 
177       max_val = max_val | ixheaacd_abs32_nrm(temp3);
178       max_val = max_val | ixheaacd_abs32_nrm(temp4);
179     }
180   }
181 
182   return ixheaacd_pnorm32(max_val);
183 }
184 
ixheaacd_init_ps_scale(ia_ps_dec_struct * ptr_ps_dec,ia_sbr_scale_fact_struct * sbr_scale_factor)185 VOID ixheaacd_init_ps_scale(ia_ps_dec_struct *ptr_ps_dec,
186                             ia_sbr_scale_fact_struct *sbr_scale_factor)
187 
188 {
189   WORD32 reserve, change;
190   WORD16 temp;
191 
192   reserve = ixheaacd_get_ps_scale(ptr_ps_dec);
193 
194   ptr_ps_dec->delay_buffer_scale = (ptr_ps_dec->delay_buffer_scale + reserve);
195   temp =
196       ixheaacd_min16(sbr_scale_factor->lb_scale, sbr_scale_factor->ov_lb_scale);
197   temp = ixheaacd_min16(temp, sbr_scale_factor->hb_scale);
198   temp = ixheaacd_min16(temp, ptr_ps_dec->delay_buffer_scale);
199   sbr_scale_factor->ps_scale = (temp - 1);
200 
201   change = (sbr_scale_factor->ps_scale - ptr_ps_dec->delay_buffer_scale);
202   change = (change + reserve);
203 
204   ixheaacd_scale_ps_states(ptr_ps_dec, (WORD16)change);
205 
206   ptr_ps_dec->delay_buffer_scale = sbr_scale_factor->ps_scale;
207 }
208 
ixheaacd_divide16_pos_dec(WORD32 op1,WORD32 op2)209 WORD32 ixheaacd_divide16_pos_dec(WORD32 op1, WORD32 op2) {
210   UWORD32 v;
211   UWORD32 u;
212   WORD k, nrm;
213 
214   nrm = ixheaacd_norm32(op2);
215   u = (op1 << nrm);
216   v = (op2 << nrm);
217   u = (u & 0xffff0000);
218   v = (v & 0xffff0000);
219 
220   if (u != 0) {
221     for (k = 16; k > 0; k--) {
222       if (u >= (UWORD32)v) {
223         u = ((u - v) << 1) + 1;
224       } else {
225         u = (u << 1);
226       }
227     }
228   }
229 
230   return (u);
231 }
232 
ixheaacd_decorr_filter1_dec(ia_ps_dec_struct * ptr_ps_dec,ia_ps_tables_struct * ps_tables_ptr,WORD16 * transient_ratio)233 VOID ixheaacd_decorr_filter1_dec(ia_ps_dec_struct *ptr_ps_dec,
234                                  ia_ps_tables_struct *ps_tables_ptr,
235                                  WORD16 *transient_ratio) {
236   WORD sb;
237   WORD m;
238 
239   WORD16 delay_buf_idx;
240   WORD16 *p_delay_buf_sub_re_im;
241   WORD16 *p_frac_delay_phase_fac_ser_re_im, *p_frac_delay_phase_fac_ser_re_im1;
242 
243   const WORD16 *p_frac_delay_phase_fac_re_im;
244   REVERB_BUFFERS_CH_RI *p_delay_buf_ser_sub_re_im;
245 
246   WORD32 *p_left_real;
247   WORD32 *p_left_imag;
248   WORD32 *p_right_real;
249   WORD32 *p_right_imag;
250 
251   p_frac_delay_phase_fac_re_im =
252       &ps_tables_ptr->frac_delay_phase_fac_qmf_sub_re_im[0];
253   p_delay_buf_ser_sub_re_im = &ptr_ps_dec->delay_buf_qmf_sub_ser_re_im;
254   p_frac_delay_phase_fac_ser_re_im =
255       &ps_tables_ptr->frac_delay_phase_fac_qmf_sub_ser_re_im[0][0];
256 
257   p_left_real = ptr_ps_dec->ptr_hyb_left_re;
258   p_left_imag = ptr_ps_dec->ptr_hyb_left_im;
259   p_right_real = ptr_ps_dec->ptr_hyb_right_re;
260   p_right_imag = ptr_ps_dec->ptr_hyb_right_im;
261 
262   delay_buf_idx = ptr_ps_dec->delay_buf_idx;
263   p_delay_buf_sub_re_im =
264       &ptr_ps_dec->delay_buf_qmf_sub_re_im[delay_buf_idx][0];
265   for (sb = 0; sb < SUBQMF_GROUPS; sb++) {
266     WORD16 real_tmp, imag_tmp, real_tmp0, imag_tmp0, real_in, imag_in, bin;
267 
268     real_tmp0 = p_delay_buf_sub_re_im[0];
269     imag_tmp0 = p_delay_buf_sub_re_im[1];
270 
271     real_in = (WORD16)(
272         ixheaacd_sub32_sat(
273             ixheaacd_mult16x16in32(real_tmp0, p_frac_delay_phase_fac_re_im[0]),
274             ixheaacd_mult16x16in32(imag_tmp0,
275                                    p_frac_delay_phase_fac_re_im[1])) >>
276         15);
277     imag_in = (WORD16)(
278         ixheaacd_add32_sat(
279             ixheaacd_mult16x16in32(real_tmp0, p_frac_delay_phase_fac_re_im[1]),
280             ixheaacd_mult16x16in32(imag_tmp0,
281                                    p_frac_delay_phase_fac_re_im[0])) >>
282         15);
283     *p_delay_buf_sub_re_im++ = ixheaacd_round16(p_left_real[sb]);
284     *p_delay_buf_sub_re_im++ = ixheaacd_round16(p_left_imag[sb]);
285     p_frac_delay_phase_fac_re_im += 2;
286 
287     p_frac_delay_phase_fac_ser_re_im1 = p_frac_delay_phase_fac_ser_re_im;
288     p_frac_delay_phase_fac_ser_re_im += 2;
289 
290     for (m = 0; m < NUM_SER_AP_LINKS; m++) {
291       WORD16 decay;
292       WORD16 delay_buf_idx_ser;
293       delay_buf_idx_ser = ptr_ps_dec->delay_buf_idx_ser[m];
294       real_tmp0 = (*p_delay_buf_ser_sub_re_im)[delay_buf_idx_ser][m][2 * sb];
295       imag_tmp0 =
296           (*p_delay_buf_ser_sub_re_im)[delay_buf_idx_ser][m][2 * sb + 1];
297 
298       real_tmp =
299           (WORD16)(ixheaacd_sub32_sat(
300                        ixheaacd_mult16x16in32(
301                            real_tmp0, p_frac_delay_phase_fac_ser_re_im1[0]),
302                        ixheaacd_mult16x16in32(
303                            imag_tmp0, p_frac_delay_phase_fac_ser_re_im1[1])) >>
304                    15);
305       imag_tmp =
306           (WORD16)(ixheaacd_add32_sat(
307                        ixheaacd_mult16x16in32(
308                            real_tmp0, p_frac_delay_phase_fac_ser_re_im1[1]),
309                        ixheaacd_mult16x16in32(
310                            imag_tmp0, p_frac_delay_phase_fac_ser_re_im1[0])) >>
311                    15);
312 
313       decay = ps_tables_ptr->rev_link_decay_ser[m];
314 
315       real_tmp = ixheaacd_sub16(real_tmp, ixheaacd_mult16_shl(real_in, decay));
316       imag_tmp = ixheaacd_sub16(imag_tmp, ixheaacd_mult16_shl(imag_in, decay));
317 
318       (*p_delay_buf_ser_sub_re_im)[delay_buf_idx_ser][m][sb * 2] =
319           ixheaacd_add16(real_in, ixheaacd_mult16_shl(real_tmp, decay));
320       (*p_delay_buf_ser_sub_re_im)[delay_buf_idx_ser][m][sb * 2 + 1] =
321           ixheaacd_add16(imag_in, ixheaacd_mult16_shl(imag_tmp, decay));
322 
323       real_in = real_tmp;
324       imag_in = imag_tmp;
325       p_frac_delay_phase_fac_ser_re_im1 += 32;
326     }
327 
328     bin = ps_tables_ptr->hybrid_to_bin[sb];
329     p_right_real[sb] =
330         ixheaacd_mult16x16in32_shl(real_in, transient_ratio[bin]);
331     p_right_imag[sb] =
332         ixheaacd_mult16x16in32_shl(imag_in, transient_ratio[bin]);
333   }
334 }
335 
ixheaacd_decorr_filter2_dec(ia_ps_dec_struct * ptr_ps_dec,WORD32 * p_buf_left_real,WORD32 * p_buf_left_imag,WORD32 * p_buf_right_real,WORD32 * p_buf_right_imag,ia_ps_tables_struct * ps_tables_ptr,WORD16 * transient_ratio)336 VOID ixheaacd_decorr_filter2_dec(
337     ia_ps_dec_struct *ptr_ps_dec, WORD32 *p_buf_left_real,
338     WORD32 *p_buf_left_imag, WORD32 *p_buf_right_real, WORD32 *p_buf_right_imag,
339     ia_ps_tables_struct *ps_tables_ptr, WORD16 *transient_ratio) {
340   WORD sb, di, sb_delay;
341   WORD m, bin;
342   WORD32 *p_left_real;
343   WORD32 *p_left_imag;
344   WORD32 *p_right_real;
345   WORD32 *p_right_imag;
346   WORD16 delay_buf_idx;
347   REVERB_BUFFERS_RI *p_delay_buf_ser_re_im;
348   WORD16 *p_delay_buf_ap_re_im;
349   const WORD16 *p_frac_delay_phase_fac_re_im;
350   WORD16 *p_frac_delay_phase_fac_ser_ap_re_im,
351       *p_frac_delay_phase_fac_ser_ap_re_im_temp;
352 
353   p_left_real = p_buf_left_real;
354   p_left_imag = p_buf_left_imag;
355   p_right_real = p_buf_right_real;
356   p_right_imag = p_buf_right_imag;
357 
358   p_delay_buf_ser_re_im = &ptr_ps_dec->delay_buf_qmf_ser_re_im;
359   p_frac_delay_phase_fac_re_im = ps_tables_ptr->frac_delay_phase_fac_qmf_re_im;
360   p_frac_delay_phase_fac_ser_ap_re_im =
361       &ps_tables_ptr->frac_delay_phase_fac_qmf_ser_re_im[0][0];
362 
363   delay_buf_idx = ptr_ps_dec->delay_buf_idx;
364 
365   p_delay_buf_ap_re_im = &ptr_ps_dec->delay_buf_qmf_ap_re_im[delay_buf_idx][0];
366   p_frac_delay_phase_fac_re_im += 6;
367   p_frac_delay_phase_fac_ser_ap_re_im += 6;
368   p_delay_buf_ap_re_im += 6;
369 
370   for (sb = 3, di = 9; sb < 23; sb++) {
371     WORD16 real_tmp, imag_tmp, real_tmp0, imag_tmp0, real_in, imag_in;
372 
373     sb_delay = sb;
374 
375     real_tmp0 = p_delay_buf_ap_re_im[0];
376     imag_tmp0 = p_delay_buf_ap_re_im[1];
377 
378     real_in = (WORD16)(
379         ixheaacd_sub32_sat(
380             ixheaacd_mult16x16in32(real_tmp0, p_frac_delay_phase_fac_re_im[0]),
381             ixheaacd_mult16x16in32(imag_tmp0,
382                                    p_frac_delay_phase_fac_re_im[1])) >>
383         15);
384     imag_in = (WORD16)(
385         ixheaacd_add32_sat(
386             ixheaacd_mult16x16in32(real_tmp0, p_frac_delay_phase_fac_re_im[1]),
387             ixheaacd_mult16x16in32(imag_tmp0,
388                                    p_frac_delay_phase_fac_re_im[0])) >>
389         15);
390 
391     *p_delay_buf_ap_re_im++ = ixheaacd_round16(p_left_real[sb]);
392     *p_delay_buf_ap_re_im++ = ixheaacd_round16(p_left_imag[sb]);
393 
394     p_frac_delay_phase_fac_re_im += 2;
395 
396     p_frac_delay_phase_fac_ser_ap_re_im_temp =
397         p_frac_delay_phase_fac_ser_ap_re_im;
398     p_frac_delay_phase_fac_ser_ap_re_im += 2;
399 
400     for (m = 0; m < NUM_SER_AP_LINKS; m++, di++) {
401       WORD16 decay;
402       WORD16 delay_buf_idx_ser;
403       delay_buf_idx_ser = ptr_ps_dec->delay_buf_idx_ser[m];
404 
405       real_tmp0 = (*p_delay_buf_ser_re_im)[delay_buf_idx_ser][m][sb_delay * 2];
406       imag_tmp0 =
407           (*p_delay_buf_ser_re_im)[delay_buf_idx_ser][m][sb_delay * 2 + 1];
408 
409       real_tmp = (WORD16)(
410           ixheaacd_sub32_sat(
411               ixheaacd_mult16x16in32(
412                   real_tmp0, p_frac_delay_phase_fac_ser_ap_re_im_temp[0]),
413               ixheaacd_mult16x16in32(
414                   imag_tmp0, p_frac_delay_phase_fac_ser_ap_re_im_temp[1])) >>
415           15);
416       imag_tmp = (WORD16)(
417           ixheaacd_add32_sat(
418               ixheaacd_mult16x16in32(
419                   real_tmp0, p_frac_delay_phase_fac_ser_ap_re_im_temp[1]),
420               ixheaacd_mult16x16in32(
421                   imag_tmp0, p_frac_delay_phase_fac_ser_ap_re_im_temp[0])) >>
422           15);
423 
424       decay = ps_tables_ptr->decay_scale_factor[di];
425 
426       real_tmp = ixheaacd_sub16(real_tmp, ixheaacd_mult16_shl(real_in, decay));
427       imag_tmp = ixheaacd_sub16(imag_tmp, ixheaacd_mult16_shl(imag_in, decay));
428 
429       (*p_delay_buf_ser_re_im)[delay_buf_idx_ser][m][sb_delay * 2] =
430           ixheaacd_add16(real_in, ixheaacd_mult16_shl(real_tmp, decay));
431       (*p_delay_buf_ser_re_im)[delay_buf_idx_ser][m][sb_delay * 2 + 1] =
432           ixheaacd_add16(imag_in, ixheaacd_mult16_shl(imag_tmp, decay));
433 
434       real_in = real_tmp;
435       imag_in = imag_tmp;
436       p_frac_delay_phase_fac_ser_ap_re_im_temp += 64;
437     }
438 
439     bin = ps_tables_ptr->delay_to_bin[sb_delay];
440     p_right_real[sb] =
441         ixheaacd_mult16x16in32_shl(real_in, transient_ratio[bin]);
442     p_right_imag[sb] =
443         ixheaacd_mult16x16in32_shl(imag_in, transient_ratio[bin]);
444   }
445 }
446 
ixheaacd_decorrelation_dec(ia_ps_dec_struct * ptr_ps_dec,WORD32 * p_buf_left_real,WORD32 * p_buf_left_imag,WORD32 * p_buf_right_real,WORD32 * p_buf_right_imag,ia_ps_tables_struct * ps_tables_ptr)447 VOID ixheaacd_decorrelation_dec(ia_ps_dec_struct *ptr_ps_dec,
448                                 WORD32 *p_buf_left_real,
449                                 WORD32 *p_buf_left_imag,
450                                 WORD32 *p_buf_right_real,
451                                 WORD32 *p_buf_right_imag,
452                                 ia_ps_tables_struct *ps_tables_ptr) {
453   WORD sb;
454 
455   WORD gr, bin, sband, maxsband;
456 
457   WORD32 peak_diff, nrg;
458   WORD32 power_buf[NUM_OF_BINS];
459   WORD16 transient_ratio[NUM_OF_BINS + 1];
460 
461   WORD32 *p_left_real;
462   WORD32 *p_left_imag;
463   WORD32 *p_right_real;
464   WORD32 *p_right_imag;
465 
466   WORD16 *p_delay_buf_re_im_ld;
467   WORD16 *p_delay_buf_re_im_sd;
468 
469   WORD usb = ptr_ps_dec->usb;
470   WORD16 delay_buf_idx;
471 
472   p_left_real = ptr_ps_dec->ptr_hyb_left_re;
473   p_left_imag = ptr_ps_dec->ptr_hyb_left_im;
474   p_right_real = ptr_ps_dec->ptr_hyb_right_re;
475   p_right_imag = ptr_ps_dec->ptr_hyb_right_im;
476 
477   {
478     WORD32 re0, im0, re1, im1;
479 
480     re0 = (p_left_real[0]);
481     im0 = (p_left_imag[0]);
482     re1 = (p_left_real[5]);
483     im1 = (p_left_imag[5]);
484 
485     power_buf[0] = ixheaacd_mult32x16in32(re0, (WORD16)(re0 >> 16));
486     power_buf[0] = ixheaacd_add32_sat(
487         power_buf[0], ixheaacd_mult32x16in32(im0, (WORD16)(im0 >> 16)));
488     power_buf[0] = ixheaacd_add32_sat(
489         power_buf[0], ixheaacd_mult32x16in32(re1, (WORD16)(re1 >> 16)));
490     power_buf[0] = ixheaacd_add32_sat(
491         power_buf[0], ixheaacd_mult32x16in32(im1, (WORD16)(im1 >> 16)));
492 
493     re0 = (p_left_real[4]);
494     im0 = (p_left_imag[4]);
495     re1 = (p_left_real[1]);
496     im1 = (p_left_imag[1]);
497 
498     power_buf[1] = ixheaacd_mult32x16in32(re0, (WORD16)(re0 >> 16));
499     power_buf[1] = ixheaacd_add32_sat(
500         power_buf[1], ixheaacd_mult32x16in32(im0, (WORD16)(im0 >> 16)));
501     power_buf[1] = ixheaacd_add32_sat(
502         power_buf[1], ixheaacd_mult32x16in32(re1, (WORD16)(re1 >> 16)));
503     power_buf[1] = ixheaacd_add32_sat(
504         power_buf[1], ixheaacd_mult32x16in32(im1, (WORD16)(im1 >> 16)));
505   }
506 
507   bin = 4 - 2;
508   for (gr = 4; gr < SUBQMF_GROUPS; gr++) {
509     WORD32 re, im;
510     sb = ps_tables_ptr->borders_group[gr];
511     re = (p_left_real[sb]);
512     im = (p_left_imag[sb]);
513     power_buf[bin] = ixheaacd_mult32x16in32(re, (WORD16)(re >> 16));
514     power_buf[bin] = ixheaacd_add32_sat(
515         power_buf[bin], ixheaacd_mult32x16in32(im, (WORD16)(im >> 16)));
516     bin++;
517   }
518 
519   p_left_real = p_buf_left_real;
520   p_left_imag = p_buf_left_imag;
521 
522   bin = NO_QMF_CHANNELS_IN_HYBRID + 5;
523   for (sband = NO_QMF_CHANNELS_IN_HYBRID; sband < NO_QMF_CHANNELS_IN_HYBRID + 6;
524        sband++) {
525     WORD32 re = (p_left_real[sband]);
526     WORD32 im = (p_left_imag[sband]);
527     power_buf[bin] = ixheaacd_mult32x16in32(re, (WORD16)(re >> 16));
528     power_buf[bin] = ixheaacd_add32_sat(
529         power_buf[bin], ixheaacd_mult32x16in32(im, (WORD16)(im >> 16)));
530     bin++;
531   }
532 
533   bin = 16 - 2;
534   for (gr = 16; gr < NO_IID_GROUPS; gr++) {
535     WORD32 accu = 0, tmp;
536     WORD32 re, im;
537 
538     maxsband = ixheaacd_min32(usb, ps_tables_ptr->borders_group[gr + 1]);
539 
540     for (sband = ps_tables_ptr->borders_group[gr]; sband < maxsband; sband++) {
541       re = (p_left_real[sband]);
542       im = (p_left_imag[sband]);
543 
544       tmp = ixheaacd_mult32x16in32(re, (WORD16)(re >> 16));
545       tmp = ixheaacd_add32_sat(tmp,
546                                ixheaacd_mult32x16in32(im, (WORD16)(im >> 16)));
547       tmp = (tmp >> ps_tables_ptr->group_shift[gr - (SUBQMF_GROUPS + 6)]);
548 
549       accu = ixheaacd_add32_sat(accu, tmp);
550     }
551     power_buf[bin] = accu;
552     bin++;
553   }
554 
555   p_left_real = ptr_ps_dec->ptr_hyb_left_re;
556   p_left_imag = ptr_ps_dec->ptr_hyb_left_im;
557 
558   for (bin = 0; bin < NUM_OF_BINS; bin++) {
559     power_buf[bin] = ixheaacd_shl32(power_buf[bin], 1);
560 
561     power_buf[bin] = ixheaacd_max32(0, power_buf[bin]);
562 
563     ptr_ps_dec->peak_decay_diff[bin] = ixheaacd_mult32x16in32_shl(
564         ptr_ps_dec->peak_decay_diff[bin], PEAK_DECAYING_FACT);
565 
566     ptr_ps_dec->peak_decay_diff[bin] =
567         ixheaacd_max32(ptr_ps_dec->peak_decay_diff[bin], power_buf[bin]);
568 
569     peak_diff = ixheaacd_add32_sat(
570         ixheaacd_mult32x16in32_shl(ptr_ps_dec->peak_decay_diff_prev[bin],
571                                    0x6000),
572         ((ixheaacd_sub32_sat(ptr_ps_dec->peak_decay_diff[bin],
573                              power_buf[bin]) >>
574           2)));
575 
576     ptr_ps_dec->peak_decay_diff_prev[bin] = peak_diff;
577 
578     nrg = ixheaacd_add32_sat(
579         ixheaacd_mult32x16in32_shl(ptr_ps_dec->energy_prev[bin], 0x6000),
580         (power_buf[bin] >> 2));
581     ptr_ps_dec->energy_prev[bin] = nrg;
582 
583     peak_diff = ixheaacd_add32_sat(peak_diff, (peak_diff >> 1));
584 
585     if (peak_diff <= nrg) {
586       transient_ratio[bin] = 0x7fff;
587     } else {
588       transient_ratio[bin] =
589           ixheaacd_extract16l((*ixheaacd_divide16_pos)(nrg, peak_diff));
590     }
591   }
592 
593   (*ixheaacd_decorr_filter1)(ptr_ps_dec, ps_tables_ptr, transient_ratio);
594 
595   transient_ratio[20] = 0;
596 
597   (*ixheaacd_decorr_filter2)(ptr_ps_dec, p_buf_left_real, p_buf_left_imag,
598                              p_buf_right_real, p_buf_right_imag, ps_tables_ptr,
599                              transient_ratio);
600 
601   {
602     WORD16 trans_ratio = transient_ratio[18];
603 
604     p_left_real = p_buf_left_real;
605     p_left_imag = p_buf_left_imag;
606     p_right_real = p_buf_right_real;
607     p_right_imag = p_buf_right_imag;
608 
609     maxsband = ixheaacd_min32((WORD16)usb, ps_tables_ptr->borders_group[21]);
610     delay_buf_idx = ptr_ps_dec->delay_buf_idx_long;
611     p_delay_buf_re_im_ld =
612         &ptr_ps_dec->delay_buf_qmf_ld_re_im[delay_buf_idx][0];
613 
614     for (sband = ps_tables_ptr->borders_group[20]; sband < maxsband; sband++) {
615       WORD16 real_in, imag_in;
616 
617       real_in = p_delay_buf_re_im_ld[0];
618       imag_in = p_delay_buf_re_im_ld[1];
619       *p_delay_buf_re_im_ld++ = ixheaacd_round16(p_left_real[sband]);
620       *p_delay_buf_re_im_ld++ = ixheaacd_round16(p_left_imag[sband]);
621 
622       p_right_real[sband] = ixheaacd_mult16x16in32_shl(real_in, trans_ratio);
623       p_right_imag[sband] = ixheaacd_mult16x16in32_shl(imag_in, trans_ratio);
624     }
625 
626     ptr_ps_dec->delay_buf_idx_long =
627         ixheaacd_add16(ptr_ps_dec->delay_buf_idx_long, 1);
628 
629     if (ptr_ps_dec->delay_buf_idx_long >= 14) {
630       ptr_ps_dec->delay_buf_idx_long = 0;
631     }
632 
633     p_delay_buf_re_im_sd = &ptr_ps_dec->delay_buf_qmf_sd_re_im[0][0];
634 
635     trans_ratio = transient_ratio[19];
636     maxsband = ixheaacd_min32((WORD16)usb, ps_tables_ptr->borders_group[22]);
637     for (sband = ps_tables_ptr->borders_group[21]; sband < maxsband; sband++) {
638       WORD16 real_in, imag_in;
639 
640       real_in = p_delay_buf_re_im_sd[0];
641       imag_in = p_delay_buf_re_im_sd[1];
642       *p_delay_buf_re_im_sd++ = ixheaacd_round16(p_left_real[sband]);
643       *p_delay_buf_re_im_sd++ = ixheaacd_round16(p_left_imag[sband]);
644 
645       p_right_real[sband] = ixheaacd_mult16x16in32_shl(real_in, trans_ratio);
646       p_right_imag[sband] = ixheaacd_mult16x16in32_shl(imag_in, trans_ratio);
647     }
648   }
649 
650   for (sband = usb; sband < NO_SYNTHESIS_CHANNELS; sband++) {
651     p_right_real[sband] = 0;
652     p_right_imag[sband] = 0;
653   }
654 
655   ptr_ps_dec->delay_buf_idx = (WORD16)(ptr_ps_dec->delay_buf_idx + 1);
656   if (ptr_ps_dec->delay_buf_idx >= DEL_ALL_PASS) {
657     ptr_ps_dec->delay_buf_idx = 0;
658   }
659 
660   {
661     WORD delay_m;
662 
663     for (delay_m = 0; delay_m < NUM_SER_AP_LINKS; delay_m++) {
664       ptr_ps_dec->delay_buf_idx_ser[delay_m] =
665           (ptr_ps_dec->delay_buf_idx_ser[delay_m] + 1);
666       if (ptr_ps_dec->delay_buf_idx_ser[delay_m] >=
667           ptr_ps_dec->delay_sample_ser[delay_m]) {
668         ptr_ps_dec->delay_buf_idx_ser[delay_m] = 0;
669       }
670     }
671   }
672 }
673 
ixheaacd_cos512(WORD phi_by_4,const WORD16 * cos_sin_lookup_tab)674 static WORD16 ixheaacd_cos512(WORD phi_by_4, const WORD16 *cos_sin_lookup_tab) {
675   WORD index;
676   index = ixheaacd_round16(ixheaacd_abs32_sat(phi_by_4));
677 
678   index = (index & 0x3FF);
679 
680   if (index < 512) {
681     return cos_sin_lookup_tab[512 - index];
682   } else {
683     return (WORD16)(-(cos_sin_lookup_tab[index - 512]));
684   }
685 }
686 
ixheaacd_sin512(WORD phi_by_4,const WORD16 * cos_sin_lookup_tab)687 static WORD16 ixheaacd_sin512(WORD phi_by_4, const WORD16 *cos_sin_lookup_tab) {
688   WORD index;
689 
690   index = ixheaacd_round16(phi_by_4);
691 
692   if (index < 0) {
693     index = (-(index)&0x3FF);
694 
695     if (index < 512) {
696       return (WORD16)(-cos_sin_lookup_tab[index]);
697     } else {
698       return (WORD16)(-cos_sin_lookup_tab[1024 - index]);
699     }
700   } else {
701     index = (index & 0x3FF);
702 
703     if (index < 512) {
704       return cos_sin_lookup_tab[index];
705     } else {
706       return cos_sin_lookup_tab[1024 - index];
707     }
708   }
709 }
710 
ixheaacd_init_rot_env(ia_ps_dec_struct * ptr_ps_dec,WORD16 env,WORD16 usb,ia_sbr_tables_struct * sbr_tables_ptr,const WORD16 * cos_sin_lookup_tab)711 VOID ixheaacd_init_rot_env(ia_ps_dec_struct *ptr_ps_dec, WORD16 env, WORD16 usb,
712                            ia_sbr_tables_struct *sbr_tables_ptr,
713                            const WORD16 *cos_sin_lookup_tab) {
714   WORD group, bin, num_iid_steps;
715   WORD16 c2, c1;
716   WORD32 alpha, beta;
717   WORD16 h11, h12, h21, h22;
718   WORD16 inv_env_len;
719   const WORD16 *p_scale_factors;
720   WORD16 *p_iid_idx;
721   WORD indexplusa, indexminusa;
722 
723   const WORD32 rescale = (0x0517cc1b << 1);
724 
725   if (env == 0) {
726     WORD usb_prev = ptr_ps_dec->usb;
727     WORD16 *ptr_tmp;
728     ptr_ps_dec->usb = usb;
729 
730     if ((usb > usb_prev) && usb_prev) {
731       WORD i, j, delay, offset1;
732       WORD ixheaacd_drc_offset =
733           (usb < NUM_OF_QUAD_MIRROR_FILTER_ALL_PASS_CHNLS
734                ? usb
735                : NUM_OF_QUAD_MIRROR_FILTER_ALL_PASS_CHNLS);
736 
737       if (ixheaacd_drc_offset > usb_prev) {
738         for (i = 0; i < NUM_SER_AP_LINKS; i++) {
739           for (j = 0; j < ptr_ps_dec->delay_sample_ser[i]; j++) {
740             ptr_tmp = &ptr_ps_dec->delay_buf_qmf_ser_re_im[j][i][usb_prev * 2];
741 
742             memset(ptr_tmp, 0,
743                    sizeof(WORD16) * (ixheaacd_drc_offset - usb_prev) * 2);
744           }
745         }
746       }
747 
748       offset1 =
749           (usb < (NUM_OF_QUAD_MIRROR_FILTER_ALL_PASS_CHNLS + SMALL_DEL_STRT)
750                ? usb
751                : (NUM_OF_QUAD_MIRROR_FILTER_ALL_PASS_CHNLS + SMALL_DEL_STRT));
752       delay = HIGH_DEL;
753 
754       if ((offset1 >= ixheaacd_drc_offset) && (offset1 <= SMALL_DEL_STRT)) {
755         for (i = 0; i < delay; i++) {
756           ptr_tmp =
757               &ptr_ps_dec->delay_buf_qmf_ld_re_im[i][ixheaacd_drc_offset * 2];
758 
759           memset(ptr_tmp, 0,
760                  sizeof(WORD16) * 2 * (offset1 - ixheaacd_drc_offset));
761         }
762       }
763 
764       delay = SMALL_DEL;
765 
766       if ((usb >= offset1) && (usb <= 16)) {
767         for (i = 0; i < delay; i++) {
768           ptr_tmp = &ptr_ps_dec->delay_buf_qmf_sd_re_im[i][offset1 * 2];
769 
770           memset(ptr_tmp, 0, sizeof(WORD16) * 2 * (usb - offset1));
771         }
772       }
773     }
774   }
775 
776   if (ptr_ps_dec->iid_quant) {
777     num_iid_steps = NUM_IID_LEVELS_FINE;
778     p_scale_factors = sbr_tables_ptr->ps_tables_ptr->scale_factors_fine;
779   } else {
780     num_iid_steps = NUM_IID_LEVELS;
781     p_scale_factors = sbr_tables_ptr->ps_tables_ptr->scale_factors;
782   }
783 
784   inv_env_len =
785       sbr_tables_ptr->env_calc_tables_ptr->sbr_inv_int_table[ixheaacd_abs16(
786           ixheaacd_sub16_sat(ptr_ps_dec->border_position[env + 1],
787                              ptr_ps_dec->border_position[env]))];
788 
789   p_iid_idx = &ptr_ps_dec->iid_par_table[env][0];
790 
791   for (group = 0; group < NO_IID_GROUPS; group++) {
792     WORD16 bplusa, bminusa;
793     WORD num_iid_idx, num_icc_idx;
794 
795     bin = sbr_tables_ptr->ps_tables_ptr->group_to_bin[group];
796 
797     num_iid_idx = p_iid_idx[bin];
798     num_icc_idx = p_iid_idx[bin + 238];
799 
800     c1 = p_scale_factors[(num_iid_steps + num_iid_idx)];
801     c2 = p_scale_factors[(num_iid_steps - num_iid_idx)];
802 
803     beta = ixheaacd_mult32x16in32_shl(
804         ixheaacd_mult16x16in32_shl(
805             sbr_tables_ptr->ps_tables_ptr->alpha_values[num_icc_idx],
806             ixheaacd_sub16(c1, c2)),
807         PSC_SQRT05F);
808     alpha = ixheaacd_shr32_dir_sat_limit(
809         ixheaacd_deposit16h_in32(
810             sbr_tables_ptr->ps_tables_ptr->alpha_values[num_icc_idx]),
811         1);
812 
813     bplusa = ixheaacd_round16(ixheaacd_add32_sat(beta, alpha));
814     bminusa = ixheaacd_round16(ixheaacd_sub32_sat(beta, alpha));
815 
816     indexplusa = ixheaacd_mult32x16in32(rescale, bplusa);
817     indexminusa = ixheaacd_mult32x16in32(rescale, bminusa);
818 
819     h11 = ixheaacd_mult16_shl(ixheaacd_cos512(indexplusa, cos_sin_lookup_tab),
820                               c2);
821     h12 = ixheaacd_mult16_shl(ixheaacd_cos512(indexminusa, cos_sin_lookup_tab),
822                               c1);
823     h21 = ixheaacd_mult16_shl(ixheaacd_sin512(indexplusa, cos_sin_lookup_tab),
824                               c2);
825     h22 = ixheaacd_mult16_shl(ixheaacd_sin512(indexminusa, cos_sin_lookup_tab),
826                               c1);
827 
828     ptr_ps_dec->delta_h11_h12[2 * group + 0] = ixheaacd_mult16_shl(
829         inv_env_len,
830         ixheaacd_sub16(h11, ptr_ps_dec->h11_h12_vec[2 * group + 0]));
831     ptr_ps_dec->delta_h11_h12[2 * group + 1] = ixheaacd_mult16_shl(
832         inv_env_len,
833         ixheaacd_sub16(h12, ptr_ps_dec->h11_h12_vec[2 * group + 1]));
834     ptr_ps_dec->delta_h21_h22[2 * group + 0] = ixheaacd_mult16_shl(
835         inv_env_len,
836         ixheaacd_sub16(h21, ptr_ps_dec->h21_h22_vec[2 * group + 0]));
837     ptr_ps_dec->delta_h21_h22[2 * group + 1] = ixheaacd_mult16_shl(
838         inv_env_len,
839         ixheaacd_sub16(h22, ptr_ps_dec->h21_h22_vec[2 * group + 1]));
840 
841     ptr_ps_dec->H11_H12[2 * group + 0] = ptr_ps_dec->h11_h12_vec[2 * group + 0];
842     ptr_ps_dec->H11_H12[2 * group + 1] = ptr_ps_dec->h11_h12_vec[2 * group + 1];
843     ptr_ps_dec->H21_H22[2 * group + 0] = ptr_ps_dec->h21_h22_vec[2 * group + 0];
844     ptr_ps_dec->H21_H22[2 * group + 1] = ptr_ps_dec->h21_h22_vec[2 * group + 1];
845 
846     ptr_ps_dec->h11_h12_vec[2 * group + 0] = h11;
847     ptr_ps_dec->h11_h12_vec[2 * group + 1] = h12;
848     ptr_ps_dec->h21_h22_vec[2 * group + 0] = h21;
849     ptr_ps_dec->h21_h22_vec[2 * group + 1] = h22;
850   }
851 }
852 
ixheaacd_apply_rot_dec(ia_ps_dec_struct * ptr_ps_dec,WORD32 * p_qmf_left_re,WORD32 * p_qmf_left_im,WORD32 * p_qmf_right_re,WORD32 * p_qmf_right_im,ia_sbr_tables_struct * sbr_tables_ptr,const WORD16 * ptr_res)853 VOID ixheaacd_apply_rot_dec(ia_ps_dec_struct *ptr_ps_dec, WORD32 *p_qmf_left_re,
854                             WORD32 *p_qmf_left_im, WORD32 *p_qmf_right_re,
855                             WORD32 *p_qmf_right_im,
856                             ia_sbr_tables_struct *sbr_tables_ptr,
857                             const WORD16 *ptr_res) {
858   WORD group, subband, max_subband, usb, k;
859   WORD32 *p_hyb_left_re, *p_hyb_left_re1;
860   WORD32 *p_hyb_left_im, *p_hyb_left_im1;
861   WORD32 *p_hyb_right_re, *p_hyb_right_re1;
862   WORD32 *p_hyb_right_im, *p_hyb_right_im1;
863   WORD32 temp_left_real, temp_left_imag;
864   WORD32 temp_right_real, temp_right_imag;
865   WORD16 hybrid_resol;
866   WORD32 tmp_real, tmp_img;
867   WORD32 tmp_real1, tmp_img1;
868   WORD32 loopcnt;
869   WORD16 H11_H12[128 * 2];
870 
871   usb = ptr_ps_dec->usb;
872 
873   p_hyb_left_re1 = ptr_ps_dec->ptr_hyb_left_re;
874   p_hyb_left_im1 = ptr_ps_dec->ptr_hyb_left_im;
875   p_hyb_right_re1 = ptr_ps_dec->ptr_hyb_right_re;
876   p_hyb_right_im1 = ptr_ps_dec->ptr_hyb_right_im;
877 
878   for (group = 0; group < NO_IID_GROUPS; group++) {
879     ptr_ps_dec->H11_H12[2 * group + 0] =
880         ixheaacd_add16(ptr_ps_dec->H11_H12[2 * group + 0],
881                        ptr_ps_dec->delta_h11_h12[2 * group + 0]);
882     ptr_ps_dec->H11_H12[2 * group + 1] =
883         ixheaacd_add16(ptr_ps_dec->H11_H12[2 * group + 1],
884                        ptr_ps_dec->delta_h11_h12[2 * group + 1]);
885 
886     ptr_ps_dec->H21_H22[2 * group + 0] =
887         ixheaacd_add16(ptr_ps_dec->H21_H22[2 * group + 0],
888                        ptr_ps_dec->delta_h21_h22[2 * group + 0]);
889     ptr_ps_dec->H21_H22[2 * group + 1] =
890         ixheaacd_add16(ptr_ps_dec->H21_H22[2 * group + 1],
891                        ptr_ps_dec->delta_h21_h22[2 * group + 1]);
892   }
893 
894   for (subband = 0; subband < SUBQMF_GROUPS; subband++) {
895     temp_left_real = ixheaacd_add32_sat(
896         ixheaacd_mult32x16in32(p_hyb_left_re1[subband],
897                                ptr_ps_dec->H11_H12[2 * subband + 0]),
898         ixheaacd_mult32x16in32(p_hyb_right_re1[subband],
899                                ptr_ps_dec->H21_H22[2 * subband + 0]));
900     temp_left_imag = ixheaacd_add32_sat(
901         ixheaacd_mult32x16in32(p_hyb_left_im1[subband],
902                                ptr_ps_dec->H11_H12[2 * subband + 0]),
903         ixheaacd_mult32x16in32(p_hyb_right_im1[subband],
904                                ptr_ps_dec->H21_H22[2 * subband + 0]));
905     temp_right_real = ixheaacd_add32_sat(
906         ixheaacd_mult32x16in32(p_hyb_left_re1[subband],
907                                ptr_ps_dec->H11_H12[2 * subband + 1]),
908         ixheaacd_mult32x16in32(p_hyb_right_re1[subband],
909                                ptr_ps_dec->H21_H22[2 * subband + 1]));
910     temp_right_imag = ixheaacd_add32_sat(
911         ixheaacd_mult32x16in32(p_hyb_left_im1[subband],
912                                ptr_ps_dec->H11_H12[2 * subband + 1]),
913         ixheaacd_mult32x16in32(p_hyb_right_im1[subband],
914                                ptr_ps_dec->H21_H22[2 * subband + 1]));
915     p_hyb_left_re1[subband] = ixheaacd_shl32(temp_left_real, 2);
916     p_hyb_left_im1[subband] = ixheaacd_shl32(temp_left_imag, 2);
917     p_hyb_right_re1[subband] = ixheaacd_shl32(temp_right_real, 2);
918     p_hyb_right_im1[subband] = ixheaacd_shl32(temp_right_imag, 2);
919   }
920 
921   p_hyb_left_re = p_qmf_left_re;
922   p_hyb_left_im = p_qmf_left_im;
923   p_hyb_right_re = p_qmf_right_re;
924   p_hyb_right_im = p_qmf_right_im;
925 
926   {
927     WORD32 *h11_h12_src = (WORD32 *)ptr_ps_dec->H11_H12;
928     WORD32 *h21_h22_src = (WORD32 *)ptr_ps_dec->H21_H22;
929     WORD32 *h11_h12_dst = (WORD32 *)H11_H12;
930 
931     for (group = SUBQMF_GROUPS; group < NO_IID_GROUPS; group++) {
932       max_subband = ixheaacd_min32(
933           usb, sbr_tables_ptr->ps_tables_ptr->borders_group[group + 1]);
934       for (subband = sbr_tables_ptr->ps_tables_ptr->borders_group[group];
935            subband < max_subband; subband++) {
936         h11_h12_dst[2 * subband] = h11_h12_src[group];
937         h11_h12_dst[2 * subband + 1] = h21_h22_src[group];
938       }
939     }
940   }
941   loopcnt = (usb + 15) >> 4;
942 
943   for (subband = 0; subband < NO_QMF_CHANNELS_IN_HYBRID; subband++) {
944     tmp_real = *p_hyb_left_re1++;
945     tmp_img = *p_hyb_left_im1++;
946     tmp_real1 = *p_hyb_right_re1++;
947     tmp_img1 = *p_hyb_right_im1++;
948 
949     hybrid_resol = ixheaacd_min16(*ptr_res++, 6);
950 
951     for (k = hybrid_resol - 2; k >= 0; k--) {
952       tmp_real = ixheaacd_add32_sat(tmp_real, *p_hyb_left_re1++);
953       tmp_img = ixheaacd_add32_sat(tmp_img, *p_hyb_left_im1++);
954       tmp_real1 = ixheaacd_add32_sat(tmp_real1, *p_hyb_right_re1++);
955       tmp_img1 = ixheaacd_add32_sat(tmp_img1, *p_hyb_right_im1++);
956     }
957 
958     p_hyb_left_re[subband] = tmp_real;
959     p_hyb_left_im[subband] = tmp_img;
960     p_hyb_right_re[subband] = tmp_real1;
961     p_hyb_right_im[subband] = tmp_img1;
962   }
963 
964   for (; subband < usb; subband++) {
965     temp_left_real =
966         ixheaacd_add32_sat(ixheaacd_mult32x16in32(p_hyb_left_re[subband],
967                                                   H11_H12[4 * subband + 0]),
968                            ixheaacd_mult32x16in32(p_hyb_right_re[subband],
969                                                   H11_H12[4 * subband + 2]));
970     temp_left_imag =
971         ixheaacd_add32_sat(ixheaacd_mult32x16in32(p_hyb_left_im[subband],
972                                                   H11_H12[4 * subband + 0]),
973                            ixheaacd_mult32x16in32(p_hyb_right_im[subband],
974                                                   H11_H12[4 * subband + 2]));
975     temp_right_real =
976         ixheaacd_add32_sat(ixheaacd_mult32x16in32(p_hyb_left_re[subband],
977                                                   H11_H12[4 * subband + 1]),
978                            ixheaacd_mult32x16in32(p_hyb_right_re[subband],
979                                                   H11_H12[4 * subband + 3]));
980     temp_right_imag =
981         ixheaacd_add32_sat(ixheaacd_mult32x16in32(p_hyb_left_im[subband],
982                                                   H11_H12[4 * subband + 1]),
983                            ixheaacd_mult32x16in32(p_hyb_right_im[subband],
984                                                   H11_H12[4 * subband + 3]));
985     p_hyb_left_re[subband] = ixheaacd_shl32(temp_left_real, 2);
986     p_hyb_left_im[subband] = ixheaacd_shl32(temp_left_imag, 2);
987     p_hyb_right_re[subband] = ixheaacd_shl32(temp_right_real, 2);
988     p_hyb_right_im[subband] = ixheaacd_shl32(temp_right_imag, 2);
989   }
990 }
991