1*15dc779aSAndroid Build Coastguard Worker /******************************************************************************
2*15dc779aSAndroid Build Coastguard Worker *
3*15dc779aSAndroid Build Coastguard Worker * Copyright (C) 2023 The Android Open Source Project
4*15dc779aSAndroid Build Coastguard Worker *
5*15dc779aSAndroid Build Coastguard Worker * Licensed under the Apache License, Version 2.0 (the "License");
6*15dc779aSAndroid Build Coastguard Worker * you may not use this file except in compliance with the License.
7*15dc779aSAndroid Build Coastguard Worker * You may obtain a copy of the License at:
8*15dc779aSAndroid Build Coastguard Worker *
9*15dc779aSAndroid Build Coastguard Worker * http://www.apache.org/licenses/LICENSE-2.0
10*15dc779aSAndroid Build Coastguard Worker *
11*15dc779aSAndroid Build Coastguard Worker * Unless required by applicable law or agreed to in writing, software
12*15dc779aSAndroid Build Coastguard Worker * distributed under the License is distributed on an "AS IS" BASIS,
13*15dc779aSAndroid Build Coastguard Worker * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14*15dc779aSAndroid Build Coastguard Worker * See the License for the specific language governing permissions and
15*15dc779aSAndroid Build Coastguard Worker * limitations under the License.
16*15dc779aSAndroid Build Coastguard Worker *
17*15dc779aSAndroid Build Coastguard Worker *****************************************************************************
18*15dc779aSAndroid Build Coastguard Worker * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19*15dc779aSAndroid Build Coastguard Worker */
20*15dc779aSAndroid Build Coastguard Worker #include <string.h>
21*15dc779aSAndroid Build Coastguard Worker #include "ixheaac_type_def.h"
22*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_mps_struct_def.h"
23*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_mps_res_rom.h"
24*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_mps_aac_struct.h"
25*15dc779aSAndroid Build Coastguard Worker #include "ixheaac_constants.h"
26*15dc779aSAndroid Build Coastguard Worker #include "ixheaac_basic_ops32.h"
27*15dc779aSAndroid Build Coastguard Worker #include "ixheaac_basic_ops40.h"
28*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_bitbuffer.h"
29*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_error_codes.h"
30*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_common_rom.h"
31*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_sbrdecsettings.h"
32*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_sbr_scale.h"
33*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_env_extr_part.h"
34*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_sbr_rom.h"
35*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_lpp_tran.h"
36*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_hybrid.h"
37*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_ps_dec.h"
38*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_env_extr.h"
39*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_mps_polyphase.h"
40*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_config.h"
41*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_qmf_dec.h"
42*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_mps_dec.h"
43*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_mps_bitdec.h"
44*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_mps_macro_def.h"
45*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_mps_basic_op.h"
46*15dc779aSAndroid Build Coastguard Worker
ixheaacd_init_tonality(ia_heaac_mps_state_struct * pstr_mps_state)47*15dc779aSAndroid Build Coastguard Worker VOID ixheaacd_init_tonality(ia_heaac_mps_state_struct *pstr_mps_state) {
48*15dc779aSAndroid Build Coastguard Worker ia_mps_dec_tonality_state_struct *ton_state = pstr_mps_state->mps_persistent_mem.ton_state;
49*15dc779aSAndroid Build Coastguard Worker WORD32 cnt = pstr_mps_state->qmf_bands * 8;
50*15dc779aSAndroid Build Coastguard Worker WORD32 qmf_bands = pstr_mps_state->qmf_bands;
51*15dc779aSAndroid Build Coastguard Worker
52*15dc779aSAndroid Build Coastguard Worker memset(ton_state->spec_prev_real, 0, cnt * sizeof(ton_state->spec_prev_real[0]));
53*15dc779aSAndroid Build Coastguard Worker memset(ton_state->spec_prev_imag, 0, cnt * sizeof(ton_state->spec_prev_imag[0]));
54*15dc779aSAndroid Build Coastguard Worker memset(ton_state->p_cross_real, 0, cnt * sizeof(ton_state->p_cross_real[0]));
55*15dc779aSAndroid Build Coastguard Worker memset(ton_state->p_cross_imag, 0, cnt * sizeof(ton_state->p_cross_imag[0]));
56*15dc779aSAndroid Build Coastguard Worker memset(ton_state->p_sum, 0, cnt * sizeof(ton_state->p_sum[0]));
57*15dc779aSAndroid Build Coastguard Worker memset(ton_state->p_sum_prev, 0, cnt * sizeof(ton_state->p_sum_prev[0]));
58*15dc779aSAndroid Build Coastguard Worker
59*15dc779aSAndroid Build Coastguard Worker memset(ton_state->buf_real, 0, qmf_bands * 6 * sizeof(ton_state->buf_real[0][0]));
60*15dc779aSAndroid Build Coastguard Worker memset(ton_state->buf_imag, 0, qmf_bands * 6 * sizeof(ton_state->buf_imag[0][0]));
61*15dc779aSAndroid Build Coastguard Worker memset(ton_state->win_buf_real, 0, qmf_bands * 16 * sizeof(ton_state->win_buf_real[0][0]));
62*15dc779aSAndroid Build Coastguard Worker memset(ton_state->win_buf_imag, 0, qmf_bands * 16 * sizeof(ton_state->win_buf_imag[0][0]));
63*15dc779aSAndroid Build Coastguard Worker }
64*15dc779aSAndroid Build Coastguard Worker
ixheaacd_zoom_fft16(WORD32 * in_real,WORD32 * in_imag,WORD32 * out_real,WORD32 * out_imag,WORD32 qmf_band,WORD32 dfrac,ia_mps_dec_mps_tables_struct * ia_mps_dec_mps_table_ptr)65*15dc779aSAndroid Build Coastguard Worker VOID ixheaacd_zoom_fft16(WORD32 *in_real, WORD32 *in_imag, WORD32 *out_real, WORD32 *out_imag,
66*15dc779aSAndroid Build Coastguard Worker WORD32 qmf_band, WORD32 dfrac,
67*15dc779aSAndroid Build Coastguard Worker ia_mps_dec_mps_tables_struct *ia_mps_dec_mps_table_ptr) {
68*15dc779aSAndroid Build Coastguard Worker WORD32 blackman[16];
69*15dc779aSAndroid Build Coastguard Worker
70*15dc779aSAndroid Build Coastguard Worker WORD32 v_real[16], v_imag[16];
71*15dc779aSAndroid Build Coastguard Worker WORD32 t_real, t_imag;
72*15dc779aSAndroid Build Coastguard Worker WORD32 e_real, e_imag;
73*15dc779aSAndroid Build Coastguard Worker
74*15dc779aSAndroid Build Coastguard Worker WORD32 temp_1, temp_2, temp3, temp4;
75*15dc779aSAndroid Build Coastguard Worker const WORD32 *bitrev = ia_mps_dec_mps_table_ptr->tonality_table_ptr->bitrev;
76*15dc779aSAndroid Build Coastguard Worker const WORD32 *w_real = ia_mps_dec_mps_table_ptr->tonality_table_ptr->w_real;
77*15dc779aSAndroid Build Coastguard Worker const WORD32 *w_imag = ia_mps_dec_mps_table_ptr->tonality_table_ptr->w_imag;
78*15dc779aSAndroid Build Coastguard Worker const WORD32 *cos_tab = ia_mps_dec_mps_table_ptr->hybrid_table_ptr->cosine_array;
79*15dc779aSAndroid Build Coastguard Worker const WORD32 *sin_tab = ia_mps_dec_mps_table_ptr->hybrid_table_ptr->sine_array;
80*15dc779aSAndroid Build Coastguard Worker
81*15dc779aSAndroid Build Coastguard Worker WORD32 i, j, s1, s2;
82*15dc779aSAndroid Build Coastguard Worker
83*15dc779aSAndroid Build Coastguard Worker temp3 = TWO_PI_BY_FIFTEEN_Q15;
84*15dc779aSAndroid Build Coastguard Worker
85*15dc779aSAndroid Build Coastguard Worker for (i = 0; i < 16; i++) {
86*15dc779aSAndroid Build Coastguard Worker temp_1 = (i << 15) + dfrac;
87*15dc779aSAndroid Build Coastguard Worker temp_2 = ixheaacd_mps_mult32_shr_15(temp_1, temp3);
88*15dc779aSAndroid Build Coastguard Worker temp_2 = ixheaacd_mps_cos(temp_2, cos_tab);
89*15dc779aSAndroid Build Coastguard Worker temp_2 >>= 1;
90*15dc779aSAndroid Build Coastguard Worker
91*15dc779aSAndroid Build Coastguard Worker temp_1 <<= 1;
92*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_cos(temp_1, cos_tab);
93*15dc779aSAndroid Build Coastguard Worker
94*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_mult32x16_shr_16(temp_1, TWO_BY_TWENTYFIVE_Q16);
95*15dc779aSAndroid Build Coastguard Worker
96*15dc779aSAndroid Build Coastguard Worker temp4 = POINT_FOUR_TWO_Q15 - temp_2;
97*15dc779aSAndroid Build Coastguard Worker
98*15dc779aSAndroid Build Coastguard Worker blackman[i] = temp_1 + temp4;
99*15dc779aSAndroid Build Coastguard Worker }
100*15dc779aSAndroid Build Coastguard Worker
101*15dc779aSAndroid Build Coastguard Worker for (i = 0; i < 16; i++) {
102*15dc779aSAndroid Build Coastguard Worker WORD32 idx = bitrev[i];
103*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_mult32_shr_30(in_real[i], w_real[i]) -
104*15dc779aSAndroid Build Coastguard Worker ixheaacd_mps_mult32_shr_30(in_imag[i], w_imag[i]);
105*15dc779aSAndroid Build Coastguard Worker v_real[idx] = ixheaacd_mps_mult32_shr_30(temp_1, blackman[i]);
106*15dc779aSAndroid Build Coastguard Worker
107*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_mult32_shr_30(in_real[i], w_imag[i]) +
108*15dc779aSAndroid Build Coastguard Worker ixheaacd_mps_mult32_shr_30(in_imag[i], w_real[i]);
109*15dc779aSAndroid Build Coastguard Worker v_imag[idx] = ixheaacd_mps_mult32_shr_30(temp_1, blackman[i]);
110*15dc779aSAndroid Build Coastguard Worker }
111*15dc779aSAndroid Build Coastguard Worker
112*15dc779aSAndroid Build Coastguard Worker for (s1 = 1, s2 = 16; s1 < 8; s1 <<= 1, s2 >>= 1) {
113*15dc779aSAndroid Build Coastguard Worker for (i = 0; i < 16; i += 2 * s1) {
114*15dc779aSAndroid Build Coastguard Worker for (j = 0; j < s1; j++) {
115*15dc779aSAndroid Build Coastguard Worker t_real = ixheaacd_mps_mult32_shr_30(v_real[i + j + s1], w_real[j * s2]) -
116*15dc779aSAndroid Build Coastguard Worker ixheaacd_mps_mult32_shr_30(v_imag[i + j + s1], w_imag[j * s2]);
117*15dc779aSAndroid Build Coastguard Worker t_imag = ixheaacd_mps_mult32_shr_30(v_real[i + j + s1], w_imag[j * s2]) +
118*15dc779aSAndroid Build Coastguard Worker ixheaacd_mps_mult32_shr_30(v_imag[i + j + s1], w_real[j * s2]);
119*15dc779aSAndroid Build Coastguard Worker
120*15dc779aSAndroid Build Coastguard Worker v_real[i + j + s1] = v_real[i + j] - t_real;
121*15dc779aSAndroid Build Coastguard Worker v_imag[i + j + s1] = v_imag[i + j] - t_imag;
122*15dc779aSAndroid Build Coastguard Worker
123*15dc779aSAndroid Build Coastguard Worker v_real[i + j] += t_real;
124*15dc779aSAndroid Build Coastguard Worker v_imag[i + j] += t_imag;
125*15dc779aSAndroid Build Coastguard Worker }
126*15dc779aSAndroid Build Coastguard Worker }
127*15dc779aSAndroid Build Coastguard Worker }
128*15dc779aSAndroid Build Coastguard Worker
129*15dc779aSAndroid Build Coastguard Worker for (j = 0; j < 8; j++) {
130*15dc779aSAndroid Build Coastguard Worker WORD32 idx = j << 1;
131*15dc779aSAndroid Build Coastguard Worker t_real = ixheaacd_mps_mult32_shr_30(v_real[j + 8], w_real[idx]) -
132*15dc779aSAndroid Build Coastguard Worker ixheaacd_mps_mult32_shr_30(v_imag[j + 8], w_imag[idx]);
133*15dc779aSAndroid Build Coastguard Worker t_imag = ixheaacd_mps_mult32_shr_30(v_real[j + 8], w_imag[idx]) +
134*15dc779aSAndroid Build Coastguard Worker ixheaacd_mps_mult32_shr_30(v_imag[j + 8], w_real[idx]);
135*15dc779aSAndroid Build Coastguard Worker
136*15dc779aSAndroid Build Coastguard Worker if ((qmf_band & ONE_BIT_MASK) == 0) {
137*15dc779aSAndroid Build Coastguard Worker out_real[j] = v_real[j] + t_real;
138*15dc779aSAndroid Build Coastguard Worker out_imag[j] = v_imag[j] + t_imag;
139*15dc779aSAndroid Build Coastguard Worker } else {
140*15dc779aSAndroid Build Coastguard Worker out_real[j] = v_real[j] - t_real;
141*15dc779aSAndroid Build Coastguard Worker out_imag[j] = v_imag[j] - t_imag;
142*15dc779aSAndroid Build Coastguard Worker }
143*15dc779aSAndroid Build Coastguard Worker }
144*15dc779aSAndroid Build Coastguard Worker
145*15dc779aSAndroid Build Coastguard Worker temp3 = MINUS_PI_BY_EIGHT_Q15;
146*15dc779aSAndroid Build Coastguard Worker for (i = 0; i < 8; i++) {
147*15dc779aSAndroid Build Coastguard Worker if ((qmf_band & ONE_BIT_MASK) == 0) {
148*15dc779aSAndroid Build Coastguard Worker temp_1 = dfrac * i;
149*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_mult32_shr_15(temp_1, temp3);
150*15dc779aSAndroid Build Coastguard Worker e_real = ixheaacd_mps_cos(temp_1, cos_tab);
151*15dc779aSAndroid Build Coastguard Worker e_imag = ixheaacd_mps_sin(temp_1, sin_tab);
152*15dc779aSAndroid Build Coastguard Worker } else {
153*15dc779aSAndroid Build Coastguard Worker temp_1 = dfrac * (i - 8);
154*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_mult32_shr_15(temp_1, temp3);
155*15dc779aSAndroid Build Coastguard Worker e_real = ixheaacd_mps_cos(temp_1, cos_tab);
156*15dc779aSAndroid Build Coastguard Worker e_imag = ixheaacd_mps_sin(temp_1, sin_tab);
157*15dc779aSAndroid Build Coastguard Worker }
158*15dc779aSAndroid Build Coastguard Worker
159*15dc779aSAndroid Build Coastguard Worker t_real = ixheaacd_mps_mult32_shr_15(out_real[i], e_real) -
160*15dc779aSAndroid Build Coastguard Worker ixheaacd_mps_mult32_shr_15(out_imag[i], e_imag);
161*15dc779aSAndroid Build Coastguard Worker out_imag[i] = ixheaacd_mps_mult32_shr_15(out_real[i], e_imag) +
162*15dc779aSAndroid Build Coastguard Worker ixheaacd_mps_mult32_shr_15(out_imag[i], e_real);
163*15dc779aSAndroid Build Coastguard Worker out_real[i] = t_real;
164*15dc779aSAndroid Build Coastguard Worker }
165*15dc779aSAndroid Build Coastguard Worker }
166*15dc779aSAndroid Build Coastguard Worker
ixheaacd_measure_tonality(ia_heaac_mps_state_struct * pstr_mps_state,WORD32 * tonality)167*15dc779aSAndroid Build Coastguard Worker VOID ixheaacd_measure_tonality(ia_heaac_mps_state_struct *pstr_mps_state, WORD32 *tonality) {
168*15dc779aSAndroid Build Coastguard Worker ia_mps_dec_tonality_state_struct *ton_state = pstr_mps_state->mps_persistent_mem.ton_state;
169*15dc779aSAndroid Build Coastguard Worker
170*15dc779aSAndroid Build Coastguard Worker WORD32 *qmf_real;
171*15dc779aSAndroid Build Coastguard Worker WORD32 *qmf_imag;
172*15dc779aSAndroid Build Coastguard Worker
173*15dc779aSAndroid Build Coastguard Worker WORD32 *spec_zoom_real;
174*15dc779aSAndroid Build Coastguard Worker WORD32 *spec_zoom_imag;
175*15dc779aSAndroid Build Coastguard Worker
176*15dc779aSAndroid Build Coastguard Worker WORD32 *spec_prev_real = ton_state->spec_prev_real;
177*15dc779aSAndroid Build Coastguard Worker WORD32 *spec_prev_imag = ton_state->spec_prev_imag;
178*15dc779aSAndroid Build Coastguard Worker
179*15dc779aSAndroid Build Coastguard Worker WORD32 *p_cross_real = ton_state->p_cross_real;
180*15dc779aSAndroid Build Coastguard Worker WORD32 *p_cross_imag = ton_state->p_cross_imag;
181*15dc779aSAndroid Build Coastguard Worker
182*15dc779aSAndroid Build Coastguard Worker WORD32 *p_sum = ton_state->p_sum;
183*15dc779aSAndroid Build Coastguard Worker WORD32 *p_sum_prev = ton_state->p_sum_prev;
184*15dc779aSAndroid Build Coastguard Worker
185*15dc779aSAndroid Build Coastguard Worker WORD32 *p_max;
186*15dc779aSAndroid Build Coastguard Worker
187*15dc779aSAndroid Build Coastguard Worker WORD32 *coh_spec;
188*15dc779aSAndroid Build Coastguard Worker WORD32 *pow_spec;
189*15dc779aSAndroid Build Coastguard Worker
190*15dc779aSAndroid Build Coastguard Worker WORD32 *p_buf_real, *p_buf_imag, *p_buf_re, *p_buf_im;
191*15dc779aSAndroid Build Coastguard Worker WORD32 *buf_real, *buf_imag;
192*15dc779aSAndroid Build Coastguard Worker WORD32 g, gmax;
193*15dc779aSAndroid Build Coastguard Worker WORD32 i, j, q, s, c, cnt;
194*15dc779aSAndroid Build Coastguard Worker
195*15dc779aSAndroid Build Coastguard Worker WORD32 const *part;
196*15dc779aSAndroid Build Coastguard Worker WORD32 pstart;
197*15dc779aSAndroid Build Coastguard Worker WORD32 pstop = 0;
198*15dc779aSAndroid Build Coastguard Worker WORD32 pqmf, num, den, tmp_ton, beta, dwin, dfrac;
199*15dc779aSAndroid Build Coastguard Worker WORD16 q_beta, q_tmp_ton;
200*15dc779aSAndroid Build Coastguard Worker
201*15dc779aSAndroid Build Coastguard Worker WORD32 qmf_bands = pstr_mps_state->qmf_bands;
202*15dc779aSAndroid Build Coastguard Worker WORD32 time_slots = pstr_mps_state->time_slots;
203*15dc779aSAndroid Build Coastguard Worker WORD32 num_input_channels = pstr_mps_state->num_input_channels;
204*15dc779aSAndroid Build Coastguard Worker WORD32 num_parameter_bands = pstr_mps_state->num_parameter_bands;
205*15dc779aSAndroid Build Coastguard Worker WORD32 sampling_freq = pstr_mps_state->sampling_freq;
206*15dc779aSAndroid Build Coastguard Worker const WORD32 *sqrt_tab = pstr_mps_state->ia_mps_dec_mps_table.common_table_ptr->sqrt_tab;
207*15dc779aSAndroid Build Coastguard Worker
208*15dc779aSAndroid Build Coastguard Worker WORD32 nstart;
209*15dc779aSAndroid Build Coastguard Worker
210*15dc779aSAndroid Build Coastguard Worker WORD32 tmp_real, tmp_imag;
211*15dc779aSAndroid Build Coastguard Worker
212*15dc779aSAndroid Build Coastguard Worker WORD32 temp_1, temp;
213*15dc779aSAndroid Build Coastguard Worker WORD16 qtemp1, qtemp2;
214*15dc779aSAndroid Build Coastguard Worker
215*15dc779aSAndroid Build Coastguard Worker spec_zoom_real = (WORD32 *)((WORD8 *)pstr_mps_state->mps_scratch_mem_v +
216*15dc779aSAndroid Build Coastguard Worker IXHEAAC_GET_SIZE_ALIGNED(SCRATCH_OFFSET_SMOOTHING, BYTE_ALIGN_8));
217*15dc779aSAndroid Build Coastguard Worker spec_zoom_imag = spec_zoom_real + IXHEAAC_GET_SIZE_ALIGNED_TYPE(
218*15dc779aSAndroid Build Coastguard Worker QMF_BANDSX8, sizeof(*spec_zoom_imag), BYTE_ALIGN_8);
219*15dc779aSAndroid Build Coastguard Worker p_max =
220*15dc779aSAndroid Build Coastguard Worker spec_zoom_imag + IXHEAAC_GET_SIZE_ALIGNED_TYPE(QMF_BANDSX8, sizeof(*p_max), BYTE_ALIGN_8);
221*15dc779aSAndroid Build Coastguard Worker coh_spec = p_max + IXHEAAC_GET_SIZE_ALIGNED_TYPE(QMF_BANDSX8, sizeof(*coh_spec), BYTE_ALIGN_8);
222*15dc779aSAndroid Build Coastguard Worker pow_spec =
223*15dc779aSAndroid Build Coastguard Worker coh_spec + IXHEAAC_GET_SIZE_ALIGNED_TYPE(QMF_BANDSX8, sizeof(*pow_spec), BYTE_ALIGN_8);
224*15dc779aSAndroid Build Coastguard Worker
225*15dc779aSAndroid Build Coastguard Worker qmf_real =
226*15dc779aSAndroid Build Coastguard Worker pow_spec + IXHEAAC_GET_SIZE_ALIGNED_TYPE(QMF_BANDSX8, sizeof(*qmf_real), BYTE_ALIGN_8);
227*15dc779aSAndroid Build Coastguard Worker qmf_imag = qmf_real + IXHEAAC_GET_SIZE_ALIGNED_TYPE(QBXTS, sizeof(*qmf_imag), BYTE_ALIGN_8);
228*15dc779aSAndroid Build Coastguard Worker
229*15dc779aSAndroid Build Coastguard Worker switch (num_parameter_bands) {
230*15dc779aSAndroid Build Coastguard Worker case PARAMETER_BANDS_4:
231*15dc779aSAndroid Build Coastguard Worker part = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->part4;
232*15dc779aSAndroid Build Coastguard Worker break;
233*15dc779aSAndroid Build Coastguard Worker case PARAMETER_BANDS_5:
234*15dc779aSAndroid Build Coastguard Worker part = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->part5;
235*15dc779aSAndroid Build Coastguard Worker break;
236*15dc779aSAndroid Build Coastguard Worker case PARAMETER_BANDS_7:
237*15dc779aSAndroid Build Coastguard Worker part = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->part7;
238*15dc779aSAndroid Build Coastguard Worker break;
239*15dc779aSAndroid Build Coastguard Worker case PARAMETER_BANDS_10:
240*15dc779aSAndroid Build Coastguard Worker part = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->part10;
241*15dc779aSAndroid Build Coastguard Worker break;
242*15dc779aSAndroid Build Coastguard Worker case PARAMETER_BANDS_14:
243*15dc779aSAndroid Build Coastguard Worker part = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->part14;
244*15dc779aSAndroid Build Coastguard Worker break;
245*15dc779aSAndroid Build Coastguard Worker case PARAMETER_BANDS_20:
246*15dc779aSAndroid Build Coastguard Worker part = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->part20;
247*15dc779aSAndroid Build Coastguard Worker break;
248*15dc779aSAndroid Build Coastguard Worker case PARAMETER_BANDS_28:
249*15dc779aSAndroid Build Coastguard Worker part = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->part28;
250*15dc779aSAndroid Build Coastguard Worker break;
251*15dc779aSAndroid Build Coastguard Worker case PARAMETER_BANDS_40:
252*15dc779aSAndroid Build Coastguard Worker part = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->part40;
253*15dc779aSAndroid Build Coastguard Worker break;
254*15dc779aSAndroid Build Coastguard Worker default:
255*15dc779aSAndroid Build Coastguard Worker part = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->part4;
256*15dc779aSAndroid Build Coastguard Worker break;
257*15dc779aSAndroid Build Coastguard Worker }
258*15dc779aSAndroid Build Coastguard Worker
259*15dc779aSAndroid Build Coastguard Worker temp = time_slots - 6;
260*15dc779aSAndroid Build Coastguard Worker
261*15dc779aSAndroid Build Coastguard Worker p_buf_real = pstr_mps_state->array_struct->buf_real;
262*15dc779aSAndroid Build Coastguard Worker p_buf_imag = pstr_mps_state->array_struct->buf_imag;
263*15dc779aSAndroid Build Coastguard Worker
264*15dc779aSAndroid Build Coastguard Worker for (q = 0; q < qmf_bands; q++) {
265*15dc779aSAndroid Build Coastguard Worker qmf_real += 6;
266*15dc779aSAndroid Build Coastguard Worker qmf_imag += 6;
267*15dc779aSAndroid Build Coastguard Worker
268*15dc779aSAndroid Build Coastguard Worker p_buf_re = p_buf_real;
269*15dc779aSAndroid Build Coastguard Worker p_buf_im = p_buf_imag;
270*15dc779aSAndroid Build Coastguard Worker for (s = 0; s < time_slots; s++) {
271*15dc779aSAndroid Build Coastguard Worker tmp_real = 0;
272*15dc779aSAndroid Build Coastguard Worker tmp_imag = 0;
273*15dc779aSAndroid Build Coastguard Worker
274*15dc779aSAndroid Build Coastguard Worker buf_real = p_buf_re;
275*15dc779aSAndroid Build Coastguard Worker buf_imag = p_buf_im;
276*15dc779aSAndroid Build Coastguard Worker
277*15dc779aSAndroid Build Coastguard Worker for (c = 0; c < num_input_channels; c++) {
278*15dc779aSAndroid Build Coastguard Worker tmp_real += *buf_real;
279*15dc779aSAndroid Build Coastguard Worker tmp_imag += *buf_imag;
280*15dc779aSAndroid Build Coastguard Worker
281*15dc779aSAndroid Build Coastguard Worker buf_real += TSXHB;
282*15dc779aSAndroid Build Coastguard Worker buf_imag += TSXHB;
283*15dc779aSAndroid Build Coastguard Worker }
284*15dc779aSAndroid Build Coastguard Worker
285*15dc779aSAndroid Build Coastguard Worker if (s == temp) {
286*15dc779aSAndroid Build Coastguard Worker qmf_real -= time_slots;
287*15dc779aSAndroid Build Coastguard Worker qmf_imag -= time_slots;
288*15dc779aSAndroid Build Coastguard Worker }
289*15dc779aSAndroid Build Coastguard Worker
290*15dc779aSAndroid Build Coastguard Worker if (s + 6 < time_slots) {
291*15dc779aSAndroid Build Coastguard Worker *qmf_real++ = tmp_real;
292*15dc779aSAndroid Build Coastguard Worker *qmf_imag++ = tmp_imag;
293*15dc779aSAndroid Build Coastguard Worker } else {
294*15dc779aSAndroid Build Coastguard Worker *qmf_real++ = ton_state->buf_real[q][s + 6 - time_slots];
295*15dc779aSAndroid Build Coastguard Worker *qmf_imag++ = ton_state->buf_imag[q][s + 6 - time_slots];
296*15dc779aSAndroid Build Coastguard Worker
297*15dc779aSAndroid Build Coastguard Worker ton_state->buf_real[q][s + 6 - time_slots] = tmp_real;
298*15dc779aSAndroid Build Coastguard Worker ton_state->buf_imag[q][s + 6 - time_slots] = tmp_imag;
299*15dc779aSAndroid Build Coastguard Worker }
300*15dc779aSAndroid Build Coastguard Worker p_buf_re += MAX_HYBRID_BANDS;
301*15dc779aSAndroid Build Coastguard Worker p_buf_re += MAX_HYBRID_BANDS;
302*15dc779aSAndroid Build Coastguard Worker }
303*15dc779aSAndroid Build Coastguard Worker qmf_real += temp;
304*15dc779aSAndroid Build Coastguard Worker qmf_imag += temp;
305*15dc779aSAndroid Build Coastguard Worker
306*15dc779aSAndroid Build Coastguard Worker p_buf_real++;
307*15dc779aSAndroid Build Coastguard Worker p_buf_imag++;
308*15dc779aSAndroid Build Coastguard Worker }
309*15dc779aSAndroid Build Coastguard Worker
310*15dc779aSAndroid Build Coastguard Worker gmax = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->gmax_fix[time_slots];
311*15dc779aSAndroid Build Coastguard Worker dwin = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->dwin_fix[time_slots];
312*15dc779aSAndroid Build Coastguard Worker
313*15dc779aSAndroid Build Coastguard Worker qtemp1 = 15;
314*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_mult32(dwin, (40 * (qmf_bands)), &qtemp1, 0);
315*15dc779aSAndroid Build Coastguard Worker beta = ixheaacd_mps_div_32(temp_1, sampling_freq, &q_beta);
316*15dc779aSAndroid Build Coastguard Worker q_beta = q_beta + qtemp1;
317*15dc779aSAndroid Build Coastguard Worker beta = ixheaacd_mps_convert_to_qn(beta, q_beta, 15);
318*15dc779aSAndroid Build Coastguard Worker
319*15dc779aSAndroid Build Coastguard Worker for (i = 0; i < num_parameter_bands; i++) {
320*15dc779aSAndroid Build Coastguard Worker tonality[i] = ONE_IN_Q15;
321*15dc779aSAndroid Build Coastguard Worker }
322*15dc779aSAndroid Build Coastguard Worker
323*15dc779aSAndroid Build Coastguard Worker for (g = 0; g < gmax; g++) {
324*15dc779aSAndroid Build Coastguard Worker nstart = pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->nstart_fix[g][time_slots];
325*15dc779aSAndroid Build Coastguard Worker if (time_slots <= 16)
326*15dc779aSAndroid Build Coastguard Worker dfrac = 0;
327*15dc779aSAndroid Build Coastguard Worker else
328*15dc779aSAndroid Build Coastguard Worker dfrac =
329*15dc779aSAndroid Build Coastguard Worker pstr_mps_state->ia_mps_dec_mps_table.tonality_table_ptr->dfrac_fix[g][time_slots - 16];
330*15dc779aSAndroid Build Coastguard Worker
331*15dc779aSAndroid Build Coastguard Worker qmf_real = pow_spec + QBX48;
332*15dc779aSAndroid Build Coastguard Worker qmf_imag = qmf_real + QMF_BANDSXTSX6;
333*15dc779aSAndroid Build Coastguard Worker for (q = 0; q < qmf_bands; q++) {
334*15dc779aSAndroid Build Coastguard Worker for (i = 0; i < 16; i++) {
335*15dc779aSAndroid Build Coastguard Worker if (nstart + i < 0) {
336*15dc779aSAndroid Build Coastguard Worker ton_state->win_buf_real[q][i] = ton_state->win_buf_real[q][16 + nstart + i];
337*15dc779aSAndroid Build Coastguard Worker ton_state->win_buf_imag[q][i] = ton_state->win_buf_imag[q][16 + nstart + i];
338*15dc779aSAndroid Build Coastguard Worker } else {
339*15dc779aSAndroid Build Coastguard Worker ton_state->win_buf_real[q][i] = qmf_real[nstart + i];
340*15dc779aSAndroid Build Coastguard Worker ton_state->win_buf_imag[q][i] = qmf_imag[nstart + i];
341*15dc779aSAndroid Build Coastguard Worker }
342*15dc779aSAndroid Build Coastguard Worker }
343*15dc779aSAndroid Build Coastguard Worker qmf_real += time_slots;
344*15dc779aSAndroid Build Coastguard Worker qmf_imag += time_slots;
345*15dc779aSAndroid Build Coastguard Worker }
346*15dc779aSAndroid Build Coastguard Worker
347*15dc779aSAndroid Build Coastguard Worker for (q = 0; q < qmf_bands; q++) {
348*15dc779aSAndroid Build Coastguard Worker ixheaacd_zoom_fft16(&(ton_state->win_buf_real[q][0]), &(ton_state->win_buf_imag[q][0]),
349*15dc779aSAndroid Build Coastguard Worker &(spec_zoom_real[q * 8]), &(spec_zoom_imag[q * 8]), q, dfrac,
350*15dc779aSAndroid Build Coastguard Worker &(pstr_mps_state->ia_mps_dec_mps_table));
351*15dc779aSAndroid Build Coastguard Worker }
352*15dc779aSAndroid Build Coastguard Worker
353*15dc779aSAndroid Build Coastguard Worker cnt = 8 * qmf_bands;
354*15dc779aSAndroid Build Coastguard Worker for (i = 0; i < cnt; i++) {
355*15dc779aSAndroid Build Coastguard Worker WORD64 temp;
356*15dc779aSAndroid Build Coastguard Worker WORD32 one_minus_beta = ONE_IN_Q15 - beta;
357*15dc779aSAndroid Build Coastguard Worker WORD32 x = *spec_zoom_real;
358*15dc779aSAndroid Build Coastguard Worker WORD32 y = *spec_zoom_imag;
359*15dc779aSAndroid Build Coastguard Worker
360*15dc779aSAndroid Build Coastguard Worker temp = x * spec_prev_real[i] + y * spec_prev_imag[i];
361*15dc779aSAndroid Build Coastguard Worker temp_1 = (WORD32)(temp >> 10);
362*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_mult32_shr_15(temp_1, beta);
363*15dc779aSAndroid Build Coastguard Worker
364*15dc779aSAndroid Build Coastguard Worker p_cross_real[i] = ixheaacd_mps_mult32_shr_15(p_cross_real[i], one_minus_beta);
365*15dc779aSAndroid Build Coastguard Worker p_cross_real[i] += temp_1;
366*15dc779aSAndroid Build Coastguard Worker
367*15dc779aSAndroid Build Coastguard Worker temp = y * spec_prev_real[i] - x * spec_prev_imag[i];
368*15dc779aSAndroid Build Coastguard Worker temp_1 = (WORD32)(temp >> 10);
369*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_mult32_shr_15(temp_1, beta);
370*15dc779aSAndroid Build Coastguard Worker
371*15dc779aSAndroid Build Coastguard Worker p_cross_imag[i] = ixheaacd_mps_mult32_shr_15(p_cross_imag[i], one_minus_beta);
372*15dc779aSAndroid Build Coastguard Worker p_cross_imag[i] += temp_1;
373*15dc779aSAndroid Build Coastguard Worker
374*15dc779aSAndroid Build Coastguard Worker temp = x * x + y * y;
375*15dc779aSAndroid Build Coastguard Worker temp_1 = (WORD32)(temp >> 10);
376*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_mult32_shr_15(temp_1, beta);
377*15dc779aSAndroid Build Coastguard Worker
378*15dc779aSAndroid Build Coastguard Worker p_sum[i] = ixheaacd_mps_mult32_shr_15(p_sum[i], one_minus_beta);
379*15dc779aSAndroid Build Coastguard Worker p_sum[i] += temp_1;
380*15dc779aSAndroid Build Coastguard Worker
381*15dc779aSAndroid Build Coastguard Worker *p_max = (p_sum[i] > p_sum_prev[i]) ? p_sum[i] : p_sum_prev[i];
382*15dc779aSAndroid Build Coastguard Worker
383*15dc779aSAndroid Build Coastguard Worker p_sum_prev[i] = p_sum[i];
384*15dc779aSAndroid Build Coastguard Worker
385*15dc779aSAndroid Build Coastguard Worker temp = p_cross_real[i] * p_cross_real[i] + p_cross_imag[i] * p_cross_imag[i];
386*15dc779aSAndroid Build Coastguard Worker temp_1 = (WORD32)(temp >> 10);
387*15dc779aSAndroid Build Coastguard Worker qtemp1 = 10;
388*15dc779aSAndroid Build Coastguard Worker temp_1 = ixheaacd_mps_sqrt(temp_1, &qtemp1, sqrt_tab);
389*15dc779aSAndroid Build Coastguard Worker *coh_spec = ixheaacd_mps_div_32(temp_1, *p_max++, &qtemp2);
390*15dc779aSAndroid Build Coastguard Worker qtemp2 = qtemp2 + qtemp1 - 10;
391*15dc779aSAndroid Build Coastguard Worker *coh_spec = ixheaacd_mps_convert_to_qn(*coh_spec, qtemp2, 10);
392*15dc779aSAndroid Build Coastguard Worker coh_spec++;
393*15dc779aSAndroid Build Coastguard Worker
394*15dc779aSAndroid Build Coastguard Worker temp = x * x + y * y + spec_prev_real[i] * spec_prev_real[i] +
395*15dc779aSAndroid Build Coastguard Worker spec_prev_imag[i] * spec_prev_imag[i];
396*15dc779aSAndroid Build Coastguard Worker *pow_spec = (WORD32)(temp >> 10);
397*15dc779aSAndroid Build Coastguard Worker
398*15dc779aSAndroid Build Coastguard Worker spec_prev_real[i] = *spec_zoom_real++;
399*15dc779aSAndroid Build Coastguard Worker spec_prev_imag[i] = *spec_zoom_imag++;
400*15dc779aSAndroid Build Coastguard Worker }
401*15dc779aSAndroid Build Coastguard Worker spec_zoom_real -= i;
402*15dc779aSAndroid Build Coastguard Worker spec_zoom_imag -= i;
403*15dc779aSAndroid Build Coastguard Worker p_max -= i;
404*15dc779aSAndroid Build Coastguard Worker coh_spec -= i;
405*15dc779aSAndroid Build Coastguard Worker pow_spec -= i;
406*15dc779aSAndroid Build Coastguard Worker
407*15dc779aSAndroid Build Coastguard Worker pstart = 0;
408*15dc779aSAndroid Build Coastguard Worker pqmf = 0;
409*15dc779aSAndroid Build Coastguard Worker for (i = 0; i < num_parameter_bands; i++) {
410*15dc779aSAndroid Build Coastguard Worker pqmf += part[i];
411*15dc779aSAndroid Build Coastguard Worker pstop = ((pqmf << 3) + ONE_IN_Q14) >> 15;
412*15dc779aSAndroid Build Coastguard Worker
413*15dc779aSAndroid Build Coastguard Worker num = 0;
414*15dc779aSAndroid Build Coastguard Worker den = 0;
415*15dc779aSAndroid Build Coastguard Worker for (j = pstart; j < pstop; j++) {
416*15dc779aSAndroid Build Coastguard Worker num += ixheaacd_mps_mult32_shr_n(*pow_spec, *coh_spec, 10);
417*15dc779aSAndroid Build Coastguard Worker coh_spec++;
418*15dc779aSAndroid Build Coastguard Worker den += *pow_spec++;
419*15dc779aSAndroid Build Coastguard Worker }
420*15dc779aSAndroid Build Coastguard Worker
421*15dc779aSAndroid Build Coastguard Worker tmp_ton = ixheaacd_mps_div_32(num, den, &q_tmp_ton);
422*15dc779aSAndroid Build Coastguard Worker ixheaacd_mps_convert_to_qn(tmp_ton, q_tmp_ton, 15);
423*15dc779aSAndroid Build Coastguard Worker
424*15dc779aSAndroid Build Coastguard Worker if (tmp_ton > 32767) {
425*15dc779aSAndroid Build Coastguard Worker tmp_ton = 32767;
426*15dc779aSAndroid Build Coastguard Worker }
427*15dc779aSAndroid Build Coastguard Worker
428*15dc779aSAndroid Build Coastguard Worker if (tmp_ton < tonality[i]) tonality[i] = tmp_ton;
429*15dc779aSAndroid Build Coastguard Worker
430*15dc779aSAndroid Build Coastguard Worker pstart = pstop;
431*15dc779aSAndroid Build Coastguard Worker }
432*15dc779aSAndroid Build Coastguard Worker coh_spec -= pstop;
433*15dc779aSAndroid Build Coastguard Worker pow_spec -= pstop;
434*15dc779aSAndroid Build Coastguard Worker }
435*15dc779aSAndroid Build Coastguard Worker return;
436*15dc779aSAndroid Build Coastguard Worker }
437