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 <stdio.h>
21 #include <string.h>
22 #include "ixheaacd_sbr_common.h"
23 #include "ixheaacd_type_def.h"
24
25 #include "ixheaacd_constants.h"
26 #include "ixheaacd_basic_ops32.h"
27 #include "ixheaacd_basic_ops16.h"
28 #include "ixheaacd_basic_ops40.h"
29 #include "ixheaacd_basic_ops.h"
30
31 #include "ixheaacd_basic_op.h"
32 #include "ixheaacd_intrinsics.h"
33 #include "ixheaacd_common_rom.h"
34 #include "ixheaacd_basic_funcs.h"
35 #include "ixheaacd_sbr_scale.h"
36 #include "ixheaacd_sbrdecsettings.h"
37 #include "ixheaacd_lpp_tran.h"
38 #include "ixheaacd_bitbuffer.h"
39 #include "ixheaacd_defines.h"
40
41 #include "ixheaacd_pns.h"
42
43 #include "ixheaacd_aac_rom.h"
44 #include "ixheaacd_pulsedata.h"
45
46 #include "ixheaacd_drc_data_struct.h"
47
48 #include "ixheaacd_lt_predict.h"
49 #include "ixheaacd_cnst.h"
50 #include "ixheaacd_ec_defines.h"
51 #include "ixheaacd_ec_struct_def.h"
52 #include "ixheaacd_channelinfo.h"
53 #include "ixheaacd_drc_dec.h"
54
55 #include "ixheaacd_sbrdecoder.h"
56 #include "ixheaacd_sbr_scale.h"
57 #include "ixheaacd_lpp_tran.h"
58 #include "ixheaacd_env_extr_part.h"
59 #include "ixheaacd_sbr_rom.h"
60 #include "ixheaacd_hybrid.h"
61 #include "ixheaacd_ps_dec.h"
62 #include "ixheaacd_env_extr.h"
63
64 #include "ixheaacd_intrinsics.h"
65 #include "ixheaacd_basic_funcs.h"
66
67 #include "ixheaacd_qmf_dec.h"
68 #include "ixheaacd_env_calc.h"
69 #include "ixheaacd_sbr_const.h"
70
71 #include "ixheaacd_pvc_dec.h"
72 #include "ixheaacd_sbr_dec.h"
73 #include "ixheaacd_function_selector.h"
74
75 #include "ixheaacd_audioobjtypes.h"
76
77 #define LPC_SCALE_FACTOR 2
78
79 #define AUTO_CORR_LEN_1024 38
80 #define AUTO_CORR_LEN_960 36
81
82 #define SHIFT 5
83
ixheaacd_mac32x16hin32(WORD32 a,WORD32 b,WORD32 c)84 static PLATFORM_INLINE WORD32 ixheaacd_mac32x16hin32(WORD32 a, WORD32 b,
85 WORD32 c) {
86 WORD32 result;
87
88 result = a + ixheaacd_mult32x16hin32(b, c);
89
90 return (result);
91 }
92
ixheaacd_macn32x16hin32(WORD32 a,WORD32 b,WORD32 c)93 static PLATFORM_INLINE WORD32 ixheaacd_macn32x16hin32(WORD32 a, WORD32 b,
94 WORD32 c) {
95 WORD32 result;
96
97 result = a - ixheaacd_mult32x16hin32(b, c);
98
99 return (result);
100 }
101
ixheaacd_filterstep3(WORD16 a0r,WORD16 a0i,WORD16 a1r,WORD16 a1i,WORD32 start_indx,WORD32 stop_idx,WORD32 low_band,WORD32 high_band,WORD32 * qmf_buffer)102 VOID ixheaacd_filterstep3(WORD16 a0r, WORD16 a0i, WORD16 a1r, WORD16 a1i,
103 WORD32 start_indx, WORD32 stop_idx, WORD32 low_band,
104 WORD32 high_band, WORD32 *qmf_buffer) {
105 WORD32 i;
106 WORD32 prev1r, prev1i;
107 WORD32 prev2r, prev2i;
108 WORD16 coef1r = (a0r);
109 WORD16 coef1i = (a0i);
110 WORD16 coef2r = (a1r);
111 WORD16 coef2i = (a1i);
112 WORD32 *p_src, *p_dst;
113 WORD32 qmf_real, qmf_imag;
114
115 WORD32 curr, curi;
116 p_src = qmf_buffer + low_band + ((start_indx) << 7);
117 prev2r = *p_src;
118 p_src += 64;
119
120 prev2i = *p_src;
121 p_src += 64;
122
123 prev1r = *p_src;
124 p_src += 64;
125
126 prev1i = *p_src;
127 p_src += 64;
128
129 p_dst = qmf_buffer + high_band + ((start_indx + 2) << 7);
130
131 for (i = stop_idx - start_indx; i != 0; i--) {
132 WORD32 accu;
133
134 curr = *p_src;
135 p_src += 64;
136
137 curi = *p_src;
138 p_src += 64;
139
140 qmf_real = (curr >> LPC_SCALE_FACTOR);
141 qmf_imag = (curi >> LPC_SCALE_FACTOR);
142
143 accu = ixheaacd_sub32(
144 ixheaacd_add32(ixheaacd_sub32(ixheaacd_mult32x16in32(prev1r, coef1r),
145 ixheaacd_mult32x16in32(prev1i, coef1i)),
146 ixheaacd_mult32x16in32(prev2r, coef2r)),
147 ixheaacd_mult32x16in32(prev2i, coef2i));
148
149 *p_dst = ixheaacd_add32(qmf_real, (accu << 1));
150 p_dst += 64;
151
152 accu = ixheaacd_add32(
153 ixheaacd_add32_sat(
154 ixheaacd_add32_sat(ixheaacd_mult32x16in32(prev1r, coef1i),
155 ixheaacd_mult32x16in32(prev1i, coef1r)),
156 ixheaacd_mult32x16in32(prev2r, coef2i)),
157 ixheaacd_mult32x16in32(prev2i, coef2r));
158
159 *p_dst = ixheaacd_add32(qmf_imag, (accu << 1));
160 p_dst += 64;
161
162 prev2r = prev1r;
163 prev1r = curr;
164 prev2i = prev1i;
165 prev1i = curi;
166 }
167 }
168
ixheaacd_covariance_matrix_calc_dec_960(WORD32 * sub_sign_xlow,ia_lpp_trans_cov_matrix * cov_matrix,WORD32 count,WORD32 len)169 VOID ixheaacd_covariance_matrix_calc_dec_960(
170 WORD32 *sub_sign_xlow, ia_lpp_trans_cov_matrix *cov_matrix,
171 WORD32 count, WORD32 len) {
172 WORD32 j, k;
173 WORD32 ixheaacd_drc_offset = 2;
174 WORD32 factor;
175 WORD32 max_val, q_factor;
176 WORD32 temp1, temp2, temp3, temp4;
177 WORD32 *temp_buf_ptr = sub_sign_xlow;
178
179 temp3 = 0;
180 for (k = count; k > 0; k--) {
181 WORD32 t_phi_01 = 0, t_phi_02 = 0, t_phi_11 = 0;
182 WORD32 t_phi_12 = 0, t_phi_22 = 0;
183
184 factor = -3;
185 j = ixheaacd_drc_offset;
186 sub_sign_xlow = temp_buf_ptr;
187
188 temp1 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
189 sub_sign_xlow += 64;
190
191 temp2 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
192 sub_sign_xlow += 64;
193
194 for (; (j = j + 3) <= ixheaacd_drc_offset + len;) {
195 temp3 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
196 sub_sign_xlow += 64;
197
198 t_phi_01 += ixheaacd_mult32x16hin32(temp3, temp2);
199 t_phi_02 += ixheaacd_mult32x16hin32(temp3, temp1);
200 t_phi_11 += ixheaacd_mult32x16hin32(temp2, temp2);
201
202 temp1 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
203 sub_sign_xlow += 64;
204
205 t_phi_01 += ixheaacd_mult32x16hin32(temp1, temp3);
206 t_phi_02 += ixheaacd_mult32x16hin32(temp1, temp2);
207 t_phi_11 += ixheaacd_mult32x16hin32(temp3, temp3);
208
209 temp2 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
210 sub_sign_xlow += 64;
211
212 t_phi_01 += ixheaacd_mult32x16hin32(temp2, temp1);
213 t_phi_02 += ixheaacd_mult32x16hin32(temp2, temp3);
214 t_phi_11 += ixheaacd_mult32x16hin32(temp1, temp1);
215 }
216
217 if (AUTO_CORR_LEN_1024 == len) {
218 temp3 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
219 sub_sign_xlow += 64;
220
221 t_phi_01 += ixheaacd_mult32x16hin32(temp3, temp2);
222 t_phi_02 += ixheaacd_mult32x16hin32(temp3, temp1);
223 t_phi_11 += ixheaacd_mult32x16hin32(temp2, temp2);
224
225 temp1 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
226 sub_sign_xlow += 64;
227
228 t_phi_01 += ixheaacd_mult32x16hin32(temp1, temp3);
229 t_phi_02 += ixheaacd_mult32x16hin32(temp1, temp2);
230 t_phi_11 += ixheaacd_mult32x16hin32(temp3, temp3);
231 }
232
233 temp2 = ixheaacd_shl32_dir(*temp_buf_ptr, factor);
234 temp4 = ixheaacd_shl32_dir(*(temp_buf_ptr + 64), factor);
235
236 if (AUTO_CORR_LEN_960 == len) {
237 temp3 = ixheaacd_shl32_dir(sub_sign_xlow[-128], factor);
238 temp1 = ixheaacd_shl32_dir(sub_sign_xlow[-64], factor);
239 }
240
241 t_phi_12 = (t_phi_01 - ixheaacd_mult32x16hin32(temp1, temp3) +
242 ixheaacd_mult32x16hin32(temp4, temp2));
243
244 t_phi_22 = (t_phi_11 - ixheaacd_mult32x16hin32(temp3, temp3) +
245 ixheaacd_mult32x16hin32(temp2, temp2));
246
247 max_val = ixheaacd_abs32_nrm(t_phi_01);
248 max_val = max_val | ixheaacd_abs32_nrm(t_phi_02);
249 max_val = max_val | ixheaacd_abs32_nrm(t_phi_12);
250 max_val = max_val | (t_phi_11);
251 max_val = max_val | (t_phi_22);
252
253 q_factor = ixheaacd_pnorm32(max_val);
254
255 cov_matrix->phi_11 = (t_phi_11 << q_factor);
256 cov_matrix->phi_22 = (t_phi_22 << q_factor);
257 cov_matrix->phi_01 = (t_phi_01 << q_factor);
258 cov_matrix->phi_02 = (t_phi_02 << q_factor);
259 cov_matrix->phi_12 = (t_phi_12 << q_factor);
260
261 cov_matrix->d = ixheaacd_sub32_sat(
262 ixheaacd_mult32(cov_matrix->phi_22, cov_matrix->phi_11),
263 ixheaacd_mult32(cov_matrix->phi_12, cov_matrix->phi_12));
264
265 cov_matrix++;
266 temp_buf_ptr++;
267 }
268 return;
269 }
270
ixheaacd_covariance_matrix_calc_dec(WORD32 * sub_sign_xlow,ia_lpp_trans_cov_matrix * cov_matrix,WORD32 count,WORD32 len)271 VOID ixheaacd_covariance_matrix_calc_dec(
272 WORD32 *sub_sign_xlow, ia_lpp_trans_cov_matrix *cov_matrix,
273 WORD32 count, WORD32 len) {
274 WORD32 j, k;
275 WORD32 ixheaacd_drc_offset = 2;
276 WORD32 factor;
277 WORD32 max_val, q_factor;
278 WORD32 temp1, temp2, temp3, temp4;
279 WORD32 *temp_buf_ptr = sub_sign_xlow;
280
281 for (k = count; k > 0; k--) {
282 WORD32 t_phi_01 = 0, t_phi_02 = 0, t_phi_11 = 0;
283 WORD32 t_phi_12 = 0, t_phi_22 = 0;
284
285 factor = -3;
286 j = ixheaacd_drc_offset;
287 sub_sign_xlow = temp_buf_ptr;
288
289 temp1 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
290 sub_sign_xlow += 64;
291
292 temp2 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
293 sub_sign_xlow += 64;
294
295 for (; (j = j + 3) <= ixheaacd_drc_offset + len;) {
296 temp3 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
297 sub_sign_xlow += 64;
298
299 t_phi_01 += ixheaacd_mult32x16hin32(temp3, temp2);
300 t_phi_02 += ixheaacd_mult32x16hin32(temp3, temp1);
301 t_phi_11 += ixheaacd_mult32x16hin32(temp2, temp2);
302
303 temp1 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
304 sub_sign_xlow += 64;
305
306 t_phi_01 += ixheaacd_mult32x16hin32(temp1, temp3);
307 t_phi_02 += ixheaacd_mult32x16hin32(temp1, temp2);
308 t_phi_11 += ixheaacd_mult32x16hin32(temp3, temp3);
309
310 temp2 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
311 sub_sign_xlow += 64;
312
313 t_phi_01 += ixheaacd_mult32x16hin32(temp2, temp1);
314 t_phi_02 += ixheaacd_mult32x16hin32(temp2, temp3);
315 t_phi_11 += ixheaacd_mult32x16hin32(temp1, temp1);
316 }
317
318 if (AUTO_CORR_LEN_960 != len) {
319 temp3 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
320 sub_sign_xlow += 64;
321
322 t_phi_01 += ixheaacd_mult32x16hin32(temp3, temp2);
323 t_phi_02 += ixheaacd_mult32x16hin32(temp3, temp1);
324 t_phi_11 += ixheaacd_mult32x16hin32(temp2, temp2);
325
326 temp1 = ixheaacd_shl32_dir(*sub_sign_xlow, factor);
327 sub_sign_xlow += 64;
328
329 t_phi_01 += ixheaacd_mult32x16hin32(temp1, temp3);
330 t_phi_02 += ixheaacd_mult32x16hin32(temp1, temp2);
331 t_phi_11 += ixheaacd_mult32x16hin32(temp3, temp3);
332 }
333 if (AUTO_CORR_LEN_960 == len) {
334 temp3 = ixheaacd_shl32_dir(sub_sign_xlow[-128], factor);
335
336 temp3 = ixheaacd_shl32_dir(sub_sign_xlow[-64], factor);
337
338 }
339
340 temp2 = ixheaacd_shl32_dir(*temp_buf_ptr, factor);
341 temp4 = ixheaacd_shl32_dir(*(temp_buf_ptr + 64), factor);
342
343 t_phi_12 = (t_phi_01 - ixheaacd_mult32x16hin32(temp1, temp3) +
344 ixheaacd_mult32x16hin32(temp4, temp2));
345
346 t_phi_22 = (t_phi_11 - ixheaacd_mult32x16hin32(temp3, temp3) +
347 ixheaacd_mult32x16hin32(temp2, temp2));
348
349 max_val = ixheaacd_abs32_nrm(t_phi_01);
350 max_val = max_val | ixheaacd_abs32_nrm(t_phi_02);
351 max_val = max_val | ixheaacd_abs32_nrm(t_phi_12);
352 max_val = max_val | (t_phi_11);
353 max_val = max_val | (t_phi_22);
354
355 q_factor = ixheaacd_pnorm32(max_val);
356
357 cov_matrix->phi_11 = (t_phi_11 << q_factor);
358 cov_matrix->phi_22 = (t_phi_22 << q_factor);
359 cov_matrix->phi_01 = (t_phi_01 << q_factor);
360 cov_matrix->phi_02 = (t_phi_02 << q_factor);
361 cov_matrix->phi_12 = (t_phi_12 << q_factor);
362
363 cov_matrix->d = ixheaacd_sub32_sat(
364 ixheaacd_mult32(cov_matrix->phi_22, cov_matrix->phi_11),
365 ixheaacd_mult32(cov_matrix->phi_12, cov_matrix->phi_12));
366
367 cov_matrix++;
368 temp_buf_ptr++;
369 }
370
371 return;
372 }
373
ixheaacd_covariance_matrix_calc_2_dec(ia_lpp_trans_cov_matrix * cov_matrix,WORD32 * real_buffer,WORD32 num_bands,WORD16 slots)374 VOID ixheaacd_covariance_matrix_calc_2_dec(
375 ia_lpp_trans_cov_matrix *cov_matrix,
376
377 WORD32 *real_buffer, WORD32 num_bands, WORD16 slots) {
378 WORD32 k;
379 WORD32 *img_buffer;
380 WORD32 *ptr_real = real_buffer;
381 ia_lpp_trans_cov_matrix *pac_arr = cov_matrix;
382
383 for (k = 0; k < num_bands; k++) {
384 WORD32 t_phi_11 = 0, t_phi_01 = 0, t_phi_01_i = 0;
385 WORD32 prev_real, prev_imag, curr_real, curr_imag;
386
387 real_buffer = ptr_real;
388 img_buffer = real_buffer + 64;
389 cov_matrix = pac_arr;
390
391 prev_real = real_buffer[-128];
392 prev_imag = img_buffer[-128];
393
394 curr_real = real_buffer[0];
395 curr_imag = img_buffer[0];
396
397 curr_real = ixheaacd_shr32(curr_real, 3);
398 curr_imag = ixheaacd_shr32(curr_imag, 3);
399 prev_real = ixheaacd_shr32(prev_real, 3);
400 prev_imag = ixheaacd_shr32(prev_imag, 3);
401
402 t_phi_01 = ixheaacd_mult32x16hin32(curr_real, prev_real);
403 t_phi_01 = ixheaacd_mac32x16hin32(t_phi_01, curr_imag, prev_imag);
404
405 t_phi_01_i = ixheaacd_mult32x16hin32(curr_imag, prev_real);
406 t_phi_01_i = ixheaacd_macn32x16hin32(t_phi_01_i, curr_real, prev_imag);
407
408 t_phi_11 = ixheaacd_mult32x16hin32(prev_real, prev_real);
409 t_phi_11 = ixheaacd_mac32x16hin32(t_phi_11, prev_imag, prev_imag);
410
411 {
412 WORD n;
413 WORD32 *real1 = &real_buffer[128];
414 WORD32 *imag1 = &img_buffer[128];
415
416 prev_real = curr_real;
417 prev_imag = curr_imag;
418
419 for (n = ((slots - 2) >> 1); n; n--) {
420 curr_real = *real1;
421 real1 += 128;
422 curr_imag = *imag1;
423 imag1 += 128;
424
425 curr_real = ixheaacd_shr32(curr_real, 3);
426 curr_imag = ixheaacd_shr32(curr_imag, 3);
427
428 t_phi_01 = ixheaacd_mac32x16hin32(t_phi_01, curr_real, prev_real);
429 t_phi_01 = ixheaacd_mac32x16hin32(t_phi_01, curr_imag, prev_imag);
430
431 t_phi_01_i = ixheaacd_mac32x16hin32(t_phi_01_i, curr_imag, prev_real);
432 t_phi_01_i = ixheaacd_macn32x16hin32(t_phi_01_i, curr_real, prev_imag);
433
434 t_phi_11 = ixheaacd_mac32x16hin32(t_phi_11, prev_real, prev_real);
435 t_phi_11 = ixheaacd_mac32x16hin32(t_phi_11, prev_imag, prev_imag);
436
437 prev_real = *real1;
438 real1 += 128;
439 prev_imag = *imag1;
440 imag1 += 128;
441
442 prev_real = ixheaacd_shr32(prev_real, 3);
443 prev_imag = ixheaacd_shr32(prev_imag, 3);
444
445 t_phi_01 = ixheaacd_mac32x16hin32(t_phi_01, prev_real, curr_real);
446 t_phi_01 = ixheaacd_mac32x16hin32(t_phi_01, prev_imag, curr_imag);
447
448 t_phi_01_i = ixheaacd_mac32x16hin32(t_phi_01_i, prev_imag, curr_real);
449 t_phi_01_i = ixheaacd_macn32x16hin32(t_phi_01_i, prev_real, curr_imag);
450
451 t_phi_11 = ixheaacd_mac32x16hin32(t_phi_11, curr_real, curr_real);
452 t_phi_11 = ixheaacd_mac32x16hin32(t_phi_11, curr_imag, curr_imag);
453 }
454
455 if (slots & 0x01) {
456 curr_real = *real1;
457 curr_imag = *imag1;
458
459 curr_real = ixheaacd_shr32(curr_real, 3);
460 curr_imag = ixheaacd_shr32(curr_imag, 3);
461
462 t_phi_01 = ixheaacd_mac32x16hin32(t_phi_01, curr_real, prev_real);
463 t_phi_01 = ixheaacd_mac32x16hin32(t_phi_01, curr_imag, prev_imag);
464
465 t_phi_01_i = ixheaacd_mac32x16hin32(t_phi_01_i, curr_imag, prev_real);
466 t_phi_01_i = ixheaacd_macn32x16hin32(t_phi_01_i, curr_real, prev_imag);
467
468 t_phi_11 = ixheaacd_mac32x16hin32(t_phi_11, prev_real, prev_real);
469 t_phi_11 = ixheaacd_mac32x16hin32(t_phi_11, prev_imag, prev_imag);
470 }
471 }
472
473 {
474 WORD32 t_phi_22 = t_phi_11;
475 WORD32 curr_real = real_buffer[-2 * 128];
476 WORD32 curr_imag = img_buffer[-2 * 128];
477
478 curr_real = ixheaacd_shr32(curr_real, 3);
479 curr_imag = ixheaacd_shr32(curr_imag, 3);
480
481 t_phi_22 = ixheaacd_mac32x16hin32(t_phi_22, curr_real, curr_real);
482 t_phi_22 = ixheaacd_mac32x16hin32(t_phi_22, curr_imag, curr_imag);
483
484 curr_real = real_buffer[(slots - 2) * 128];
485 curr_imag = img_buffer[(slots - 2) * 128];
486
487 curr_real = ixheaacd_shr32(curr_real, 3);
488 curr_imag = ixheaacd_shr32(curr_imag, 3);
489
490 t_phi_11 = ixheaacd_mac32x16hin32(t_phi_11, curr_real, curr_real);
491 t_phi_11 = ixheaacd_mac32x16hin32(t_phi_11, curr_imag, curr_imag);
492
493 cov_matrix->phi_11 = t_phi_11;
494 cov_matrix->phi_22 = t_phi_22;
495 }
496
497 {
498 WORD32 t_phi_12 = t_phi_01;
499
500 t_phi_12 = ixheaacd_mac32x16hin32(t_phi_12, real_buffer[-128] >> 3,
501 real_buffer[-2 * 128] >> 3);
502 t_phi_12 = ixheaacd_mac32x16hin32(t_phi_12, img_buffer[-128] >> 3,
503 img_buffer[-2 * 128] >> 3);
504 t_phi_01 =
505 ixheaacd_mac32x16hin32(t_phi_01, real_buffer[(slots - 1) * 128] >> 3,
506 real_buffer[(slots - 2) * 128] >> 3);
507 t_phi_01 =
508 ixheaacd_mac32x16hin32(t_phi_01, img_buffer[(slots - 1) * 128] >> 3,
509 img_buffer[(slots - 2) * 128] >> 3);
510
511 cov_matrix->phi_01 = t_phi_01;
512 cov_matrix->phi_12 = t_phi_12;
513 }
514
515 {
516 WORD32 t_phi_12_i = t_phi_01_i;
517
518 t_phi_12_i = ixheaacd_mac32x16hin32(t_phi_12_i, img_buffer[-128] >> 3,
519 real_buffer[-2 * 128] >> 3);
520 t_phi_12_i = ixheaacd_macn32x16hin32(t_phi_12_i, real_buffer[-128] >> 3,
521 img_buffer[-2 * 128] >> 3);
522 t_phi_01_i =
523 ixheaacd_mac32x16hin32(t_phi_01_i, img_buffer[(slots - 1) * 128] >> 3,
524 real_buffer[(slots - 2) * 128] >> 3);
525 t_phi_01_i = ixheaacd_macn32x16hin32(t_phi_01_i,
526 real_buffer[(slots - 1) * 128] >> 3,
527 img_buffer[(slots - 2) * 128] >> 3);
528
529 cov_matrix->phi_01_im = t_phi_01_i;
530 cov_matrix->phi_12_im = t_phi_12_i;
531 }
532
533 {
534 WORD16 n, len_by_4, p;
535 WORD32 t_phi_02 = 0x00, t_phi_02_i = 0x00;
536
537 len_by_4 = (slots >> 2);
538 p = 0;
539 for (n = 0; n < len_by_4; n++) {
540 WORD32 real1, real2, imag1, imag2;
541 real1 = real_buffer[p * 128];
542 real2 = real_buffer[(p - 2) * 128];
543 imag1 = img_buffer[p * 128];
544 imag2 = img_buffer[(p - 2) * 128];
545
546 real1 = ixheaacd_shr32(real1, 3);
547 real2 = ixheaacd_shr32(real2, 3);
548 imag1 = ixheaacd_shr32(imag1, 3);
549 imag2 = ixheaacd_shr32(imag2, 3);
550
551 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, real1, real2);
552 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, imag1, imag2);
553 t_phi_02_i = ixheaacd_mac32x16hin32(t_phi_02_i, imag1, real2);
554 t_phi_02_i = ixheaacd_macn32x16hin32(t_phi_02_i, real1, imag2);
555
556 real1 = real_buffer[(p + 1) * 128];
557 real2 = real_buffer[(p - 1) * 128];
558 imag1 = img_buffer[(p + 1) * 128];
559 imag2 = img_buffer[(p - 1) * 128];
560
561 real1 = ixheaacd_shr32(real1, 3);
562 real2 = ixheaacd_shr32(real2, 3);
563 imag1 = ixheaacd_shr32(imag1, 3);
564 imag2 = ixheaacd_shr32(imag2, 3);
565
566 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, real1, real2);
567 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, imag1, imag2);
568 t_phi_02_i = ixheaacd_mac32x16hin32(t_phi_02_i, imag1, real2);
569 t_phi_02_i = ixheaacd_macn32x16hin32(t_phi_02_i, real1, imag2);
570
571 real1 = real_buffer[(p + 2) * 128];
572 real2 = real_buffer[p * 128];
573 imag1 = img_buffer[(p + 2) * 128];
574 imag2 = img_buffer[p * 128];
575
576 real1 = ixheaacd_shr32(real1, 3);
577 real2 = ixheaacd_shr32(real2, 3);
578 imag1 = ixheaacd_shr32(imag1, 3);
579 imag2 = ixheaacd_shr32(imag2, 3);
580
581 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, real1, real2);
582 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, imag1, imag2);
583 t_phi_02_i = ixheaacd_mac32x16hin32(t_phi_02_i, imag1, real2);
584 t_phi_02_i = ixheaacd_macn32x16hin32(t_phi_02_i, real1, imag2);
585
586 real1 = real_buffer[(p + 3) * 128];
587 real2 = real_buffer[(p + 1) * 128];
588 imag1 = img_buffer[(p + 3) * 128];
589 imag2 = img_buffer[(p + 1) * 128];
590
591 real1 = ixheaacd_shr32(real1, 3);
592 real2 = ixheaacd_shr32(real2, 3);
593 imag1 = ixheaacd_shr32(imag1, 3);
594 imag2 = ixheaacd_shr32(imag2, 3);
595
596 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, real1, real2);
597 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, imag1, imag2);
598 t_phi_02_i = ixheaacd_mac32x16hin32(t_phi_02_i, imag1, real2);
599 t_phi_02_i = ixheaacd_macn32x16hin32(t_phi_02_i, real1, imag2);
600 p += 4;
601 }
602 n = ixheaacd_shl16(len_by_4, 2);
603 for (; n < slots; n++) {
604 WORD32 real1, real2, imag1, imag2;
605 real1 = real_buffer[(n * 128)];
606 real2 = real_buffer[(n - 2) * 128];
607 imag1 = img_buffer[n * 128];
608 imag2 = img_buffer[(n - 2) * 128];
609
610 real1 = ixheaacd_shr32(real1, 3);
611 real2 = ixheaacd_shr32(real2, 3);
612 imag1 = ixheaacd_shr32(imag1, 3);
613 imag2 = ixheaacd_shr32(imag2, 3);
614
615 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, real1, real2);
616 t_phi_02 = ixheaacd_mac32x16hin32(t_phi_02, imag1, imag2);
617 t_phi_02_i = ixheaacd_mac32x16hin32(t_phi_02_i, imag1, real2);
618 t_phi_02_i = ixheaacd_macn32x16hin32(t_phi_02_i, real1, imag2);
619 }
620
621 cov_matrix->phi_02 = t_phi_02;
622 cov_matrix->phi_02_im = t_phi_02_i;
623 }
624 ptr_real++;
625 pac_arr++;
626 }
627 }
628
ixheaacd_filt_step3_lp(WORD len,WORD32 coef1,WORD32 coef2,WORD32 * pqmf_real_low,WORD32 * pqmf_real_high)629 static PLATFORM_INLINE VOID ixheaacd_filt_step3_lp(WORD len, WORD32 coef1,
630 WORD32 coef2,
631 WORD32 *pqmf_real_low,
632 WORD32 *pqmf_real_high) {
633 WORD32 prev1;
634 WORD32 prev2;
635 WORD32 i;
636
637 prev2 = *pqmf_real_low;
638 pqmf_real_low += 64;
639
640 prev1 = *pqmf_real_low;
641 pqmf_real_low += 64;
642
643 for (i = len; i >= 0; i -= 2) {
644 WORD32 curr = *pqmf_real_low;
645 WORD32 temp = ixheaacd_mult32x16hin32(prev2, coef2);
646 pqmf_real_low += 64;
647
648 *pqmf_real_high = ixheaacd_add32_sat((curr >> LPC_SCALE_FACTOR),
649 ((ixheaacd_mac32x16hin32(temp, prev1, coef1)) << 1));
650 pqmf_real_high += 64;
651
652 prev2 = *pqmf_real_low;
653 temp = ixheaacd_mult32x16hin32(prev1, coef2);
654 pqmf_real_low += 64;
655
656 *pqmf_real_high = ixheaacd_add32_sat((prev2 >> LPC_SCALE_FACTOR),
657 ((ixheaacd_mac32x16hin32(temp, curr, coef1)) << 1));
658 pqmf_real_high += 64;
659
660 prev1 = prev2;
661 prev2 = curr;
662 }
663 }
664
ixheaacd_filter1_lp(ia_sbr_hf_generator_struct * hf_generator,ia_lpp_trans_cov_matrix * cov_matrix_seq,WORD32 * bw_array,WORD16 * degree_alias,WORD32 start_idx,WORD32 stop_idx,WORD32 max_qmf_subband,WORD32 start_patch,WORD32 stop_patch,WORD32 * sub_sig_x)665 VOID ixheaacd_filter1_lp(ia_sbr_hf_generator_struct *hf_generator,
666 ia_lpp_trans_cov_matrix *cov_matrix_seq,
667 WORD32 *bw_array, WORD16 *degree_alias,
668 WORD32 start_idx, WORD32 stop_idx,
669 WORD32 max_qmf_subband, WORD32 start_patch,
670 WORD32 stop_patch, WORD32 *sub_sig_x) {
671 WORD16 k1, k1_below = 0, k1_below2 = 0;
672 WORD32 i;
673 WORD16 alpha_real[LPC_ORDER];
674 WORD32 low_band, high_band;
675 WORD32 patch;
676 WORD16 bw = 0;
677 WORD32 a0r, a1r;
678
679 WORD num_patches = hf_generator->pstr_settings->num_patches;
680 ia_patch_param_struct *patch_param =
681 hf_generator->pstr_settings->str_patch_param;
682 WORD32 bw_index[MAX_NUM_PATCHES];
683
684 memset(bw_index, 0, sizeof(WORD32) * num_patches);
685
686 for (low_band = start_patch; low_band < stop_patch; low_band++) {
687 ia_lpp_trans_cov_matrix *p_cov_matrix = &cov_matrix_seq[low_band];
688
689 alpha_real[1] = 0;
690 alpha_real[0] = 0;
691
692 if (p_cov_matrix->d != 0) {
693 WORD32 tmp_r, temp_real, modulus_d;
694 WORD16 inverse_d;
695 WORD32 norm_d;
696
697 norm_d = ixheaacd_norm32(p_cov_matrix->d);
698
699 inverse_d =
700 (WORD16)(*ixheaacd_fix_div)(0x40000000, (p_cov_matrix->d << norm_d));
701 modulus_d = ixheaacd_abs32(p_cov_matrix->d);
702
703 tmp_r =
704 (ixheaacd_sub32_sat(
705 ixheaacd_mult32(p_cov_matrix->phi_01, p_cov_matrix->phi_12),
706 ixheaacd_mult32(p_cov_matrix->phi_02, p_cov_matrix->phi_11)) >>
707 LPC_SCALE_FACTOR);
708 temp_real = ixheaacd_abs32(tmp_r);
709
710 if (temp_real < modulus_d) {
711 alpha_real[1] = (WORD16)(
712 (ixheaacd_mult32x16in32_shl_sat(tmp_r, inverse_d) << norm_d) >> 15);
713 }
714
715 tmp_r =
716 (ixheaacd_sub32_sat(
717 ixheaacd_mult32(p_cov_matrix->phi_02, p_cov_matrix->phi_12),
718 ixheaacd_mult32(p_cov_matrix->phi_01, p_cov_matrix->phi_22)) >>
719 LPC_SCALE_FACTOR);
720 temp_real = ixheaacd_abs32(tmp_r);
721
722 if (temp_real < modulus_d) {
723 alpha_real[0] = (WORD16)(
724 (ixheaacd_mult32x16in32_shl_sat(tmp_r, inverse_d) << norm_d) >> 15);
725 }
726 }
727
728 if (p_cov_matrix->phi_11 == 0) {
729 k1 = 0;
730 } else {
731 if (ixheaacd_abs32_sat(p_cov_matrix->phi_01) >= p_cov_matrix->phi_11) {
732 if (p_cov_matrix->phi_01 < 0) {
733 k1 = 0x7fff;
734 } else {
735 k1 = (WORD16)-0x8000;
736 }
737 } else {
738 k1 = -((WORD16)(
739 (*ixheaacd_fix_div)(p_cov_matrix->phi_01, p_cov_matrix->phi_11)));
740 }
741 }
742
743 if (low_band > 1) {
744 WORD16 deg = ixheaacd_sub16_sat(
745 0x7fff, ixheaacd_mult16_shl_sat(k1_below, k1_below));
746 degree_alias[low_band] = 0;
747
748 if (((low_band & 1) == 0) && (k1 < 0)) {
749 if (k1_below < 0) {
750 degree_alias[low_band] = 0x7fff;
751
752 if (k1_below2 > 0) {
753 degree_alias[low_band - 1] = deg;
754 }
755 } else {
756 if (k1_below2 > 0) {
757 degree_alias[low_band] = deg;
758 }
759 }
760 }
761
762 if (((low_band & 1) != 0) && (k1 > 0)) {
763 if (k1_below > 0) {
764 degree_alias[low_band] = 0x7fff;
765
766 if (k1_below2 < 0) {
767 degree_alias[low_band - 1] = deg;
768 }
769 } else {
770 if (k1_below2 < 0) {
771 degree_alias[low_band] = deg;
772 }
773 }
774 }
775 }
776
777 k1_below2 = k1_below;
778 k1_below = k1;
779
780 patch = 0;
781 while (patch < num_patches) {
782 ia_patch_param_struct *p_loc_patch_param = &patch_param[patch];
783 WORD32 bw_vec, bw_idx;
784 WORD16 alpha1, alpha2;
785
786 high_band = (((low_band + p_loc_patch_param->dst_end_band) << 8) >> 8);
787
788 if ((low_band < p_loc_patch_param->src_start_band) ||
789 (low_band >= p_loc_patch_param->src_end_band) ||
790 (high_band < max_qmf_subband)) {
791 patch++;
792 continue;
793 }
794
795 bw_idx = bw_index[patch];
796 while (high_band >= hf_generator->pstr_settings->bw_borders[bw_idx]) {
797 bw_idx++;
798 bw_index[patch] = bw_idx;
799 }
800
801 bw_vec = bw_array[bw_idx];
802 alpha1 = alpha_real[0];
803 alpha2 = alpha_real[1];
804
805 bw = ixheaacd_extract16h(bw_vec);
806 a0r = ixheaacd_mult16x16in32_shl(bw, alpha1);
807 bw = ixheaacd_mult16_shl_sat(bw, bw);
808 a1r = ixheaacd_mult16x16in32_shl(bw, alpha2);
809
810 {
811 WORD32 *p_sub_signal_xlow = sub_sig_x + low_band + ((start_idx) << 6);
812 WORD32 *p_sub_signal_xhigh =
813 sub_sig_x + high_band + ((start_idx + 2) << 6);
814 WORD32 len = stop_idx - start_idx - 1;
815
816 if (bw > 0) {
817 ixheaacd_filt_step3_lp(len, a0r, a1r, p_sub_signal_xlow,
818 p_sub_signal_xhigh);
819
820 } else {
821 p_sub_signal_xlow += 128;
822 for (i = len; i >= 0; i--) {
823 *p_sub_signal_xhigh = *p_sub_signal_xlow >> LPC_SCALE_FACTOR;
824 p_sub_signal_xlow += 64;
825 p_sub_signal_xhigh += 64;
826 }
827 }
828 }
829
830 patch++;
831 }
832 }
833 }
834
ixheaacd_clr_subsamples(WORD32 * ptr_qmf_buf,WORD32 num,WORD32 size)835 VOID ixheaacd_clr_subsamples(WORD32 *ptr_qmf_buf, WORD32 num, WORD32 size) {
836 WORD32 i;
837 for (i = num; i >= 0; i--) {
838 memset(ptr_qmf_buf, 0, sizeof(WORD32) * (size));
839 ptr_qmf_buf += 64;
840 }
841 }
842
ixheaacd_low_pow_hf_generator(ia_sbr_hf_generator_struct * hf_generator,WORD32 ** qmf_real,WORD16 * degree_alias,WORD32 start_idx,WORD32 stop_idx,WORD32 num_if_bands,WORD32 max_qmf_subband,WORD32 * sbr_invf_mode,WORD32 * sbr_invf_mode_prev,WORD32 norm_max,WORD32 * sub_sig_x)843 VOID ixheaacd_low_pow_hf_generator(ia_sbr_hf_generator_struct *hf_generator,
844 WORD32 **qmf_real, WORD16 *degree_alias,
845 WORD32 start_idx, WORD32 stop_idx,
846 WORD32 num_if_bands, WORD32 max_qmf_subband,
847 WORD32 *sbr_invf_mode,
848 WORD32 *sbr_invf_mode_prev, WORD32 norm_max,
849 WORD32 *sub_sig_x) {
850 WORD32 bw_array[MAX_NUM_PATCHES];
851 WORD32 i;
852 WORD32 start_patch, stop_patch, low_band, high_band;
853 ia_patch_param_struct *patch_param =
854 hf_generator->pstr_settings->str_patch_param;
855 WORD32 patch;
856 ia_lpp_trans_cov_matrix cov_matrix_seq[MAX_COLS];
857
858 WORD32 actual_stop_band;
859 WORD32 num_patches = hf_generator->pstr_settings->num_patches;
860 WORD32 auto_corr_length = hf_generator->pstr_settings->num_columns + 6;
861
862 stop_idx = (hf_generator->pstr_settings->num_columns + stop_idx);
863
864 ixheaacd_invfilt_level_emphasis(hf_generator, num_if_bands, sbr_invf_mode,
865 sbr_invf_mode_prev, bw_array);
866
867 actual_stop_band =
868 ixheaacd_add16(patch_param[num_patches - 1].dst_start_band,
869 patch_param[num_patches - 1].num_bands_in_patch);
870
871 {
872 WORD32 *p_qmf_real;
873 WORD32 len = 6, num;
874
875 if (len > stop_idx) len = stop_idx;
876
877 p_qmf_real = &qmf_real[start_idx][actual_stop_band];
878 num = (len - start_idx - 1);
879 ixheaacd_clr_subsamples(p_qmf_real, num,
880 (NO_SYNTHESIS_CHANNELS - actual_stop_band));
881
882 if (actual_stop_band < 32) {
883 num = (stop_idx - len - 1);
884 p_qmf_real = &qmf_real[len][actual_stop_band];
885 ixheaacd_clr_subsamples(p_qmf_real, num,
886 (NO_ANALYSIS_CHANNELS - actual_stop_band));
887 }
888 }
889
890 start_patch = ixheaacd_max16(
891 1, ixheaacd_sub16(hf_generator->pstr_settings->start_patch, 2));
892 stop_patch = patch_param[0].dst_start_band;
893
894 {
895 WORD32 *ptr = &sub_sig_x[0];
896 WORD32 *plpc_filt_states_real = &hf_generator->lpc_filt_states_real[0][0];
897 for (i = LPC_ORDER; i != 0; i--) {
898 memcpy(ptr, plpc_filt_states_real, sizeof(WORD32) * (stop_patch));
899 ptr += NO_SYNTHESIS_CHANNELS;
900 plpc_filt_states_real += 32;
901 }
902 }
903 if (norm_max != 30) {
904 if (30 == hf_generator->pstr_settings->num_columns) {
905 (*ixheaacd_covariance_matrix_calc_960)(sub_sig_x + start_patch,
906 &cov_matrix_seq[start_patch],
907 (stop_patch - start_patch),
908 auto_corr_length);
909 } else
910 (*ixheaacd_covariance_matrix_calc)(sub_sig_x + start_patch,
911 &cov_matrix_seq[start_patch],
912 (stop_patch - start_patch),
913 auto_corr_length);
914 } else {
915 memset(&cov_matrix_seq[0], 0,
916 sizeof(ia_lpp_trans_cov_matrix) * stop_patch);
917 }
918
919 ixheaacd_filter1_lp(hf_generator, cov_matrix_seq, bw_array, degree_alias,
920 start_idx, stop_idx, max_qmf_subband, start_patch,
921 stop_patch, sub_sig_x);
922
923 start_patch = hf_generator->pstr_settings->start_patch;
924 stop_patch = hf_generator->pstr_settings->stop_patch;
925
926 for (low_band = start_patch; low_band < stop_patch; low_band++) {
927 WORD32 src_start_band, src_end_band, dst_start_band;
928 patch = 0;
929
930 while (patch < num_patches) {
931 ia_patch_param_struct *ptr_loc_patch_param = &patch_param[patch];
932
933 src_start_band = ptr_loc_patch_param->src_start_band;
934 src_end_band = ptr_loc_patch_param->src_end_band;
935 dst_start_band = ptr_loc_patch_param->dst_start_band;
936
937 high_band = (low_band + ptr_loc_patch_param->dst_end_band);
938
939 if ((low_band < src_start_band) || (low_band >= src_end_band) ||
940 (high_band >= NO_SYNTHESIS_CHANNELS)) {
941 patch++;
942 continue;
943 }
944
945 if ((high_band != dst_start_band)) {
946 degree_alias[high_band] = degree_alias[low_band];
947 }
948
949 patch++;
950 }
951 }
952
953 memcpy(hf_generator->bw_array_prev, bw_array, sizeof(WORD32) * num_if_bands);
954 }
955
ixheaacd_hf_generator(ia_sbr_hf_generator_struct * hf_generator,ia_sbr_scale_fact_struct * scale_factor,WORD32 ** qmf_real,WORD32 ** qmf_imag,WORD32 factor,WORD32 start_idx,WORD32 stop_idx,WORD32 num_if_bands,WORD32 max_qmf_subband,WORD32 * sbr_invf_mode,WORD32 * sbr_invf_mode_prev,WORD32 * sub_sig_x,WORD audio_object_type)956 VOID ixheaacd_hf_generator(ia_sbr_hf_generator_struct *hf_generator,
957 ia_sbr_scale_fact_struct *scale_factor,
958 WORD32 **qmf_real, WORD32 **qmf_imag, WORD32 factor,
959 WORD32 start_idx, WORD32 stop_idx,
960 WORD32 num_if_bands, WORD32 max_qmf_subband,
961 WORD32 *sbr_invf_mode, WORD32 *sbr_invf_mode_prev,
962 WORD32 *sub_sig_x, WORD audio_object_type) {
963 WORD32 bw_index[MAX_NUM_PATCHES];
964 WORD32 bw_array[MAX_NUM_PATCHES];
965
966 WORD32 i, j;
967 WORD32 start_patch, stop_patch, low_band, high_band;
968 ia_patch_param_struct *patch_param =
969 hf_generator->pstr_settings->str_patch_param;
970 WORD32 patch;
971
972 WORD16 alpha_real[LPC_ORDER];
973 WORD16 a0r, a1r;
974 WORD16 alpha_imag[LPC_ORDER];
975 WORD16 a0i = 0, a1i = 0;
976
977 WORD16 bw = 0;
978
979 ia_lpp_trans_cov_matrix cov_matrix;
980 ia_lpp_trans_cov_matrix cov_matrix_seq[MAX_COLS];
981
982 WORD32 common_scale;
983 WORD32 actual_stop_band;
984 WORD32 num_patches = hf_generator->pstr_settings->num_patches;
985
986 WORD32 auto_corr_length = hf_generator->pstr_settings->num_columns + 6;
987
988 start_idx = (start_idx * factor);
989
990 stop_idx = (hf_generator->pstr_settings->num_columns + (stop_idx * factor));
991
992 ixheaacd_invfilt_level_emphasis(hf_generator, num_if_bands, sbr_invf_mode,
993 sbr_invf_mode_prev, bw_array);
994
995 actual_stop_band =
996 ixheaacd_add16(patch_param[num_patches - 1].dst_start_band,
997 patch_param[num_patches - 1].num_bands_in_patch);
998
999 for (i = start_idx; i < stop_idx; i++) {
1000 WORD32 *p_qmf_real = &qmf_real[i][actual_stop_band];
1001 WORD32 *p_qmf_imag = &qmf_imag[i][actual_stop_band];
1002
1003 for (j = NO_SYNTHESIS_CHANNELS - actual_stop_band; j != 0; j--) {
1004 *p_qmf_real++ = 0;
1005 *p_qmf_imag++ = 0;
1006 }
1007 }
1008
1009 memset(bw_index, 0, sizeof(WORD32) * num_patches);
1010
1011 common_scale =
1012 ixheaacd_min32(scale_factor->ov_lb_scale, scale_factor->lb_scale);
1013
1014 start_patch = hf_generator->pstr_settings->start_patch;
1015 stop_patch = hf_generator->pstr_settings->stop_patch;
1016
1017 {
1018 WORD32 *ptr;
1019 for (i = 0; i < LPC_ORDER; i++) {
1020 ptr = sub_sig_x + (start_patch) + i * 128;
1021 memcpy(ptr, &hf_generator->lpc_filt_states_real[i][start_patch],
1022 sizeof(WORD32) * (stop_patch - start_patch));
1023 memcpy(ptr + 64, &hf_generator->lpc_filt_states_imag[i][start_patch],
1024 sizeof(WORD32) * (stop_patch - start_patch));
1025 }
1026 }
1027 if (audio_object_type != AOT_ER_AAC_ELD &&
1028 audio_object_type != AOT_ER_AAC_LD) {
1029 if (auto_corr_length == 36) {
1030 (*ixheaacd_covariance_matrix_calc_2)(
1031 &cov_matrix_seq[start_patch],
1032 (sub_sig_x + start_patch + LPC_ORDER * 128),
1033 (stop_patch - start_patch), auto_corr_length);
1034 } else {
1035 (*ixheaacd_covariance_matrix_calc_2)(
1036 &cov_matrix_seq[start_patch],
1037 (sub_sig_x + start_patch + LPC_ORDER * 128),
1038 (stop_patch - start_patch), 38);
1039 }
1040 } else {
1041 if (hf_generator->pstr_settings->num_columns == 15) {
1042 (*ixheaacd_covariance_matrix_calc_2)(
1043 &cov_matrix_seq[start_patch],
1044 (sub_sig_x + start_patch + LPC_ORDER * 128),
1045 (stop_patch - start_patch),
1046 hf_generator->pstr_settings->num_columns);
1047 } else {
1048 (*ixheaacd_covariance_matrix_calc_2)(
1049 &cov_matrix_seq[start_patch],
1050 (sub_sig_x + start_patch + LPC_ORDER * 128),
1051 (stop_patch - start_patch), 16);
1052 }
1053 }
1054
1055 for (low_band = start_patch; low_band < stop_patch; low_band++) {
1056 FLAG reset_lpc_coeff = 0;
1057 WORD32 max_val;
1058 WORD32 q_shift;
1059 WORD32 v;
1060 max_val = ixheaacd_abs32_nrm(cov_matrix_seq[low_band].phi_01);
1061 max_val = max_val | ixheaacd_abs32_nrm(cov_matrix_seq[low_band].phi_02);
1062 max_val = max_val | ixheaacd_abs32_nrm(cov_matrix_seq[low_band].phi_12);
1063
1064 max_val = max_val | (cov_matrix_seq[low_band].phi_11);
1065 max_val = max_val | (cov_matrix_seq[low_band].phi_22);
1066 max_val = max_val | ixheaacd_abs32_nrm(cov_matrix_seq[low_band].phi_01_im);
1067 max_val = max_val | ixheaacd_abs32_nrm(cov_matrix_seq[low_band].phi_02_im);
1068 max_val = max_val | ixheaacd_abs32_nrm(cov_matrix_seq[low_band].phi_12_im);
1069
1070 q_shift = ixheaacd_pnorm32(max_val);
1071
1072 cov_matrix.phi_11 = (cov_matrix_seq[low_band].phi_11 << q_shift);
1073 cov_matrix.phi_22 = (cov_matrix_seq[low_band].phi_22 << q_shift);
1074 cov_matrix.phi_01 = (cov_matrix_seq[low_band].phi_01 << q_shift);
1075 cov_matrix.phi_02 = (cov_matrix_seq[low_band].phi_02 << q_shift);
1076 cov_matrix.phi_12 = (cov_matrix_seq[low_band].phi_12 << q_shift);
1077 cov_matrix.phi_01_im = (cov_matrix_seq[low_band].phi_01_im << q_shift);
1078 cov_matrix.phi_02_im = (cov_matrix_seq[low_band].phi_02_im << q_shift);
1079 cov_matrix.phi_12_im = (cov_matrix_seq[low_band].phi_12_im << q_shift);
1080
1081 max_val = ixheaacd_mult32(cov_matrix.phi_12, cov_matrix.phi_12);
1082 max_val = ixheaacd_add32_sat(
1083 max_val, ixheaacd_mult32(cov_matrix.phi_12_im, cov_matrix.phi_12_im));
1084
1085 v = ixheaacd_sub32_sat(
1086 ixheaacd_mult32(cov_matrix.phi_11, cov_matrix.phi_22), max_val)
1087 << 1;
1088 cov_matrix.d = v;
1089
1090 alpha_real[1] = 0;
1091 alpha_imag[1] = 0;
1092
1093 if (cov_matrix.d != 0) {
1094 WORD32 tmp_r, temp_real, modulus_d;
1095 WORD32 tmp_i, temp_imag;
1096 WORD16 inverse_d;
1097 WORD32 norm_d;
1098
1099 norm_d = ixheaacd_norm32(cov_matrix.d);
1100
1101 inverse_d =
1102 (WORD16)(*ixheaacd_fix_div)(0x40000000, (cov_matrix.d << norm_d));
1103
1104 modulus_d = ixheaacd_abs32_sat(cov_matrix.d);
1105 tmp_r =
1106 (ixheaacd_sub32_sat(
1107 ixheaacd_sub32_sat(
1108 ixheaacd_mult32(cov_matrix.phi_01, cov_matrix.phi_12),
1109 ixheaacd_mult32(cov_matrix.phi_01_im, cov_matrix.phi_12_im)),
1110 ixheaacd_mult32(cov_matrix.phi_02, cov_matrix.phi_11))) >>
1111 (LPC_SCALE_FACTOR - 1);
1112 tmp_i = (ixheaacd_sub32_sat(
1113 ixheaacd_add32_sat(
1114 ixheaacd_mult32(cov_matrix.phi_01_im, cov_matrix.phi_12),
1115 ixheaacd_mult32(cov_matrix.phi_01, cov_matrix.phi_12_im)),
1116 ixheaacd_mult32(cov_matrix.phi_02_im, cov_matrix.phi_11))) >>
1117 (LPC_SCALE_FACTOR - 1);
1118 temp_imag = ixheaacd_abs32(tmp_i);
1119 temp_real = ixheaacd_abs32(tmp_r);
1120
1121 if (temp_real >= modulus_d) {
1122 reset_lpc_coeff = 1;
1123 } else {
1124 alpha_real[1] = (WORD16)(
1125 (ixheaacd_mult32x16in32(tmp_r, inverse_d) << (norm_d + 1)) >> 15);
1126 }
1127
1128 if (temp_imag >= modulus_d) {
1129 reset_lpc_coeff = 1;
1130 } else {
1131 alpha_imag[1] = (WORD16)(
1132 (ixheaacd_mult32x16in32(tmp_i, inverse_d) << (norm_d + 1)) >> 15);
1133 }
1134 }
1135
1136 alpha_real[0] = 0;
1137 alpha_imag[0] = 0;
1138
1139 if (cov_matrix.phi_11 != 0) {
1140 WORD32 tmp_r, temp_real;
1141 WORD32 tmp_i = 0, temp_imag = 0;
1142 WORD16 inverse_r11;
1143 WORD32 norm_r11;
1144
1145 norm_r11 = ixheaacd_norm32(cov_matrix.phi_11);
1146
1147 inverse_r11 = (WORD16)(*ixheaacd_fix_div)(
1148 0x40000000, (cov_matrix.phi_11 << norm_r11));
1149
1150 tmp_r = ixheaacd_add32_sat(
1151 ixheaacd_add32(
1152 (cov_matrix.phi_01 >> (LPC_SCALE_FACTOR + 1)),
1153 ixheaacd_mult32x16in32(cov_matrix.phi_12, alpha_real[1])),
1154 ixheaacd_mult32x16in32(cov_matrix.phi_12_im, alpha_imag[1]));
1155 tmp_i = ixheaacd_sub32_sat(
1156 ixheaacd_add32(
1157 (cov_matrix.phi_01_im >> (LPC_SCALE_FACTOR + 1)),
1158 ixheaacd_mult32x16in32(cov_matrix.phi_12, alpha_imag[1])),
1159 ixheaacd_mult32x16in32(cov_matrix.phi_12_im, alpha_real[1]));
1160
1161 tmp_r = tmp_r << 1;
1162 tmp_i = tmp_i << 1;
1163
1164 temp_imag = ixheaacd_abs32(tmp_i);
1165 temp_real = ixheaacd_abs32(tmp_r);
1166
1167 if (temp_real >= cov_matrix.phi_11) {
1168 reset_lpc_coeff = 1;
1169 } else {
1170 alpha_real[0] = (WORD16)(
1171 (ixheaacd_mult32x16in32(ixheaacd_sub32_sat(0, tmp_r), inverse_r11)
1172 << (norm_r11 + 1)) >>
1173 15);
1174 }
1175
1176 if (temp_imag >= cov_matrix.phi_11) {
1177 reset_lpc_coeff = 1;
1178 } else {
1179 alpha_imag[0] = (WORD16)(
1180 (ixheaacd_mult32x16in32(ixheaacd_sub32_sat(0, tmp_i), inverse_r11)
1181 << (norm_r11 + 1)) >>
1182 15);
1183 }
1184 }
1185
1186 if (ixheaacd_add32_sat((alpha_real[0] * alpha_real[0]),
1187 (alpha_imag[0] * alpha_imag[0])) >= 0x40000000L) {
1188 reset_lpc_coeff = 1;
1189 }
1190
1191 if (ixheaacd_add32_sat((alpha_real[1] * alpha_real[1]),
1192 (alpha_imag[1] * alpha_imag[1])) >= 0x40000000L) {
1193 reset_lpc_coeff = 1;
1194 }
1195
1196 if (reset_lpc_coeff) {
1197 alpha_real[0] = 0;
1198 alpha_real[1] = 0;
1199 alpha_imag[0] = 0;
1200 alpha_imag[1] = 0;
1201 }
1202
1203 patch = 0;
1204
1205 while (patch < num_patches) {
1206 high_band = (low_band + patch_param[patch].dst_end_band);
1207
1208 if ((low_band < patch_param[patch].src_start_band) ||
1209 (low_band >= patch_param[patch].src_end_band)) {
1210 patch++;
1211 continue;
1212 }
1213
1214 if (high_band < max_qmf_subband) {
1215 patch++;
1216 continue;
1217 }
1218
1219 while ((bw_index[patch] < MAX_NUM_PATCHES - 1) &&
1220 (bw_index[patch] < MAX_NUM_NOISE_VALUES) &&
1221 (high_band >=
1222 hf_generator->pstr_settings->bw_borders[bw_index[patch]])) {
1223 bw_index[patch]++;
1224 }
1225
1226 bw = ixheaacd_extract16h(bw_array[bw_index[patch]]);
1227 a0r = ixheaacd_mult16_shl_sat(bw, alpha_real[0]);
1228 a0i = ixheaacd_mult16_shl_sat(bw, alpha_imag[0]);
1229 bw = ixheaacd_mult16_shl_sat(bw, bw);
1230 a1r = ixheaacd_mult16_shl_sat(bw, alpha_real[1]);
1231 a1i = ixheaacd_mult16_shl_sat(bw, alpha_imag[1]);
1232
1233 if (bw > 0) {
1234 ixheaacd_filterstep3(a0r, a0i, a1r, a1i, start_idx, stop_idx, low_band,
1235 high_band, sub_sig_x);
1236
1237 } else {
1238 WORD32 *p_src = sub_sig_x + low_band + ((start_idx + 2) << 7);
1239 WORD32 *p_dst = sub_sig_x + high_band + ((start_idx + 2) << 7);
1240
1241 for (i = stop_idx - start_idx; i != 0; i--) {
1242 *(p_dst) = *(p_src) >> LPC_SCALE_FACTOR;
1243 p_src += 64;
1244 p_dst += 64;
1245 *(p_dst) = *(p_src) >> LPC_SCALE_FACTOR;
1246 p_src += 64;
1247 p_dst += 64;
1248 }
1249 }
1250
1251 patch++;
1252 }
1253 }
1254
1255 memcpy(hf_generator->bw_array_prev, bw_array, sizeof(WORD32) * num_if_bands);
1256
1257 scale_factor->hb_scale = (WORD16)(common_scale - LPC_SCALE_FACTOR);
1258 }
1259