xref: /aosp_15_r20/external/libxaac/decoder/ixheaacd_esbr_envcal.c (revision 15dc779a375ca8b5125643b829a8aa4b70d7f451)
1*15dc779aSAndroid Build Coastguard Worker /******************************************************************************
2*15dc779aSAndroid Build Coastguard Worker  *                                                                            *
3*15dc779aSAndroid Build Coastguard Worker  * Copyright (C) 2018 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 <stdlib.h>
21*15dc779aSAndroid Build Coastguard Worker #include <math.h>
22*15dc779aSAndroid Build Coastguard Worker #include <string.h>
23*15dc779aSAndroid Build Coastguard Worker 
24*15dc779aSAndroid Build Coastguard Worker #include "ixheaac_type_def.h"
25*15dc779aSAndroid Build Coastguard Worker #include "ixheaac_error_standards.h"
26*15dc779aSAndroid Build Coastguard Worker #include "ixheaac_sbr_const.h"
27*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_sbrdecsettings.h"
28*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_bitbuffer.h"
29*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_sbr_common.h"
30*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_drc_data_struct.h"
31*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_drc_dec.h"
32*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_sbrdecoder.h"
33*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_bitbuffer.h"
34*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_env_extr_part.h"
35*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_sbr_rom.h"
36*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_common_rom.h"
37*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_hybrid.h"
38*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_sbr_scale.h"
39*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_ps_dec.h"
40*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_freq_sca.h"
41*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_lpp_tran.h"
42*15dc779aSAndroid Build Coastguard Worker #include "ixheaacd_env_extr.h"
43*15dc779aSAndroid Build Coastguard Worker 
44*15dc779aSAndroid Build Coastguard Worker #include "ixheaac_esbr_rom.h"
45*15dc779aSAndroid Build Coastguard Worker 
46*15dc779aSAndroid Build Coastguard Worker #define ABS(A) fabs(A)
47*15dc779aSAndroid Build Coastguard Worker 
ixheaacd_shellsort(WORD32 * in,WORD32 n)48*15dc779aSAndroid Build Coastguard Worker VOID ixheaacd_shellsort(WORD32 *in, WORD32 n) {
49*15dc779aSAndroid Build Coastguard Worker   WORD32 i, j, v;
50*15dc779aSAndroid Build Coastguard Worker   WORD32 inc = 1;
51*15dc779aSAndroid Build Coastguard Worker 
52*15dc779aSAndroid Build Coastguard Worker   do
53*15dc779aSAndroid Build Coastguard Worker     inc = 3 * inc + 1;
54*15dc779aSAndroid Build Coastguard Worker   while (inc <= n);
55*15dc779aSAndroid Build Coastguard Worker 
56*15dc779aSAndroid Build Coastguard Worker   do {
57*15dc779aSAndroid Build Coastguard Worker     inc = inc / 3;
58*15dc779aSAndroid Build Coastguard Worker     for (i = inc + 1; i <= n; i++) {
59*15dc779aSAndroid Build Coastguard Worker       v = in[i - 1];
60*15dc779aSAndroid Build Coastguard Worker       j = i;
61*15dc779aSAndroid Build Coastguard Worker       while (in[j - inc - 1] > v) {
62*15dc779aSAndroid Build Coastguard Worker         in[j - 1] = in[j - inc - 1];
63*15dc779aSAndroid Build Coastguard Worker         j -= inc;
64*15dc779aSAndroid Build Coastguard Worker         if (j <= inc) break;
65*15dc779aSAndroid Build Coastguard Worker       }
66*15dc779aSAndroid Build Coastguard Worker       in[j - 1] = v;
67*15dc779aSAndroid Build Coastguard Worker     }
68*15dc779aSAndroid Build Coastguard Worker   } while (inc > 1);
69*15dc779aSAndroid Build Coastguard Worker }
70*15dc779aSAndroid Build Coastguard Worker 
ixheaacd_sbr_env_calc(ia_sbr_frame_info_data_struct * frame_data,FLOAT32 input_real[][64],FLOAT32 input_imag[][64],FLOAT32 input_real1[][64],FLOAT32 input_imag1[][64],WORD32 x_over_qmf[MAX_NUM_PATCHES],FLOAT32 * scratch_buff,FLOAT32 * env_out,WORD32 ldmps_present,WORD32 ec_flag)71*15dc779aSAndroid Build Coastguard Worker WORD32 ixheaacd_sbr_env_calc(ia_sbr_frame_info_data_struct *frame_data, FLOAT32 input_real[][64],
72*15dc779aSAndroid Build Coastguard Worker                              FLOAT32 input_imag[][64], FLOAT32 input_real1[][64],
73*15dc779aSAndroid Build Coastguard Worker                              FLOAT32 input_imag1[][64], WORD32 x_over_qmf[MAX_NUM_PATCHES],
74*15dc779aSAndroid Build Coastguard Worker                              FLOAT32 *scratch_buff, FLOAT32 *env_out, WORD32 ldmps_present,
75*15dc779aSAndroid Build Coastguard Worker                              WORD32 ec_flag) {
76*15dc779aSAndroid Build Coastguard Worker   IA_ERRORCODE err_code = IA_NO_ERROR;
77*15dc779aSAndroid Build Coastguard Worker   WORD8 harmonics[64];
78*15dc779aSAndroid Build Coastguard Worker   FLOAT32(*env_tmp)[48];
79*15dc779aSAndroid Build Coastguard Worker   FLOAT32(*noise_level_pvc)[48];
80*15dc779aSAndroid Build Coastguard Worker   FLOAT32(*nrg_est_pvc)[48];
81*15dc779aSAndroid Build Coastguard Worker   FLOAT32(*nrg_ref_pvc)[48];
82*15dc779aSAndroid Build Coastguard Worker   FLOAT32(*nrg_gain_pvc)[48];
83*15dc779aSAndroid Build Coastguard Worker   FLOAT32(*nrg_tone_pvc)[48];
84*15dc779aSAndroid Build Coastguard Worker 
85*15dc779aSAndroid Build Coastguard Worker   WORD32 n, c, li, ui, i, j, k = 0, l, m = 0, kk = 0, o, next = -1, ui2, flag,
86*15dc779aSAndroid Build Coastguard Worker                              tmp, noise_absc_flag, smooth_length;
87*15dc779aSAndroid Build Coastguard Worker   WORD32 upsamp_4_flag = frame_data->pstr_sbr_header->is_usf_4;
88*15dc779aSAndroid Build Coastguard Worker 
89*15dc779aSAndroid Build Coastguard Worker   FLOAT32 *ptr_real_buf, *ptr_imag_buf, nrg = 0, p_ref, p_est, avg_gain, g_max,
90*15dc779aSAndroid Build Coastguard Worker                                         p_adj, boost_gain, sb_gain, sb_noise,
91*15dc779aSAndroid Build Coastguard Worker                                         temp[64];
92*15dc779aSAndroid Build Coastguard Worker 
93*15dc779aSAndroid Build Coastguard Worker   WORD32 t;
94*15dc779aSAndroid Build Coastguard Worker   WORD32 start_pos = 0;
95*15dc779aSAndroid Build Coastguard Worker   WORD32 end_pos = 0;
96*15dc779aSAndroid Build Coastguard Worker 
97*15dc779aSAndroid Build Coastguard Worker   WORD32 slot_idx;
98*15dc779aSAndroid Build Coastguard Worker 
99*15dc779aSAndroid Build Coastguard Worker   FLOAT32 *prev_env_noise_level = frame_data->prev_noise_level;
100*15dc779aSAndroid Build Coastguard Worker   FLOAT32 *nrg_tone = scratch_buff;
101*15dc779aSAndroid Build Coastguard Worker   FLOAT32 *noise_level = scratch_buff + 64;
102*15dc779aSAndroid Build Coastguard Worker   FLOAT32 *nrg_est = scratch_buff + 128;
103*15dc779aSAndroid Build Coastguard Worker   FLOAT32 *nrg_ref = scratch_buff + 192;
104*15dc779aSAndroid Build Coastguard Worker   FLOAT32 *nrg_gain = scratch_buff + 256;
105*15dc779aSAndroid Build Coastguard Worker 
106*15dc779aSAndroid Build Coastguard Worker   const FLOAT32 *smooth_filt;
107*15dc779aSAndroid Build Coastguard Worker 
108*15dc779aSAndroid Build Coastguard Worker   FLOAT32 *sfb_nrg = frame_data->flt_env_sf_arr;
109*15dc779aSAndroid Build Coastguard Worker   FLOAT32 *noise_floor = frame_data->flt_noise_floor;
110*15dc779aSAndroid Build Coastguard Worker   ia_frame_info_struct *p_frame_info = &frame_data->str_frame_info_details;
111*15dc779aSAndroid Build Coastguard Worker 
112*15dc779aSAndroid Build Coastguard Worker   ia_frame_info_struct *pvc_frame_info = &frame_data->str_pvc_frame_info;
113*15dc779aSAndroid Build Coastguard Worker   WORD32 smoothing_length = frame_data->pstr_sbr_header->smoothing_mode ? 0 : 4;
114*15dc779aSAndroid Build Coastguard Worker   WORD32 int_mode = frame_data->pstr_sbr_header->interpol_freq;
115*15dc779aSAndroid Build Coastguard Worker   WORD32 limiter_band = frame_data->pstr_sbr_header->limiter_bands;
116*15dc779aSAndroid Build Coastguard Worker   WORD32 limiter_gains = frame_data->pstr_sbr_header->limiter_gains;
117*15dc779aSAndroid Build Coastguard Worker   WORD32 *add_harmonics = frame_data->add_harmonics;
118*15dc779aSAndroid Build Coastguard Worker   WORD32 sub_band_start =
119*15dc779aSAndroid Build Coastguard Worker       frame_data->pstr_sbr_header->pstr_freq_band_data->sub_band_start;
120*15dc779aSAndroid Build Coastguard Worker   WORD32 sub_band_end =
121*15dc779aSAndroid Build Coastguard Worker       frame_data->pstr_sbr_header->pstr_freq_band_data->sub_band_end;
122*15dc779aSAndroid Build Coastguard Worker   WORD32 reset = frame_data->reset_flag;
123*15dc779aSAndroid Build Coastguard Worker   WORD32 num_subbands = sub_band_end - sub_band_start;
124*15dc779aSAndroid Build Coastguard Worker   WORD32 bs_num_env = p_frame_info->num_env;
125*15dc779aSAndroid Build Coastguard Worker   WORD32 trans_env = p_frame_info->transient_env;
126*15dc779aSAndroid Build Coastguard Worker   WORD32 sbr_mode = frame_data->sbr_mode;
127*15dc779aSAndroid Build Coastguard Worker   WORD32 prev_sbr_mode = frame_data->prev_sbr_mode;
128*15dc779aSAndroid Build Coastguard Worker 
129*15dc779aSAndroid Build Coastguard Worker   WORD16 *freq_band_table[2];
130*15dc779aSAndroid Build Coastguard Worker   const WORD16 *num_sf_bands =
131*15dc779aSAndroid Build Coastguard Worker       frame_data->pstr_sbr_header->pstr_freq_band_data->num_sf_bands;
132*15dc779aSAndroid Build Coastguard Worker   WORD16 *freq_band_table_noise =
133*15dc779aSAndroid Build Coastguard Worker       frame_data->pstr_sbr_header->pstr_freq_band_data->freq_band_tbl_noise;
134*15dc779aSAndroid Build Coastguard Worker   WORD32 num_nf_bands =
135*15dc779aSAndroid Build Coastguard Worker       frame_data->pstr_sbr_header->pstr_freq_band_data->num_nf_bands;
136*15dc779aSAndroid Build Coastguard Worker 
137*15dc779aSAndroid Build Coastguard Worker   WORD32 harm_index = frame_data->harm_index;
138*15dc779aSAndroid Build Coastguard Worker   WORD32 phase_index = frame_data->phase_index;
139*15dc779aSAndroid Build Coastguard Worker   WORD32 esbr_start_up = frame_data->pstr_sbr_header->esbr_start_up;
140*15dc779aSAndroid Build Coastguard Worker   WORD32 esbr_start_up_pvc = frame_data->pstr_sbr_header->esbr_start_up_pvc;
141*15dc779aSAndroid Build Coastguard Worker   WORD8(*harm_flag_prev)[64] = &frame_data->harm_flag_prev;
142*15dc779aSAndroid Build Coastguard Worker   FLOAT32(*e_gain)[5][64] = &frame_data->e_gain;
143*15dc779aSAndroid Build Coastguard Worker   FLOAT32(*noise_buf)[5][64] = &frame_data->noise_buf;
144*15dc779aSAndroid Build Coastguard Worker   WORD32(*lim_table)[4][12 + 1] = &frame_data->lim_table;
145*15dc779aSAndroid Build Coastguard Worker   WORD32(*gate_mode)[4] = &frame_data->gate_mode;
146*15dc779aSAndroid Build Coastguard Worker   WORD32 freq_inv = 1;
147*15dc779aSAndroid Build Coastguard Worker 
148*15dc779aSAndroid Build Coastguard Worker   WORD8(*harm_flag_varlen_prev)[64] = &frame_data->harm_flag_varlen_prev;
149*15dc779aSAndroid Build Coastguard Worker   WORD8(*harm_flag_varlen)[64] = &frame_data->harm_flag_varlen;
150*15dc779aSAndroid Build Coastguard Worker   WORD32 band_loop_end;
151*15dc779aSAndroid Build Coastguard Worker 
152*15dc779aSAndroid Build Coastguard Worker   WORD32 rate = upsamp_4_flag ? 4 : 2;
153*15dc779aSAndroid Build Coastguard Worker   FLOAT64 guard = 1e-17;
154*15dc779aSAndroid Build Coastguard Worker 
155*15dc779aSAndroid Build Coastguard Worker   if (ldmps_present == 1) rate = 1;
156*15dc779aSAndroid Build Coastguard Worker 
157*15dc779aSAndroid Build Coastguard Worker   env_tmp = frame_data->env_tmp;
158*15dc779aSAndroid Build Coastguard Worker   noise_level_pvc = frame_data->noise_level_pvc;
159*15dc779aSAndroid Build Coastguard Worker   nrg_est_pvc = frame_data->nrg_est_pvc;
160*15dc779aSAndroid Build Coastguard Worker   nrg_ref_pvc = frame_data->nrg_ref_pvc;
161*15dc779aSAndroid Build Coastguard Worker   nrg_gain_pvc = frame_data->nrg_gain_pvc;
162*15dc779aSAndroid Build Coastguard Worker   nrg_tone_pvc = frame_data->nrg_tone_pvc;
163*15dc779aSAndroid Build Coastguard Worker 
164*15dc779aSAndroid Build Coastguard Worker   freq_band_table[0] =
165*15dc779aSAndroid Build Coastguard Worker       frame_data->pstr_sbr_header->pstr_freq_band_data->freq_band_table[0];
166*15dc779aSAndroid Build Coastguard Worker   freq_band_table[1] =
167*15dc779aSAndroid Build Coastguard Worker       frame_data->pstr_sbr_header->pstr_freq_band_data->freq_band_table[1];
168*15dc779aSAndroid Build Coastguard Worker 
169*15dc779aSAndroid Build Coastguard Worker   if (reset || (ldmps_present == 1)) {
170*15dc779aSAndroid Build Coastguard Worker     esbr_start_up = 1;
171*15dc779aSAndroid Build Coastguard Worker     esbr_start_up_pvc = 1;
172*15dc779aSAndroid Build Coastguard Worker     if (reset) phase_index = 0;
173*15dc779aSAndroid Build Coastguard Worker     if (ixheaacd_createlimiterbands(
174*15dc779aSAndroid Build Coastguard Worker             (*lim_table), (*gate_mode),
175*15dc779aSAndroid Build Coastguard Worker             frame_data->pstr_sbr_header->pstr_freq_band_data->freq_band_tbl_lo, num_sf_bands[LOW],
176*15dc779aSAndroid Build Coastguard Worker             x_over_qmf, frame_data->sbr_patching_mode, upsamp_4_flag, &frame_data->patch_param,
177*15dc779aSAndroid Build Coastguard Worker             ec_flag))
178*15dc779aSAndroid Build Coastguard Worker       return IA_FATAL_ERROR;
179*15dc779aSAndroid Build Coastguard Worker   }
180*15dc779aSAndroid Build Coastguard Worker 
181*15dc779aSAndroid Build Coastguard Worker   if (frame_data->sbr_patching_mode != frame_data->prev_sbr_patching_mode) {
182*15dc779aSAndroid Build Coastguard Worker     if (ixheaacd_createlimiterbands(
183*15dc779aSAndroid Build Coastguard Worker             (*lim_table), (*gate_mode),
184*15dc779aSAndroid Build Coastguard Worker             frame_data->pstr_sbr_header->pstr_freq_band_data->freq_band_tbl_lo, num_sf_bands[LOW],
185*15dc779aSAndroid Build Coastguard Worker             x_over_qmf, frame_data->sbr_patching_mode, upsamp_4_flag, &frame_data->patch_param,
186*15dc779aSAndroid Build Coastguard Worker             ec_flag))
187*15dc779aSAndroid Build Coastguard Worker       return IA_FATAL_ERROR;
188*15dc779aSAndroid Build Coastguard Worker 
189*15dc779aSAndroid Build Coastguard Worker     frame_data->prev_sbr_patching_mode = frame_data->sbr_patching_mode;
190*15dc779aSAndroid Build Coastguard Worker   }
191*15dc779aSAndroid Build Coastguard Worker 
192*15dc779aSAndroid Build Coastguard Worker   memset(harmonics, 0, 64 * sizeof(WORD8));
193*15dc779aSAndroid Build Coastguard Worker 
194*15dc779aSAndroid Build Coastguard Worker   if (sbr_mode == PVC_SBR) {
195*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_sf_bands[HIGH]; i++) {
196*15dc779aSAndroid Build Coastguard Worker       li =
197*15dc779aSAndroid Build Coastguard Worker           frame_data->pstr_sbr_header->pstr_freq_band_data->freq_band_tbl_hi[i];
198*15dc779aSAndroid Build Coastguard Worker       ui = frame_data->pstr_sbr_header->pstr_freq_band_data
199*15dc779aSAndroid Build Coastguard Worker                ->freq_band_tbl_hi[i + 1];
200*15dc779aSAndroid Build Coastguard Worker       tmp = ((ui + li) - (sub_band_start << 1)) >> 1;
201*15dc779aSAndroid Build Coastguard Worker 
202*15dc779aSAndroid Build Coastguard Worker       if ((tmp >= 64) || (tmp < 0)) {
203*15dc779aSAndroid Build Coastguard Worker         if (ec_flag)
204*15dc779aSAndroid Build Coastguard Worker           tmp = 0;
205*15dc779aSAndroid Build Coastguard Worker         else
206*15dc779aSAndroid Build Coastguard Worker           return -1;
207*15dc779aSAndroid Build Coastguard Worker       }
208*15dc779aSAndroid Build Coastguard Worker 
209*15dc779aSAndroid Build Coastguard Worker       harmonics[tmp] = add_harmonics[i];
210*15dc779aSAndroid Build Coastguard Worker     }
211*15dc779aSAndroid Build Coastguard Worker 
212*15dc779aSAndroid Build Coastguard Worker     for (t = 0; t < p_frame_info->border_vec[0]; t++) {
213*15dc779aSAndroid Build Coastguard Worker       for (c = 0; c < 64; c++) {
214*15dc779aSAndroid Build Coastguard Worker         frame_data->qmapped_pvc[c][t] = frame_data->qmapped_pvc[c][t + 16];
215*15dc779aSAndroid Build Coastguard Worker       }
216*15dc779aSAndroid Build Coastguard Worker     }
217*15dc779aSAndroid Build Coastguard Worker 
218*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < bs_num_env; i++) {
219*15dc779aSAndroid Build Coastguard Worker       if (kk > MAX_NOISE_ENVELOPES) {
220*15dc779aSAndroid Build Coastguard Worker         if (ec_flag)
221*15dc779aSAndroid Build Coastguard Worker           kk = MAX_NOISE_ENVELOPES;
222*15dc779aSAndroid Build Coastguard Worker         else
223*15dc779aSAndroid Build Coastguard Worker           return IA_FATAL_ERROR;
224*15dc779aSAndroid Build Coastguard Worker       }
225*15dc779aSAndroid Build Coastguard Worker       if (p_frame_info->border_vec[i] == p_frame_info->noise_border_vec[kk]) kk++, next++;
226*15dc779aSAndroid Build Coastguard Worker 
227*15dc779aSAndroid Build Coastguard Worker       start_pos = p_frame_info->border_vec[i];
228*15dc779aSAndroid Build Coastguard Worker       end_pos = p_frame_info->border_vec[i + 1];
229*15dc779aSAndroid Build Coastguard Worker       if ((start_pos < 0) || (end_pos > MAX_FREQ_COEFFS_SBR)) {
230*15dc779aSAndroid Build Coastguard Worker         if (ec_flag) {
231*15dc779aSAndroid Build Coastguard Worker           start_pos = 0;
232*15dc779aSAndroid Build Coastguard Worker           end_pos = MAX_FREQ_COEFFS_SBR;
233*15dc779aSAndroid Build Coastguard Worker         } else
234*15dc779aSAndroid Build Coastguard Worker           return IA_FATAL_ERROR;
235*15dc779aSAndroid Build Coastguard Worker       }
236*15dc779aSAndroid Build Coastguard Worker 
237*15dc779aSAndroid Build Coastguard Worker       for (t = start_pos; t < end_pos; t++) {
238*15dc779aSAndroid Build Coastguard Worker         band_loop_end = num_sf_bands[p_frame_info->freq_res[i]];
239*15dc779aSAndroid Build Coastguard Worker 
240*15dc779aSAndroid Build Coastguard Worker         for (c = 0, o = 0, j = 0; j < band_loop_end; j++) {
241*15dc779aSAndroid Build Coastguard Worker           li = freq_band_table[p_frame_info->freq_res[i]][j];
242*15dc779aSAndroid Build Coastguard Worker           ui = freq_band_table[p_frame_info->freq_res[i]][j + 1];
243*15dc779aSAndroid Build Coastguard Worker           ui2 = frame_data->pstr_sbr_header->pstr_freq_band_data
244*15dc779aSAndroid Build Coastguard Worker                     ->freq_band_tbl_noise[o + 1];
245*15dc779aSAndroid Build Coastguard Worker 
246*15dc779aSAndroid Build Coastguard Worker           for (k = 0; k < ui - li; k++) {
247*15dc779aSAndroid Build Coastguard Worker             o = (k + li >= ui2) ? o + 1 : o;
248*15dc779aSAndroid Build Coastguard Worker             if (o >= MAX_NOISE_COEFFS) {
249*15dc779aSAndroid Build Coastguard Worker               if (ec_flag)
250*15dc779aSAndroid Build Coastguard Worker                 o = MAX_NOISE_COEFFS - 1;
251*15dc779aSAndroid Build Coastguard Worker               else
252*15dc779aSAndroid Build Coastguard Worker                 return IA_FATAL_ERROR;
253*15dc779aSAndroid Build Coastguard Worker             }
254*15dc779aSAndroid Build Coastguard Worker             ui2 = freq_band_table_noise[o + 1];
255*15dc779aSAndroid Build Coastguard Worker 
256*15dc779aSAndroid Build Coastguard Worker             frame_data->qmapped_pvc[c][t] =
257*15dc779aSAndroid Build Coastguard Worker                 noise_floor[next * num_nf_bands + o];
258*15dc779aSAndroid Build Coastguard Worker             c++;
259*15dc779aSAndroid Build Coastguard Worker           }
260*15dc779aSAndroid Build Coastguard Worker         }
261*15dc779aSAndroid Build Coastguard Worker       }
262*15dc779aSAndroid Build Coastguard Worker     }
263*15dc779aSAndroid Build Coastguard Worker 
264*15dc779aSAndroid Build Coastguard Worker     kk = 0;
265*15dc779aSAndroid Build Coastguard Worker     next = -1;
266*15dc779aSAndroid Build Coastguard Worker 
267*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < bs_num_env; i++) {
268*15dc779aSAndroid Build Coastguard Worker       if (kk > MAX_NOISE_ENVELOPES) {
269*15dc779aSAndroid Build Coastguard Worker         if (ec_flag)
270*15dc779aSAndroid Build Coastguard Worker           kk = MAX_NOISE_ENVELOPES;
271*15dc779aSAndroid Build Coastguard Worker         else
272*15dc779aSAndroid Build Coastguard Worker           return IA_FATAL_ERROR;
273*15dc779aSAndroid Build Coastguard Worker       }
274*15dc779aSAndroid Build Coastguard Worker       if (p_frame_info->border_vec[i] == p_frame_info->noise_border_vec[kk]) kk++, next++;
275*15dc779aSAndroid Build Coastguard Worker 
276*15dc779aSAndroid Build Coastguard Worker       start_pos = pvc_frame_info->border_vec[i];
277*15dc779aSAndroid Build Coastguard Worker       end_pos = pvc_frame_info->border_vec[i + 1];
278*15dc779aSAndroid Build Coastguard Worker       if ((start_pos < 0) || (end_pos > MAX_FREQ_COEFFS_SBR)) {
279*15dc779aSAndroid Build Coastguard Worker         if (ec_flag) {
280*15dc779aSAndroid Build Coastguard Worker           start_pos = 0;
281*15dc779aSAndroid Build Coastguard Worker           end_pos = MAX_FREQ_COEFFS_SBR;
282*15dc779aSAndroid Build Coastguard Worker         } else
283*15dc779aSAndroid Build Coastguard Worker           return IA_FATAL_ERROR;
284*15dc779aSAndroid Build Coastguard Worker       }
285*15dc779aSAndroid Build Coastguard Worker       for (t = start_pos; t < end_pos; t++) {
286*15dc779aSAndroid Build Coastguard Worker         for (c = 0; c < 64; c++) {
287*15dc779aSAndroid Build Coastguard Worker           env_tmp[c][t] = env_out[64 * t + c];
288*15dc779aSAndroid Build Coastguard Worker         }
289*15dc779aSAndroid Build Coastguard Worker       }
290*15dc779aSAndroid Build Coastguard Worker 
291*15dc779aSAndroid Build Coastguard Worker       noise_absc_flag =
292*15dc779aSAndroid Build Coastguard Worker           (i == trans_env || i == frame_data->env_short_flag_prev) ? 1 : 0;
293*15dc779aSAndroid Build Coastguard Worker 
294*15dc779aSAndroid Build Coastguard Worker       if (prev_sbr_mode == ORIG_SBR) noise_absc_flag = 0;
295*15dc779aSAndroid Build Coastguard Worker 
296*15dc779aSAndroid Build Coastguard Worker       smooth_length = (noise_absc_flag ? 0 : smoothing_length);
297*15dc779aSAndroid Build Coastguard Worker       smooth_filt = *ixheaac_fir_table[smooth_length];
298*15dc779aSAndroid Build Coastguard Worker 
299*15dc779aSAndroid Build Coastguard Worker       for (t = start_pos; t < frame_data->sin_len_for_cur_top; t++) {
300*15dc779aSAndroid Build Coastguard Worker         band_loop_end =
301*15dc779aSAndroid Build Coastguard Worker             num_sf_bands[frame_data->str_frame_info_prev
302*15dc779aSAndroid Build Coastguard Worker                              .freq_res[frame_data->var_len_id_prev]];
303*15dc779aSAndroid Build Coastguard Worker 
304*15dc779aSAndroid Build Coastguard Worker         for (c = 0, o = 0, j = 0; j < band_loop_end; j++) {
305*15dc779aSAndroid Build Coastguard Worker           double tmp;
306*15dc779aSAndroid Build Coastguard Worker 
307*15dc779aSAndroid Build Coastguard Worker           li = freq_band_table[frame_data->str_frame_info_prev
308*15dc779aSAndroid Build Coastguard Worker                                    .freq_res[frame_data->var_len_id_prev]][j];
309*15dc779aSAndroid Build Coastguard Worker           ui = freq_band_table[frame_data->str_frame_info_prev
310*15dc779aSAndroid Build Coastguard Worker                                    .freq_res[frame_data->var_len_id_prev]]
311*15dc779aSAndroid Build Coastguard Worker                               [j + 1];
312*15dc779aSAndroid Build Coastguard Worker           ui2 = frame_data->pstr_sbr_header->pstr_freq_band_data
313*15dc779aSAndroid Build Coastguard Worker                     ->freq_band_tbl_noise[o + 1];
314*15dc779aSAndroid Build Coastguard Worker 
315*15dc779aSAndroid Build Coastguard Worker           for (flag = 0, k = li; k < ui; k++) {
316*15dc779aSAndroid Build Coastguard Worker             flag = ((*harm_flag_varlen)[c] &&
317*15dc779aSAndroid Build Coastguard Worker                     (t >= frame_data->sin_start_for_cur_top ||
318*15dc779aSAndroid Build Coastguard Worker                      (*harm_flag_varlen_prev)[c + sub_band_start]))
319*15dc779aSAndroid Build Coastguard Worker                        ? 1
320*15dc779aSAndroid Build Coastguard Worker                        : flag;
321*15dc779aSAndroid Build Coastguard Worker 
322*15dc779aSAndroid Build Coastguard Worker             nrg_ref_pvc[c][t] = env_tmp[k][t];
323*15dc779aSAndroid Build Coastguard Worker             for (nrg = 0, l = 0; l < rate; l++) {
324*15dc779aSAndroid Build Coastguard Worker               nrg +=
325*15dc779aSAndroid Build Coastguard Worker                   (input_real[rate * t + l][k] * input_real[rate * t + l][k]) +
326*15dc779aSAndroid Build Coastguard Worker                   (input_imag[rate * t + l][k] * input_imag[rate * t + l][k]);
327*15dc779aSAndroid Build Coastguard Worker             }
328*15dc779aSAndroid Build Coastguard Worker             nrg_est_pvc[c][t] = nrg / rate;
329*15dc779aSAndroid Build Coastguard Worker             c++;
330*15dc779aSAndroid Build Coastguard Worker           }
331*15dc779aSAndroid Build Coastguard Worker 
332*15dc779aSAndroid Build Coastguard Worker           if (!int_mode && ui != li) {
333*15dc779aSAndroid Build Coastguard Worker             for (nrg = 0, k = c - (ui - li); k < c; k++) {
334*15dc779aSAndroid Build Coastguard Worker               nrg += nrg_est_pvc[k][t];
335*15dc779aSAndroid Build Coastguard Worker             }
336*15dc779aSAndroid Build Coastguard Worker             nrg /= (ui - li);
337*15dc779aSAndroid Build Coastguard Worker           } else {
338*15dc779aSAndroid Build Coastguard Worker             nrg = 0;
339*15dc779aSAndroid Build Coastguard Worker           }
340*15dc779aSAndroid Build Coastguard Worker           c -= (ui - li);
341*15dc779aSAndroid Build Coastguard Worker 
342*15dc779aSAndroid Build Coastguard Worker           for (k = 0; k < ui - li; k++) {
343*15dc779aSAndroid Build Coastguard Worker             o = (k + li >= ui2) ? o + 1 : o;
344*15dc779aSAndroid Build Coastguard Worker             if (o >= MAX_NOISE_COEFFS) {
345*15dc779aSAndroid Build Coastguard Worker               if (ec_flag)
346*15dc779aSAndroid Build Coastguard Worker                 o = MAX_NOISE_COEFFS - 1;
347*15dc779aSAndroid Build Coastguard Worker               else
348*15dc779aSAndroid Build Coastguard Worker                 return IA_FATAL_ERROR;
349*15dc779aSAndroid Build Coastguard Worker             }
350*15dc779aSAndroid Build Coastguard Worker             ui2 = freq_band_table_noise[o + 1];
351*15dc779aSAndroid Build Coastguard Worker             nrg_est_pvc[c][t] = (!int_mode) ? nrg : nrg_est_pvc[c][t];
352*15dc779aSAndroid Build Coastguard Worker             nrg_tone_pvc[c][t] = 0.0f;
353*15dc779aSAndroid Build Coastguard Worker 
354*15dc779aSAndroid Build Coastguard Worker             tmp = frame_data->qmapped_pvc[c][t] /
355*15dc779aSAndroid Build Coastguard Worker                   (1 + frame_data->qmapped_pvc[c][t] + guard);
356*15dc779aSAndroid Build Coastguard Worker 
357*15dc779aSAndroid Build Coastguard Worker             if (flag) {
358*15dc779aSAndroid Build Coastguard Worker               nrg_gain_pvc[c][t] = (FLOAT32)sqrt(nrg_ref_pvc[c][t] * tmp /
359*15dc779aSAndroid Build Coastguard Worker                                                  (nrg_est_pvc[c][t] + 1));
360*15dc779aSAndroid Build Coastguard Worker 
361*15dc779aSAndroid Build Coastguard Worker               nrg_tone_pvc[c][t] = (FLOAT32)(
362*15dc779aSAndroid Build Coastguard Worker                   (harmonics[c] && (t >= frame_data->sine_position ||
363*15dc779aSAndroid Build Coastguard Worker                                     (*harm_flag_prev)[c + sub_band_start]))
364*15dc779aSAndroid Build Coastguard Worker                       ? sqrt(nrg_ref_pvc[c][t] * tmp /
365*15dc779aSAndroid Build Coastguard Worker                              (frame_data->qmapped_pvc[c][t] + guard))
366*15dc779aSAndroid Build Coastguard Worker                       : nrg_tone_pvc[c][t]);
367*15dc779aSAndroid Build Coastguard Worker 
368*15dc779aSAndroid Build Coastguard Worker               nrg_tone_pvc[c][t] =
369*15dc779aSAndroid Build Coastguard Worker                   (FLOAT32)(((*harm_flag_varlen)[c] &&
370*15dc779aSAndroid Build Coastguard Worker                              (t >= frame_data->sin_start_for_cur_top ||
371*15dc779aSAndroid Build Coastguard Worker                               (*harm_flag_varlen_prev)[c + sub_band_start]))
372*15dc779aSAndroid Build Coastguard Worker                                 ? sqrt(nrg_ref_pvc[c][t] * tmp /
373*15dc779aSAndroid Build Coastguard Worker                                        (prev_env_noise_level[o] + guard))
374*15dc779aSAndroid Build Coastguard Worker                                 : nrg_tone_pvc[c][t]);
375*15dc779aSAndroid Build Coastguard Worker 
376*15dc779aSAndroid Build Coastguard Worker             } else {
377*15dc779aSAndroid Build Coastguard Worker               if (noise_absc_flag) {
378*15dc779aSAndroid Build Coastguard Worker                 nrg_gain_pvc[c][t] =
379*15dc779aSAndroid Build Coastguard Worker                     (FLOAT32)sqrt(nrg_ref_pvc[c][t] / (nrg_est_pvc[c][t] + 1));
380*15dc779aSAndroid Build Coastguard Worker               } else {
381*15dc779aSAndroid Build Coastguard Worker                 nrg_gain_pvc[c][t] = (FLOAT32)sqrt(
382*15dc779aSAndroid Build Coastguard Worker                     nrg_ref_pvc[c][t] * tmp /
383*15dc779aSAndroid Build Coastguard Worker                     ((nrg_est_pvc[c][t] + 1) * (frame_data->qmapped_pvc[c][t] + guard)));
384*15dc779aSAndroid Build Coastguard Worker               }
385*15dc779aSAndroid Build Coastguard Worker             }
386*15dc779aSAndroid Build Coastguard Worker 
387*15dc779aSAndroid Build Coastguard Worker             noise_level_pvc[c][t] = (FLOAT32)sqrt(nrg_ref_pvc[c][t] * tmp);
388*15dc779aSAndroid Build Coastguard Worker             c++;
389*15dc779aSAndroid Build Coastguard Worker           }
390*15dc779aSAndroid Build Coastguard Worker         }
391*15dc779aSAndroid Build Coastguard Worker 
392*15dc779aSAndroid Build Coastguard Worker         for (c = 0; c < (*gate_mode)[limiter_band]; c++) {
393*15dc779aSAndroid Build Coastguard Worker           p_ref = p_est = 0.0f;
394*15dc779aSAndroid Build Coastguard Worker           p_adj = 0;
395*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
396*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
397*15dc779aSAndroid Build Coastguard Worker             p_ref += nrg_ref_pvc[k][t];
398*15dc779aSAndroid Build Coastguard Worker             p_est += nrg_est_pvc[k][t];
399*15dc779aSAndroid Build Coastguard Worker           }
400*15dc779aSAndroid Build Coastguard Worker           avg_gain = (FLOAT32)sqrt((p_ref + EPS) / (p_est + EPS));
401*15dc779aSAndroid Build Coastguard Worker           g_max = avg_gain * ixheaac_g_lim_gains[limiter_gains];
402*15dc779aSAndroid Build Coastguard Worker           g_max > 1.0e5f ? g_max = 1.0e5f : 0;
403*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
404*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
405*15dc779aSAndroid Build Coastguard Worker             if (g_max <= nrg_gain_pvc[k][t]) {
406*15dc779aSAndroid Build Coastguard Worker               noise_level_pvc[k][t] =
407*15dc779aSAndroid Build Coastguard Worker                   (FLOAT32)(noise_level_pvc[k][t] * (g_max / (nrg_gain_pvc[k][t] + guard)));
408*15dc779aSAndroid Build Coastguard Worker               nrg_gain_pvc[k][t] = g_max;
409*15dc779aSAndroid Build Coastguard Worker             }
410*15dc779aSAndroid Build Coastguard Worker 
411*15dc779aSAndroid Build Coastguard Worker             p_adj +=
412*15dc779aSAndroid Build Coastguard Worker                 nrg_gain_pvc[k][t] * nrg_gain_pvc[k][t] * nrg_est_pvc[k][t];
413*15dc779aSAndroid Build Coastguard Worker 
414*15dc779aSAndroid Build Coastguard Worker             if (nrg_tone_pvc[k][t]) {
415*15dc779aSAndroid Build Coastguard Worker               p_adj += nrg_tone_pvc[k][t] * nrg_tone_pvc[k][t];
416*15dc779aSAndroid Build Coastguard Worker             } else if (!noise_absc_flag) {
417*15dc779aSAndroid Build Coastguard Worker               p_adj += noise_level_pvc[k][t] * noise_level_pvc[k][t];
418*15dc779aSAndroid Build Coastguard Worker             }
419*15dc779aSAndroid Build Coastguard Worker           }
420*15dc779aSAndroid Build Coastguard Worker           boost_gain = (FLOAT32)sqrt((p_ref + EPS) / (p_adj + EPS));
421*15dc779aSAndroid Build Coastguard Worker           boost_gain = boost_gain > 1.584893192f ? 1.584893192f : boost_gain;
422*15dc779aSAndroid Build Coastguard Worker 
423*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
424*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
425*15dc779aSAndroid Build Coastguard Worker             nrg_gain_pvc[k][t] *= boost_gain;
426*15dc779aSAndroid Build Coastguard Worker             noise_level_pvc[k][t] *= boost_gain;
427*15dc779aSAndroid Build Coastguard Worker             nrg_tone_pvc[k][t] *= boost_gain;
428*15dc779aSAndroid Build Coastguard Worker           }
429*15dc779aSAndroid Build Coastguard Worker         }
430*15dc779aSAndroid Build Coastguard Worker       }
431*15dc779aSAndroid Build Coastguard Worker 
432*15dc779aSAndroid Build Coastguard Worker       for (; t < end_pos; t++) {
433*15dc779aSAndroid Build Coastguard Worker         band_loop_end = num_sf_bands[pvc_frame_info->freq_res[i]];
434*15dc779aSAndroid Build Coastguard Worker 
435*15dc779aSAndroid Build Coastguard Worker         for (c = 0, o = 0, j = 0; j < band_loop_end; j++) {
436*15dc779aSAndroid Build Coastguard Worker           double tmp;
437*15dc779aSAndroid Build Coastguard Worker 
438*15dc779aSAndroid Build Coastguard Worker           li = freq_band_table[pvc_frame_info->freq_res[i]][j];
439*15dc779aSAndroid Build Coastguard Worker           ui = freq_band_table[pvc_frame_info->freq_res[i]][j + 1];
440*15dc779aSAndroid Build Coastguard Worker           ui2 = frame_data->pstr_sbr_header->pstr_freq_band_data
441*15dc779aSAndroid Build Coastguard Worker                     ->freq_band_tbl_noise[o + 1];
442*15dc779aSAndroid Build Coastguard Worker 
443*15dc779aSAndroid Build Coastguard Worker           for (flag = 0, k = li; k < ui; k++) {
444*15dc779aSAndroid Build Coastguard Worker             flag = (harmonics[c] && (t >= frame_data->sine_position ||
445*15dc779aSAndroid Build Coastguard Worker                                      (*harm_flag_prev)[c + sub_band_start]))
446*15dc779aSAndroid Build Coastguard Worker                        ? 1
447*15dc779aSAndroid Build Coastguard Worker                        : flag;
448*15dc779aSAndroid Build Coastguard Worker 
449*15dc779aSAndroid Build Coastguard Worker             nrg_ref_pvc[c][t] = env_tmp[k][t];
450*15dc779aSAndroid Build Coastguard Worker             for (nrg = 0, l = 0; l < rate; l++) {
451*15dc779aSAndroid Build Coastguard Worker               nrg +=
452*15dc779aSAndroid Build Coastguard Worker                   (input_real[rate * t + l][k] * input_real[rate * t + l][k]) +
453*15dc779aSAndroid Build Coastguard Worker                   (input_imag[rate * t + l][k] * input_imag[rate * t + l][k]);
454*15dc779aSAndroid Build Coastguard Worker             }
455*15dc779aSAndroid Build Coastguard Worker             nrg_est_pvc[c][t] = nrg / rate;
456*15dc779aSAndroid Build Coastguard Worker             c++;
457*15dc779aSAndroid Build Coastguard Worker           }
458*15dc779aSAndroid Build Coastguard Worker 
459*15dc779aSAndroid Build Coastguard Worker           if (!int_mode && ui != li) {
460*15dc779aSAndroid Build Coastguard Worker             for (nrg = 0, k = c - (ui - li); k < c; k++) {
461*15dc779aSAndroid Build Coastguard Worker               nrg += nrg_est_pvc[k][t];
462*15dc779aSAndroid Build Coastguard Worker             }
463*15dc779aSAndroid Build Coastguard Worker             nrg /= (ui - li);
464*15dc779aSAndroid Build Coastguard Worker           } else {
465*15dc779aSAndroid Build Coastguard Worker             nrg = 0;
466*15dc779aSAndroid Build Coastguard Worker           }
467*15dc779aSAndroid Build Coastguard Worker           c -= (ui - li);
468*15dc779aSAndroid Build Coastguard Worker 
469*15dc779aSAndroid Build Coastguard Worker           for (k = 0; k < ui - li; k++) {
470*15dc779aSAndroid Build Coastguard Worker             o = (k + li >= ui2) ? o + 1 : o;
471*15dc779aSAndroid Build Coastguard Worker             if (o >= MAX_NOISE_COEFFS) {
472*15dc779aSAndroid Build Coastguard Worker               if (ec_flag)
473*15dc779aSAndroid Build Coastguard Worker                 o = MAX_NOISE_COEFFS - 1;
474*15dc779aSAndroid Build Coastguard Worker               else
475*15dc779aSAndroid Build Coastguard Worker                 return IA_FATAL_ERROR;
476*15dc779aSAndroid Build Coastguard Worker             }
477*15dc779aSAndroid Build Coastguard Worker             ui2 = freq_band_table_noise[o + 1];
478*15dc779aSAndroid Build Coastguard Worker             nrg_est_pvc[c][t] = (!int_mode) ? nrg : nrg_est_pvc[c][t];
479*15dc779aSAndroid Build Coastguard Worker             nrg_tone_pvc[c][t] = 0.0f;
480*15dc779aSAndroid Build Coastguard Worker 
481*15dc779aSAndroid Build Coastguard Worker             tmp = frame_data->qmapped_pvc[c][t] /
482*15dc779aSAndroid Build Coastguard Worker                   (1 + frame_data->qmapped_pvc[c][t] + guard);
483*15dc779aSAndroid Build Coastguard Worker 
484*15dc779aSAndroid Build Coastguard Worker             if (flag) {
485*15dc779aSAndroid Build Coastguard Worker               nrg_gain_pvc[c][t] = (FLOAT32)sqrt(nrg_ref_pvc[c][t] * tmp /
486*15dc779aSAndroid Build Coastguard Worker                                                  (nrg_est_pvc[c][t] + 1));
487*15dc779aSAndroid Build Coastguard Worker 
488*15dc779aSAndroid Build Coastguard Worker               nrg_tone_pvc[c][t] = (FLOAT32)(
489*15dc779aSAndroid Build Coastguard Worker                   (harmonics[c] && (t >= frame_data->sine_position ||
490*15dc779aSAndroid Build Coastguard Worker                                     (*harm_flag_prev)[c + sub_band_start]))
491*15dc779aSAndroid Build Coastguard Worker                       ? sqrt(nrg_ref_pvc[c][t] * tmp /
492*15dc779aSAndroid Build Coastguard Worker                              (frame_data->qmapped_pvc[c][t] + guard))
493*15dc779aSAndroid Build Coastguard Worker                       : nrg_tone_pvc[c][t]);
494*15dc779aSAndroid Build Coastguard Worker             } else {
495*15dc779aSAndroid Build Coastguard Worker               if (noise_absc_flag) {
496*15dc779aSAndroid Build Coastguard Worker                 nrg_gain_pvc[c][t] =
497*15dc779aSAndroid Build Coastguard Worker                     (FLOAT32)sqrt(nrg_ref_pvc[c][t] / (nrg_est_pvc[c][t] + 1));
498*15dc779aSAndroid Build Coastguard Worker               } else {
499*15dc779aSAndroid Build Coastguard Worker                 nrg_gain_pvc[c][t] = (FLOAT32)sqrt(
500*15dc779aSAndroid Build Coastguard Worker                     nrg_ref_pvc[c][t] * tmp /
501*15dc779aSAndroid Build Coastguard Worker                     ((nrg_est_pvc[c][t] + 1) * (frame_data->qmapped_pvc[c][t] + guard)));
502*15dc779aSAndroid Build Coastguard Worker               }
503*15dc779aSAndroid Build Coastguard Worker             }
504*15dc779aSAndroid Build Coastguard Worker 
505*15dc779aSAndroid Build Coastguard Worker             noise_level_pvc[c][t] = (FLOAT32)sqrt(nrg_ref_pvc[c][t] * tmp);
506*15dc779aSAndroid Build Coastguard Worker             c++;
507*15dc779aSAndroid Build Coastguard Worker           }
508*15dc779aSAndroid Build Coastguard Worker         }
509*15dc779aSAndroid Build Coastguard Worker 
510*15dc779aSAndroid Build Coastguard Worker         for (c = 0; c < (*gate_mode)[limiter_band]; c++) {
511*15dc779aSAndroid Build Coastguard Worker           p_ref = p_est = 0.0f;
512*15dc779aSAndroid Build Coastguard Worker           p_adj = 0;
513*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
514*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
515*15dc779aSAndroid Build Coastguard Worker             p_ref += nrg_ref_pvc[k][t];
516*15dc779aSAndroid Build Coastguard Worker             p_est += nrg_est_pvc[k][t];
517*15dc779aSAndroid Build Coastguard Worker           }
518*15dc779aSAndroid Build Coastguard Worker           avg_gain = (FLOAT32)sqrt((p_ref + EPS) / (p_est + EPS));
519*15dc779aSAndroid Build Coastguard Worker           g_max = avg_gain * ixheaac_g_lim_gains[limiter_gains];
520*15dc779aSAndroid Build Coastguard Worker           g_max > 1.0e5f ? g_max = 1.0e5f : 0;
521*15dc779aSAndroid Build Coastguard Worker 
522*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
523*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
524*15dc779aSAndroid Build Coastguard Worker             if (g_max <= nrg_gain_pvc[k][t]) {
525*15dc779aSAndroid Build Coastguard Worker               noise_level_pvc[k][t] =
526*15dc779aSAndroid Build Coastguard Worker                   (FLOAT32)(noise_level_pvc[k][t] *
527*15dc779aSAndroid Build Coastguard Worker                             (g_max / (nrg_gain_pvc[k][t] + guard)));
528*15dc779aSAndroid Build Coastguard Worker               nrg_gain_pvc[k][t] = g_max;
529*15dc779aSAndroid Build Coastguard Worker             }
530*15dc779aSAndroid Build Coastguard Worker 
531*15dc779aSAndroid Build Coastguard Worker             p_adj +=
532*15dc779aSAndroid Build Coastguard Worker                 nrg_gain_pvc[k][t] * nrg_gain_pvc[k][t] * nrg_est_pvc[k][t];
533*15dc779aSAndroid Build Coastguard Worker 
534*15dc779aSAndroid Build Coastguard Worker             if (nrg_tone_pvc[k][t]) {
535*15dc779aSAndroid Build Coastguard Worker               p_adj += nrg_tone_pvc[k][t] * nrg_tone_pvc[k][t];
536*15dc779aSAndroid Build Coastguard Worker             } else if (!noise_absc_flag) {
537*15dc779aSAndroid Build Coastguard Worker               p_adj += noise_level_pvc[k][t] * noise_level_pvc[k][t];
538*15dc779aSAndroid Build Coastguard Worker             }
539*15dc779aSAndroid Build Coastguard Worker           }
540*15dc779aSAndroid Build Coastguard Worker 
541*15dc779aSAndroid Build Coastguard Worker           boost_gain = (FLOAT32)sqrt((p_ref + EPS) / (p_adj + EPS));
542*15dc779aSAndroid Build Coastguard Worker           boost_gain = boost_gain > 1.584893192f ? 1.584893192f : boost_gain;
543*15dc779aSAndroid Build Coastguard Worker 
544*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
545*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
546*15dc779aSAndroid Build Coastguard Worker             nrg_gain_pvc[k][t] *= boost_gain;
547*15dc779aSAndroid Build Coastguard Worker             noise_level_pvc[k][t] *= boost_gain;
548*15dc779aSAndroid Build Coastguard Worker             nrg_tone_pvc[k][t] *= boost_gain;
549*15dc779aSAndroid Build Coastguard Worker           }
550*15dc779aSAndroid Build Coastguard Worker         }
551*15dc779aSAndroid Build Coastguard Worker       }
552*15dc779aSAndroid Build Coastguard Worker 
553*15dc779aSAndroid Build Coastguard Worker       if (esbr_start_up_pvc) {
554*15dc779aSAndroid Build Coastguard Worker         for (n = 0; n < 4; n++) {
555*15dc779aSAndroid Build Coastguard Worker           for (c = 0; c < num_subbands; c++) {
556*15dc779aSAndroid Build Coastguard Worker             (*e_gain)[n][c] = nrg_gain_pvc[c][start_pos];
557*15dc779aSAndroid Build Coastguard Worker             (*noise_buf)[n][c] = noise_level_pvc[c][start_pos];
558*15dc779aSAndroid Build Coastguard Worker           }
559*15dc779aSAndroid Build Coastguard Worker         }
560*15dc779aSAndroid Build Coastguard Worker         esbr_start_up_pvc = 0;
561*15dc779aSAndroid Build Coastguard Worker         esbr_start_up = 0;
562*15dc779aSAndroid Build Coastguard Worker       }
563*15dc779aSAndroid Build Coastguard Worker       for (l = rate * pvc_frame_info->border_vec[i];
564*15dc779aSAndroid Build Coastguard Worker            l < rate * pvc_frame_info->border_vec[1 + i]; l++) {
565*15dc779aSAndroid Build Coastguard Worker         ptr_real_buf = *(input_real + l) + sub_band_start;
566*15dc779aSAndroid Build Coastguard Worker         ptr_imag_buf = *(input_imag + l) + sub_band_start;
567*15dc779aSAndroid Build Coastguard Worker 
568*15dc779aSAndroid Build Coastguard Worker         slot_idx = (WORD32)l / rate;
569*15dc779aSAndroid Build Coastguard Worker         if (sub_band_start & 1) {
570*15dc779aSAndroid Build Coastguard Worker           freq_inv = -1;
571*15dc779aSAndroid Build Coastguard Worker         } else {
572*15dc779aSAndroid Build Coastguard Worker           freq_inv = 1;
573*15dc779aSAndroid Build Coastguard Worker         }
574*15dc779aSAndroid Build Coastguard Worker 
575*15dc779aSAndroid Build Coastguard Worker         for (k = 0; k < num_subbands; k++) {
576*15dc779aSAndroid Build Coastguard Worker           (*e_gain)[4][k] = nrg_gain_pvc[k][slot_idx];
577*15dc779aSAndroid Build Coastguard Worker           (*noise_buf)[4][k] = noise_level_pvc[k][slot_idx];
578*15dc779aSAndroid Build Coastguard Worker           c = 0, sb_gain = 0, sb_noise = 0;
579*15dc779aSAndroid Build Coastguard Worker           for (n = 4 - smooth_length; n <= 4; n++) {
580*15dc779aSAndroid Build Coastguard Worker             sb_gain += (*e_gain)[n][k] * smooth_filt[c];
581*15dc779aSAndroid Build Coastguard Worker             sb_noise += (*noise_buf)[n][k] * smooth_filt[c++];
582*15dc779aSAndroid Build Coastguard Worker           }
583*15dc779aSAndroid Build Coastguard Worker           phase_index = (phase_index + 1) & 511;
584*15dc779aSAndroid Build Coastguard Worker           sb_noise = (nrg_tone_pvc[k][slot_idx] != 0 || noise_absc_flag)
585*15dc779aSAndroid Build Coastguard Worker                          ? 0
586*15dc779aSAndroid Build Coastguard Worker                          : sb_noise;
587*15dc779aSAndroid Build Coastguard Worker 
588*15dc779aSAndroid Build Coastguard Worker           *ptr_real_buf =
589*15dc779aSAndroid Build Coastguard Worker               *ptr_real_buf * sb_gain +
590*15dc779aSAndroid Build Coastguard Worker               sb_noise * ixheaac_random_phase[phase_index][0] +
591*15dc779aSAndroid Build Coastguard Worker               nrg_tone_pvc[k][slot_idx] * ixheaac_hphase_tbl[0][harm_index];
592*15dc779aSAndroid Build Coastguard Worker           *ptr_imag_buf = *ptr_imag_buf * sb_gain +
593*15dc779aSAndroid Build Coastguard Worker                           sb_noise * ixheaac_random_phase[phase_index][1] +
594*15dc779aSAndroid Build Coastguard Worker                           nrg_tone_pvc[k][slot_idx] * freq_inv *
595*15dc779aSAndroid Build Coastguard Worker                               ixheaac_hphase_tbl[1][harm_index];
596*15dc779aSAndroid Build Coastguard Worker 
597*15dc779aSAndroid Build Coastguard Worker           ptr_real_buf++;
598*15dc779aSAndroid Build Coastguard Worker           ptr_imag_buf++;
599*15dc779aSAndroid Build Coastguard Worker           freq_inv = -freq_inv;
600*15dc779aSAndroid Build Coastguard Worker         }
601*15dc779aSAndroid Build Coastguard Worker 
602*15dc779aSAndroid Build Coastguard Worker         harm_index = (harm_index + 1) & 3;
603*15dc779aSAndroid Build Coastguard Worker 
604*15dc779aSAndroid Build Coastguard Worker         memcpy(temp, (*e_gain)[0], 64 * sizeof(FLOAT32));
605*15dc779aSAndroid Build Coastguard Worker         for (n = 0; n < 4; n++) {
606*15dc779aSAndroid Build Coastguard Worker           memcpy((*e_gain)[n], (*e_gain)[n + 1], 64 * sizeof(FLOAT32));
607*15dc779aSAndroid Build Coastguard Worker         }
608*15dc779aSAndroid Build Coastguard Worker         memcpy((*e_gain)[4], temp, 64 * sizeof(FLOAT32));
609*15dc779aSAndroid Build Coastguard Worker 
610*15dc779aSAndroid Build Coastguard Worker         memcpy(temp, (*noise_buf)[0], 64 * sizeof(FLOAT32));
611*15dc779aSAndroid Build Coastguard Worker         for (n = 0; n < 4; n++) {
612*15dc779aSAndroid Build Coastguard Worker           memcpy((*noise_buf)[n], (*noise_buf)[n + 1], 64 * sizeof(FLOAT32));
613*15dc779aSAndroid Build Coastguard Worker         }
614*15dc779aSAndroid Build Coastguard Worker         memcpy((*noise_buf)[4], temp, 64 * sizeof(FLOAT32));
615*15dc779aSAndroid Build Coastguard Worker       }
616*15dc779aSAndroid Build Coastguard Worker     }
617*15dc779aSAndroid Build Coastguard Worker   } else {
618*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_sf_bands[HIGH]; i++) {
619*15dc779aSAndroid Build Coastguard Worker       li =
620*15dc779aSAndroid Build Coastguard Worker           frame_data->pstr_sbr_header->pstr_freq_band_data->freq_band_tbl_hi[i];
621*15dc779aSAndroid Build Coastguard Worker       ui = frame_data->pstr_sbr_header->pstr_freq_band_data
622*15dc779aSAndroid Build Coastguard Worker                ->freq_band_tbl_hi[i + 1];
623*15dc779aSAndroid Build Coastguard Worker       tmp = ((ui + li) - (sub_band_start << 1)) >> 1;
624*15dc779aSAndroid Build Coastguard Worker       if ((tmp >= 64) || (tmp < 0)) return -1;
625*15dc779aSAndroid Build Coastguard Worker 
626*15dc779aSAndroid Build Coastguard Worker       harmonics[tmp] = add_harmonics[i];
627*15dc779aSAndroid Build Coastguard Worker     }
628*15dc779aSAndroid Build Coastguard Worker 
629*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < bs_num_env; i++) {
630*15dc779aSAndroid Build Coastguard Worker       if (kk > MAX_NOISE_ENVELOPES) {
631*15dc779aSAndroid Build Coastguard Worker         if (ec_flag)
632*15dc779aSAndroid Build Coastguard Worker           kk = MAX_NOISE_ENVELOPES;
633*15dc779aSAndroid Build Coastguard Worker         else
634*15dc779aSAndroid Build Coastguard Worker           return IA_FATAL_ERROR;
635*15dc779aSAndroid Build Coastguard Worker       }
636*15dc779aSAndroid Build Coastguard Worker 
637*15dc779aSAndroid Build Coastguard Worker       if (p_frame_info->border_vec[i] == p_frame_info->noise_border_vec[kk])
638*15dc779aSAndroid Build Coastguard Worker         kk++, next++;
639*15dc779aSAndroid Build Coastguard Worker 
640*15dc779aSAndroid Build Coastguard Worker       noise_absc_flag =
641*15dc779aSAndroid Build Coastguard Worker           (i == trans_env || i == frame_data->env_short_flag_prev) ? 1 : 0;
642*15dc779aSAndroid Build Coastguard Worker 
643*15dc779aSAndroid Build Coastguard Worker       smooth_length = (noise_absc_flag ? 0 : smoothing_length);
644*15dc779aSAndroid Build Coastguard Worker       smooth_filt = *ixheaac_fir_table[smooth_length];
645*15dc779aSAndroid Build Coastguard Worker 
646*15dc779aSAndroid Build Coastguard Worker       if (sbr_mode == ORIG_SBR) {
647*15dc779aSAndroid Build Coastguard Worker         for (c = 0, o = 0, j = 0; j < num_sf_bands[p_frame_info->freq_res[i]];
648*15dc779aSAndroid Build Coastguard Worker              j++) {
649*15dc779aSAndroid Build Coastguard Worker           double tmp;
650*15dc779aSAndroid Build Coastguard Worker           li = freq_band_table[p_frame_info->freq_res[i]][j];
651*15dc779aSAndroid Build Coastguard Worker           ui = freq_band_table[p_frame_info->freq_res[i]][j + 1];
652*15dc779aSAndroid Build Coastguard Worker           ui2 = frame_data->pstr_sbr_header->pstr_freq_band_data
653*15dc779aSAndroid Build Coastguard Worker                     ->freq_band_tbl_noise[o + 1];
654*15dc779aSAndroid Build Coastguard Worker 
655*15dc779aSAndroid Build Coastguard Worker           if (p_frame_info->border_vec[i] >= p_frame_info->border_vec[i + 1]) {
656*15dc779aSAndroid Build Coastguard Worker             for (flag = 0, k = li; k < ui; k++) {
657*15dc779aSAndroid Build Coastguard Worker               flag = (harmonics[c] &&
658*15dc779aSAndroid Build Coastguard Worker                 (i >= trans_env || (*harm_flag_prev)[c + sub_band_start]))
659*15dc779aSAndroid Build Coastguard Worker                 ? 1
660*15dc779aSAndroid Build Coastguard Worker                 : flag;
661*15dc779aSAndroid Build Coastguard Worker               nrg_est[c++] = 0;
662*15dc779aSAndroid Build Coastguard Worker             }
663*15dc779aSAndroid Build Coastguard Worker           } else {
664*15dc779aSAndroid Build Coastguard Worker             for (flag = 0, k = li; k < ui; k++) {
665*15dc779aSAndroid Build Coastguard Worker               for (nrg = 0, l = rate * p_frame_info->border_vec[i];
666*15dc779aSAndroid Build Coastguard Worker                 l < rate * p_frame_info->border_vec[i + 1]; l++) {
667*15dc779aSAndroid Build Coastguard Worker                 nrg += (input_real[l][k] * input_real[l][k]) +
668*15dc779aSAndroid Build Coastguard Worker                   (input_imag[l][k] * input_imag[l][k]);
669*15dc779aSAndroid Build Coastguard Worker               }
670*15dc779aSAndroid Build Coastguard Worker               flag = (harmonics[c] &&
671*15dc779aSAndroid Build Coastguard Worker                 (i >= trans_env || (*harm_flag_prev)[c + sub_band_start]))
672*15dc779aSAndroid Build Coastguard Worker                 ? 1
673*15dc779aSAndroid Build Coastguard Worker                 : flag;
674*15dc779aSAndroid Build Coastguard Worker               nrg_est[c++] = nrg / (rate * p_frame_info->border_vec[i + 1] -
675*15dc779aSAndroid Build Coastguard Worker                 rate * p_frame_info->border_vec[i]);
676*15dc779aSAndroid Build Coastguard Worker             }
677*15dc779aSAndroid Build Coastguard Worker           }
678*15dc779aSAndroid Build Coastguard Worker           if (!int_mode && ui != li) {
679*15dc779aSAndroid Build Coastguard Worker             for (nrg = 0, k = c - (ui - li); k < c; k++) {
680*15dc779aSAndroid Build Coastguard Worker               nrg += nrg_est[k];
681*15dc779aSAndroid Build Coastguard Worker             }
682*15dc779aSAndroid Build Coastguard Worker             nrg /= (ui - li);
683*15dc779aSAndroid Build Coastguard Worker           } else {
684*15dc779aSAndroid Build Coastguard Worker             nrg = 0;
685*15dc779aSAndroid Build Coastguard Worker           }
686*15dc779aSAndroid Build Coastguard Worker           c -= (ui - li);
687*15dc779aSAndroid Build Coastguard Worker 
688*15dc779aSAndroid Build Coastguard Worker           for (k = 0; k < ui - li; k++) {
689*15dc779aSAndroid Build Coastguard Worker             o = (k + li >= ui2) ? o + 1 : o;
690*15dc779aSAndroid Build Coastguard Worker             if (o >= MAX_NOISE_COEFFS) {
691*15dc779aSAndroid Build Coastguard Worker               if (ec_flag)
692*15dc779aSAndroid Build Coastguard Worker                 o = MAX_NOISE_COEFFS - 1;
693*15dc779aSAndroid Build Coastguard Worker               else
694*15dc779aSAndroid Build Coastguard Worker                 return IA_FATAL_ERROR;
695*15dc779aSAndroid Build Coastguard Worker             }
696*15dc779aSAndroid Build Coastguard Worker             ui2 = frame_data->pstr_sbr_header->pstr_freq_band_data
697*15dc779aSAndroid Build Coastguard Worker                       ->freq_band_tbl_noise[o + 1];
698*15dc779aSAndroid Build Coastguard Worker             nrg_ref[c] = sfb_nrg[m];
699*15dc779aSAndroid Build Coastguard Worker             nrg_est[c] = (!int_mode) ? nrg : nrg_est[c];
700*15dc779aSAndroid Build Coastguard Worker             nrg_tone[c] = 0;
701*15dc779aSAndroid Build Coastguard Worker             tmp = noise_floor[next * num_nf_bands + o] /
702*15dc779aSAndroid Build Coastguard Worker                   (1 + noise_floor[next * num_nf_bands + o] + guard);
703*15dc779aSAndroid Build Coastguard Worker             if (flag) {
704*15dc779aSAndroid Build Coastguard Worker               nrg_gain[c] = (FLOAT32)sqrt(nrg_ref[c] * tmp / (nrg_est[c] + 1));
705*15dc779aSAndroid Build Coastguard Worker               nrg_tone[c] = (FLOAT32)(
706*15dc779aSAndroid Build Coastguard Worker                   (harmonics[c] &&
707*15dc779aSAndroid Build Coastguard Worker                    (i >= trans_env || (*harm_flag_prev)[c + sub_band_start]))
708*15dc779aSAndroid Build Coastguard Worker                       ? sqrt(nrg_ref[c] * tmp /
709*15dc779aSAndroid Build Coastguard Worker                              ABS(noise_floor[next * num_nf_bands + o] + guard))
710*15dc779aSAndroid Build Coastguard Worker                       : nrg_tone[c]);
711*15dc779aSAndroid Build Coastguard Worker             } else {
712*15dc779aSAndroid Build Coastguard Worker               if (noise_absc_flag)
713*15dc779aSAndroid Build Coastguard Worker                 nrg_gain[c] = (FLOAT32)sqrt(nrg_ref[c] / (nrg_est[c] + 1));
714*15dc779aSAndroid Build Coastguard Worker               else
715*15dc779aSAndroid Build Coastguard Worker                 nrg_gain[c] = (FLOAT32)sqrt(
716*15dc779aSAndroid Build Coastguard Worker                     nrg_ref[c] * tmp /
717*15dc779aSAndroid Build Coastguard Worker                     ((nrg_est[c] + 1) *
718*15dc779aSAndroid Build Coastguard Worker                      ABS(noise_floor[next * num_nf_bands + o] + guard)));
719*15dc779aSAndroid Build Coastguard Worker             }
720*15dc779aSAndroid Build Coastguard Worker             noise_level[c] = (FLOAT32)sqrt(nrg_ref[c] * tmp);
721*15dc779aSAndroid Build Coastguard Worker             c++;
722*15dc779aSAndroid Build Coastguard Worker           }
723*15dc779aSAndroid Build Coastguard Worker           m++;
724*15dc779aSAndroid Build Coastguard Worker         }
725*15dc779aSAndroid Build Coastguard Worker 
726*15dc779aSAndroid Build Coastguard Worker         for (c = 0; c < (*gate_mode)[limiter_band]; c++) {
727*15dc779aSAndroid Build Coastguard Worker           p_ref = p_est = 0;
728*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
729*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
730*15dc779aSAndroid Build Coastguard Worker             p_ref += nrg_ref[k];
731*15dc779aSAndroid Build Coastguard Worker             p_est += nrg_est[k];
732*15dc779aSAndroid Build Coastguard Worker           }
733*15dc779aSAndroid Build Coastguard Worker           avg_gain = (FLOAT32)sqrt((p_ref + EPS) / (p_est + EPS));
734*15dc779aSAndroid Build Coastguard Worker           g_max = avg_gain * ixheaac_g_lim_gains[limiter_gains];
735*15dc779aSAndroid Build Coastguard Worker           g_max > 1.0e5f ? g_max = 1.0e5f : 0;
736*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
737*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
738*15dc779aSAndroid Build Coastguard Worker             if (g_max <= nrg_gain[k]) {
739*15dc779aSAndroid Build Coastguard Worker               noise_level[k] = (FLOAT32)(noise_level[k] * (g_max / (nrg_gain[k] + guard)));
740*15dc779aSAndroid Build Coastguard Worker               nrg_gain[k] = g_max;
741*15dc779aSAndroid Build Coastguard Worker             }
742*15dc779aSAndroid Build Coastguard Worker           }
743*15dc779aSAndroid Build Coastguard Worker           p_adj = 0;
744*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
745*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
746*15dc779aSAndroid Build Coastguard Worker             p_adj += nrg_gain[k] * nrg_gain[k] * nrg_est[k];
747*15dc779aSAndroid Build Coastguard Worker             if (nrg_tone[k])
748*15dc779aSAndroid Build Coastguard Worker               p_adj += nrg_tone[k] * nrg_tone[k];
749*15dc779aSAndroid Build Coastguard Worker             else if (!noise_absc_flag)
750*15dc779aSAndroid Build Coastguard Worker               p_adj += noise_level[k] * noise_level[k];
751*15dc779aSAndroid Build Coastguard Worker           }
752*15dc779aSAndroid Build Coastguard Worker           boost_gain = (FLOAT32)sqrt((p_ref + EPS) / (p_adj + EPS));
753*15dc779aSAndroid Build Coastguard Worker           boost_gain = boost_gain > 1.584893192f ? 1.584893192f : boost_gain;
754*15dc779aSAndroid Build Coastguard Worker           for (k = (*lim_table)[limiter_band][c];
755*15dc779aSAndroid Build Coastguard Worker                k < (*lim_table)[limiter_band][c + 1]; k++) {
756*15dc779aSAndroid Build Coastguard Worker             nrg_gain[k] *= boost_gain;
757*15dc779aSAndroid Build Coastguard Worker             noise_level[k] *= boost_gain;
758*15dc779aSAndroid Build Coastguard Worker             nrg_tone[k] *= boost_gain;
759*15dc779aSAndroid Build Coastguard Worker           }
760*15dc779aSAndroid Build Coastguard Worker         }
761*15dc779aSAndroid Build Coastguard Worker 
762*15dc779aSAndroid Build Coastguard Worker         if (esbr_start_up && (ldmps_present != 1)) {
763*15dc779aSAndroid Build Coastguard Worker           for (n = 0; n < 4; n++) {
764*15dc779aSAndroid Build Coastguard Worker             memcpy((*e_gain)[n], nrg_gain, num_subbands * sizeof(FLOAT32));
765*15dc779aSAndroid Build Coastguard Worker             memcpy((*noise_buf)[n], noise_level,
766*15dc779aSAndroid Build Coastguard Worker                    num_subbands * sizeof(FLOAT32));
767*15dc779aSAndroid Build Coastguard Worker           }
768*15dc779aSAndroid Build Coastguard Worker           esbr_start_up = 0;
769*15dc779aSAndroid Build Coastguard Worker           esbr_start_up_pvc = 0;
770*15dc779aSAndroid Build Coastguard Worker         }
771*15dc779aSAndroid Build Coastguard Worker 
772*15dc779aSAndroid Build Coastguard Worker         for (l = rate * p_frame_info->border_vec[i];
773*15dc779aSAndroid Build Coastguard Worker              l < rate * p_frame_info->border_vec[i + 1]; l++) {
774*15dc779aSAndroid Build Coastguard Worker           ptr_real_buf = *(input_real + l) + sub_band_start;
775*15dc779aSAndroid Build Coastguard Worker           ptr_imag_buf = *(input_imag + l) + sub_band_start;
776*15dc779aSAndroid Build Coastguard Worker 
777*15dc779aSAndroid Build Coastguard Worker           freq_inv = 1;
778*15dc779aSAndroid Build Coastguard Worker           if ((ldmps_present == 1) && (sub_band_start & 1)) freq_inv = -1;
779*15dc779aSAndroid Build Coastguard Worker 
780*15dc779aSAndroid Build Coastguard Worker           for (k = 0; k < num_subbands; k++) {
781*15dc779aSAndroid Build Coastguard Worker             (*e_gain)[4][k] = nrg_gain[k];
782*15dc779aSAndroid Build Coastguard Worker             (*noise_buf)[4][k] = noise_level[k];
783*15dc779aSAndroid Build Coastguard Worker             c = 0, sb_gain = 0, sb_noise = 0;
784*15dc779aSAndroid Build Coastguard Worker             for (n = 4 - smooth_length; n <= 4; n++) {
785*15dc779aSAndroid Build Coastguard Worker               sb_gain += (*e_gain)[n][k] * smooth_filt[c];
786*15dc779aSAndroid Build Coastguard Worker               sb_noise += (*noise_buf)[n][k] * smooth_filt[c++];
787*15dc779aSAndroid Build Coastguard Worker             }
788*15dc779aSAndroid Build Coastguard Worker 
789*15dc779aSAndroid Build Coastguard Worker             phase_index = (phase_index + 1) & 511;
790*15dc779aSAndroid Build Coastguard Worker             sb_noise = (nrg_tone[k] != 0 || noise_absc_flag) ? 0 : sb_noise;
791*15dc779aSAndroid Build Coastguard Worker 
792*15dc779aSAndroid Build Coastguard Worker             if (ldmps_present == 1) {
793*15dc779aSAndroid Build Coastguard Worker               *ptr_real_buf = *ptr_real_buf * sb_gain +
794*15dc779aSAndroid Build Coastguard Worker                               sb_noise * ixheaac_random_phase[phase_index][0] +
795*15dc779aSAndroid Build Coastguard Worker                               nrg_tone[k] * ixheaac_hphase_tbl[0][harm_index];
796*15dc779aSAndroid Build Coastguard Worker               *ptr_imag_buf =
797*15dc779aSAndroid Build Coastguard Worker                   *ptr_imag_buf * sb_gain +
798*15dc779aSAndroid Build Coastguard Worker                   sb_noise * ixheaac_random_phase[phase_index][1] +
799*15dc779aSAndroid Build Coastguard Worker                   nrg_tone[k] * freq_inv * ixheaac_hphase_tbl[1][harm_index];
800*15dc779aSAndroid Build Coastguard Worker 
801*15dc779aSAndroid Build Coastguard Worker               freq_inv = -freq_inv;
802*15dc779aSAndroid Build Coastguard Worker             } else {
803*15dc779aSAndroid Build Coastguard Worker                 *ptr_real_buf = *ptr_real_buf * sb_gain +
804*15dc779aSAndroid Build Coastguard Worker                             sb_noise * ixheaac_random_phase[phase_index][0];
805*15dc779aSAndroid Build Coastguard Worker                 *ptr_imag_buf = *ptr_imag_buf * sb_gain +
806*15dc779aSAndroid Build Coastguard Worker                             sb_noise * ixheaac_random_phase[phase_index][1];
807*15dc779aSAndroid Build Coastguard Worker             }
808*15dc779aSAndroid Build Coastguard Worker 
809*15dc779aSAndroid Build Coastguard Worker             ptr_real_buf++;
810*15dc779aSAndroid Build Coastguard Worker             ptr_imag_buf++;
811*15dc779aSAndroid Build Coastguard Worker           }
812*15dc779aSAndroid Build Coastguard Worker           if (ldmps_present == 1) harm_index = (harm_index + 1) & 3;
813*15dc779aSAndroid Build Coastguard Worker 
814*15dc779aSAndroid Build Coastguard Worker           memcpy(temp, (*e_gain)[0], 64 * sizeof(FLOAT32));
815*15dc779aSAndroid Build Coastguard Worker           for (n = 0; n < 4; n++)
816*15dc779aSAndroid Build Coastguard Worker             memcpy((*e_gain)[n], (*e_gain)[n + 1], 64 * sizeof(FLOAT32));
817*15dc779aSAndroid Build Coastguard Worker           memcpy((*e_gain)[4], temp, 64 * sizeof(FLOAT32));
818*15dc779aSAndroid Build Coastguard Worker           memcpy(temp, (*noise_buf)[0], 64 * sizeof(FLOAT32));
819*15dc779aSAndroid Build Coastguard Worker           for (n = 0; n < 4; n++)
820*15dc779aSAndroid Build Coastguard Worker             memcpy((*noise_buf)[n], (*noise_buf)[n + 1], 64 * sizeof(FLOAT32));
821*15dc779aSAndroid Build Coastguard Worker           memcpy((*noise_buf)[4], temp, 64 * sizeof(FLOAT32));
822*15dc779aSAndroid Build Coastguard Worker         }
823*15dc779aSAndroid Build Coastguard Worker 
824*15dc779aSAndroid Build Coastguard Worker         if (ldmps_present != 1) {
825*15dc779aSAndroid Build Coastguard Worker           err_code = ixheaacd_apply_inter_tes(
826*15dc779aSAndroid Build Coastguard Worker               *(input_real1 + rate * p_frame_info->border_vec[i]),
827*15dc779aSAndroid Build Coastguard Worker               *(input_imag1 + rate * p_frame_info->border_vec[i]),
828*15dc779aSAndroid Build Coastguard Worker               *(input_real + rate * p_frame_info->border_vec[i]),
829*15dc779aSAndroid Build Coastguard Worker               *(input_imag + rate * p_frame_info->border_vec[i]),
830*15dc779aSAndroid Build Coastguard Worker               rate * p_frame_info->border_vec[i + 1] - rate * p_frame_info->border_vec[i],
831*15dc779aSAndroid Build Coastguard Worker               sub_band_start, num_subbands, frame_data->inter_temp_shape_mode[i]);
832*15dc779aSAndroid Build Coastguard Worker           if (err_code != 0) {
833*15dc779aSAndroid Build Coastguard Worker             return err_code;
834*15dc779aSAndroid Build Coastguard Worker           }
835*15dc779aSAndroid Build Coastguard Worker 
836*15dc779aSAndroid Build Coastguard Worker         for (l = rate * p_frame_info->border_vec[i];
837*15dc779aSAndroid Build Coastguard Worker              l < rate * p_frame_info->border_vec[i + 1]; l++) {
838*15dc779aSAndroid Build Coastguard Worker           ptr_real_buf = *(input_real + l) + sub_band_start;
839*15dc779aSAndroid Build Coastguard Worker           ptr_imag_buf = *(input_imag + l) + sub_band_start;
840*15dc779aSAndroid Build Coastguard Worker           if (sub_band_start & 1) {
841*15dc779aSAndroid Build Coastguard Worker             freq_inv = -1;
842*15dc779aSAndroid Build Coastguard Worker           } else {
843*15dc779aSAndroid Build Coastguard Worker             freq_inv = 1;
844*15dc779aSAndroid Build Coastguard Worker           }
845*15dc779aSAndroid Build Coastguard Worker           for (k = 0; k < num_subbands; k++) {
846*15dc779aSAndroid Build Coastguard Worker             *ptr_real_buf += nrg_tone[k] * ixheaac_hphase_tbl[0][harm_index];
847*15dc779aSAndroid Build Coastguard Worker             *ptr_imag_buf +=
848*15dc779aSAndroid Build Coastguard Worker                 nrg_tone[k] * freq_inv * ixheaac_hphase_tbl[1][harm_index];
849*15dc779aSAndroid Build Coastguard Worker 
850*15dc779aSAndroid Build Coastguard Worker             ptr_real_buf++;
851*15dc779aSAndroid Build Coastguard Worker             ptr_imag_buf++;
852*15dc779aSAndroid Build Coastguard Worker             freq_inv = -freq_inv;
853*15dc779aSAndroid Build Coastguard Worker           }
854*15dc779aSAndroid Build Coastguard Worker           harm_index = (harm_index + 1) & 3;
855*15dc779aSAndroid Build Coastguard Worker         }
856*15dc779aSAndroid Build Coastguard Worker       }
857*15dc779aSAndroid Build Coastguard Worker     }
858*15dc779aSAndroid Build Coastguard Worker   }
859*15dc779aSAndroid Build Coastguard Worker }
860*15dc779aSAndroid Build Coastguard Worker 
861*15dc779aSAndroid Build Coastguard Worker   for (i = 0; i < 64; i++) {
862*15dc779aSAndroid Build Coastguard Worker     (*harm_flag_varlen_prev)[i] = (*harm_flag_prev)[i];
863*15dc779aSAndroid Build Coastguard Worker     (*harm_flag_varlen)[i] = harmonics[i];
864*15dc779aSAndroid Build Coastguard Worker   }
865*15dc779aSAndroid Build Coastguard Worker 
866*15dc779aSAndroid Build Coastguard Worker   memcpy(&((*harm_flag_prev)[0]) + sub_band_start, harmonics,
867*15dc779aSAndroid Build Coastguard Worker          (64 - sub_band_start) * sizeof(WORD8));
868*15dc779aSAndroid Build Coastguard Worker 
869*15dc779aSAndroid Build Coastguard Worker   if (trans_env == bs_num_env) {
870*15dc779aSAndroid Build Coastguard Worker     frame_data->env_short_flag_prev = 0;
871*15dc779aSAndroid Build Coastguard Worker   } else {
872*15dc779aSAndroid Build Coastguard Worker     frame_data->env_short_flag_prev = -1;
873*15dc779aSAndroid Build Coastguard Worker   }
874*15dc779aSAndroid Build Coastguard Worker 
875*15dc779aSAndroid Build Coastguard Worker   if (ldmps_present != 1) {
876*15dc779aSAndroid Build Coastguard Worker   memcpy((VOID *)&frame_data->str_frame_info_prev,
877*15dc779aSAndroid Build Coastguard Worker          (VOID *)&frame_data->str_frame_info_details,
878*15dc779aSAndroid Build Coastguard Worker          sizeof(ia_frame_info_struct));
879*15dc779aSAndroid Build Coastguard Worker 
880*15dc779aSAndroid Build Coastguard Worker   if (frame_data->str_frame_info_details.num_env == 1) {
881*15dc779aSAndroid Build Coastguard Worker     frame_data->var_len_id_prev = 0;
882*15dc779aSAndroid Build Coastguard Worker   } else if (frame_data->str_frame_info_details.num_env == 2) {
883*15dc779aSAndroid Build Coastguard Worker     frame_data->var_len_id_prev = 1;
884*15dc779aSAndroid Build Coastguard Worker   }
885*15dc779aSAndroid Build Coastguard Worker 
886*15dc779aSAndroid Build Coastguard Worker   if ((frame_data->str_frame_info_details.num_noise_env < 1) ||
887*15dc779aSAndroid Build Coastguard Worker         (frame_data->str_frame_info_details.num_noise_env > 2)) {
888*15dc779aSAndroid Build Coastguard Worker       if (ec_flag)
889*15dc779aSAndroid Build Coastguard Worker         frame_data->str_frame_info_details.num_noise_env = 1;
890*15dc779aSAndroid Build Coastguard Worker       else
891*15dc779aSAndroid Build Coastguard Worker         return IA_FATAL_ERROR;
892*15dc779aSAndroid Build Coastguard Worker     }
893*15dc779aSAndroid Build Coastguard Worker 
894*15dc779aSAndroid Build Coastguard Worker   for (i = 0; i < num_nf_bands; i++) {
895*15dc779aSAndroid Build Coastguard Worker     prev_env_noise_level[i] =
896*15dc779aSAndroid Build Coastguard Worker         frame_data->flt_noise_floor
897*15dc779aSAndroid Build Coastguard Worker             [(frame_data->str_frame_info_details.num_noise_env - 1) *
898*15dc779aSAndroid Build Coastguard Worker                  num_nf_bands +
899*15dc779aSAndroid Build Coastguard Worker              i];
900*15dc779aSAndroid Build Coastguard Worker   }
901*15dc779aSAndroid Build Coastguard Worker }
902*15dc779aSAndroid Build Coastguard Worker 
903*15dc779aSAndroid Build Coastguard Worker   frame_data->harm_index = harm_index;
904*15dc779aSAndroid Build Coastguard Worker   frame_data->phase_index = phase_index;
905*15dc779aSAndroid Build Coastguard Worker   frame_data->pstr_sbr_header->esbr_start_up = esbr_start_up;
906*15dc779aSAndroid Build Coastguard Worker   frame_data->pstr_sbr_header->esbr_start_up_pvc = esbr_start_up_pvc;
907*15dc779aSAndroid Build Coastguard Worker   return 0;
908*15dc779aSAndroid Build Coastguard Worker }
909*15dc779aSAndroid Build Coastguard Worker 
ixheaacd_createlimiterbands(WORD32 lim_table[4][12+1],WORD32 gate_mode[4],WORD16 * freq_band_tbl,WORD32 ixheaacd_num_bands,WORD32 x_over_qmf[MAX_NUM_PATCHES],WORD32 b_patching_mode,WORD32 upsamp_4_flag,struct ixheaacd_lpp_trans_patch * patch_param,WORD32 ec_flag)910*15dc779aSAndroid Build Coastguard Worker IA_ERRORCODE ixheaacd_createlimiterbands(WORD32 lim_table[4][12 + 1], WORD32 gate_mode[4],
911*15dc779aSAndroid Build Coastguard Worker                                          WORD16 *freq_band_tbl, WORD32 ixheaacd_num_bands,
912*15dc779aSAndroid Build Coastguard Worker                                          WORD32 x_over_qmf[MAX_NUM_PATCHES],
913*15dc779aSAndroid Build Coastguard Worker                                          WORD32 b_patching_mode, WORD32 upsamp_4_flag,
914*15dc779aSAndroid Build Coastguard Worker                                          struct ixheaacd_lpp_trans_patch *patch_param,
915*15dc779aSAndroid Build Coastguard Worker                                          WORD32 ec_flag) {
916*15dc779aSAndroid Build Coastguard Worker   WORD32 i, j, k, is_patch_border[2];
917*15dc779aSAndroid Build Coastguard Worker   WORD32 patch_borders[MAX_NUM_PATCHES + 1];
918*15dc779aSAndroid Build Coastguard Worker   WORD32 temp_limiter_band_calc[32 + MAX_NUM_PATCHES + 1];
919*15dc779aSAndroid Build Coastguard Worker 
920*15dc779aSAndroid Build Coastguard Worker   double num_octave;
921*15dc779aSAndroid Build Coastguard Worker   WORD32 num_patches;
922*15dc779aSAndroid Build Coastguard Worker 
923*15dc779aSAndroid Build Coastguard Worker   WORD32 sub_band_start = freq_band_tbl[0];
924*15dc779aSAndroid Build Coastguard Worker   WORD32 sub_band_end = freq_band_tbl[ixheaacd_num_bands];
925*15dc779aSAndroid Build Coastguard Worker 
926*15dc779aSAndroid Build Coastguard Worker   const double log2 = log(2.0);
927*15dc779aSAndroid Build Coastguard Worker   const double limbnd_per_oct[4] = {0, 1.2, 2.0, 3.0};
928*15dc779aSAndroid Build Coastguard Worker 
929*15dc779aSAndroid Build Coastguard Worker   if (!b_patching_mode && (x_over_qmf != NULL)) {
930*15dc779aSAndroid Build Coastguard Worker     num_patches = 0;
931*15dc779aSAndroid Build Coastguard Worker     if (upsamp_4_flag) {
932*15dc779aSAndroid Build Coastguard Worker       for (i = 1; i < MAX_NUM_PATCHES; i++)
933*15dc779aSAndroid Build Coastguard Worker         if (x_over_qmf[i] != 0) num_patches++;
934*15dc779aSAndroid Build Coastguard Worker     } else {
935*15dc779aSAndroid Build Coastguard Worker       for (i = 1; i < 4; i++)
936*15dc779aSAndroid Build Coastguard Worker         if (x_over_qmf[i] != 0) num_patches++;
937*15dc779aSAndroid Build Coastguard Worker     }
938*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_patches; i++) {
939*15dc779aSAndroid Build Coastguard Worker       patch_borders[i] = x_over_qmf[i] - sub_band_start;
940*15dc779aSAndroid Build Coastguard Worker     }
941*15dc779aSAndroid Build Coastguard Worker   } else {
942*15dc779aSAndroid Build Coastguard Worker     num_patches = patch_param->num_patches;
943*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_patches; i++) {
944*15dc779aSAndroid Build Coastguard Worker       patch_borders[i] = patch_param->start_subband[i] - sub_band_start;
945*15dc779aSAndroid Build Coastguard Worker     }
946*15dc779aSAndroid Build Coastguard Worker   }
947*15dc779aSAndroid Build Coastguard Worker   patch_borders[i] = sub_band_end - sub_band_start;
948*15dc779aSAndroid Build Coastguard Worker 
949*15dc779aSAndroid Build Coastguard Worker   lim_table[0][0] = freq_band_tbl[0] - sub_band_start;
950*15dc779aSAndroid Build Coastguard Worker   lim_table[0][1] = freq_band_tbl[ixheaacd_num_bands] - sub_band_start;
951*15dc779aSAndroid Build Coastguard Worker   gate_mode[0] = 1;
952*15dc779aSAndroid Build Coastguard Worker 
953*15dc779aSAndroid Build Coastguard Worker   for (i = 1; i < 4; i++) {
954*15dc779aSAndroid Build Coastguard Worker     for (k = 0; k <= ixheaacd_num_bands; k++) {
955*15dc779aSAndroid Build Coastguard Worker       temp_limiter_band_calc[k] = freq_band_tbl[k] - sub_band_start;
956*15dc779aSAndroid Build Coastguard Worker     }
957*15dc779aSAndroid Build Coastguard Worker 
958*15dc779aSAndroid Build Coastguard Worker     for (k = 1; k < num_patches; k++) {
959*15dc779aSAndroid Build Coastguard Worker       temp_limiter_band_calc[ixheaacd_num_bands + k] = patch_borders[k];
960*15dc779aSAndroid Build Coastguard Worker     }
961*15dc779aSAndroid Build Coastguard Worker 
962*15dc779aSAndroid Build Coastguard Worker     gate_mode[i] = ixheaacd_num_bands + num_patches - 1;
963*15dc779aSAndroid Build Coastguard Worker     ixheaacd_shellsort(temp_limiter_band_calc, gate_mode[i] + 1);
964*15dc779aSAndroid Build Coastguard Worker 
965*15dc779aSAndroid Build Coastguard Worker     for (j = 1; j <= gate_mode[i]; j++) {
966*15dc779aSAndroid Build Coastguard Worker       num_octave = log((double)(temp_limiter_band_calc[j] + sub_band_start) /
967*15dc779aSAndroid Build Coastguard Worker                        (temp_limiter_band_calc[j - 1] + sub_band_start)) /
968*15dc779aSAndroid Build Coastguard Worker                    log2;
969*15dc779aSAndroid Build Coastguard Worker 
970*15dc779aSAndroid Build Coastguard Worker       if (num_octave * limbnd_per_oct[i] < 0.49) {
971*15dc779aSAndroid Build Coastguard Worker         if (temp_limiter_band_calc[j] == temp_limiter_band_calc[j - 1]) {
972*15dc779aSAndroid Build Coastguard Worker           temp_limiter_band_calc[j] = sub_band_end;
973*15dc779aSAndroid Build Coastguard Worker           ixheaacd_shellsort(temp_limiter_band_calc, gate_mode[i] + 1);
974*15dc779aSAndroid Build Coastguard Worker           gate_mode[i]--;
975*15dc779aSAndroid Build Coastguard Worker           j--;
976*15dc779aSAndroid Build Coastguard Worker           continue;
977*15dc779aSAndroid Build Coastguard Worker         }
978*15dc779aSAndroid Build Coastguard Worker 
979*15dc779aSAndroid Build Coastguard Worker         is_patch_border[0] = is_patch_border[1] = 0;
980*15dc779aSAndroid Build Coastguard Worker 
981*15dc779aSAndroid Build Coastguard Worker         for (k = 0; k <= num_patches; k++) {
982*15dc779aSAndroid Build Coastguard Worker           if (temp_limiter_band_calc[j - 1] == patch_borders[k]) {
983*15dc779aSAndroid Build Coastguard Worker             is_patch_border[0] = 1;
984*15dc779aSAndroid Build Coastguard Worker             break;
985*15dc779aSAndroid Build Coastguard Worker           }
986*15dc779aSAndroid Build Coastguard Worker         }
987*15dc779aSAndroid Build Coastguard Worker 
988*15dc779aSAndroid Build Coastguard Worker         for (k = 0; k <= num_patches; k++) {
989*15dc779aSAndroid Build Coastguard Worker           if (temp_limiter_band_calc[j] == patch_borders[k]) {
990*15dc779aSAndroid Build Coastguard Worker             is_patch_border[1] = 1;
991*15dc779aSAndroid Build Coastguard Worker             break;
992*15dc779aSAndroid Build Coastguard Worker           }
993*15dc779aSAndroid Build Coastguard Worker         }
994*15dc779aSAndroid Build Coastguard Worker 
995*15dc779aSAndroid Build Coastguard Worker         if (!is_patch_border[1]) {
996*15dc779aSAndroid Build Coastguard Worker           temp_limiter_band_calc[j] = sub_band_end;
997*15dc779aSAndroid Build Coastguard Worker           ixheaacd_shellsort(temp_limiter_band_calc, gate_mode[i] + 1);
998*15dc779aSAndroid Build Coastguard Worker           gate_mode[i]--;
999*15dc779aSAndroid Build Coastguard Worker           j--;
1000*15dc779aSAndroid Build Coastguard Worker         } else if (!is_patch_border[0]) {
1001*15dc779aSAndroid Build Coastguard Worker           temp_limiter_band_calc[j - 1] = sub_band_end;
1002*15dc779aSAndroid Build Coastguard Worker           ixheaacd_shellsort(temp_limiter_band_calc, gate_mode[i] + 1);
1003*15dc779aSAndroid Build Coastguard Worker           gate_mode[i]--;
1004*15dc779aSAndroid Build Coastguard Worker           j--;
1005*15dc779aSAndroid Build Coastguard Worker         }
1006*15dc779aSAndroid Build Coastguard Worker       }
1007*15dc779aSAndroid Build Coastguard Worker     }
1008*15dc779aSAndroid Build Coastguard Worker     if (gate_mode[i] > 12) {
1009*15dc779aSAndroid Build Coastguard Worker       if (ec_flag)
1010*15dc779aSAndroid Build Coastguard Worker         gate_mode[i] = 12;
1011*15dc779aSAndroid Build Coastguard Worker       else
1012*15dc779aSAndroid Build Coastguard Worker         return IA_FATAL_ERROR;
1013*15dc779aSAndroid Build Coastguard Worker     }
1014*15dc779aSAndroid Build Coastguard Worker     for (k = 0; k <= gate_mode[i]; k++) {
1015*15dc779aSAndroid Build Coastguard Worker       lim_table[i][k] = temp_limiter_band_calc[k];
1016*15dc779aSAndroid Build Coastguard Worker     }
1017*15dc779aSAndroid Build Coastguard Worker   }
1018*15dc779aSAndroid Build Coastguard Worker   return IA_NO_ERROR;
1019*15dc779aSAndroid Build Coastguard Worker }
1020*15dc779aSAndroid Build Coastguard Worker 
ixheaacd_apply_inter_tes(FLOAT32 * qmf_real1,FLOAT32 * qmf_imag1,FLOAT32 * qmf_real,FLOAT32 * qmf_imag,WORD32 num_sample,WORD32 sub_band_start,WORD32 num_subband,WORD32 gamma_idx)1021*15dc779aSAndroid Build Coastguard Worker WORD32 ixheaacd_apply_inter_tes(FLOAT32 *qmf_real1, FLOAT32 *qmf_imag1,
1022*15dc779aSAndroid Build Coastguard Worker                                 FLOAT32 *qmf_real, FLOAT32 *qmf_imag,
1023*15dc779aSAndroid Build Coastguard Worker                                 WORD32 num_sample, WORD32 sub_band_start,
1024*15dc779aSAndroid Build Coastguard Worker                                 WORD32 num_subband, WORD32 gamma_idx) {
1025*15dc779aSAndroid Build Coastguard Worker   WORD32 sub_band_end = sub_band_start + num_subband;
1026*15dc779aSAndroid Build Coastguard Worker   FLOAT32 subsample_power_high[TIMESLOT_BUFFER_SIZE],
1027*15dc779aSAndroid Build Coastguard Worker       subsample_power_low[TIMESLOT_BUFFER_SIZE];
1028*15dc779aSAndroid Build Coastguard Worker   FLOAT32 total_power_high = 0.0f;
1029*15dc779aSAndroid Build Coastguard Worker   FLOAT32 total_power_low = 0.0f, total_power_high_after = 1.0e-6f;
1030*15dc779aSAndroid Build Coastguard Worker   FLOAT32 gain[TIMESLOT_BUFFER_SIZE];
1031*15dc779aSAndroid Build Coastguard Worker   FLOAT32 gain_adj, gain_adj_2;
1032*15dc779aSAndroid Build Coastguard Worker   FLOAT32 gamma = ixheaac_q_gamma_table[gamma_idx];
1033*15dc779aSAndroid Build Coastguard Worker   WORD32 i, j;
1034*15dc779aSAndroid Build Coastguard Worker 
1035*15dc779aSAndroid Build Coastguard Worker   if (num_sample > TIMESLOT_BUFFER_SIZE)
1036*15dc779aSAndroid Build Coastguard Worker   {
1037*15dc779aSAndroid Build Coastguard Worker     return IA_FATAL_ERROR;
1038*15dc779aSAndroid Build Coastguard Worker   }
1039*15dc779aSAndroid Build Coastguard Worker   if (gamma > 0) {
1040*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_sample; i++) {
1041*15dc779aSAndroid Build Coastguard Worker       memcpy(&qmf_real[64 * i], &qmf_real1[64 * i],
1042*15dc779aSAndroid Build Coastguard Worker              sub_band_start * sizeof(FLOAT32));
1043*15dc779aSAndroid Build Coastguard Worker       memcpy(&qmf_imag[64 * i], &qmf_imag1[64 * i],
1044*15dc779aSAndroid Build Coastguard Worker              sub_band_start * sizeof(FLOAT32));
1045*15dc779aSAndroid Build Coastguard Worker     }
1046*15dc779aSAndroid Build Coastguard Worker 
1047*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_sample; i++) {
1048*15dc779aSAndroid Build Coastguard Worker       subsample_power_low[i] = 0.0f;
1049*15dc779aSAndroid Build Coastguard Worker       for (j = 0; j < sub_band_start; j++) {
1050*15dc779aSAndroid Build Coastguard Worker         subsample_power_low[i] += qmf_real[64 * i + j] * qmf_real[64 * i + j];
1051*15dc779aSAndroid Build Coastguard Worker         subsample_power_low[i] += qmf_imag[64 * i + j] * qmf_imag[64 * i + j];
1052*15dc779aSAndroid Build Coastguard Worker       }
1053*15dc779aSAndroid Build Coastguard Worker       subsample_power_high[i] = 0.0f;
1054*15dc779aSAndroid Build Coastguard Worker       for (j = sub_band_start; j < sub_band_end; j++) {
1055*15dc779aSAndroid Build Coastguard Worker         subsample_power_high[i] += qmf_real[64 * i + j] * qmf_real[64 * i + j];
1056*15dc779aSAndroid Build Coastguard Worker         subsample_power_high[i] += qmf_imag[64 * i + j] * qmf_imag[64 * i + j];
1057*15dc779aSAndroid Build Coastguard Worker       }
1058*15dc779aSAndroid Build Coastguard Worker       total_power_low += subsample_power_low[i];
1059*15dc779aSAndroid Build Coastguard Worker       total_power_high += subsample_power_high[i];
1060*15dc779aSAndroid Build Coastguard Worker     }
1061*15dc779aSAndroid Build Coastguard Worker 
1062*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_sample; i++) {
1063*15dc779aSAndroid Build Coastguard Worker       gain[i] = (FLOAT32)(sqrt(subsample_power_low[i] * num_sample /
1064*15dc779aSAndroid Build Coastguard Worker                                (total_power_low + 1.0e-6f)));
1065*15dc779aSAndroid Build Coastguard Worker     }
1066*15dc779aSAndroid Build Coastguard Worker 
1067*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_sample; i++) {
1068*15dc779aSAndroid Build Coastguard Worker       gain[i] = (FLOAT32)(1.0f + gamma * (gain[i] - 1.0f));
1069*15dc779aSAndroid Build Coastguard Worker     }
1070*15dc779aSAndroid Build Coastguard Worker 
1071*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_sample; i++) {
1072*15dc779aSAndroid Build Coastguard Worker       if (gain[i] < 0.2f) {
1073*15dc779aSAndroid Build Coastguard Worker         gain[i] = 0.2f;
1074*15dc779aSAndroid Build Coastguard Worker       }
1075*15dc779aSAndroid Build Coastguard Worker 
1076*15dc779aSAndroid Build Coastguard Worker       subsample_power_high[i] *= gain[i] * gain[i];
1077*15dc779aSAndroid Build Coastguard Worker       total_power_high_after += subsample_power_high[i];
1078*15dc779aSAndroid Build Coastguard Worker     }
1079*15dc779aSAndroid Build Coastguard Worker 
1080*15dc779aSAndroid Build Coastguard Worker     gain_adj_2 = total_power_high / total_power_high_after;
1081*15dc779aSAndroid Build Coastguard Worker     gain_adj = (FLOAT32)(sqrt(gain_adj_2));
1082*15dc779aSAndroid Build Coastguard Worker 
1083*15dc779aSAndroid Build Coastguard Worker     for (i = 0; i < num_sample; i++) {
1084*15dc779aSAndroid Build Coastguard Worker       gain[i] *= gain_adj;
1085*15dc779aSAndroid Build Coastguard Worker 
1086*15dc779aSAndroid Build Coastguard Worker       for (j = sub_band_start; j < sub_band_end; j++) {
1087*15dc779aSAndroid Build Coastguard Worker         qmf_real[64 * i + j] *= gain[i];
1088*15dc779aSAndroid Build Coastguard Worker         qmf_imag[64 * i + j] *= gain[i];
1089*15dc779aSAndroid Build Coastguard Worker       }
1090*15dc779aSAndroid Build Coastguard Worker     }
1091*15dc779aSAndroid Build Coastguard Worker   }
1092*15dc779aSAndroid Build Coastguard Worker   return 0;
1093*15dc779aSAndroid Build Coastguard Worker }
1094