xref: /aosp_15_r20/external/libxaac/decoder/armv7/ixheaacd_qmf_dec_armv7.c (revision 15dc779a375ca8b5125643b829a8aa4b70d7f451)
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 
22 #include "ixheaacd_sbr_common.h"
23 #include "ixheaac_type_def.h"
24 
25 #include "ixheaac_constants.h"
26 #include "ixheaac_basic_ops32.h"
27 #include "ixheaac_basic_ops16.h"
28 #include "ixheaac_basic_ops40.h"
29 #include "ixheaac_basic_ops.h"
30 
31 #include "ixheaacd_intrinsics.h"
32 #include "ixheaacd_common_rom.h"
33 #include "ixheaacd_bitbuffer.h"
34 #include "ixheaacd_sbrdecsettings.h"
35 #include "ixheaacd_sbr_scale.h"
36 #include "ixheaacd_lpp_tran.h"
37 #include "ixheaacd_env_extr_part.h"
38 #include "ixheaacd_sbr_rom.h"
39 #include "ixheaacd_hybrid.h"
40 #include "ixheaacd_ps_dec.h"
41 #include "ixheaacd_env_extr.h"
42 #include "ixheaacd_qmf_dec.h"
43 
44 #include "ixheaac_basic_op.h"
45 #include "ixheaacd_env_calc.h"
46 
47 #include "ixheaacd_interface.h"
48 
49 #include "ixheaacd_function_selector.h"
50 #include "ixheaacd_audioobjtypes.h"
51 
52 #define DCT3_LEN (32)
53 #define DCT2_LEN (64)
54 
55 #define LP_SHIFT_VAL 7
56 #define HQ_SHIFT_64 4
57 #define RADIXSHIFT 1
58 #define ROUNDING_SPECTRA 1
59 #define HQ_SHIFT_VAL 4
60 
61 extern const WORD32 ixheaacd_ldmps_polyphase_filter_coeff_fix[1280];
62 
ixheaacd_dct2_64(WORD32 * x,WORD32 * X,ia_qmf_dec_tables_struct * qmf_dec_tables_ptr,WORD16 * filter_states)63 VOID ixheaacd_dct2_64(WORD32 *x, WORD32 *X,
64                       ia_qmf_dec_tables_struct *qmf_dec_tables_ptr,
65                       WORD16 *filter_states) {
66   ixheaacd_pretwdct2(x, X);
67 
68   ixheaacd_sbr_imdct_using_fft(qmf_dec_tables_ptr->w1024, 32, X, x,
69                                qmf_dec_tables_ptr->dig_rev_table2_128,
70                                qmf_dec_tables_ptr->dig_rev_table2_128,
71                                qmf_dec_tables_ptr->dig_rev_table2_128,
72                                qmf_dec_tables_ptr->dig_rev_table2_128);
73 
74   ixheaacd_fftposttw(x, qmf_dec_tables_ptr);
75 
76   ixheaacd_posttwdct2(x, filter_states, qmf_dec_tables_ptr);
77 
78   return;
79 }
80 
ixheaacd_cplx_anal_qmffilt(const WORD16 * time_sample_buf,ia_sbr_scale_fact_struct * sbr_scale_factor,WORD32 ** qmf_real,WORD32 ** qmf_imag,ia_sbr_qmf_filter_bank_struct * qmf_bank,ia_qmf_dec_tables_struct * qmf_dec_tables_ptr,WORD32 ch_fac,WORD32 low_pow_flag,WORD audio_object_type)81 VOID ixheaacd_cplx_anal_qmffilt(const WORD16 *time_sample_buf,
82                                 ia_sbr_scale_fact_struct *sbr_scale_factor,
83                                 WORD32 **qmf_real, WORD32 **qmf_imag,
84                                 ia_sbr_qmf_filter_bank_struct *qmf_bank,
85                                 ia_qmf_dec_tables_struct *qmf_dec_tables_ptr,
86                                 WORD32 ch_fac, WORD32 low_pow_flag,
87                                 WORD audio_object_type) {
88   WORD32 i, k;
89   WORD32 num_time_slots = qmf_bank->num_time_slots;
90 
91   WORD32 analysis_buffer[4 * NO_ANALYSIS_CHANNELS];
92   WORD16 *filter_states = qmf_bank->core_samples_buffer;
93 
94   WORD16 *fp1, *fp2, *tmp;
95 
96   WORD16 *filter_1;
97   WORD16 *filter_2;
98   WORD16 *filt_ptr;
99   if (audio_object_type != AOT_ER_AAC_ELD &&
100       audio_object_type != AOT_ER_AAC_LD) {
101     qmf_bank->filter_pos +=
102         (qmf_dec_tables_ptr->qmf_c - qmf_bank->analy_win_coeff);
103     qmf_bank->analy_win_coeff = qmf_dec_tables_ptr->qmf_c;
104   } else {
105     qmf_bank->filter_pos +=
106         (qmf_dec_tables_ptr->qmf_c_eld3 - qmf_bank->analy_win_coeff);
107     qmf_bank->analy_win_coeff = qmf_dec_tables_ptr->qmf_c_eld3;
108   }
109 
110   filter_1 = qmf_bank->filter_pos;
111 
112   if (audio_object_type != AOT_ER_AAC_ELD &&
113       audio_object_type != AOT_ER_AAC_LD) {
114     filter_2 = filter_1 + 64;
115   } else {
116     filter_2 = filter_1 + 32;
117   }
118 
119   sbr_scale_factor->st_lb_scale = 0;
120   sbr_scale_factor->lb_scale = -10;
121   if (!low_pow_flag) {
122     if (audio_object_type != AOT_ER_AAC_ELD &&
123         audio_object_type != AOT_ER_AAC_LD) {
124       sbr_scale_factor->lb_scale = -8;
125     } else {
126       sbr_scale_factor->lb_scale = -9;
127     }
128     qmf_bank->cos_twiddle =
129         (WORD16 *)qmf_dec_tables_ptr->sbr_sin_cos_twiddle_l32;
130     qmf_bank->alt_sin_twiddle =
131         (WORD16 *)qmf_dec_tables_ptr->sbr_alt_sin_twiddle_l32;
132     if (audio_object_type != AOT_ER_AAC_ELD &&
133         audio_object_type != AOT_ER_AAC_LD) {
134       qmf_bank->t_cos = (WORD16 *)qmf_dec_tables_ptr->sbr_t_cos_sin_l32;
135     } else {
136       qmf_bank->t_cos =
137           (WORD16 *)qmf_dec_tables_ptr->ixheaacd_sbr_t_cos_sin_l32_eld;
138     }
139   }
140 
141   fp1 = qmf_bank->anal_filter_states;
142   fp2 = qmf_bank->anal_filter_states + NO_ANALYSIS_CHANNELS;
143 
144   if (audio_object_type == AOT_ER_AAC_ELD ||
145       audio_object_type == AOT_ER_AAC_LD) {
146     filter_2 = qmf_bank->filter_2;
147     fp1 = qmf_bank->fp1_anal;
148     fp2 = qmf_bank->fp2_anal;
149   }
150 
151   for (i = 0; i < num_time_slots; i++) {
152     for (k = 0; k < NO_ANALYSIS_CHANNELS; k++)
153       filter_states[NO_ANALYSIS_CHANNELS - 1 - k] = time_sample_buf[ch_fac * k];
154 
155     if (audio_object_type != AOT_ER_AAC_ELD &&
156         audio_object_type != AOT_ER_AAC_LD) {
157       ixheaacd_sbr_qmfanal32_winadds(fp1, fp2, filter_1, filter_2,
158                                      analysis_buffer, filter_states,
159                                      time_sample_buf, ch_fac);
160     } else {
161       ixheaacd_sbr_qmfanal32_winadds_eld(fp1, fp2, filter_1, filter_2,
162                                          analysis_buffer, filter_states,
163                                          time_sample_buf, ch_fac);
164     }
165 
166     time_sample_buf += NO_ANALYSIS_CHANNELS * ch_fac;
167 
168     filter_states -= NO_ANALYSIS_CHANNELS;
169     if (filter_states < qmf_bank->anal_filter_states) {
170       filter_states = qmf_bank->anal_filter_states + 288;
171     }
172 
173     tmp = fp1;
174     fp1 = fp2;
175     fp2 = tmp;
176     if (audio_object_type != AOT_ER_AAC_ELD &&
177         audio_object_type != AOT_ER_AAC_LD) {
178       filter_1 += 64;
179       filter_2 += 64;
180     } else {
181       filter_1 += 32;
182       filter_2 += 32;
183     }
184 
185     filt_ptr = filter_1;
186     filter_1 = filter_2;
187     filter_2 = filt_ptr;
188     if (audio_object_type != AOT_ER_AAC_ELD &&
189         audio_object_type != AOT_ER_AAC_LD) {
190       if (filter_2 > (qmf_bank->analy_win_coeff + 640)) {
191         filter_1 = (WORD16 *)qmf_bank->analy_win_coeff;
192         filter_2 = (WORD16 *)qmf_bank->analy_win_coeff + 64;
193       }
194     } else {
195       if (filter_2 > (qmf_bank->analy_win_coeff + 320)) {
196         filter_1 = (WORD16 *)qmf_bank->analy_win_coeff;
197         filter_2 = (WORD16 *)qmf_bank->analy_win_coeff + 32;
198       }
199     }
200 
201     if (!low_pow_flag) {
202       ixheaacd_fwd_modulation(analysis_buffer, qmf_real[i], qmf_imag[i],
203                               qmf_bank, qmf_dec_tables_ptr, 0);
204     } else {
205       ixheaacd_dct3_32(
206           (WORD32 *)analysis_buffer, qmf_real[i], qmf_dec_tables_ptr->dct23_tw,
207           qmf_dec_tables_ptr->post_fft_tbl, qmf_dec_tables_ptr->w_16,
208           qmf_dec_tables_ptr->dig_rev_table4_16);
209     }
210   }
211 
212   qmf_bank->filter_pos = filter_1;
213   qmf_bank->core_samples_buffer = filter_states;
214 
215   if (audio_object_type == AOT_ER_AAC_ELD || audio_object_type == AOT_ER_AAC_LD)
216 
217   {
218     qmf_bank->fp1_anal = fp1;
219     qmf_bank->fp2_anal = fp2;
220     qmf_bank->filter_2 = filter_2;
221   }
222 }
223 
ixheaacd_cplx_anal_qmffilt_32(const WORD32 * time_sample_buf,ia_sbr_scale_fact_struct * sbr_scale_factor,WORD32 ** qmf_real,WORD32 ** qmf_imag,ia_sbr_qmf_filter_bank_struct * qmf_bank,ia_qmf_dec_tables_struct * qmf_dec_tables_ptr,WORD32 ch_fac,WORD32 ldsbr_present)224 VOID ixheaacd_cplx_anal_qmffilt_32(const WORD32 *time_sample_buf,
225                                    ia_sbr_scale_fact_struct *sbr_scale_factor,
226                                    WORD32 **qmf_real, WORD32 **qmf_imag,
227                                    ia_sbr_qmf_filter_bank_struct *qmf_bank,
228                                    ia_qmf_dec_tables_struct *qmf_dec_tables_ptr,
229                                    WORD32 ch_fac, WORD32 ldsbr_present) {
230   WORD32 i, k;
231   WORD32 num_time_slots = qmf_bank->num_time_slots;
232 
233   WORD32 analysis_buffer[4 * NO_ANALYSIS_CHANNELS];
234   WORD32 *filter_states = qmf_bank->core_samples_buffer_32;
235 
236   WORD32 *fp1, *fp2, *tmp;
237 
238   WORD32 *filter_1;
239   WORD32 *filter_2;
240   WORD32 *filt_ptr;
241   WORD32 start_slot = 2;
242 
243   if (ldsbr_present) {
244     qmf_bank->filter_pos_32 +=
245         (qmf_dec_tables_ptr->qmf_c_ldsbr_mps - qmf_bank->analy_win_coeff_32);
246     qmf_bank->analy_win_coeff_32 = qmf_dec_tables_ptr->qmf_c_ldsbr_mps;
247   } else {
248     qmf_bank->filter_pos_32 += (ixheaacd_ldmps_polyphase_filter_coeff_fix -
249                                 qmf_bank->analy_win_coeff_32);
250     qmf_bank->analy_win_coeff_32 =
251         (WORD32 *)ixheaacd_ldmps_polyphase_filter_coeff_fix;
252   }
253 
254   filter_1 = qmf_bank->filter_pos_32;
255   filter_2 = filter_1 + qmf_bank->no_channels;
256 
257   sbr_scale_factor->st_lb_scale = 0;
258   sbr_scale_factor->lb_scale = -10;
259 
260   sbr_scale_factor->lb_scale = -9;
261   if (qmf_bank->no_channels != 64) {
262     qmf_bank->cos_twiddle =
263         (WORD16 *)qmf_dec_tables_ptr->sbr_sin_cos_twiddle_l32;
264     qmf_bank->alt_sin_twiddle =
265         (WORD16 *)qmf_dec_tables_ptr->sbr_alt_sin_twiddle_l32;
266   } else {
267     qmf_bank->cos_twiddle =
268         (WORD16 *)qmf_dec_tables_ptr->sbr_sin_cos_twiddle_l64;
269     qmf_bank->alt_sin_twiddle =
270         (WORD16 *)qmf_dec_tables_ptr->sbr_alt_sin_twiddle_l64;
271   }
272   qmf_bank->t_cos =
273       (WORD16 *)qmf_dec_tables_ptr->ixheaacd_sbr_t_cos_sin_l32_eld;
274 
275   fp1 = qmf_bank->anal_filter_states_32;
276   fp2 = qmf_bank->anal_filter_states_32 + qmf_bank->no_channels;
277 
278   filter_2 = qmf_bank->filter_2_32;
279   fp1 = qmf_bank->fp1_anal_32;
280   fp2 = qmf_bank->fp2_anal_32;
281 
282   for (i = start_slot; i < num_time_slots + start_slot; i++) {
283     for (k = 0; k < qmf_bank->no_channels; k++)
284       filter_states[qmf_bank->no_channels - 1 - k] =
285           time_sample_buf[ch_fac * k];
286 
287     if (ldsbr_present) {
288       ixheaacd_sbr_qmfanal32_winadd_eld_32(fp1, fp2, filter_1, filter_2,
289                                            analysis_buffer);
290     } else {
291       ixheaacd_sbr_qmfanal32_winadd_eld_mps(fp1, fp2, filter_1, filter_2,
292                                             analysis_buffer);
293     }
294 
295     time_sample_buf += qmf_bank->no_channels * ch_fac;
296 
297     filter_states -= qmf_bank->no_channels;
298 
299     if (filter_states < qmf_bank->anal_filter_states_32) {
300       filter_states = qmf_bank->anal_filter_states_32 +
301                       ((qmf_bank->no_channels * 10) - qmf_bank->no_channels);
302     }
303 
304     tmp = fp1;
305     fp1 = fp2;
306     fp2 = tmp;
307 
308     filter_1 += qmf_bank->no_channels;
309     filter_2 += qmf_bank->no_channels;
310 
311     filt_ptr = filter_1;
312     filter_1 = filter_2;
313     filter_2 = filt_ptr;
314 
315     if (filter_2 >
316         (qmf_bank->analy_win_coeff_32 + (qmf_bank->no_channels * 10))) {
317       filter_1 = (WORD32 *)qmf_bank->analy_win_coeff_32;
318       filter_2 = (WORD32 *)qmf_bank->analy_win_coeff_32 + qmf_bank->no_channels;
319     }
320 
321     ixheaacd_fwd_modulation(analysis_buffer, qmf_real[i], qmf_imag[i], qmf_bank,
322                             qmf_dec_tables_ptr, 1);
323   }
324 
325   qmf_bank->filter_pos_32 = filter_1;
326   qmf_bank->core_samples_buffer_32 = filter_states;
327 
328   qmf_bank->fp1_anal_32 = fp1;
329   qmf_bank->fp2_anal_32 = fp2;
330   qmf_bank->filter_2_32 = filter_2;
331 }
332 
ixheaacd_inv_modulation_lp(WORD32 * qmf_real,WORD16 * filter_states,ia_sbr_qmf_filter_bank_struct * syn_qmf,ia_qmf_dec_tables_struct * qmf_dec_tables_ptr)333 VOID ixheaacd_inv_modulation_lp(WORD32 *qmf_real, WORD16 *filter_states,
334                                 ia_sbr_qmf_filter_bank_struct *syn_qmf,
335                                 ia_qmf_dec_tables_struct *qmf_dec_tables_ptr) {
336   WORD32 L = syn_qmf->no_channels;
337   const WORD32 M = (L >> 1);
338   WORD32 *dct_in = qmf_real;
339   WORD32 time_out[2 * NO_SYNTHESIS_CHANNELS];
340 
341   WORD32 ui_rem = ((WORD32)(&time_out[0]) % 8);
342   WORD32 *ptime_out = (pVOID)((WORD8 *)&time_out[0] + 8 - ui_rem);
343 
344   if (L == 64)
345     ixheaacd_dec_DCT2_64_asm(dct_in, ptime_out, qmf_dec_tables_ptr->w1024,
346                              qmf_dec_tables_ptr->dig_rev_table2_128,
347                              qmf_dec_tables_ptr->post_fft_tbl,
348                              qmf_dec_tables_ptr->dct23_tw, filter_states + M);
349   else
350     ixheaacd_dct2_32(dct_in, time_out, qmf_dec_tables_ptr, filter_states);
351 
352   filter_states[3 * M] = 0;
353 }
354 
ixheaacd_inv_emodulation(WORD32 * qmf_real,ia_sbr_qmf_filter_bank_struct * syn_qmf,ia_qmf_dec_tables_struct * qmf_dec_tables_ptr)355 VOID ixheaacd_inv_emodulation(WORD32 *qmf_real,
356                               ia_sbr_qmf_filter_bank_struct *syn_qmf,
357                               ia_qmf_dec_tables_struct *qmf_dec_tables_ptr) {
358   ixheaacd_cos_sin_mod(qmf_real, syn_qmf, (WORD16 *)qmf_dec_tables_ptr->w1024,
359                        (WORD32 *)qmf_dec_tables_ptr->dig_rev_table2_128);
360 }
361 
ixheaacd_esbr_cos_sin_mod(WORD32 * subband,ia_sbr_qmf_filter_bank_struct * qmf_bank,WORD32 * p_twiddle,WORD32 * p_dig_rev_tbl)362 VOID ixheaacd_esbr_cos_sin_mod(WORD32 *subband,
363                                ia_sbr_qmf_filter_bank_struct *qmf_bank,
364                                WORD32 *p_twiddle, WORD32 *p_dig_rev_tbl) {
365   WORD32 z;
366   WORD32 temp[128];
367   WORD32 scaleshift = 0;
368 
369   WORD32 M_2;
370   WORD32 M = ixheaac_shr32(qmf_bank->no_channels, 1);
371 
372   const WORD32 *p_sin;
373   const WORD32 *p_sin_cos;
374 
375   WORD32 subband_tmp[128];
376 
377   p_sin_cos = qmf_bank->esbr_cos_twiddle;
378   ixheaacd_esbr_cos_sin_mod_loop1(subband, M, p_sin_cos, subband_tmp);
379 
380   M_2 = ixheaac_shr32(M, 1);
381   if (M == 32) {
382     ixheaacd_esbr_radix4bfly(p_twiddle, subband_tmp, 1, 8);
383     ixheaacd_esbr_radix4bfly(p_twiddle + 48, subband_tmp, 4, 2);
384     ixheaacd_postradixcompute2(subband, subband_tmp, p_dig_rev_tbl, 32);
385 
386     ixheaacd_esbr_radix4bfly(p_twiddle, &subband_tmp[64], 1, 8);
387     ixheaacd_esbr_radix4bfly(p_twiddle + 48, &subband_tmp[64], 4, 2);
388     ixheaacd_postradixcompute2(&subband[64], &subband_tmp[64], p_dig_rev_tbl,
389                                32);
390 
391   }
392 
393   else if (M == 16) {
394     ixheaacd_esbr_radix4bfly(p_twiddle, subband_tmp, 1, 4);
395     ixheaacd_postradixcompute4(subband, subband_tmp, p_dig_rev_tbl, 16);
396 
397     ixheaacd_esbr_radix4bfly(p_twiddle, &subband_tmp[64], 1, 4);
398     ixheaacd_postradixcompute4(&subband[64], &subband_tmp[64], p_dig_rev_tbl,
399                                16);
400 
401   }
402 
403   else if (M == 12) {
404     for (z = 0; z < (qmf_bank->no_channels >> 1); z++) {
405       temp[z] = subband_tmp[2 * z];
406       temp[12 + z] = subband_tmp[2 * z + 1];
407     }
408 
409     ixheaacd_complex_fft_p3(temp, &temp[12], 12, -1, &scaleshift);
410 
411     for (z = 0; z < (qmf_bank->no_channels >> 1); z++) {
412       subband[2 * z] = temp[z];
413       subband[2 * z + 1] = temp[z + 12];
414     }
415     scaleshift = 0;
416     for (z = 0; z < (qmf_bank->no_channels >> 1); z++) {
417       temp[z] = subband_tmp[64 + 2 * z];
418       temp[12 + z] = subband_tmp[64 + 2 * z + 1];
419     }
420 
421     ixheaacd_complex_fft_p3(temp, &temp[12], 12, -1, &scaleshift);
422 
423     for (z = 0; z < (qmf_bank->no_channels >> 1); z++) {
424       subband[64 + 2 * z] = temp[z];
425       subband[64 + 2 * z + 1] = temp[z + 12];
426     }
427 
428   }
429 
430   else {
431     for (z = 0; z < (qmf_bank->no_channels >> 1); z++) {
432       temp[z] = subband_tmp[2 * z];
433       temp[8 + z] = subband_tmp[2 * z + 1];
434     }
435 
436     (*ixheaacd_complex_fft_p2)(temp, &temp[8], 8, -1, &scaleshift);
437 
438     for (z = 0; z < (qmf_bank->no_channels >> 1); z++) {
439       subband[2 * z] = temp[z] << scaleshift;
440       subband[2 * z + 1] = temp[z + 8] << scaleshift;
441     }
442     scaleshift = 0;
443     for (z = 0; z < (qmf_bank->no_channels >> 1); z++) {
444       temp[z] = subband_tmp[64 + 2 * z];
445       temp[8 + z] = subband_tmp[64 + 2 * z + 1];
446     }
447 
448     (*ixheaacd_complex_fft_p2)(temp, &temp[8], 8, -1, &scaleshift);
449 
450     for (z = 0; z < (qmf_bank->no_channels >> 1); z++) {
451       subband[64 + 2 * z] = temp[z] << scaleshift;
452       subband[64 + 2 * z + 1] = temp[8 + z] << scaleshift;
453     }
454   }
455   p_sin = qmf_bank->esbr_alt_sin_twiddle;
456   ixheaacd_esbr_cos_sin_mod_loop2(subband, p_sin, M);
457 }
458 
ixheaacd_esbr_qmfsyn32_winadd(WORD32 * tmp1,WORD32 * tmp2,WORD32 * inp1,WORD32 * sample_buffer,WORD32 ch_fac)459 VOID ixheaacd_esbr_qmfsyn32_winadd(WORD32 *tmp1, WORD32 *tmp2, WORD32 *inp1,
460                                    WORD32 *sample_buffer, WORD32 ch_fac) {
461   WORD32 k;
462 
463   for (k = 0; k < 32; k++) {
464     WORD64 syn_out = 0;
465 
466     syn_out =
467         ixheaac_add64(syn_out, ixheaac_mult64(tmp1[0 + k], inp1[2 * (k + 0)]));
468     syn_out =
469         ixheaac_add64(syn_out, ixheaac_mult64(tmp1[128 + k], inp1[2 * (k + 64)]));
470     syn_out =
471         ixheaac_add64(syn_out, ixheaac_mult64(tmp1[256 + k], inp1[2 * (k + 128)]));
472     syn_out =
473         ixheaac_add64(syn_out, ixheaac_mult64(tmp1[384 + k], inp1[2 * (k + 192)]));
474     syn_out =
475         ixheaac_add64(syn_out, ixheaac_mult64(tmp1[512 + k], inp1[2 * (k + 256)]));
476 
477     syn_out =
478         ixheaac_add64(syn_out, ixheaac_mult64(tmp2[64 + k], inp1[2 * (k + 32)]));
479     syn_out =
480         ixheaac_add64(syn_out, ixheaac_mult64(tmp2[192 + k], inp1[2 * (k + 96)]));
481     syn_out =
482         ixheaac_add64(syn_out, ixheaac_mult64(tmp2[320 + k], inp1[2 * (k + 160)]));
483     syn_out =
484         ixheaac_add64(syn_out, ixheaac_mult64(tmp2[448 + k], inp1[2 * (k + 224)]));
485     syn_out =
486         ixheaac_add64(syn_out, ixheaac_mult64(tmp2[576 + k], inp1[2 * (k + 288)]));
487 
488     sample_buffer[ch_fac * k] = (WORD32)(syn_out >> 31);
489   }
490 }
491