1 /******************************************************************************
2 * *
3 * Copyright (C) 2018 The Android Open Source Project
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 *****************************************************************************
18 * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19 */
20 #include "ixheaacd_sbr_common.h"
21 #include "ixheaacd_type_def.h"
22
23 #include "ixheaacd_constants.h"
24 #include "ixheaacd_basic_ops32.h"
25 #include "ixheaacd_basic_ops16.h"
26 #include "ixheaacd_basic_ops40.h"
27 #include "ixheaacd_basic_ops.h"
28
29 #include "ixheaacd_intrinsics.h"
30 #include "ixheaacd_bitbuffer.h"
31 #include "ixheaacd_sbrdecsettings.h"
32 #include "ixheaacd_defines.h"
33
34 #include "ixheaacd_pns.h"
35
36 #include "ixheaacd_aac_rom.h"
37 #include "ixheaacd_pulsedata.h"
38 #include "ixheaacd_drc_data_struct.h"
39
40 #include "ixheaacd_lt_predict.h"
41
42 #include "ixheaacd_channelinfo.h"
43 #include "ixheaacd_drc_dec.h"
44
45 #include "ixheaacd_sbrdecoder.h"
46 #include "ixheaacd_sbr_scale.h"
47 #include "ixheaacd_lpp_tran.h"
48
49 #include "ixheaacd_env_extr_part.h"
50 #include "ixheaacd_sbr_rom.h"
51 #include "ixheaacd_hybrid.h"
52 #include "ixheaacd_ps_dec.h"
53 #include "ixheaacd_env_extr.h"
54
55 #include "ixheaacd_sbr_const.h"
56 #include "ixheaacd_common_rom.h"
57 #include "ixheaacd_freq_sca.h"
58
59 #include "ixheaacd_basic_funcs.h"
60 #include "ixheaacd_env_extr.h"
61
62 #include "ixheaacd_env_calc.h"
63 #include "ixheaacd_basic_op.h"
64
65 #include "ixheaacd_qmf_dec.h"
66
67 #include "ixheaacd_pvc_dec.h"
68 #include "ixheaacd_sbr_dec.h"
69 #include "ixheaacd_function_selector.h"
70
71 #include "ixheaacd_audioobjtypes.h"
72
73 #define FACTOR 0x010b0000 * 2
74
ixheaacd_alias_reduction(WORD16 * deg_patched,WORD16 * nrg_gain,WORD16 * nrg_est,WORD8 * alias_red_buf,WORD32 num_sub_bands,ixheaacd_misc_tables * pstr_common_tables)75 static VOID ixheaacd_alias_reduction(WORD16 *deg_patched, WORD16 *nrg_gain,
76 WORD16 *nrg_est, WORD8 *alias_red_buf,
77 WORD32 num_sub_bands,
78 ixheaacd_misc_tables *pstr_common_tables) {
79 WORD32 group, grouping, i, num_groups, k;
80 WORD16 f_group_vec[MAX_FREQ_COEFFS], *ptr_f_group_vec;
81
82 grouping = 0;
83 i = 0;
84
85 for (k = 0; k < num_sub_bands - 1; k++) {
86 if ((deg_patched[k + 1] != 0) && alias_red_buf[k]) {
87 if (grouping == 0) {
88 f_group_vec[i] = k;
89 grouping = 1;
90 i++;
91 } else {
92 if ((f_group_vec[i - 1] + 3) == k) {
93 f_group_vec[i] = (k + 1);
94 grouping = 0;
95 i++;
96 }
97 }
98 } else {
99 if (grouping) {
100 grouping = 0;
101 f_group_vec[i] = k;
102
103 if (alias_red_buf[k]) f_group_vec[i] = k + 1;
104
105 i++;
106 }
107 }
108 }
109
110 if (grouping) {
111 f_group_vec[i] = num_sub_bands;
112 i++;
113 }
114 num_groups = (i >> 1);
115
116 ptr_f_group_vec = f_group_vec;
117
118 for (group = num_groups; group != 0; group--) {
119 WORD16 nrg_amp_mant;
120 WORD16 nrg_amp_exp;
121 WORD16 nrgMod_m;
122 WORD16 nrgMod_e;
123 WORD16 grp_gain_mant;
124 WORD16 grp_gain_exp;
125 WORD16 compensation_m;
126 WORD16 compensation_e;
127 WORD32 nrg_mod_mant;
128 WORD32 nrg_mod_exp;
129
130 WORD32 start_grp = *ptr_f_group_vec++;
131 WORD32 stop_grp = *ptr_f_group_vec++;
132
133 ixheaacd_avggain_calc(nrg_est, nrg_gain, start_grp, stop_grp, &nrg_amp_mant,
134 &nrg_amp_exp, &grp_gain_mant, &grp_gain_exp,
135 pstr_common_tables, 1);
136
137 nrg_mod_mant = 0;
138 nrg_mod_exp = 0;
139 {
140 WORD16 *ptr_nrg_gain_mant = &nrg_gain[2 * start_grp];
141
142 for (k = start_grp; k < stop_grp; k++) {
143 WORD32 tmp_mant, tmp_gain_mant, gain_m;
144 WORD32 tmp_e, tmp_gain_exp;
145 WORD16 one_minus_alpha, alpha = deg_patched[k];
146
147 if (k < (num_sub_bands - 1)) {
148 alpha = ixheaacd_max16(deg_patched[k + 1], alpha);
149 }
150 gain_m = (alpha * grp_gain_mant);
151 one_minus_alpha = 0x7fff - alpha;
152
153 tmp_gain_mant = *ptr_nrg_gain_mant;
154 tmp_gain_exp = *(ptr_nrg_gain_mant + 1);
155
156 {
157 WORD32 exp_diff;
158
159 tmp_gain_mant = (one_minus_alpha * tmp_gain_mant) >> 15;
160
161 exp_diff = (grp_gain_exp - tmp_gain_exp);
162
163 if (exp_diff >= 0) {
164 tmp_gain_exp = grp_gain_exp;
165 tmp_gain_mant = ixheaacd_shr32(tmp_gain_mant, exp_diff);
166
167 tmp_gain_mant = (gain_m >> 15) + tmp_gain_mant;
168
169 } else {
170 tmp_gain_mant =
171 (ixheaacd_shr32(gain_m, (15 - exp_diff))) + tmp_gain_mant;
172 }
173 }
174 *ptr_nrg_gain_mant++ = tmp_gain_mant;
175 *ptr_nrg_gain_mant++ = tmp_gain_exp;
176
177 tmp_mant = (tmp_gain_mant * (nrg_est[2 * k])) >> 16;
178 tmp_e = (tmp_gain_exp + (nrg_est[2 * k + 1]) + 1);
179
180 {
181 WORD32 exp_diff;
182 exp_diff = tmp_e - nrg_mod_exp;
183 if (exp_diff >= 0) {
184 nrg_mod_mant = tmp_mant + (ixheaacd_shr32(nrg_mod_mant, exp_diff));
185 nrg_mod_exp = tmp_e;
186 } else {
187 exp_diff = -exp_diff;
188 nrg_mod_mant = (ixheaacd_shr32(tmp_mant, exp_diff)) + nrg_mod_mant;
189 }
190 }
191 }
192 }
193
194 {
195 WORD32 norm_val;
196 norm_val = 16 - ixheaacd_pnorm32(nrg_mod_mant);
197 if (norm_val > 0) {
198 nrg_mod_mant >>= norm_val;
199 nrg_mod_exp += norm_val;
200 }
201 }
202
203 nrgMod_m = (WORD16)nrg_mod_mant;
204 nrgMod_e = (WORD16)nrg_mod_exp;
205
206 compensation_e = ixheaacd_fix_mant_div(nrg_amp_mant, nrgMod_m,
207 &compensation_m, pstr_common_tables);
208 compensation_e += nrg_amp_exp - nrgMod_e + 1 + 1;
209
210 {
211 WORD16 *ptr_nrg_gain_mant = &nrg_gain[2 * start_grp];
212
213 for (k = stop_grp - start_grp; k != 0; k--) {
214 WORD16 temp1, temp2;
215 temp1 = *ptr_nrg_gain_mant;
216 temp2 = *(ptr_nrg_gain_mant + 1);
217 temp1 = (temp1 * compensation_m) >> 16;
218 temp2 = (temp2 + compensation_e);
219 *ptr_nrg_gain_mant++ = temp1;
220 *ptr_nrg_gain_mant++ = temp2;
221 }
222 }
223 }
224 }
225
ixheaacd_noiselimiting(ia_freq_band_data_struct * pstr_freq_band_data,WORD32 skip_bands,WORD16 * ptr_enrg_orig,WORD16 * nrg_est,WORD16 * nrg_gain,WORD16 * noise_level_mant,WORD16 * nrg_sine,WORD16 * ptr_limit_gain_table,FLAG noise_absc_flag,ixheaacd_misc_tables * pstr_common_tables)226 VOID ixheaacd_noiselimiting(ia_freq_band_data_struct *pstr_freq_band_data,
227 WORD32 skip_bands, WORD16 *ptr_enrg_orig,
228 WORD16 *nrg_est, WORD16 *nrg_gain,
229 WORD16 *noise_level_mant, WORD16 *nrg_sine,
230 WORD16 *ptr_limit_gain_table, FLAG noise_absc_flag,
231 ixheaacd_misc_tables *pstr_common_tables) {
232 WORD32 c, k;
233 WORD32 temp_val;
234 WORD16 limit_gain_mant = *ptr_limit_gain_table++;
235 WORD16 limit_gain_exp = *ptr_limit_gain_table;
236 for (c = 0; c < pstr_freq_band_data->num_lf_bands; c++) {
237 WORD16 max_gain_mant;
238 WORD16 sum_orig_mant, sum_orig_exp;
239 WORD16 max_gain_exp;
240 WORD32 max_temp;
241 WORD32 start_band = 0;
242 WORD32 stop_band = 0;
243
244 if ((pstr_freq_band_data->freq_band_tbl_lim[c] > skip_bands)) {
245 start_band = (pstr_freq_band_data->freq_band_tbl_lim[c] - skip_bands);
246 }
247
248 if ((pstr_freq_band_data->freq_band_tbl_lim[c + 1] > skip_bands)) {
249 stop_band = (pstr_freq_band_data->freq_band_tbl_lim[c + 1] - skip_bands);
250 }
251
252 if ((start_band < stop_band)) {
253 ixheaacd_avggain_calc(ptr_enrg_orig, nrg_est, start_band, stop_band,
254 &sum_orig_mant, &sum_orig_exp, &max_gain_mant,
255 &max_gain_exp, pstr_common_tables, 0);
256
257 max_temp = ixheaacd_mult16x16in32_shl(max_gain_mant, limit_gain_mant);
258 max_gain_exp = (max_gain_exp + limit_gain_exp);
259
260 temp_val = ixheaacd_norm32(max_temp);
261
262 max_gain_exp = (WORD16)(max_gain_exp - temp_val);
263 max_gain_mant = (WORD16)((max_temp << temp_val) >> 16);
264
265 if ((max_gain_exp >= MAX_GAIN_EXP)) {
266 max_gain_mant = 0x3000;
267 max_gain_exp = MAX_GAIN_EXP;
268 }
269
270 {
271 WORD16 *ptr_nrg_gain = &nrg_gain[2 * start_band];
272 WORD16 *p_noise_level = &noise_level_mant[2 * start_band];
273
274 for (k = stop_band - start_band; k != 0; k--) {
275 WORD16 noise_amp_mant;
276 WORD16 noise_amp_exp;
277
278 WORD16 t_gain_mant = *(ptr_nrg_gain);
279 WORD16 t_gain_exp = *(ptr_nrg_gain + 1);
280
281 if (((t_gain_exp > max_gain_exp)) ||
282 ((t_gain_exp == max_gain_exp) && (t_gain_mant > max_gain_mant))) {
283 noise_amp_exp =
284 ixheaacd_fix_mant_div(max_gain_mant, t_gain_mant,
285 &noise_amp_mant, pstr_common_tables);
286 noise_amp_exp += (max_gain_exp - t_gain_exp) + 1;
287
288 *p_noise_level = ixheaacd_extract16h(ixheaacd_shl32_dir_sat_limit(
289 ixheaacd_mult16x16in32_shl(*p_noise_level, noise_amp_mant),
290 noise_amp_exp));
291
292 *ptr_nrg_gain = max_gain_mant;
293 *(ptr_nrg_gain + 1) = max_gain_exp;
294 }
295 ptr_nrg_gain += 2;
296 p_noise_level += 2;
297 }
298 }
299
300 {
301 WORD16 boost_gain_mant;
302 WORD16 boost_gain_exp;
303 WORD16 accu_m;
304 WORD16 accu_e;
305 WORD32 accu_m_t;
306 WORD32 accu_e_t;
307 WORD16 *ptr_nrg_gain = &nrg_gain[2 * start_band];
308 WORD16 *ptr_enrg_est_buf = &nrg_est[2 * start_band];
309 WORD16 *p_noise_level = &noise_level_mant[2 * start_band];
310 WORD16 *p_nrg_sine = &nrg_sine[2 * start_band];
311
312 accu_m_t = 0;
313 accu_e_t = 0;
314
315 for (k = stop_band - start_band; k != 0; k--) {
316 WORD32 tmp_mant, tmp_e;
317
318 tmp_mant = *ptr_nrg_gain++;
319 tmp_e = *ptr_nrg_gain++;
320 tmp_mant = (tmp_mant * (*ptr_enrg_est_buf++));
321 tmp_e = (tmp_e + (*ptr_enrg_est_buf++));
322 tmp_mant = tmp_mant >> 15;
323 {
324 WORD32 exp_diff;
325 exp_diff = tmp_e - accu_e_t;
326 if (exp_diff >= 0) {
327 accu_m_t = tmp_mant + ixheaacd_shr32(accu_m_t, exp_diff);
328 accu_e_t = tmp_e;
329 } else {
330 exp_diff = -exp_diff;
331 accu_m_t = ixheaacd_shr32(tmp_mant, exp_diff) + accu_m_t;
332 }
333 }
334
335 if (p_nrg_sine[0] != 0) {
336 WORD32 exp_diff = p_nrg_sine[1] - accu_e_t;
337 if (exp_diff >= 0) {
338 accu_m_t = p_nrg_sine[0] + ixheaacd_shr32(accu_m_t, exp_diff);
339 accu_e_t = p_nrg_sine[1];
340 } else {
341 exp_diff = -exp_diff;
342 accu_m_t = accu_m_t + ixheaacd_shr32(p_nrg_sine[0], exp_diff);
343 }
344
345 } else {
346 if (noise_absc_flag == 0) {
347 WORD32 exp_diff = p_noise_level[1] - accu_e_t;
348 if (exp_diff >= 0) {
349 accu_m_t =
350 p_noise_level[0] + ixheaacd_shr32(accu_m_t, exp_diff);
351 accu_e_t = p_noise_level[1];
352 } else {
353 exp_diff = -exp_diff;
354 accu_m_t =
355 accu_m_t + ixheaacd_shr32(p_noise_level[0], exp_diff);
356 }
357 }
358 }
359 p_noise_level += 2;
360 p_nrg_sine += 2;
361 }
362
363 {
364 WORD32 norm_val;
365 norm_val = 16 - ixheaacd_norm32(accu_m_t);
366 if (norm_val > 0) {
367 accu_m_t >>= norm_val;
368 accu_e_t += norm_val;
369 }
370 }
371
372 accu_m = (WORD16)accu_m_t;
373 accu_e = (WORD16)accu_e_t;
374
375 boost_gain_exp = ixheaacd_fix_mant_div(
376 sum_orig_mant, accu_m, &boost_gain_mant, pstr_common_tables);
377
378 boost_gain_exp += (sum_orig_exp - accu_e) + 1;
379
380 if ((boost_gain_exp > 2) ||
381 ((boost_gain_exp == 2) && (boost_gain_mant > 0x5061))) {
382 boost_gain_mant = 0x5061;
383 boost_gain_exp = 2;
384 }
385
386 ptr_nrg_gain = &nrg_gain[2 * start_band];
387 p_noise_level = &noise_level_mant[2 * start_band];
388 p_nrg_sine = &nrg_sine[2 * start_band];
389
390 for (k = stop_band - start_band; k != 0; k--) {
391 WORD16 temp1, temp2, temp3;
392
393 temp1 = *ptr_nrg_gain;
394 temp2 = *p_nrg_sine;
395 temp3 = *p_noise_level;
396
397 temp1 = ixheaacd_mult16_shl(temp1, boost_gain_mant);
398 temp2 = ixheaacd_mult16_shl(temp2, boost_gain_mant);
399 temp3 = ixheaacd_mult16_shl(temp3, boost_gain_mant);
400 *ptr_nrg_gain++ = temp1;
401 *p_nrg_sine++ = temp2;
402 *p_noise_level++ = temp3;
403
404 temp1 = *ptr_nrg_gain;
405 temp2 = *p_nrg_sine;
406 temp3 = *p_noise_level;
407
408 temp1 = (temp1 + boost_gain_exp);
409 temp2 = (temp2 + boost_gain_exp);
410 temp3 = (temp3 + boost_gain_exp);
411 *ptr_nrg_gain++ = (temp1);
412 *p_nrg_sine++ = (temp2);
413 *p_noise_level++ = (temp3);
414 }
415 }
416 }
417 }
418 }
419
ixheaacd_conv_ergtoamplitudelp_dec(WORD32 bands,WORD16 noise_e,WORD16 * nrg_sine,WORD16 * nrg_gain,WORD16 * noise_level_mant,WORD16 * sqrt_table)420 VOID ixheaacd_conv_ergtoamplitudelp_dec(WORD32 bands, WORD16 noise_e,
421 WORD16 *nrg_sine, WORD16 *nrg_gain,
422 WORD16 *noise_level_mant,
423 WORD16 *sqrt_table) {
424 WORD32 k;
425 for (k = 0; k < bands; k++) {
426 WORD32 shift;
427 ixheaacd_fix_mant_exp_sqrt(&nrg_sine[2 * k], sqrt_table);
428 ixheaacd_fix_mant_exp_sqrt(&nrg_gain[2 * k], sqrt_table);
429 ixheaacd_fix_mant_exp_sqrt(&noise_level_mant[2 * k], sqrt_table);
430
431 shift = (noise_e - noise_level_mant[2 * k + 1]);
432
433 shift = (shift - 4);
434 if (shift > 0)
435 noise_level_mant[2 * k] = (noise_level_mant[2 * k] >> shift);
436 else
437 noise_level_mant[2 * k] = (noise_level_mant[2 * k] << -shift);
438
439 shift = (nrg_sine[2 * k + 1] - noise_e);
440 if (shift > 0)
441 nrg_sine[2 * k] = ixheaacd_shl16_sat(nrg_sine[2 * k], (WORD16)shift);
442 else
443 nrg_sine[2 * k] = ixheaacd_shr16(nrg_sine[2 * k], (WORD16)-shift);
444 }
445 }
446
ixheaacd_conv_ergtoamplitude_dec(WORD32 bands,WORD16 noise_e,WORD16 * nrg_sine,WORD16 * nrg_gain,WORD16 * noise_level_mant,WORD16 * sqrt_table)447 VOID ixheaacd_conv_ergtoamplitude_dec(WORD32 bands, WORD16 noise_e,
448 WORD16 *nrg_sine, WORD16 *nrg_gain,
449 WORD16 *noise_level_mant,
450 WORD16 *sqrt_table) {
451 WORD32 k;
452 for (k = 0; k < bands; k++) {
453 WORD32 shift;
454
455 ixheaacd_fix_mant_exp_sqrt(&nrg_sine[2 * k], sqrt_table);
456 ixheaacd_fix_mant_exp_sqrt(&nrg_gain[2 * k], sqrt_table);
457 ixheaacd_fix_mant_exp_sqrt(&noise_level_mant[2 * k], sqrt_table);
458
459 shift = (noise_e - noise_level_mant[2 * k + 1]);
460
461 shift = (shift - 4);
462 if (shift > 0)
463 noise_level_mant[2 * k] = (noise_level_mant[2 * k] >> shift);
464 else
465 noise_level_mant[2 * k] = (noise_level_mant[2 * k] << -shift);
466 }
467 }
468
ixheaacd_adapt_noise_gain_calc(ia_sbr_calc_env_struct * ptr_sbr_calc_env,WORD32 noise_e,WORD32 num_sub_bands,WORD32 skip_bands,WORD16 * nrg_gain,WORD16 * noise_level_mant,WORD16 * nrg_sine,WORD32 start_pos,WORD32 end_pos,WORD32 input_e,WORD32 adj_e,WORD32 final_e,WORD32 sub_band_start,WORD32 lb_scale,FLAG noise_absc_flag,WORD32 smooth_length,WORD32 ** anal_buf_real_mant,WORD32 ** anal_buf_imag_mant,WORD32 low_pow_flag,ia_sbr_tables_struct * ptr_sbr_tables)469 static PLATFORM_INLINE VOID ixheaacd_adapt_noise_gain_calc(
470 ia_sbr_calc_env_struct *ptr_sbr_calc_env, WORD32 noise_e,
471 WORD32 num_sub_bands, WORD32 skip_bands, WORD16 *nrg_gain,
472 WORD16 *noise_level_mant, WORD16 *nrg_sine, WORD32 start_pos,
473 WORD32 end_pos, WORD32 input_e, WORD32 adj_e, WORD32 final_e,
474 WORD32 sub_band_start, WORD32 lb_scale, FLAG noise_absc_flag,
475 WORD32 smooth_length, WORD32 **anal_buf_real_mant,
476 WORD32 **anal_buf_imag_mant, WORD32 low_pow_flag,
477 ia_sbr_tables_struct *ptr_sbr_tables) {
478 WORD32 l, k;
479 WORD32 scale_change;
480 WORD32 bands = num_sub_bands - skip_bands;
481 WORD16 *ptr_filt_buf;
482 WORD16 *ptr_filt_buf_noise;
483 WORD16 *ptr_gain = &nrg_gain[0];
484
485 if (ptr_sbr_calc_env->start_up) {
486 WORD16 *ptr_noise = noise_level_mant;
487 ptr_sbr_calc_env->start_up = 0;
488
489 ptr_sbr_calc_env->filt_buf_noise_e = noise_e;
490 ptr_filt_buf = &ptr_sbr_calc_env->filt_buf_me[skip_bands * 2];
491 ptr_filt_buf_noise = &ptr_sbr_calc_env->filt_buf_noise_m[skip_bands];
492
493 for (k = bands; k != 0; k--) {
494 WORD16 temp1 = *ptr_gain++;
495 WORD16 temp2 = *ptr_gain++;
496 WORD16 temp3 = *ptr_noise;
497 ptr_noise += 2;
498
499 *ptr_filt_buf++ = temp1;
500 *ptr_filt_buf++ = temp2;
501 *ptr_filt_buf_noise++ = temp3;
502 }
503 } else {
504 ixheaacd_equalize_filt_buff_exp(
505 &ptr_sbr_calc_env->filt_buf_me[2 * skip_bands], nrg_gain, bands);
506 }
507
508 for (l = start_pos; l < end_pos; l++) {
509 if ((l < MAX_COLS)) {
510 scale_change = (adj_e - input_e);
511 } else {
512 scale_change = (final_e - input_e);
513
514 if (((l == MAX_COLS)) && ((start_pos < MAX_COLS))) {
515 WORD32 diff = final_e - noise_e;
516 noise_e = final_e;
517 ixheaacd_noise_level_rescaling(noise_level_mant, diff, bands, 2);
518 }
519 }
520
521 ixheaacd_noise_level_rescaling(ptr_sbr_calc_env->filt_buf_noise_m,
522 ptr_sbr_calc_env->filt_buf_noise_e - noise_e,
523 num_sub_bands, 1);
524
525 ptr_sbr_calc_env->filt_buf_noise_e = noise_e;
526
527 {
528 WORD32 *anal_buf_real_m_l;
529 anal_buf_real_m_l = anal_buf_real_mant[l];
530
531 if (low_pow_flag) {
532 WORD32 index = ptr_sbr_calc_env->ph_index;
533 WORD32 harm_index = ptr_sbr_calc_env->harm_index;
534 WORD32 freq_inv_flag = (sub_band_start & 1);
535 WORD32 *ptr_real_buf = &anal_buf_real_m_l[sub_band_start];
536
537 const WORD32 *ptr_rand_ph = &ptr_sbr_tables->sbr_rand_ph[index + 1];
538
539 ptr_sbr_calc_env->ph_index =
540 (WORD16)((index + num_sub_bands) & (SBR_NF_NO_RANDOM_VAL - 1));
541 ptr_sbr_calc_env->harm_index = (WORD16)(((harm_index + 1)) & 3);
542
543 if (!(harm_index & 0x1)) {
544 (*ixheaacd_harm_idx_zerotwolp)(
545 ptr_real_buf, nrg_gain, scale_change, nrg_sine, ptr_rand_ph,
546 noise_level_mant, num_sub_bands, noise_absc_flag, harm_index);
547 } else {
548 WORD32 noise = (noise_e - 16) - lb_scale;
549
550 freq_inv_flag = (!freq_inv_flag);
551 freq_inv_flag = (freq_inv_flag << 1) - 1;
552
553 if (harm_index == 3) freq_inv_flag = -freq_inv_flag;
554
555 ixheaacd_harm_idx_onethreelp(ptr_real_buf, nrg_gain, scale_change,
556 nrg_sine, ptr_rand_ph, noise_level_mant,
557 num_sub_bands, noise_absc_flag,
558 freq_inv_flag, noise, sub_band_start);
559 }
560
561 } else {
562 WORD16 smooth_ratio;
563 WORD32 *anal_buf_imag_m_l;
564 anal_buf_imag_m_l = anal_buf_imag_mant[l];
565
566 if (((l - start_pos) < smooth_length)) {
567 smooth_ratio = ptr_sbr_tables->env_calc_tables_ptr
568 ->sbr_smooth_filter[(l - start_pos)];
569 } else {
570 smooth_ratio = 0;
571 }
572
573 ixheaacd_adj_timeslot(
574 &anal_buf_real_m_l[sub_band_start],
575 &anal_buf_imag_m_l[sub_band_start],
576 &ptr_sbr_calc_env->filt_buf_me[2 * skip_bands],
577 &ptr_sbr_calc_env->filt_buf_noise_m[skip_bands], nrg_gain,
578 noise_level_mant, nrg_sine, (WORD16)(noise_e - 16),
579 &ptr_sbr_calc_env->harm_index, (WORD16)sub_band_start,
580 (WORD16)(bands), (WORD16)scale_change, smooth_ratio,
581 noise_absc_flag, &ptr_sbr_calc_env->ph_index, ptr_sbr_tables);
582 }
583 }
584 }
585
586 ixheaacd_filt_buf_update(ptr_sbr_calc_env->filt_buf_me + 2 * skip_bands,
587 ptr_sbr_calc_env->filt_buf_noise_m + skip_bands,
588 nrg_gain, noise_level_mant, bands);
589 }
590
ixheaacd_calc_subband_gains(ia_freq_band_data_struct * pstr_freq_band_data,ia_sbr_frame_info_data_struct * ptr_frame_data,WORD32 freq_res,WORD16 * ptr_noise_floor,WORD32 num_sf_bands,WORD32 mvalue,WORD32 env,WORD8 * sine_mapped_matrix,WORD8 * alias_red_buf,WORD16 * ptr_enrg_orig,WORD16 * nrg_sine,WORD16 * nrg_est,WORD16 * nrg_gain,WORD16 * noise_level_mant,FLAG noise_absc_flag,ixheaacd_misc_tables * pstr_common_tables)591 VOID ixheaacd_calc_subband_gains(ia_freq_band_data_struct *pstr_freq_band_data,
592 ia_sbr_frame_info_data_struct *ptr_frame_data,
593 WORD32 freq_res, WORD16 *ptr_noise_floor,
594 WORD32 num_sf_bands, WORD32 mvalue, WORD32 env,
595 WORD8 *sine_mapped_matrix,
596 WORD8 *alias_red_buf, WORD16 *ptr_enrg_orig,
597 WORD16 *nrg_sine, WORD16 *nrg_est,
598 WORD16 *nrg_gain, WORD16 *noise_level_mant,
599 FLAG noise_absc_flag,
600 ixheaacd_misc_tables *pstr_common_tables) {
601 WORD16 *ptr_freq_band_tbl = pstr_freq_band_data->freq_band_table[freq_res];
602 WORD32 ui_noise = pstr_freq_band_data->freq_band_tbl_noise[1];
603 WORD32 nb_idx = 0;
604 WORD16 tmp_noise_mant;
605 WORD16 tmp_noise_exp;
606 WORD8 *ptr_sine_mapped = sine_mapped_matrix;
607 WORD32 sub_band_start = pstr_freq_band_data->sub_band_start;
608 WORD32 skip_bands = (ptr_frame_data->max_qmf_subband_aac - sub_band_start);
609 WORD8 *ptr_sine_mapped_1 = &sine_mapped_matrix[skip_bands];
610 WORD32 k, c = 0, j;
611
612 WORD16 *ptr_env_sf_arr = &ptr_frame_data->int_env_sf_arr[mvalue];
613 WORD8 *ptr_alias_red_buf =
614 &alias_red_buf[ptr_freq_band_tbl[0] - sub_band_start];
615
616 tmp_noise_mant = (WORD16)(ptr_noise_floor[nb_idx] & MASK_M);
617 tmp_noise_exp =
618 (WORD16)(ptr_noise_floor[nb_idx] & MASK_FOR_EXP) - NOISE_EXP_OFFSET;
619
620 for (j = 0; j < num_sf_bands; j++) {
621 WORD8 sine_present_flag;
622 WORD16 tmp_nrg_ref_exp, tmp_nrg_ref_mant;
623 WORD16 li = *ptr_freq_band_tbl++;
624 WORD16 ui = *ptr_freq_band_tbl;
625 WORD16 env_sf_val = *ptr_env_sf_arr++;
626
627 tmp_nrg_ref_exp =
628 (WORD16)((env_sf_val & (WORD16)MASK_FOR_EXP) - NRG_EXP_OFFSET);
629 tmp_nrg_ref_mant = (WORD16)(env_sf_val & MASK_M);
630
631 sine_present_flag = 0;
632 for (k = li; k < ui; k++) {
633 if ((env >= *ptr_sine_mapped++)) sine_present_flag = 1;
634 }
635 for (k = li; k < ui; k++) {
636 *ptr_alias_red_buf++ = !sine_present_flag;
637
638 if ((k >= ui_noise)) {
639 nb_idx++;
640 ui_noise = pstr_freq_band_data->freq_band_tbl_noise[nb_idx + 1];
641 tmp_noise_mant = (WORD16)(ptr_noise_floor[nb_idx] & MASK_M);
642 tmp_noise_exp =
643 (WORD16)(ptr_noise_floor[nb_idx] & MASK_FOR_EXP) - NOISE_EXP_OFFSET;
644 }
645
646 if ((k >= ptr_frame_data->max_qmf_subband_aac)) {
647 ptr_enrg_orig[2 * c] = tmp_nrg_ref_mant;
648 ptr_enrg_orig[2 * c + 1] = tmp_nrg_ref_exp;
649 nrg_sine[2 * c] = 0;
650 nrg_sine[2 * c + 1] = 0;
651
652 ixheaacd_subbandgain_calc(
653 tmp_nrg_ref_mant, tmp_noise_mant, nrg_est[2 * c],
654 nrg_est[2 * c + 1], tmp_noise_exp, tmp_nrg_ref_exp,
655 sine_present_flag,
656 (env >= ptr_sine_mapped_1[c]) ? (FLAG)1 : (FLAG)0, noise_absc_flag,
657 &nrg_gain[2 * c], &noise_level_mant[2 * c], &nrg_sine[2 * c],
658 pstr_common_tables);
659 c++;
660 }
661 }
662 }
663 }
664
665 #define ALIGN_SIZE64(x) ((((x) + 7) >> 3) << 3)
666
ixheaacd_calc_sbrenvelope(ia_sbr_scale_fact_struct * ptr_sbr_scale_fac,ia_sbr_calc_env_struct * ptr_sbr_calc_env,ia_sbr_header_data_struct * ptr_header_data,ia_sbr_frame_info_data_struct * ptr_frame_data,ia_sbr_prev_frame_data_struct * ptr_frame_data_prev,WORD32 ** anal_buf_real_mant,WORD32 ** anal_buf_imag_mant,WORD16 * deg_patched,FLAG low_pow_flag,ia_sbr_tables_struct * ptr_sbr_tables,ixheaacd_misc_tables * pstr_common_tables,WORD32 * ptr_qmf_matrix,WORD32 audio_object_type)667 IA_ERRORCODE ixheaacd_calc_sbrenvelope(
668 ia_sbr_scale_fact_struct *ptr_sbr_scale_fac,
669 ia_sbr_calc_env_struct *ptr_sbr_calc_env,
670 ia_sbr_header_data_struct *ptr_header_data,
671 ia_sbr_frame_info_data_struct *ptr_frame_data,
672 ia_sbr_prev_frame_data_struct *ptr_frame_data_prev,
673 WORD32 **anal_buf_real_mant, WORD32 **anal_buf_imag_mant,
674 WORD16 *deg_patched, FLAG low_pow_flag,
675 ia_sbr_tables_struct *ptr_sbr_tables,
676 ixheaacd_misc_tables *pstr_common_tables, WORD32 *ptr_qmf_matrix,
677 WORD32 audio_object_type) {
678 WORD32 i, j, m;
679 WORD32 noise_floor_idx;
680 WORD32 start_pos, end_pos;
681 WORD32 freq_res;
682 WORD32 num_env = ptr_frame_data->str_frame_info_details.num_env;
683 WORD16 *ptr_border_vec = ptr_frame_data->str_frame_info_details.border_vec;
684 IA_ERRORCODE err_code = IA_NO_ERROR;
685 WORD16 *ptr_noise_floor;
686 ia_freq_band_data_struct *pstr_freq_band_data =
687 ptr_header_data->pstr_freq_band_data;
688
689 FLAG noise_absc_flag;
690 WORD32 smooth_length;
691
692 const WORD16 *num_sf_bands = pstr_freq_band_data->num_sf_bands;
693 const WORD32 num_nf_bands = pstr_freq_band_data->num_nf_bands;
694
695 WORD32 sub_band_start = pstr_freq_band_data->sub_band_start;
696 WORD32 sub_band_end = pstr_freq_band_data->sub_band_end;
697 WORD32 num_sub_bands;
698 WORD32 skip_bands;
699 WORD32 bands;
700
701 WORD num_cols;
702 WORD32 first_start;
703
704 WORD16 *ptr_sbr_lim_gain;
705 WORD32 max_sfb_nrg_exp;
706
707 WORD16 *ptr_enrg_orig;
708
709 WORD32 input_e;
710 WORD32 ov_adj_e;
711 WORD32 adj_e;
712 WORD32 output_e;
713 WORD32 final_e;
714 WORD16 noise_e;
715 WORD16 lb_scale;
716
717 WORD16 nrg_est[2 * MAX_FREQ_COEFFS];
718
719 WORD16 nrg_gain[2 * MAX_FREQ_COEFFS];
720 WORD16 noise_level_mant[2 * MAX_FREQ_COEFFS];
721 WORD16 nrg_sine[2 * MAX_FREQ_COEFFS];
722
723 WORD8 sine_mapped_matrix[MAX_FREQ_COEFFS];
724 WORD8 alias_red_buf[64];
725
726 ptr_noise_floor = ptr_frame_data->int_noise_floor;
727
728 ptr_enrg_orig =
729 (WORD16 *)((WORD8 *)ptr_frame_data +
730 ALIGN_SIZE64(sizeof(ia_sbr_frame_info_data_struct)));
731
732 num_env = ptr_frame_data->str_frame_info_details.num_env;
733 ptr_border_vec = ptr_frame_data->str_frame_info_details.border_vec;
734 num_sub_bands = (sub_band_end - sub_band_start);
735 skip_bands = (ptr_frame_data->max_qmf_subband_aac - sub_band_start);
736
737 ixheaacd_map_sineflags(
738 pstr_freq_band_data->freq_band_table[HIGH],
739 pstr_freq_band_data->num_sf_bands[HIGH], ptr_frame_data->add_harmonics,
740 ptr_sbr_calc_env->harm_flags_prev,
741 ptr_frame_data->str_frame_info_details.transient_env, sine_mapped_matrix);
742
743 adj_e = 0;
744 {
745 WORD16 max_noise;
746 WORD32 first_band;
747
748 if (ptr_frame_data_prev->max_qmf_subband_aac >
749 ptr_frame_data->max_qmf_subband_aac)
750 first_band = (ptr_frame_data_prev->max_qmf_subband_aac - sub_band_start);
751 else
752 first_band = (ptr_frame_data->max_qmf_subband_aac - sub_band_start);
753
754 max_noise = 0;
755 for (i = first_band; i < num_sub_bands; i++) {
756 if (ptr_sbr_calc_env->filt_buf_noise_m[i] > max_noise) {
757 max_noise = ptr_sbr_calc_env->filt_buf_noise_m[i];
758 }
759 }
760 adj_e = ((ptr_sbr_calc_env->filt_buf_noise_e - ixheaacd_norm32(max_noise)) -
761 16);
762 }
763
764 final_e = 0;
765 {
766 WORD16 *ptr_env_sf_buf = ptr_frame_data->int_env_sf_arr;
767 for (i = 0; i < num_env; i++) {
768 WORD32 temp_val;
769
770 max_sfb_nrg_exp = NRG_EXP_OFFSET - SHORT_BITS;
771
772 freq_res = ptr_frame_data->str_frame_info_details.freq_res[i];
773
774 for (j = 0; j < num_sf_bands[freq_res]; j++) {
775 temp_val = ((*ptr_env_sf_buf++ & MASK_FOR_EXP));
776
777 if ((temp_val > max_sfb_nrg_exp)) {
778 max_sfb_nrg_exp = temp_val;
779 }
780 }
781
782 max_sfb_nrg_exp = (max_sfb_nrg_exp - NRG_EXP_OFFSET);
783
784 temp_val = ((max_sfb_nrg_exp + 13) >> 1);
785
786 if ((ptr_border_vec[i] < SBR_TIME_SLOTS)) {
787 if ((temp_val > adj_e)) {
788 adj_e = (WORD16)temp_val;
789 }
790 }
791
792 if ((ptr_border_vec[i + 1] > SBR_TIME_SLOTS)) {
793 if ((temp_val > final_e)) {
794 final_e = (WORD16)temp_val;
795 }
796 }
797 }
798 }
799
800 m = 0;
801 noise_floor_idx = 0;
802
803 for (i = 0; i < num_env; i++) {
804 if (audio_object_type == AOT_ER_AAC_ELD ||
805 audio_object_type == AOT_ER_AAC_LD) {
806 start_pos = ptr_border_vec[i];
807 end_pos = ptr_border_vec[i + 1];
808 } else {
809 start_pos = SBR_TIME_STEP * ptr_border_vec[i];
810 end_pos = SBR_TIME_STEP * ptr_border_vec[i + 1];
811 }
812 if ((start_pos >= MAX_ENV_COLS) || (end_pos > MAX_ENV_COLS))
813 return IA_FATAL_ERROR;
814 freq_res = ptr_frame_data->str_frame_info_details.freq_res[i];
815
816 if (noise_floor_idx >= MAX_NOISE_ENVELOPES) return IA_FATAL_ERROR;
817
818 if (ptr_border_vec[i] ==
819 ptr_frame_data->str_frame_info_details
820 .noise_border_vec[noise_floor_idx + 1]) {
821 ptr_noise_floor += num_nf_bands;
822 noise_floor_idx++;
823 }
824
825 if ((i == ptr_frame_data->str_frame_info_details.transient_env) ||
826 (i == ptr_sbr_calc_env->tansient_env_prev)) {
827 noise_absc_flag = 1;
828 smooth_length = 0;
829 } else {
830 noise_absc_flag = 0;
831 smooth_length = ((1 - ptr_header_data->smoothing_mode) << 2);
832 }
833
834 input_e = 15 - ptr_sbr_scale_fac->hb_scale;
835
836 if (ptr_header_data->interpol_freq) {
837 (*ixheaacd_enery_calc_per_subband)(
838 start_pos, end_pos, ptr_frame_data->max_qmf_subband_aac, sub_band_end,
839 input_e, nrg_est, low_pow_flag, ptr_sbr_tables, ptr_qmf_matrix);
840 } else {
841 ixheaacd_enery_calc_persfb(
842 anal_buf_real_mant, anal_buf_imag_mant, num_sf_bands[freq_res],
843 pstr_freq_band_data->freq_band_table[freq_res], start_pos, end_pos,
844 ptr_frame_data->max_qmf_subband_aac, input_e, nrg_est, low_pow_flag,
845 ptr_sbr_tables);
846 }
847
848 ixheaacd_calc_subband_gains(
849 pstr_freq_band_data, ptr_frame_data, freq_res, ptr_noise_floor,
850 num_sf_bands[freq_res], m, i, sine_mapped_matrix, alias_red_buf,
851 ptr_enrg_orig, nrg_sine, nrg_est, nrg_gain, noise_level_mant,
852 noise_absc_flag, pstr_common_tables);
853
854 m += num_sf_bands[freq_res];
855
856 ptr_sbr_lim_gain =
857 &ptr_sbr_tables->env_calc_tables_ptr
858 ->sbr_lim_gains_m[2 * ptr_header_data->limiter_gains];
859 ixheaacd_noiselimiting(pstr_freq_band_data, skip_bands, ptr_enrg_orig,
860 nrg_est, nrg_gain, noise_level_mant, nrg_sine,
861 ptr_sbr_lim_gain, noise_absc_flag,
862 pstr_common_tables);
863
864 if (low_pow_flag) {
865 ixheaacd_alias_reduction(deg_patched + sub_band_start, nrg_gain, nrg_est,
866 alias_red_buf, num_sub_bands,
867 pstr_common_tables);
868 }
869
870 if ((start_pos < MAX_COLS)) {
871 noise_e = adj_e;
872 } else {
873 noise_e = final_e;
874 }
875
876 bands = num_sub_bands - skip_bands;
877
878 if (low_pow_flag) {
879 (*ixheaacd_conv_ergtoamplitudelp)(
880 bands, noise_e, nrg_sine, nrg_gain, noise_level_mant,
881 (WORD16 *)pstr_common_tables->sqrt_table);
882 } else
883
884 {
885 (*ixheaacd_conv_ergtoamplitude)(bands, noise_e, nrg_sine, nrg_gain,
886 noise_level_mant,
887 (WORD16 *)pstr_common_tables->sqrt_table);
888 }
889
890 lb_scale = ixheaacd_sub16(15, ptr_sbr_scale_fac->lb_scale);
891
892 ixheaacd_adapt_noise_gain_calc(
893 ptr_sbr_calc_env, noise_e, num_sub_bands, skip_bands, nrg_gain,
894 noise_level_mant, nrg_sine, start_pos, end_pos, input_e, adj_e, final_e,
895 ptr_frame_data->max_qmf_subband_aac, lb_scale, noise_absc_flag,
896 smooth_length, anal_buf_real_mant, anal_buf_imag_mant, low_pow_flag,
897 ptr_sbr_tables);
898 }
899
900 first_start = ptr_border_vec[0] * SBR_TIME_STEP;
901 {
902 WORD32 ov_reserve, reserve;
903
904 ov_reserve = reserve = 0;
905
906 if (audio_object_type != AOT_ER_AAC_ELD) {
907 if (ptr_header_data->channel_mode == PS_STEREO) {
908 ov_reserve = (*ixheaacd_ixheaacd_expsubbandsamples)(
909 anal_buf_real_mant, anal_buf_imag_mant,
910 ptr_frame_data->max_qmf_subband_aac, sub_band_end, 0, first_start,
911 low_pow_flag);
912
913 reserve = (*ixheaacd_ixheaacd_expsubbandsamples)(
914 anal_buf_real_mant, anal_buf_imag_mant,
915 ptr_frame_data->max_qmf_subband_aac, sub_band_end, first_start,
916 MAX_COLS, low_pow_flag);
917 }
918 }
919
920 output_e = 0;
921
922 ov_adj_e = 15 - ptr_sbr_scale_fac->ov_hb_scale;
923
924 if (((ov_adj_e - ov_reserve) > (adj_e - reserve)))
925 output_e = (ov_adj_e - ov_reserve);
926 else
927 output_e = (adj_e - reserve);
928
929 (*ixheaacd_adjust_scale)(anal_buf_real_mant, anal_buf_imag_mant,
930 ptr_frame_data->max_qmf_subband_aac, sub_band_end,
931 0, first_start, (ov_adj_e - output_e),
932 low_pow_flag);
933
934 num_cols = (ptr_header_data->num_time_slots * ptr_header_data->time_step);
935
936 (*ixheaacd_adjust_scale)(anal_buf_real_mant, anal_buf_imag_mant,
937 ptr_frame_data->max_qmf_subband_aac, sub_band_end,
938 first_start, num_cols, (adj_e - output_e),
939 low_pow_flag);
940 }
941
942 ptr_sbr_scale_fac->hb_scale = (WORD16)(15 - output_e);
943
944 ptr_sbr_scale_fac->ov_hb_scale = (WORD16)(15 - final_e);
945
946 if (ptr_frame_data->str_frame_info_details.transient_env == num_env) {
947 ptr_sbr_calc_env->tansient_env_prev = 0;
948 } else {
949 ptr_sbr_calc_env->tansient_env_prev = -1;
950 }
951 return err_code;
952 }
953
ixheaacd_equalize_filt_buff_exp(WORD16 * ptr_filt_buf,WORD16 * nrg_gain,WORD32 subbands)954 VOID ixheaacd_equalize_filt_buff_exp(WORD16 *ptr_filt_buf, WORD16 *nrg_gain,
955 WORD32 subbands) {
956 WORD32 band;
957 WORD32 diff;
958 WORD32 gain_m, gain_e;
959 WORD32 filt_buf_mant, filt_buf_exp;
960
961 for (band = subbands - 1; band >= 0; band--) {
962 filt_buf_exp = *(ptr_filt_buf + 1);
963 gain_e = *(nrg_gain + 1);
964 filt_buf_mant = *ptr_filt_buf;
965 gain_m = *nrg_gain;
966 diff = (gain_e - filt_buf_exp);
967
968 if (diff >= 0) {
969 *(ptr_filt_buf + 1) = (WORD16)(gain_e);
970
971 *ptr_filt_buf = (WORD16)(*ptr_filt_buf >> diff);
972 } else {
973 WORD32 reserve;
974 reserve = (ixheaacd_norm32(filt_buf_mant) - 16);
975
976 if ((diff + reserve) >= 0) {
977 *ptr_filt_buf = (WORD16)(filt_buf_mant << -diff);
978 *(ptr_filt_buf + 1) = (WORD16)(filt_buf_exp + diff);
979 } else {
980 WORD32 shift;
981
982 *ptr_filt_buf = (WORD16)(filt_buf_mant << reserve);
983
984 *(ptr_filt_buf + 1) = (WORD16)(filt_buf_exp - reserve);
985
986 shift = -(reserve + diff);
987
988 *nrg_gain = (WORD16)(gain_m >> shift);
989 *(nrg_gain + 1) = (WORD16)(*(nrg_gain + 1) + shift);
990 }
991 }
992 nrg_gain += 2;
993 ptr_filt_buf += 2;
994 }
995 }
996
ixheaacd_filt_buf_update(WORD16 * ptr_filt_buf,WORD16 * ptr_filt_buf_noise,WORD16 * nrg_gain,WORD16 * noise_level_mant,WORD32 num_sub_bands)997 static PLATFORM_INLINE VOID ixheaacd_filt_buf_update(WORD16 *ptr_filt_buf,
998 WORD16 *ptr_filt_buf_noise,
999 WORD16 *nrg_gain,
1000 WORD16 *noise_level_mant,
1001 WORD32 num_sub_bands) {
1002 WORD32 k;
1003 WORD32 temp1, temp2;
1004
1005 for (k = num_sub_bands - 1; k >= 0; k--) {
1006 temp1 = *nrg_gain;
1007 nrg_gain += 2;
1008 temp2 = *noise_level_mant;
1009 noise_level_mant += 2;
1010
1011 *ptr_filt_buf = temp1;
1012 ptr_filt_buf += 2;
1013 *ptr_filt_buf_noise++ = temp2;
1014 }
1015 }
1016
ixheaacd_noise_level_rescaling(WORD16 * noise_level_mant,WORD32 diff,WORD32 num_sub_bands,WORD32 ixheaacd_drc_offset)1017 VOID ixheaacd_noise_level_rescaling(WORD16 *noise_level_mant, WORD32 diff,
1018 WORD32 num_sub_bands,
1019 WORD32 ixheaacd_drc_offset) {
1020 WORD32 k;
1021
1022 if (diff > 0) {
1023 for (k = num_sub_bands - 1; k >= 0; k--) {
1024 *noise_level_mant = *noise_level_mant >> diff;
1025 noise_level_mant += ixheaacd_drc_offset;
1026 }
1027 } else if (diff < 0) {
1028 diff = -diff;
1029 for (k = num_sub_bands - 1; k >= 0; k--) {
1030 *noise_level_mant = *noise_level_mant << diff;
1031 noise_level_mant += ixheaacd_drc_offset;
1032 }
1033 }
1034 }
1035
ixheaacd_adjust_scale_dec(WORD32 ** re,WORD32 ** im,WORD32 sub_band_start,WORD32 sub_band_end,WORD32 start_pos,WORD32 next_pos,WORD32 shift,FLAG low_pow_flag)1036 VOID ixheaacd_adjust_scale_dec(WORD32 **re, WORD32 **im, WORD32 sub_band_start,
1037 WORD32 sub_band_end, WORD32 start_pos,
1038 WORD32 next_pos, WORD32 shift,
1039 FLAG low_pow_flag) {
1040 WORD32 k, l;
1041
1042 if (shift != 0) {
1043 WORD32 num_sub_bands = (sub_band_end - sub_band_start);
1044
1045 shift = ixheaacd_min32(shift, 31);
1046 shift = ixheaacd_max32(shift, -31);
1047
1048 if (low_pow_flag) {
1049 if (shift > 0) {
1050 for (l = start_pos; l < next_pos; l++) {
1051 WORD32 *ptr = re[l] + sub_band_start;
1052 for (k = num_sub_bands - 1; k >= 0; k--) {
1053 *ptr = (*ptr << shift);
1054 ptr++;
1055 }
1056 }
1057 } else {
1058 shift = -shift;
1059 for (l = start_pos; l < next_pos; l++) {
1060 WORD32 *ptr = re[l] + sub_band_start;
1061 for (k = num_sub_bands - 1; k >= 0; k--) {
1062 *ptr = (*ptr >> shift);
1063 ptr++;
1064 }
1065 }
1066 }
1067 } else {
1068 if (shift > 0) {
1069 for (l = start_pos; l < next_pos; l++) {
1070 WORD32 *ptr = re[l] + sub_band_start;
1071 WORD32 *pti = im[l] + sub_band_start;
1072 for (k = num_sub_bands; k > 0; k--) {
1073 *ptr = (*ptr << shift);
1074 *pti = (*pti << shift);
1075 pti++;
1076 ptr++;
1077 }
1078 }
1079 } else {
1080 shift = -shift;
1081 for (l = start_pos; l < next_pos; l++) {
1082 WORD32 *ptr = re[l] + sub_band_start;
1083 WORD32 *pti = im[l] + sub_band_start;
1084 for (k = num_sub_bands; k > 0; k--) {
1085 *ptr = (*ptr >> shift);
1086 *pti = (*pti >> shift);
1087 ptr++;
1088 pti++;
1089 }
1090 }
1091 }
1092 }
1093 }
1094 }
1095
ixheaacd_expsubbandsamples_dec(WORD32 ** re,WORD32 ** im,WORD32 sub_band_start,WORD32 sub_band_end,WORD32 start_pos,WORD32 next_pos,FLAG low_pow_flag)1096 WORD16 ixheaacd_expsubbandsamples_dec(WORD32 **re, WORD32 **im,
1097 WORD32 sub_band_start,
1098 WORD32 sub_band_end, WORD32 start_pos,
1099 WORD32 next_pos, FLAG low_pow_flag) {
1100 WORD32 l, k;
1101 WORD16 max_shift;
1102
1103 WORD32 value;
1104 WORD32 max_abs;
1105 WORD32 num_sub_bands;
1106
1107 WORD32 *ptr_real;
1108 WORD32 *ptr_imag;
1109
1110 max_abs = 1;
1111 num_sub_bands = (sub_band_end - sub_band_start);
1112
1113 if (low_pow_flag) {
1114 for (l = start_pos; l < next_pos; l++) {
1115 WORD32 temp_real;
1116 ptr_real = re[l] + sub_band_start;
1117 temp_real = *ptr_real++;
1118 for (k = num_sub_bands; k > 0; k--) {
1119 value = ixheaacd_abs32_nrm(temp_real);
1120 max_abs |= value;
1121 temp_real = *ptr_real++;
1122 }
1123 }
1124 max_shift = ixheaacd_pnorm32(max_abs);
1125 } else {
1126 for (l = start_pos; l < next_pos; l++) {
1127 ptr_real = re[l] + sub_band_start;
1128 ptr_imag = im[l] + sub_band_start;
1129
1130 for (k = num_sub_bands; k > 0; k--) {
1131 WORD32 temp_real = *ptr_real++;
1132 WORD32 tempIm = *ptr_imag++;
1133
1134 temp_real = ixheaacd_abs32_nrm(temp_real);
1135 max_abs |= temp_real;
1136 tempIm = ixheaacd_abs32_nrm(tempIm);
1137 max_abs |= tempIm;
1138 }
1139 }
1140 max_shift = ixheaacd_pnorm32(max_abs);
1141 }
1142
1143 return max_shift;
1144 }
1145
1146 #define SHIFT_BEFORE_SQUARE 4
1147
ixheaacd_enery_calc_per_subband_dec(WORD32 start_pos,WORD32 next_pos,WORD32 sub_band_start,WORD32 sub_band_end,WORD32 frame_exp,WORD16 * nrg_est,FLAG low_pow_flag,ia_sbr_tables_struct * ptr_sbr_tables,WORD32 * ptr_qmf_matrix)1148 VOID ixheaacd_enery_calc_per_subband_dec(WORD32 start_pos, WORD32 next_pos,
1149 WORD32 sub_band_start,
1150 WORD32 sub_band_end, WORD32 frame_exp,
1151 WORD16 *nrg_est, FLAG low_pow_flag,
1152 ia_sbr_tables_struct *ptr_sbr_tables,
1153 WORD32 *ptr_qmf_matrix) {
1154 WORD16 temp;
1155 WORD16 inv_width;
1156 WORD16 sum_m;
1157 WORD32 accu;
1158 WORD32 k, l;
1159 WORD32 pre_shift_val;
1160 WORD32 shift;
1161 WORD32 *p_real;
1162 WORD32 max_shift_gap = SHIFT_BEFORE_SQUARE;
1163 WORD32 extra_shift = 0;
1164 WORD32 num_cols = next_pos - start_pos;
1165
1166 if (low_pow_flag) {
1167 max_shift_gap -= 1;
1168 p_real = ptr_qmf_matrix + sub_band_start + (start_pos << 6);
1169 extra_shift++;
1170 } else {
1171 p_real = ptr_qmf_matrix + sub_band_start + (start_pos << 7);
1172 num_cols = num_cols << 1;
1173 }
1174 inv_width = ptr_sbr_tables->env_calc_tables_ptr
1175 ->sbr_inv_int_table[(next_pos - start_pos)];
1176 frame_exp = (frame_exp << 1);
1177
1178 {
1179 WORD32 *ptr;
1180 for (k = sub_band_start; k < sub_band_end; k++) {
1181 WORD32 max_val = 1;
1182
1183 ptr = p_real;
1184
1185 for (l = num_cols; l != 0; l -= 2) {
1186 WORD32 value = ixheaacd_abs32_nrm(*ptr);
1187 ptr += 64;
1188 max_val = ixheaacd_max32(value, max_val);
1189 value = ixheaacd_abs32_nrm(*ptr);
1190 ptr += 64;
1191 max_val = ixheaacd_max32(value, max_val);
1192 }
1193 pre_shift_val = (ixheaacd_pnorm32(max_val) - max_shift_gap);
1194
1195 accu = 0L;
1196 shift = 16 - pre_shift_val;
1197 ptr = p_real;
1198
1199 if (shift > 0)
1200 for (l = num_cols; l != 0; l -= 2) {
1201 temp = (WORD16)((*(ptr) >> shift));
1202 ptr += 64;
1203 accu += (temp * temp);
1204 temp = (WORD16)((*(ptr) >> shift));
1205 ptr += 64;
1206 accu += (temp * temp);
1207 }
1208 else
1209 for (l = num_cols; l != 0; l -= 2) {
1210 temp = (WORD16)((*(ptr) << (-shift)));
1211 ptr += 64;
1212 accu += (temp * temp);
1213 temp = (WORD16)((*(ptr) << (-shift)));
1214 ptr += 64;
1215 accu += (temp * temp);
1216 }
1217
1218 if (accu != 0L) {
1219 shift = -(ixheaacd_pnorm32(accu));
1220 sum_m = (WORD16)(ixheaacd_shr32_dir_sat_limit(accu, (16 + shift)));
1221 *nrg_est++ = ixheaacd_mult16_shl_sat(sum_m, inv_width);
1222 shift = (shift - (pre_shift_val << 1));
1223 shift += extra_shift;
1224 *nrg_est++ = (WORD16)(frame_exp + shift + 1);
1225 } else {
1226 *nrg_est++ = 0;
1227 *nrg_est++ = 0;
1228 }
1229
1230 p_real++;
1231 }
1232 }
1233 }
1234
ixheaacd_enery_calc_persfb(WORD32 ** anal_buf_real,WORD32 ** anal_buf_imag,WORD32 num_sf_bands,WORD16 * freq_band_table,WORD32 start_pos,WORD32 next_pos,WORD32 max_qmf_subband_aac,WORD32 frame_exp,WORD16 * nrg_est,FLAG low_pow_flag,ia_sbr_tables_struct * ptr_sbr_tables)1235 VOID ixheaacd_enery_calc_persfb(WORD32 **anal_buf_real, WORD32 **anal_buf_imag,
1236 WORD32 num_sf_bands, WORD16 *freq_band_table,
1237 WORD32 start_pos, WORD32 next_pos,
1238 WORD32 max_qmf_subband_aac, WORD32 frame_exp,
1239 WORD16 *nrg_est, FLAG low_pow_flag,
1240 ia_sbr_tables_struct *ptr_sbr_tables) {
1241 WORD16 inv_width;
1242 WORD32 pre_shift_val;
1243 WORD32 shift;
1244 WORD32 sum_e;
1245 WORD16 sum_m;
1246
1247 WORD32 j, k, l;
1248 WORD32 li, ui;
1249 WORD32 accu_line;
1250 WORD32 accumulate;
1251 WORD32 extra_shift = 10;
1252
1253 inv_width = ptr_sbr_tables->env_calc_tables_ptr
1254 ->sbr_inv_int_table[(next_pos - start_pos)];
1255
1256 frame_exp = (frame_exp << 1);
1257
1258 if (low_pow_flag) extra_shift++;
1259
1260 for (j = 0; j < num_sf_bands; j++) {
1261 li = freq_band_table[j];
1262
1263 if ((li >= max_qmf_subband_aac)) {
1264 ui = freq_band_table[j + 1];
1265
1266 pre_shift_val = (*ixheaacd_ixheaacd_expsubbandsamples)(
1267 anal_buf_real, anal_buf_imag, li, ui, start_pos, next_pos,
1268 low_pow_flag);
1269
1270 pre_shift_val = (pre_shift_val - SHIFT_BEFORE_SQUARE);
1271
1272 accumulate = 0;
1273
1274 for (k = li; k < ui; k++) {
1275 WORD32 pre_shift1 = (16 - pre_shift_val);
1276 accu_line = 0L;
1277 pre_shift1 = min(pre_shift1, 31);
1278 {
1279 WORD32 *ptr = &anal_buf_real[start_pos][k];
1280 WORD32 inc = !low_pow_flag;
1281 for (l = (next_pos - start_pos) << inc; l != 0; l--) {
1282 WORD16 temp;
1283 temp = ixheaacd_extract16l(ixheaacd_shr32_dir(*ptr, pre_shift1));
1284 ptr += 64;
1285 accu_line = ixheaacd_mac16x16in32_sat(accu_line, temp, temp);
1286 }
1287 }
1288 accumulate =
1289 ixheaacd_add32_sat(accumulate, ixheaacd_shr32(accu_line, 9));
1290 }
1291
1292 shift = ixheaacd_pnorm32(accumulate);
1293
1294 sum_m = ixheaacd_extract16l(
1295 ixheaacd_shr32_dir_sat_limit(accumulate, (16 - shift)));
1296
1297 if (sum_m == 0) {
1298 sum_e = 0;
1299 } else {
1300 sum_m = ixheaacd_mult16_shl_sat(sum_m, inv_width);
1301
1302 sum_m = ixheaacd_mult16_shl_sat(
1303 sum_m,
1304 ptr_sbr_tables->env_calc_tables_ptr->sbr_inv_int_table[ui - li]);
1305
1306 sum_e = ((frame_exp + extra_shift) - shift);
1307
1308 sum_e = (sum_e - (pre_shift_val << 1));
1309 }
1310
1311 for (k = li; k < ui; k++) {
1312 *nrg_est++ = sum_m;
1313 *nrg_est++ = (WORD16)sum_e;
1314 }
1315 }
1316 }
1317 }
1318
ixheaacd_subbandgain_calc(WORD16 e_orig_mant_matrix,WORD16 tmp_noise_mant,WORD16 nrg_est_mant,WORD16 nrg_est_exp,WORD16 tmp_noise_exp,WORD16 nrg_ref_exp,FLAG sine_present_flag,FLAG sine_mapped_matrix,FLAG noise_absc_flag,WORD16 * ptr_nrg_gain_mant,WORD16 * ptr_noise_floor_mant,WORD16 * ptr_nrg_sine_m,ixheaacd_misc_tables * pstr_common_tables)1319 VOID ixheaacd_subbandgain_calc(WORD16 e_orig_mant_matrix, WORD16 tmp_noise_mant,
1320 WORD16 nrg_est_mant, WORD16 nrg_est_exp,
1321 WORD16 tmp_noise_exp, WORD16 nrg_ref_exp,
1322 FLAG sine_present_flag, FLAG sine_mapped_matrix,
1323 FLAG noise_absc_flag, WORD16 *ptr_nrg_gain_mant,
1324 WORD16 *ptr_noise_floor_mant,
1325 WORD16 *ptr_nrg_sine_m,
1326 ixheaacd_misc_tables *pstr_common_tables) {
1327 WORD16 var1_mant;
1328 WORD16 var1_exp;
1329 WORD16 var2_mant;
1330 WORD16 var2_exp;
1331 WORD16 var3_mant;
1332 WORD16 var3_exp;
1333 WORD32 temp;
1334
1335 if (nrg_est_mant == 0) {
1336 nrg_est_mant = 0x4000;
1337 nrg_est_exp = 1;
1338 }
1339
1340 var1_mant = ixheaacd_mult16_shl_sat(e_orig_mant_matrix, tmp_noise_mant);
1341 var1_exp = (nrg_ref_exp + tmp_noise_exp);
1342
1343 {
1344 WORD32 accu, exp_diff;
1345
1346 exp_diff = tmp_noise_exp - 1;
1347
1348 if (exp_diff >= 0) {
1349 accu = tmp_noise_mant + ixheaacd_shr32(0x4000, exp_diff);
1350 var2_exp = tmp_noise_exp;
1351 } else {
1352 exp_diff = -exp_diff;
1353 accu = ixheaacd_shr32((WORD32)tmp_noise_mant, exp_diff) + 0x4000;
1354 var2_exp = 1;
1355 }
1356 if (ixheaacd_abs32(accu) >= 0x8000) {
1357 accu = accu >> 1;
1358 var2_exp++;
1359 }
1360 var2_mant = (WORD16)(accu);
1361 }
1362
1363 temp = ixheaacd_fix_mant_div(var1_mant, var2_mant, ptr_noise_floor_mant,
1364 pstr_common_tables);
1365 *(ptr_noise_floor_mant + 1) = temp + (var1_exp - var2_exp) + 1;
1366
1367 if (sine_present_flag || !noise_absc_flag) {
1368 var3_mant = ixheaacd_mult16_shl_sat(var2_mant, nrg_est_mant);
1369 var3_exp = (var2_exp + nrg_est_exp);
1370 } else {
1371 var3_mant = nrg_est_mant;
1372 var3_exp = nrg_est_exp;
1373 }
1374
1375 if (sine_present_flag == 0) {
1376 var1_mant = e_orig_mant_matrix;
1377 var1_exp = nrg_ref_exp;
1378 }
1379
1380 temp = ixheaacd_fix_mant_div(var1_mant, var3_mant, ptr_nrg_gain_mant,
1381 pstr_common_tables);
1382 *(ptr_nrg_gain_mant + 1) = temp + (var1_exp - var3_exp) + 1;
1383
1384 if (sine_present_flag && sine_mapped_matrix) {
1385 temp = ixheaacd_fix_mant_div(e_orig_mant_matrix, var2_mant, ptr_nrg_sine_m,
1386 pstr_common_tables);
1387 *(ptr_nrg_sine_m + 1) = temp + (nrg_ref_exp - var2_exp) + 1;
1388 }
1389 }
1390
ixheaacd_avggain_calc(WORD16 * ptr_enrg_orig,WORD16 * nrg_est,WORD32 sub_band_start,WORD32 sub_band_end,WORD16 * ptr_enrg_orig_mant,WORD16 * ptr_sum_ref_exp,WORD16 * ptr_avg_gain_mant,WORD16 * ptr_avg_gain_exp,ixheaacd_misc_tables * pstr_common_tables,WORD32 flag)1391 VOID ixheaacd_avggain_calc(WORD16 *ptr_enrg_orig, WORD16 *nrg_est,
1392 WORD32 sub_band_start, WORD32 sub_band_end,
1393 WORD16 *ptr_enrg_orig_mant, WORD16 *ptr_sum_ref_exp,
1394 WORD16 *ptr_avg_gain_mant, WORD16 *ptr_avg_gain_exp,
1395 ixheaacd_misc_tables *pstr_common_tables,
1396 WORD32 flag) {
1397 WORD16 sum_orig_mant;
1398 WORD16 sum_orig_exp;
1399 WORD16 sum_est_mant;
1400 WORD16 sum_est_exp;
1401
1402 WORD32 accu_sum_orig_mant;
1403 WORD32 accu_sum_orig_exp;
1404 WORD32 accu_sum_est_mant;
1405 WORD32 accu_sum_est_exp;
1406
1407 WORD32 k, temp;
1408 WORD16 *ptr_enrg_orig_buf;
1409 WORD16 *ptr_enrg_est_buf;
1410
1411 {
1412 accu_sum_orig_mant = 0;
1413 accu_sum_orig_exp = 0;
1414
1415 accu_sum_est_mant = 0;
1416 accu_sum_est_exp = 0;
1417 }
1418
1419 ptr_enrg_orig_buf = &ptr_enrg_orig[sub_band_start << 1];
1420 ptr_enrg_est_buf = &nrg_est[sub_band_start << 1];
1421
1422 for (k = sub_band_end - sub_band_start; k != 0; k--) {
1423 WORD16 tmp_mant, tmp_e;
1424 WORD16 tmp2_m, tmp2_e;
1425
1426 tmp_mant = *ptr_enrg_orig_buf++;
1427 tmp_e = *ptr_enrg_orig_buf++;
1428 tmp2_m = *ptr_enrg_est_buf++;
1429 tmp2_e = *ptr_enrg_est_buf++;
1430 {
1431 WORD32 exp_diff;
1432 exp_diff = tmp_e - accu_sum_orig_exp;
1433 if (exp_diff >= 0) {
1434 accu_sum_orig_mant =
1435 tmp_mant + ixheaacd_shr32(accu_sum_orig_mant, exp_diff);
1436 accu_sum_orig_exp = tmp_e;
1437 } else {
1438 exp_diff = -exp_diff;
1439 accu_sum_orig_mant =
1440 ixheaacd_shr32(tmp_mant, exp_diff) + accu_sum_orig_mant;
1441 }
1442 }
1443 if (flag) {
1444 tmp_mant = (tmp_mant * tmp2_m) >> 16;
1445 tmp_e = (tmp_e + tmp2_e + 1);
1446
1447 } else {
1448 tmp_mant = tmp2_m;
1449 tmp_e = tmp2_e;
1450 }
1451
1452 {
1453 WORD32 exp_diff;
1454 exp_diff = tmp_e - accu_sum_est_exp;
1455 if (exp_diff >= 0) {
1456 accu_sum_est_mant =
1457 tmp_mant + ixheaacd_shr32(accu_sum_est_mant, exp_diff);
1458 accu_sum_est_exp = tmp_e;
1459 } else {
1460 exp_diff = -exp_diff;
1461 accu_sum_est_mant =
1462 ixheaacd_shr32(tmp_mant, exp_diff) + accu_sum_est_mant;
1463 }
1464 }
1465 }
1466 {
1467 WORD32 norm_val;
1468 norm_val = 16 - ixheaacd_pnorm32(accu_sum_orig_mant);
1469 if (norm_val > 0) {
1470 accu_sum_orig_mant >>= norm_val;
1471 accu_sum_orig_exp += norm_val;
1472 }
1473 norm_val = 16 - ixheaacd_pnorm32(accu_sum_est_mant);
1474 if (norm_val > 0) {
1475 accu_sum_est_mant >>= norm_val;
1476 accu_sum_est_exp += norm_val;
1477 }
1478 }
1479
1480 if (!flag) {
1481 sum_orig_mant = (WORD16)accu_sum_orig_mant;
1482 sum_orig_exp = (WORD16)accu_sum_orig_exp;
1483 sum_est_mant = (WORD16)accu_sum_est_mant;
1484 sum_est_exp = (WORD16)accu_sum_est_exp;
1485 } else {
1486 sum_est_mant = (WORD16)accu_sum_orig_mant;
1487 sum_est_exp = (WORD16)accu_sum_orig_exp;
1488 sum_orig_mant = (WORD16)accu_sum_est_mant;
1489 sum_orig_exp = (WORD16)accu_sum_est_exp;
1490 }
1491
1492 {
1493 temp = ixheaacd_fix_mant_div(sum_orig_mant, sum_est_mant, ptr_avg_gain_mant,
1494 pstr_common_tables);
1495 *ptr_avg_gain_exp = temp + (sum_orig_exp - sum_est_exp) + 1;
1496 *ptr_enrg_orig_mant = sum_orig_mant;
1497 *ptr_sum_ref_exp = sum_orig_exp;
1498 }
1499 }
1500
ixheaacd_harm_idx_zerotwolp_dec(WORD32 * ptr_real_buf,WORD16 * ptr_gain_buf,WORD32 scale_change,WORD16 * ptr_sine_level_buf,const WORD32 * ptr_rand_ph,WORD16 * noise_level_mant,WORD32 num_sub_bands,FLAG noise_absc_flag,WORD32 harm_index)1501 VOID ixheaacd_harm_idx_zerotwolp_dec(WORD32 *ptr_real_buf, WORD16 *ptr_gain_buf,
1502 WORD32 scale_change,
1503 WORD16 *ptr_sine_level_buf,
1504 const WORD32 *ptr_rand_ph,
1505 WORD16 *noise_level_mant,
1506 WORD32 num_sub_bands, FLAG noise_absc_flag,
1507 WORD32 harm_index) {
1508 WORD32 shift, k;
1509 WORD32 signal_real;
1510 WORD32 sine_level;
1511
1512 scale_change = scale_change - 1;
1513 if (!noise_absc_flag) {
1514 for (k = 0; k < num_sub_bands; k++) {
1515 signal_real = ixheaacd_mult32x16in32(*ptr_real_buf, *ptr_gain_buf++);
1516 shift = (*ptr_gain_buf++ - scale_change);
1517
1518 if (shift > 0)
1519 signal_real = (signal_real << shift);
1520 else
1521 signal_real = (signal_real >> -(shift));
1522
1523 sine_level = (ptr_sine_level_buf[2 * k] << 16);
1524
1525 if (sine_level == 0) {
1526 *ptr_real_buf++ = ixheaacd_mac16x16in32_shl_sat(
1527 signal_real, ixheaacd_extract16h(ptr_rand_ph[k]),
1528 noise_level_mant[2 * k]);
1529 } else if (harm_index == 0)
1530 *ptr_real_buf++ = ixheaacd_add32_sat(signal_real, sine_level);
1531 else
1532 *ptr_real_buf++ = ixheaacd_sub32_sat(signal_real, sine_level);
1533 }
1534 } else {
1535 for (k = 0; k < num_sub_bands; k++) {
1536 signal_real = ixheaacd_mult32x16in32(*ptr_real_buf, *ptr_gain_buf++);
1537 shift = (*ptr_gain_buf++ - scale_change);
1538
1539 if (shift > 0)
1540 signal_real = (signal_real << shift);
1541 else
1542 signal_real = (signal_real >> -(shift));
1543
1544 sine_level = (ptr_sine_level_buf[2 * k] << 16);
1545
1546 if (harm_index == 0)
1547 *ptr_real_buf++ = ixheaacd_add32_sat(signal_real, sine_level);
1548 else
1549 *ptr_real_buf++ = ixheaacd_sub32_sat(signal_real, sine_level);
1550 }
1551 }
1552 }
1553
ixheaacd_harm_idx_onethreelp(WORD32 * ptr_real_buf,WORD16 * ptr_gain_buf,WORD32 scale_change,WORD16 * ptr_sine_level_buf,const WORD32 * ptr_rand_ph,WORD16 * noise_level_mant,WORD32 num_sub_bands,FLAG noise_absc_flag,WORD32 freq_inv_flag,WORD32 noise_e,WORD32 sub_band_start)1554 VOID ixheaacd_harm_idx_onethreelp(
1555 WORD32 *ptr_real_buf, WORD16 *ptr_gain_buf, WORD32 scale_change,
1556 WORD16 *ptr_sine_level_buf, const WORD32 *ptr_rand_ph,
1557 WORD16 *noise_level_mant, WORD32 num_sub_bands, FLAG noise_absc_flag,
1558 WORD32 freq_inv_flag, WORD32 noise_e, WORD32 sub_band_start) {
1559 WORD32 shift, k = 0;
1560 WORD32 signal_real, temp_mult, temp_mult2;
1561 WORD16 sine_level, sine_level_prev, sine_level_next;
1562 WORD32 tone_count = 0;
1563 WORD16 tmp;
1564
1565 scale_change = scale_change - 1;
1566
1567 signal_real = ixheaacd_mult32x16in32(*ptr_real_buf, *ptr_gain_buf++);
1568 shift = (*ptr_gain_buf++ - scale_change);
1569
1570 if (shift > 0)
1571 signal_real = (signal_real << shift);
1572 else
1573 signal_real = (signal_real >> -(shift));
1574
1575 sine_level = ((ptr_sine_level_buf[2 * 0]));
1576
1577 if (num_sub_bands > 1) {
1578 sine_level_next = ((ptr_sine_level_buf[2 * 1]));
1579 } else {
1580 sine_level_next = 0;
1581 }
1582
1583 if (ptr_sine_level_buf[2 * 0] != 0) {
1584 tone_count++;
1585 } else {
1586 if (!noise_absc_flag) {
1587 signal_real = ixheaacd_mac16x16in32_shl_sat(
1588 signal_real, ixheaacd_extract16h(ptr_rand_ph[k]), *noise_level_mant);
1589 }
1590 }
1591
1592 noise_level_mant += 2;
1593 temp_mult2 = ixheaacd_mult32x16in32(FACTOR, sine_level_next);
1594 temp_mult = ixheaacd_mult32x16in32(FACTOR, sine_level);
1595 tmp = noise_e;
1596
1597 if (tmp > 0) {
1598 temp_mult = ixheaacd_shl32(temp_mult, tmp);
1599 } else {
1600 temp_mult = ixheaacd_shr32(temp_mult, -tmp);
1601 }
1602
1603 if (freq_inv_flag < 0) {
1604 *(ptr_real_buf - 1) = ixheaacd_add32_sat(*(ptr_real_buf - 1), temp_mult);
1605 signal_real = ixheaacd_sub32_sat(signal_real, temp_mult2);
1606 } else {
1607 *(ptr_real_buf - 1) = ixheaacd_sub32_sat(*(ptr_real_buf - 1), temp_mult);
1608 signal_real = ixheaacd_add32_sat(signal_real, temp_mult2);
1609 }
1610 *ptr_real_buf++ = signal_real;
1611
1612 num_sub_bands = num_sub_bands - 1;
1613 for (k = 1; k < num_sub_bands; k++) {
1614 WORD16 gain_m = *ptr_gain_buf++;
1615 WORD16 gain_e = *ptr_gain_buf++;
1616 WORD32 q_real = *ptr_real_buf;
1617
1618 signal_real = ixheaacd_mult32x16in32(q_real, gain_m);
1619
1620 if ((shift = (gain_e - scale_change)) >= 0)
1621 signal_real = (signal_real << shift);
1622 else
1623 signal_real = (signal_real >> -(shift));
1624
1625 sine_level_prev = sine_level;
1626 sine_level = sine_level_next;
1627 if (sine_level != 0) {
1628 tone_count++;
1629 }
1630 sine_level_next = (ptr_sine_level_buf[2 * (k + 1)]);
1631
1632 if ((!noise_absc_flag) && (sine_level == 0)) {
1633 signal_real = ixheaacd_mac16x16in32_shl_sat(
1634 signal_real, ixheaacd_extract16h(ptr_rand_ph[k]), *noise_level_mant);
1635 }
1636 noise_level_mant += 2;
1637
1638 if (tone_count <= 16) {
1639 WORD32 temp_mult;
1640 WORD32 add_sine = ixheaacd_mult32x16in32(
1641 FACTOR, ixheaacd_sub16(sine_level_prev, sine_level_next));
1642 temp_mult = add_sine * freq_inv_flag;
1643 signal_real = ixheaacd_add32_sat(signal_real, temp_mult);
1644 }
1645 *ptr_real_buf++ = signal_real;
1646 freq_inv_flag = -(freq_inv_flag);
1647 }
1648
1649 freq_inv_flag = (freq_inv_flag + 1) >> 1;
1650
1651 if (num_sub_bands > 0) {
1652 WORD32 temp_mult_sine;
1653 signal_real = ixheaacd_mult32x16in32(*ptr_real_buf, *ptr_gain_buf++);
1654 shift = (*ptr_gain_buf - scale_change);
1655
1656 if (shift > 0)
1657 signal_real = (signal_real << shift);
1658 else
1659 signal_real = (signal_real >> -(shift));
1660
1661 temp_mult_sine = ixheaacd_mult32x16in32(FACTOR, sine_level);
1662 sine_level = sine_level_next;
1663
1664 if (sine_level != 0) {
1665 tone_count++;
1666 } else {
1667 if (!noise_absc_flag) {
1668 signal_real = ixheaacd_mac16x16in32_shl_sat(
1669 signal_real, ixheaacd_extract16h(ptr_rand_ph[k]),
1670 *noise_level_mant);
1671 }
1672 }
1673
1674 if (tone_count <= 16) {
1675 temp_mult2 = ixheaacd_mult32x16in32(FACTOR, sine_level);
1676
1677 if (freq_inv_flag) {
1678 *ptr_real_buf++ = ixheaacd_add32_sat(signal_real, temp_mult_sine);
1679
1680 if ((k + sub_band_start) < 62) {
1681 *ptr_real_buf = ixheaacd_sub32_sat(*ptr_real_buf, temp_mult2);
1682 }
1683 } else {
1684 *ptr_real_buf++ = ixheaacd_sub32_sat(signal_real, temp_mult_sine);
1685
1686 if ((k + sub_band_start) < 62) {
1687 *ptr_real_buf = ixheaacd_add32_sat(*ptr_real_buf, temp_mult2);
1688 }
1689 }
1690 } else {
1691 *ptr_real_buf = signal_real;
1692 }
1693 }
1694 }
1695
ixheaacd_harm_idx_zerotwo(FLAG noise_absc_flag,WORD16 num_sub_bands,WORD32 * ptr_real_buf,WORD32 * ptr_imag,WORD16 * smoothed_gain,WORD16 * smoothed_noise,WORD32 factor,WORD16 * ptr_gain_buf,WORD16 scale_change,const WORD32 * ptr_rand_ph,WORD16 * ptr_sine_level_buf,WORD16 noise_e,WORD32 harm_index)1696 VOID ixheaacd_harm_idx_zerotwo(FLAG noise_absc_flag, WORD16 num_sub_bands,
1697 WORD32 *ptr_real_buf, WORD32 *ptr_imag,
1698 WORD16 *smoothed_gain, WORD16 *smoothed_noise,
1699 WORD32 factor, WORD16 *ptr_gain_buf,
1700 WORD16 scale_change, const WORD32 *ptr_rand_ph,
1701 WORD16 *ptr_sine_level_buf, WORD16 noise_e,
1702 WORD32 harm_index) {
1703 WORD32 k;
1704 WORD32 signal_real, sig_imag;
1705 WORD32 shift;
1706 WORD32 sine_level;
1707 ptr_gain_buf++;
1708
1709 for (k = 0; k < num_sub_bands; k++) {
1710 signal_real = ixheaacd_mult32x16in32(*ptr_real_buf, smoothed_gain[0]);
1711 sig_imag = ixheaacd_mult32x16in32(*ptr_imag, smoothed_gain[0]);
1712
1713 shift = ixheaacd_sub16(*ptr_gain_buf, scale_change);
1714 ptr_gain_buf += 2;
1715
1716 if (shift > 0) {
1717 signal_real = ixheaacd_shl32(signal_real, shift);
1718 sig_imag = ixheaacd_shl32(sig_imag, shift);
1719 } else {
1720 shift = -shift;
1721 signal_real = ixheaacd_shr32(signal_real, shift);
1722 sig_imag = ixheaacd_shr32(sig_imag, shift);
1723 }
1724
1725 ptr_rand_ph++;
1726
1727 if (*ptr_sine_level_buf != 0) {
1728 WORD32 tmp = ixheaacd_sub16(ptr_sine_level_buf[1], noise_e);
1729
1730 if (tmp > 0)
1731 sine_level = ixheaacd_shl32(ptr_sine_level_buf[0], tmp);
1732 else
1733 sine_level = ixheaacd_shr32(ptr_sine_level_buf[0], tmp);
1734
1735 if (harm_index == 0)
1736 *ptr_real_buf = ixheaacd_add32_sat(signal_real, sine_level);
1737 else
1738 *ptr_real_buf = ixheaacd_sub32_sat(signal_real, sine_level);
1739
1740 *ptr_imag = sig_imag;
1741 } else {
1742 if (!noise_absc_flag) {
1743 WORD32 random = *ptr_rand_ph;
1744 WORD16 noise = smoothed_noise[0];
1745
1746 *ptr_real_buf = ixheaacd_mac16x16in32_shl_sat(
1747 signal_real, ixheaacd_extract16h(random), noise);
1748 *ptr_imag = ixheaacd_mac16x16in32_shl_sat(
1749 sig_imag, ixheaacd_extract16l(random), noise);
1750 } else {
1751 *ptr_real_buf = signal_real;
1752 *ptr_imag = sig_imag;
1753 }
1754 }
1755
1756 smoothed_noise += factor;
1757 smoothed_gain += 2;
1758 ptr_sine_level_buf += 2;
1759 ptr_real_buf++;
1760 ptr_imag++;
1761 }
1762 }
1763
ixheaacd_harm_idx_onethree(FLAG noise_absc_flag,WORD16 num_sub_bands,WORD32 * ptr_real_buf,WORD32 * ptr_imag,WORD16 * smoothed_gain,WORD16 * smoothed_noise,WORD32 factor,WORD16 * ptr_gain_buf,WORD16 scale_change,const WORD32 * ptr_rand_ph,WORD16 * ptr_sine_level_buf,WORD16 noise_e,WORD32 freq_inv_flag,WORD32 harm_index)1764 VOID ixheaacd_harm_idx_onethree(FLAG noise_absc_flag, WORD16 num_sub_bands,
1765 WORD32 *ptr_real_buf, WORD32 *ptr_imag,
1766 WORD16 *smoothed_gain, WORD16 *smoothed_noise,
1767 WORD32 factor, WORD16 *ptr_gain_buf,
1768 WORD16 scale_change, const WORD32 *ptr_rand_ph,
1769 WORD16 *ptr_sine_level_buf, WORD16 noise_e,
1770 WORD32 freq_inv_flag, WORD32 harm_index) {
1771 WORD32 k;
1772 WORD32 signal_real, sig_imag;
1773 WORD32 shift;
1774 WORD32 sine_level;
1775
1776 ptr_gain_buf++;
1777
1778 if (harm_index == 1) freq_inv_flag = !freq_inv_flag;
1779
1780 for (k = 0; k < num_sub_bands; k++) {
1781 signal_real = ixheaacd_mult32x16in32(*ptr_real_buf, smoothed_gain[0]);
1782 sig_imag = ixheaacd_mult32x16in32(*ptr_imag, smoothed_gain[0]);
1783
1784 shift = ixheaacd_sub16(*ptr_gain_buf, scale_change);
1785 ptr_gain_buf += 2;
1786
1787 if (shift > 0) {
1788 signal_real = ixheaacd_shl32(signal_real, shift);
1789 sig_imag = ixheaacd_shl32(sig_imag, shift);
1790 } else {
1791 shift = -shift;
1792 signal_real = ixheaacd_shr32(signal_real, shift);
1793 sig_imag = ixheaacd_shr32(sig_imag, shift);
1794 }
1795
1796 ptr_rand_ph++;
1797
1798 if (*ptr_sine_level_buf != 0) {
1799 WORD32 tmp = ixheaacd_sub16(ptr_sine_level_buf[1], noise_e);
1800
1801 if (tmp > 0)
1802 sine_level = ixheaacd_shl32(ptr_sine_level_buf[0], tmp);
1803 else
1804 sine_level = ixheaacd_shr32(ptr_sine_level_buf[0], -tmp);
1805
1806 *ptr_real_buf = signal_real;
1807
1808 if (freq_inv_flag) {
1809 *ptr_imag = ixheaacd_add32_sat(sig_imag, sine_level);
1810 } else {
1811 *ptr_imag = ixheaacd_sub32_sat(sig_imag, sine_level);
1812 }
1813
1814 } else {
1815 if (!noise_absc_flag) {
1816 WORD32 random = *ptr_rand_ph;
1817 WORD16 noise = smoothed_noise[0];
1818
1819 *ptr_real_buf = ixheaacd_mac16x16in32_shl_sat(
1820 signal_real, ixheaacd_extract16h(random), noise);
1821 *ptr_imag = ixheaacd_mac16x16in32_shl_sat(
1822 sig_imag, ixheaacd_extract16l(random), noise);
1823 } else {
1824 *ptr_real_buf = signal_real;
1825 *ptr_imag = sig_imag;
1826 }
1827 }
1828
1829 freq_inv_flag = (!freq_inv_flag);
1830 smoothed_gain += 2;
1831 smoothed_noise += factor;
1832 ptr_sine_level_buf += 2;
1833 ptr_real_buf++;
1834 ptr_imag++;
1835 }
1836 }