1 /******************************************************************************
2 * *
3 * Copyright (C) 2018 The Android Open Source Project
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 *****************************************************************************
18 * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19 */
20 #include <string.h>
21 #include <stdio.h>
22 #include <stdlib.h>
23 #include <assert.h>
24 #include "ixheaacd_sbr_common.h"
25 #include "ixheaacd_type_def.h"
26 #include "ixheaacd_constants.h"
27 #include "ixheaacd_basic_ops32.h"
28 #include "ixheaacd_basic_ops16.h"
29 #include "ixheaacd_basic_ops40.h"
30 #include "ixheaacd_basic_ops.h"
31
32 #include "ixheaacd_error_standards.h"
33 #include "ixheaacd_apicmd_standards.h"
34 #include "ixheaacd_aac_config.h"
35 #include "ixheaacd_api_defs.h"
36
37 #include "ixheaacd_definitions.h"
38 #include "ixheaacd_error_codes.h"
39 #include "ixheaacd_bitbuffer.h"
40
41 #include "ixheaacd_audioobjtypes.h"
42 #include "ixheaacd_sbrdecsettings.h"
43 #include "ixheaacd_memory_standards.h"
44
45 #include "ixheaacd_bitbuffer.h"
46 #include "ixheaacd_adts.h"
47 #include "ixheaacd_defines.h"
48 #include "ixheaacd_aac_rom.h"
49
50 #include "ixheaacd_sbr_scale.h"
51 #include "ixheaacd_lpp_tran.h"
52 #include "ixheaacd_env_extr_part.h"
53 #include "ixheaacd_sbr_rom.h"
54
55 #include "ixheaacd_hybrid.h"
56 #include "ixheaacd_ps_dec.h"
57 #include "ixheaacd_ps_bitdec.h"
58
59 #include "ixheaacd_pulsedata.h"
60
61 #include "ixheaacd_pns.h"
62 #include "ixheaacd_drc_data_struct.h"
63
64 #include "ixheaacd_lt_predict.h"
65
66 #include "ixheaacd_channelinfo.h"
67 #include "ixheaacd_drc_dec.h"
68 #include "ixheaacd_sbr_const.h"
69 #include "ixheaacd_sbrdecoder.h"
70 #include "ixheaacd_env_extr.h"
71 #include "ixheaacd_common_rom.h"
72 #include "ixheaacd_freq_sca.h"
73 #include "ixheaacd_qmf_dec.h"
74 #include "ixheaacd_env_calc.h"
75
76 #include "ixheaacd_pvc_dec.h"
77 #include "ixheaacd_sbr_dec.h"
78 #include "ixheaacd_block.h"
79 #include "ixheaacd_channel.h"
80
81 #include "ixheaacd_audioobjtypes.h"
82 #include "ixheaacd_latmdemux.h"
83
84 #include "ixheaacd_aacdec.h"
85 #include "ixheaacd_mps_polyphase.h"
86 #include "ixheaacd_config.h"
87 #include "ixheaacd_mps_dec.h"
88 #include "ixheaacd_struct_def.h"
89 #include "ixheaacd_headerdecode.h"
90 #include "ixheaacd_adts_crc_check.h"
91
92 #include "ixheaacd_multichannel.h"
93 #include "ixheaacd_ver_number.h"
94
95 #include "ixheaacd_interface.h"
96 #include "ixheaacd_info.h"
97
98 #include "ixheaacd_config.h"
99
100 #include "ixheaacd_struct.h"
101 #include "ixheaacd_cnst.h"
102 #include "ixheaacd_mps_polyphase.h"
103 #include "ixheaacd_tns_usac.h"
104 #include "ixheaacd_acelp_info.h"
105
106 #include "ixheaacd_main.h"
107 #include "ixheaacd_arith_dec.h"
108 #include "ixheaacd_create.h"
109 #include "ixheaacd_function_selector.h"
110
111 #define MAX_TRACKS_PER_LAYER 50
112
113 #define ALIGN_SIZE64(x) ((((x) + 7) >> 3) << 3)
114
115 #define IA_ENHAACPDEC_NUM_MEMTABS (4)
116
117 #define NUM_AAC_TABLES 8
118
119 #define IXHEAACD_CCE_DEC_INFO_MEM_SIZE (610)
120 #define IXHEAACD_CCE_DEC_INFO_MEM_SIZE_8 (IXHEAACD_CCE_DEC_INFO_MEM_SIZE + 8)
121
ixheaacd_dec_mem_api(ia_exhaacplus_dec_api_struct * p_obj_exhaacplus_dec,WORD32 i_cmd,WORD32 i_idx,VOID * pv_value)122 IA_ERRORCODE ixheaacd_dec_mem_api(
123 ia_exhaacplus_dec_api_struct *p_obj_exhaacplus_dec, WORD32 i_cmd,
124 WORD32 i_idx, VOID *pv_value) {
125 pUWORD32 pui_value = pv_value;
126
127 if (i_idx < 0 || i_idx >= IA_ENHAACPDEC_NUM_MEMTABS) {
128 return IA_ENHAACPLUS_DEC_API_FATAL_INVALID_MEMTAB_INDEX;
129 }
130
131 if (i_cmd == IA_API_CMD_SET_MEM_PTR) {
132 if (pv_value == 0) {
133 return (IA_ENHAACPLUS_DEC_API_FATAL_MEM_ALLOC);
134 }
135 if (((SIZE_T)pv_value %
136 p_obj_exhaacplus_dec->p_mem_info_aac[i_idx].ui_alignment) != 0) {
137 return (IA_ENHAACPLUS_DEC_API_FATAL_MEM_ALIGN);
138 }
139 p_obj_exhaacplus_dec->pp_mem_aac[i_idx] = pv_value;
140 memset(p_obj_exhaacplus_dec->pp_mem_aac[i_idx], 0,
141 p_obj_exhaacplus_dec->p_mem_info_aac[i_idx].ui_size);
142
143 if (i_idx == IA_ENHAACPLUS_DEC_PERSIST_IDX) {
144 pUWORD8 p_temp = pv_value;
145 UWORD32 *meminfo =
146 (UWORD32 *)p_obj_exhaacplus_dec->p_mem_info_aac + i_idx;
147 UWORD32 pers_size = meminfo[0];
148 p_temp = p_temp + pers_size -
149 (sizeof(ia_dec_data_struct) +
150 sizeof(ia_audio_specific_config_struct) + (8300));
151 p_obj_exhaacplus_dec->p_state_aac = pv_value;
152
153 p_obj_exhaacplus_dec->p_state_aac->pstr_dec_data = p_temp;
154 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config =
155 p_temp + sizeof(ia_dec_data_struct);
156 p_obj_exhaacplus_dec->p_state_aac->header_ptr =
157 p_temp + sizeof(ia_dec_data_struct) +
158 sizeof(ia_audio_specific_config_struct);
159 }
160
161 } else {
162 UWORD32 *meminfo =
163 (UWORD32 *)(p_obj_exhaacplus_dec->p_mem_info_aac + i_idx);
164 *pui_value = *(meminfo + (i_cmd - IA_API_CMD_GET_MEM_INFO_SIZE));
165 }
166
167 return IA_NO_ERROR;
168 }
169
170 static PLATFORM_INLINE VOID
ixheaacd_init_sbr_tables(ia_sbr_tables_struct * ptr_sbr_tables)171 ixheaacd_init_sbr_tables(ia_sbr_tables_struct *ptr_sbr_tables) {
172 ptr_sbr_tables->env_calc_tables_ptr =
173 (ia_env_calc_tables_struct *)&ixheaacd_aac_dec_env_calc_tables;
174 ptr_sbr_tables->qmf_dec_tables_ptr =
175 (ia_qmf_dec_tables_struct *)&ixheaacd_aac_qmf_dec_tables;
176 ptr_sbr_tables->env_extr_tables_ptr =
177 (ia_env_extr_tables_struct *)&ixheaacd_aac_dec_env_extr_tables;
178 ptr_sbr_tables->ps_tables_ptr =
179 (ia_ps_tables_struct *)&ixheaacd_aac_dec_ps_tables;
180 }
181
ixheaacd_updatebytesconsumed(ia_aac_dec_state_struct * p_state_enhaacplus_dec,struct ia_bit_buf_struct * it_bit_buff)182 VOID ixheaacd_updatebytesconsumed(
183 ia_aac_dec_state_struct *p_state_enhaacplus_dec,
184 struct ia_bit_buf_struct *it_bit_buff) {
185 p_state_enhaacplus_dec->i_bytes_consumed =
186 (it_bit_buff->ptr_read_next - it_bit_buff->ptr_bit_buf_base);
187 if ((p_state_enhaacplus_dec->i_bytes_consumed == 0) &&
188 (it_bit_buff->cnt_bits == 0)) {
189 p_state_enhaacplus_dec->i_bytes_consumed =
190 p_state_enhaacplus_dec->ui_in_bytes;
191 }
192 if (it_bit_buff->cnt_bits < 0) {
193 p_state_enhaacplus_dec->i_bytes_consumed = 0;
194 p_state_enhaacplus_dec->ui_out_bytes = 0;
195 p_state_enhaacplus_dec->b_n_raw_data_blk = 0;
196 }
197 }
198
ixheaacd_readifadts(ia_aac_dec_state_struct * p_state_enhaacplus_dec,struct ia_bit_buf_struct * it_bit_buff,ia_adts_header_struct * adts)199 WORD32 ixheaacd_readifadts(ia_aac_dec_state_struct *p_state_enhaacplus_dec,
200 struct ia_bit_buf_struct *it_bit_buff,
201 ia_adts_header_struct *adts) {
202 WORD error;
203
204 if ((error = ixheaacd_find_syncword(adts, it_bit_buff)) != 0) {
205 ixheaacd_updatebytesconsumed(p_state_enhaacplus_dec, it_bit_buff);
206 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_ADTS_SYNC_LOST;
207 }
208 if ((error = ixheaacd_check_if_adts(
209 adts, it_bit_buff,
210 p_state_enhaacplus_dec->p_config->ui_max_channels)) != 0) {
211 p_state_enhaacplus_dec->i_bytes_consumed = 1;
212
213 if (it_bit_buff->cnt_bits < 0) {
214 p_state_enhaacplus_dec->i_bytes_consumed = 0;
215 p_state_enhaacplus_dec->ui_out_bytes = 0;
216 error = IA_ENHAACPLUS_DEC_EXE_NONFATAL_INSUFFICIENT_INPUT_BYTES;
217 return error;
218 }
219 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_ADTS_SYNC_LOST;
220 }
221 p_state_enhaacplus_dec->b_n_raw_data_blk =
222 (WORD8)(adts->no_raw_data_blocks + 1);
223 return 0;
224 }
225
ixheaacd_allocate_aac_scr(ia_aac_dec_scratch_struct * aac_scratch_struct,VOID * base_scratch_ptr,VOID * output_ptr,WORD channel,WORD max_channel,WORD32 audio_object_type)226 static VOID ixheaacd_allocate_aac_scr(
227 ia_aac_dec_scratch_struct *aac_scratch_struct, VOID *base_scratch_ptr,
228 VOID *output_ptr, WORD channel, WORD max_channel,
229 WORD32 audio_object_type) {
230 aac_scratch_struct->base_scr_8k = base_scratch_ptr;
231 aac_scratch_struct->extra_scr_4k[1] = (WORD8 *)base_scratch_ptr;
232 if (channel == 1) {
233 aac_scratch_struct->extra_scr_4k[0] =
234 (WORD8 *)base_scratch_ptr + (IXHEAACD_CCE_DEC_INFO_MEM_SIZE_8 * 1024) +
235 (4 * 1024);
236 } else {
237 aac_scratch_struct->extra_scr_4k[0] = output_ptr;
238
239 if (max_channel > 2) {
240 aac_scratch_struct->extra_scr_4k[0] =
241 (WORD8 *)base_scratch_ptr +
242 (IXHEAACD_CCE_DEC_INFO_MEM_SIZE_8 * 1024) + (8 * 1024);
243 }
244 }
245
246 aac_scratch_struct->extra_scr_4k[2] =
247 (WORD8 *)base_scratch_ptr + (IXHEAACD_CCE_DEC_INFO_MEM_SIZE_8 * 1024) +
248 (46 * 1024);
249
250 if (audio_object_type == AOT_ER_AAC_ELD ||
251 audio_object_type == AOT_ER_AAC_LD) {
252 aac_scratch_struct->extra_scr_4k[0] =
253 (WORD8 *)base_scratch_ptr + (IXHEAACD_CCE_DEC_INFO_MEM_SIZE_8 * 1024) +
254 (4 * 1024);
255
256 aac_scratch_struct->extra_scr_4k[2] =
257 (WORD8 *)base_scratch_ptr + (IXHEAACD_CCE_DEC_INFO_MEM_SIZE_8 * 1024) +
258 (46 * 1024);
259
260 aac_scratch_struct->extra_scr_4k[3] =
261 (WORD8 *)base_scratch_ptr + (IXHEAACD_CCE_DEC_INFO_MEM_SIZE_8 * 1024) +
262 (54 * 1024);
263 }
264 if ((audio_object_type == AOT_ER_AAC_LD) ||
265 (audio_object_type == AOT_AAC_LTP)) {
266 aac_scratch_struct->in_data =
267 (WORD32 *)((WORD8 *)base_scratch_ptr +
268 (IXHEAACD_CCE_DEC_INFO_MEM_SIZE_8 * 1024) + (62 * 1024) +
269 (4 * 16));
270 aac_scratch_struct->out_data =
271 (WORD32 *)((WORD8 *)base_scratch_ptr +
272 (IXHEAACD_CCE_DEC_INFO_MEM_SIZE_8 * 1024) + (56 * 1024) +
273 (4 * 16));
274 }
275 }
276
ixheaacd_allocate_sbr_scr(ia_sbr_scr_struct * sbr_scratch_struct,VOID * base_scratch_ptr,VOID * output_ptr,WORD total_elements,WORD ch_fac,WORD32 audio_object_type)277 VOID ixheaacd_allocate_sbr_scr(ia_sbr_scr_struct *sbr_scratch_struct,
278 VOID *base_scratch_ptr, VOID *output_ptr,
279 WORD total_elements, WORD ch_fac,
280 WORD32 audio_object_type) {
281 WORD32 temp = 0;
282 sbr_scratch_struct->ptr_work_buf_core = base_scratch_ptr;
283 sbr_scratch_struct->ptr_work_buf = (WORD8 *)base_scratch_ptr + (18 * 1024);
284
285 if (total_elements > 1) {
286 sbr_scratch_struct->extra_scr_1k[0] =
287 (WORD8 *)base_scratch_ptr + (18 * 1024);
288
289 sbr_scratch_struct->extra_scr_1k[1] =
290 (WORD8 *)base_scratch_ptr + (19 * 1024);
291 }
292
293 else {
294 if (ch_fac == 1) {
295 temp = 2;
296 } else {
297 temp = 4;
298 }
299
300 if (audio_object_type != AOT_ER_AAC_ELD) {
301 sbr_scratch_struct->extra_scr_1k[0] = (WORD8 *)output_ptr + (temp * 1024);
302
303 sbr_scratch_struct->extra_scr_1k[1] =
304 (WORD8 *)base_scratch_ptr + (18 * 1024);
305 } else {
306 sbr_scratch_struct->extra_scr_1k[0] =
307 (WORD8 *)base_scratch_ptr + (18 * 1024);
308
309 sbr_scratch_struct->extra_scr_1k[1] =
310 (WORD8 *)base_scratch_ptr + (19 * 1024);
311 }
312 }
313 }
314
ixheaacd_dec_api(pVOID p_ia_enhaacplus_dec_obj,WORD32 i_cmd,WORD32 i_idx,pVOID pv_value)315 IA_ERRORCODE ixheaacd_dec_api(pVOID p_ia_enhaacplus_dec_obj, WORD32 i_cmd,
316 WORD32 i_idx, pVOID pv_value) {
317 ia_exhaacplus_dec_api_struct *p_obj_exhaacplus_dec = p_ia_enhaacplus_dec_obj;
318 pUWORD32 pui_value = pv_value;
319 pWORD32 pui_value_signed = pv_value;
320 pWORD8 pb_value = pv_value;
321 pVOID *pp_value = (pVOID *)pv_value;
322
323 if ((i_cmd != IA_API_CMD_GET_API_SIZE) &&
324 (i_cmd != IA_API_CMD_GET_LIB_ID_STRINGS)) {
325 if (p_ia_enhaacplus_dec_obj == 0) {
326 return (IA_ENHAACPLUS_DEC_API_FATAL_MEM_ALLOC);
327 }
328 if (((SIZE_T)p_ia_enhaacplus_dec_obj & 3) != 0) {
329 return (IA_ENHAACPLUS_DEC_API_FATAL_MEM_ALIGN);
330 }
331 }
332
333 switch (i_cmd) {
334 case IA_API_CMD_GET_MEM_INFO_SIZE:
335 case IA_API_CMD_GET_MEM_INFO_ALIGNMENT:
336 case IA_API_CMD_GET_MEM_INFO_TYPE:
337 case IA_API_CMD_SET_MEM_PTR: {
338 return ixheaacd_dec_mem_api(p_ia_enhaacplus_dec_obj, i_cmd, i_idx,
339 pv_value);
340 }
341
342 case IA_API_CMD_GET_TABLE_INFO_SIZE:
343 case IA_API_CMD_GET_TABLE_INFO_ALIGNMENT:
344 case IA_API_CMD_SET_TABLE_PTR:
345 case IA_API_CMD_GET_TABLE_PTR: {
346 return ixheaacd_dec_table_api(p_ia_enhaacplus_dec_obj, i_cmd, i_idx,
347 pv_value);
348 }
349 };
350
351 switch (i_cmd) {
352 case IA_API_CMD_GET_LIB_ID_STRINGS: {
353 WORD8 *i1_ver;
354 WORD8 ver_char;
355
356 if (i_idx == IA_CMD_TYPE_LIB_NAME)
357 i1_ver = (WORD8 *)LIBNAME;
358 else if (i_idx == IA_CMD_TYPE_LIB_VERSION)
359 i1_ver = (WORD8 *)xHE_AAC_DEC_ITTIAM_VER;
360 else
361 return IA_ENHAACPLUS_DEC_API_FATAL_INVALID_LIB_ID_STRINGS_IDX;
362
363 ver_char = *i1_ver++;
364
365 for (; ver_char != '\0';) {
366 if (ver_char != '$') {
367 *pb_value++ = ver_char;
368 }
369 ver_char = *i1_ver++;
370 }
371 *pb_value = ver_char;
372
373 break;
374 }
375 case IA_API_CMD_GET_API_SIZE: {
376 *pui_value = sizeof(ia_exhaacplus_dec_api_struct);
377 break;
378 }
379 case IA_API_CMD_INIT: {
380 switch (i_idx) {
381 case IA_CMD_TYPE_INIT_API_PRE_CONFIG_PARAMS: {
382 memset(p_obj_exhaacplus_dec, 0, sizeof(*p_obj_exhaacplus_dec));
383 p_obj_exhaacplus_dec->aac_config.ui_pcm_wdsz = 16;
384 p_obj_exhaacplus_dec->aac_config.flag_downmix = 0;
385 p_obj_exhaacplus_dec->aac_config.flag_08khz_out = 0;
386 p_obj_exhaacplus_dec->aac_config.flag_16khz_out = 0;
387 p_obj_exhaacplus_dec->aac_config.flag_to_stereo = 0;
388 p_obj_exhaacplus_dec->aac_config.down_sample_flag = 0;
389 p_obj_exhaacplus_dec->aac_config.header_dec_done = 0;
390 p_obj_exhaacplus_dec->aac_config.frame_status = 1;
391 p_obj_exhaacplus_dec->aac_config.ui_mp4_flag = 0;
392 p_obj_exhaacplus_dec->aac_config.ui_disable_sync = 0;
393 p_obj_exhaacplus_dec->aac_config.ui_auto_sbr_upsample = 1;
394 p_obj_exhaacplus_dec->aac_config.ui_samp_freq = 0;
395 p_obj_exhaacplus_dec->aac_config.ui_channel_mode = 3;
396 p_obj_exhaacplus_dec->aac_config.ui_sbr_mode = 0;
397 p_obj_exhaacplus_dec->aac_config.ui_effect_type = 0;
398 p_obj_exhaacplus_dec->aac_config.ui_target_loudness = -24;
399 p_obj_exhaacplus_dec->aac_config.ui_loud_norm_flag = 0;
400 p_obj_exhaacplus_dec->aac_config.ui_pce_found_in_hdr = 0;
401 p_obj_exhaacplus_dec->aac_config.loas_present = 0;
402 p_obj_exhaacplus_dec->aac_config.ld_decoder = 0;
403 p_obj_exhaacplus_dec->aac_config.ui_drc_enable = 1;
404 p_obj_exhaacplus_dec->aac_config.ui_drc_boost = 0;
405 p_obj_exhaacplus_dec->aac_config.ui_drc_cut = 0;
406 p_obj_exhaacplus_dec->aac_config.ui_drc_target_level = 108;
407 p_obj_exhaacplus_dec->aac_config.ui_drc_set = 0;
408 p_obj_exhaacplus_dec->aac_config.ui_flush_cmd = 0;
409
410 p_obj_exhaacplus_dec->aac_config.ui_max_channels = 6;
411
412 p_obj_exhaacplus_dec->aac_config.ui_coupling_channel = 0;
413 p_obj_exhaacplus_dec->aac_config.downmix = 0;
414 p_obj_exhaacplus_dec->aac_config.ui_n_channels = 2;
415 p_obj_exhaacplus_dec->aac_config.i_channel_mask = 3;
416
417 {
418 ia_aac_dec_tables_struct *pstr_aac_tables =
419 &p_obj_exhaacplus_dec->aac_tables;
420 pstr_aac_tables->pstr_huffmann_tables =
421 (ia_aac_dec_huffman_tables_struct
422 *)&ixheaacd_aac_huffmann_tables;
423 pstr_aac_tables->pstr_block_tables =
424 (ia_aac_dec_block_tables_struct *)&ixheaacd_aac_block_tables;
425 pstr_aac_tables->pstr_imdct_tables =
426 (ia_aac_dec_imdct_tables_struct *)&ixheaacd_imdct_tables;
427
428 ixheaacd_huff_tables_create(pstr_aac_tables);
429 }
430 ixheaacd_init_sbr_tables(&p_obj_exhaacplus_dec->str_sbr_tables);
431 p_obj_exhaacplus_dec->common_tables =
432 (ixheaacd_misc_tables *)&ixheaacd_str_fft_n_transcendent_tables;
433 p_obj_exhaacplus_dec->aac_config.ui_qmf_bands = 64;
434
435 break;
436 }
437 case IA_CMD_TYPE_INIT_API_POST_CONFIG_PARAMS: {
438 ixheaacd_fill_aac_mem_tables(p_obj_exhaacplus_dec);
439 break;
440 }
441 case IA_CMD_TYPE_INIT_PROCESS: {
442 WORD32 err_code = 0;
443 if (p_obj_exhaacplus_dec->p_state_aac->fatal_err_present) {
444 err_code = IA_FATAL_ERROR;
445 } else {
446 err_code = ixheaacd_dec_init(p_obj_exhaacplus_dec);
447 }
448 if (err_code != 0) {
449 if (err_code < 0)
450 p_obj_exhaacplus_dec->p_state_aac->fatal_err_present = 1;
451 p_obj_exhaacplus_dec->p_state_aac->i_bytes_consumed =
452 p_obj_exhaacplus_dec->p_state_aac->ui_in_bytes;
453 }
454 return err_code;
455 break;
456 }
457 case IA_CMD_TYPE_INIT_DONE_QUERY: {
458 if (p_obj_exhaacplus_dec->p_state_aac->ui_init_done == 1) {
459 *pui_value = 1;
460 } else {
461 *pui_value = 0;
462 }
463 break;
464 }
465
466 case IA_CMD_TYPE_GA_HDR: {
467 return ixheaacd_decoder_2_ga_hdr(p_obj_exhaacplus_dec);
468 break;
469 }
470
471 case IA_CMD_TYPE_FLUSH_MEM: {
472 return ixheaacd_decoder_flush_api(p_obj_exhaacplus_dec);
473 break;
474 }
475
476 default: {
477 return IA_ENHAACPLUS_DEC_API_NONFATAL_CMD_TYPE_NOT_SUPPORTED;
478 }
479 };
480 break;
481 }
482 case IA_API_CMD_SET_CONFIG_PARAM: {
483 switch (i_idx) {
484 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_SAMP_FREQ: {
485 if ((*pui_value < 8000) || (*pui_value > 96000)) {
486 return (IA_ENHAACPLUS_DEC_CONFIG_FATAL_INVALID_SAMPLE_RATE);
487 }
488 p_obj_exhaacplus_dec->aac_config.ui_samp_freq = *pui_value;
489 break;
490 }
491 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_PCM_WDSZ: {
492 if ((*pui_value != 16) && (*pui_value != 24)) {
493 p_obj_exhaacplus_dec->aac_config.ui_pcm_wdsz = 16;
494 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_PCM_WDSZ);
495 }
496 p_obj_exhaacplus_dec->aac_config.ui_pcm_wdsz = *pui_value;
497 break;
498 }
499 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_DOWNMIX: {
500 if ((*pui_value != 1) && (*pui_value != 0)) {
501 p_obj_exhaacplus_dec->aac_config.flag_downmix = 0;
502 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_DOWNMIX);
503 }
504 p_obj_exhaacplus_dec->aac_config.flag_downmix = *pui_value;
505 p_obj_exhaacplus_dec->aac_config.downmix = *pui_value;
506 break;
507 }
508
509 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_TOSTEREO: {
510 if ((*pui_value != 1) && (*pui_value != 0)) {
511 p_obj_exhaacplus_dec->aac_config.flag_to_stereo = 1;
512 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_TOSTEREO);
513 }
514 p_obj_exhaacplus_dec->aac_config.flag_to_stereo = *pui_value;
515 break;
516 }
517 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_DSAMPLE: {
518 if ((*pui_value != 1) && (*pui_value != 0)) {
519 p_obj_exhaacplus_dec->aac_config.down_sample_flag = 0;
520 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_DSAMPLE);
521 }
522 p_obj_exhaacplus_dec->aac_config.down_sample_flag = *pui_value;
523 break;
524 }
525
526 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_FRAMEOK: {
527 if ((*pui_value != 1) && (*pui_value != 0)) {
528 p_obj_exhaacplus_dec->aac_config.frame_status = 1;
529 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_FRAMEOK);
530 }
531 p_obj_exhaacplus_dec->aac_config.frame_status = *pui_value;
532 break;
533 }
534
535 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_ISMP4: {
536 if ((*pui_value != 1) && (*pui_value != 0)) {
537 p_obj_exhaacplus_dec->aac_config.ui_mp4_flag = 0;
538 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_MP4FLAG);
539 }
540 p_obj_exhaacplus_dec->aac_config.ui_mp4_flag = *pui_value;
541 break;
542 }
543 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_ISLOAS: {
544 if ((*pui_value != 1) && (*pui_value != 0)) {
545 p_obj_exhaacplus_dec->aac_config.loas_present = 0;
546 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_LOASFLAG);
547 }
548 p_obj_exhaacplus_dec->aac_config.loas_present = *pui_value;
549 break;
550 }
551 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_DRC_ENABLE: {
552 if ((*pui_value != 1) && (*pui_value != 0)) {
553 p_obj_exhaacplus_dec->aac_config.ui_drc_enable = 0;
554 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_DRCFLAG);
555 }
556 p_obj_exhaacplus_dec->aac_config.ui_drc_enable = *pui_value;
557 break;
558 }
559 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_DRC_CUT: {
560 p_obj_exhaacplus_dec->aac_config.ui_drc_set = 1;
561 if (*pui_value > 127) {
562 p_obj_exhaacplus_dec->aac_config.ui_drc_cut = 0;
563 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_DRC_CUT);
564 }
565 p_obj_exhaacplus_dec->aac_config.ui_drc_cut =
566 (WORD32)((*pui_value / 127.0) * 100);
567 break;
568 }
569
570 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_DRC_BOOST: {
571 p_obj_exhaacplus_dec->aac_config.ui_drc_set = 1;
572 if (*pui_value > 127) {
573 p_obj_exhaacplus_dec->aac_config.ui_drc_boost = 0;
574 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_DRC_BOOST);
575 }
576 p_obj_exhaacplus_dec->aac_config.ui_drc_boost =
577 (WORD32)((*pui_value / 127.0) * 100);
578 break;
579 }
580
581 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_DRC_TARGET_LEVEL: {
582 p_obj_exhaacplus_dec->aac_config.ui_drc_set = 1;
583 if (*pui_value > 127) {
584 p_obj_exhaacplus_dec->aac_config.ui_drc_target_level = 108;
585 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_DRC_TARGET);
586 }
587 p_obj_exhaacplus_dec->aac_config.ui_drc_target_level = *pui_value;
588 break;
589 }
590 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_DRC_HEAVY_COMP: {
591 p_obj_exhaacplus_dec->aac_config.ui_drc_set = 1;
592 if ((*pui_value != 1) && (*pui_value != 0)) {
593 p_obj_exhaacplus_dec->aac_config.ui_drc_heavy_comp = 0;
594 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_DRCFLAG);
595 }
596 p_obj_exhaacplus_dec->aac_config.ui_drc_heavy_comp = *pui_value;
597 break;
598 }
599 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_DISABLE_SYNC: {
600 if ((*pui_value != 1) && (*pui_value != 0)) {
601 p_obj_exhaacplus_dec->aac_config.ui_disable_sync = 0;
602 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_SYNCFLAG);
603 }
604 p_obj_exhaacplus_dec->aac_config.ui_disable_sync = *pui_value;
605 break;
606 }
607 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_AUTO_SBR_UPSAMPLE: {
608 if ((*pui_value != 1) && (*pui_value != 0)) {
609 p_obj_exhaacplus_dec->aac_config.ui_auto_sbr_upsample = 0;
610 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_SBRUPFLAG);
611 }
612 p_obj_exhaacplus_dec->aac_config.ui_auto_sbr_upsample = *pui_value;
613 break;
614 }
615 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_MAX_CHANNEL: {
616 if (*pui_value > 8) {
617 p_obj_exhaacplus_dec->aac_config.ui_max_channels = 8;
618 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_MAX_CHANNEL);
619 }
620 if (*pui_value < 2) {
621 p_obj_exhaacplus_dec->aac_config.ui_max_channels = 2;
622 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_MAX_CHANNEL);
623 }
624 p_obj_exhaacplus_dec->aac_config.ui_max_channels = *pui_value;
625 break;
626 }
627 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_FRAMESIZE: {
628 if (*pui_value == 1) {
629 p_obj_exhaacplus_dec->aac_config.framesize_480 = 1;
630 } else if (*pui_value == 0) {
631 p_obj_exhaacplus_dec->aac_config.framesize_480 = 0;
632 } else {
633 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_FRAMSZ);
634 }
635 break;
636 }
637
638 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_LD_TESTING: {
639 if (*pui_value == 1) {
640 p_obj_exhaacplus_dec->aac_config.ld_decoder = 1;
641 } else if (*pui_value == 0) {
642 p_obj_exhaacplus_dec->aac_config.ld_decoder = 0;
643 } else {
644 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_LD_CONFIG);
645 }
646 break;
647 }
648
649 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_ELD_SBR_PRESENT: {
650 if (*pui_value == 1) {
651 p_obj_exhaacplus_dec->aac_config.eld_sbr_present = 1;
652 } else if (*pui_value == 0) {
653 p_obj_exhaacplus_dec->aac_config.eld_sbr_present = 0;
654 } else {
655 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_ELDSBR);
656 }
657 break;
658 }
659 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_COUP_CHANNEL: {
660 if (*pui_value > 16) {
661 p_obj_exhaacplus_dec->aac_config.ui_coupling_channel = 1;
662 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_COUP_CHANNEL);
663 }
664 p_obj_exhaacplus_dec->aac_config.ui_coupling_channel = *pui_value;
665 break;
666 }
667
668 case IA_ENHAACPLUS_DEC_CONFIG_PARAM_DOWNMIX_STEREO: {
669 if ((*pui_value != 1) && (*pui_value != 0)) {
670 p_obj_exhaacplus_dec->aac_config.downmix = 0;
671 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_DOWNMIX);
672 }
673 p_obj_exhaacplus_dec->aac_config.downmix = *pui_value;
674 break;
675 }
676
677 case IA_ENHAACPLUS_DEC_DRC_EFFECT_TYPE: {
678 if (((*pui_value_signed) > 8) || ((*pui_value_signed) < -1)) {
679 p_obj_exhaacplus_dec->aac_config.ui_effect_type = -1;
680 return (IA_ENHAACPLUS_DEC_CONFIG_NON_FATAL_INVALID_EFFECT_TYPE);
681 }
682 p_obj_exhaacplus_dec->aac_config.ui_effect_type = *pui_value_signed;
683 break;
684 }
685 case IA_ENHAACPLUS_DEC_DRC_TARGET_LOUDNESS: {
686 if (*pui_value_signed >= 0) {
687 p_obj_exhaacplus_dec->aac_config.ui_loud_norm_flag = 1;
688 }
689 *pui_value_signed = -(*pui_value_signed >> 2);
690 if (((*pui_value_signed) > 0) || ((*pui_value_signed) < -63)) {
691 p_obj_exhaacplus_dec->aac_config.ui_target_loudness = 0;
692 return (IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_TARGET_LOUDNESS);
693 }
694 p_obj_exhaacplus_dec->aac_config.ui_target_loudness =
695 *pui_value_signed;
696 break;
697 }
698 default: { return IA_ENHAACPLUS_DEC_API_FATAL_INVALID_CONFIG_PARAM; }
699 }
700 break;
701 }
702
703 case IA_API_CMD_GET_CONFIG_PARAM: {
704 UWORD32 i;
705 WORD32 *pvalue =
706 (WORD32 *)(&p_obj_exhaacplus_dec->aac_config.ui_pcm_wdsz);
707
708 if (i_idx >= 0 && i_idx <= 8) {
709 *pui_value = pvalue[i_idx];
710 } else if (IA_ENHAACPLUS_DEC_CONFIG_GET_NUM_PRE_ROLL_FRAMES == i_idx) {
711 WORD32 *ptri_value = (WORD32 *)pv_value;
712 ia_audio_specific_config_struct *ptr_audio_specific_config =
713 ((ia_audio_specific_config_struct *)
714 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config);
715
716 for (i = 0; i < MAX_AUDIO_PREROLLS + 1; i++) {
717 if (ptr_audio_specific_config->str_usac_config.str_usac_dec_config
718 .preroll_bytes[i] == 0) {
719 break;
720 }
721 }
722
723 *ptri_value = i;
724 } else if (IA_ENHAACPLUS_DEC_CONFIG_EXT_ELE_PTR == i_idx) {
725 ia_audio_specific_config_struct *ptr_audio_specific_config =
726 ((ia_audio_specific_config_struct *)
727 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config);
728
729 for (i = 0; i < ptr_audio_specific_config->str_usac_config
730 .str_usac_dec_config.num_config_extensions;
731 i++) {
732 pp_value[i] = ptr_audio_specific_config->str_usac_config
733 .str_usac_dec_config.usac_cfg_ext_info_buf[i];
734 }
735
736 for (i = 0; i < ptr_audio_specific_config->str_usac_config
737 .str_usac_dec_config.num_elements;
738 i++) {
739 if (ptr_audio_specific_config->str_usac_config.str_usac_dec_config
740 .usac_ext_ele_payload_present[i]) {
741 pp_value[i + 16] =
742 ptr_audio_specific_config->str_usac_config.str_usac_dec_config
743 .usac_ext_ele_payload_buf[i];
744 }
745 }
746 } else if (IA_ENHAACPLUS_DEC_CONFIG_EXT_ELE_BUF_SIZES == i_idx) {
747 WORD32 *ptri_value = (WORD32 *)pv_value;
748 ia_audio_specific_config_struct *ptr_audio_specific_config =
749 ((ia_audio_specific_config_struct *)
750 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config);
751 for (i = 0; i < ptr_audio_specific_config->str_usac_config
752 .str_usac_dec_config.num_config_extensions;
753 i++) {
754 ptri_value[i] = ptr_audio_specific_config->str_usac_config
755 .str_usac_dec_config.usac_cfg_ext_info_len[i];
756 }
757 for (i = 0; i < ptr_audio_specific_config->str_usac_config
758 .str_usac_dec_config.num_elements;
759 i++) {
760 ptri_value[i + 16] =
761 ptr_audio_specific_config->str_usac_config.str_usac_dec_config
762 .usac_ext_ele_payload_len[i];
763 }
764
765 } else if (IA_ENHAACPLUS_DEC_CONFIG_NUM_ELE == i_idx) {
766 UWORD32 *ptri_value = (UWORD32 *)pv_value;
767 ia_audio_specific_config_struct *ptr_audio_specific_config =
768 ((ia_audio_specific_config_struct *)
769 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config);
770 *ptri_value = ptr_audio_specific_config->str_usac_config
771 .str_usac_dec_config.num_elements;
772
773 } else if (IA_ENHAACPLUS_DEC_CONFIG_NUM_CONFIG_EXT == i_idx) {
774 UWORD32 *ptri_value = (UWORD32 *)pv_value;
775 ia_audio_specific_config_struct *ptr_audio_specific_config =
776 ((ia_audio_specific_config_struct *)
777 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config);
778 *ptri_value = ptr_audio_specific_config->str_usac_config
779 .str_usac_dec_config.num_config_extensions;
780 } else if (IA_ENHAACPLUS_DEC_CONFIG_GAIN_PAYLOAD_LEN == i_idx) {
781 UWORD32 *ptri_value = (UWORD32 *)pv_value;
782 ia_audio_specific_config_struct *ptr_audio_specific_config =
783 ((ia_audio_specific_config_struct *)
784 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config);
785 WORD32 preroll_counter = ptr_audio_specific_config->str_usac_config
786 .str_usac_dec_config.preroll_counter;
787 *ptri_value =
788 ptr_audio_specific_config->str_usac_config.str_usac_dec_config
789 .usac_ext_gain_payload_len[preroll_counter];
790 } else if (IA_ENHAACPLUS_DEC_CONFIG_GAIN_PAYLOAD_BUF == i_idx) {
791 WORD32 payload_buffer_offeset = 0;
792 ia_audio_specific_config_struct *ptr_audio_specific_config =
793 ((ia_audio_specific_config_struct *)
794 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config);
795 WORD32 preroll_counter = ptr_audio_specific_config->str_usac_config
796 .str_usac_dec_config.preroll_counter;
797 for (i = 0; i < (UWORD32)preroll_counter; i++)
798 payload_buffer_offeset +=
799 ptr_audio_specific_config->str_usac_config.str_usac_dec_config
800 .usac_ext_gain_payload_len[i] *
801 sizeof(WORD8);
802 *pp_value = ptr_audio_specific_config->str_usac_config
803 .str_usac_dec_config.usac_ext_gain_payload_buf +
804 payload_buffer_offeset;
805 }
806
807 else {
808 return IA_ENHAACPLUS_DEC_API_FATAL_INVALID_CONFIG_PARAM;
809 }
810 break;
811 }
812
813 case IA_API_CMD_GET_MEMTABS_SIZE: {
814 *pui_value = (sizeof(ia_mem_info_struct) + sizeof(pVOID *)) *
815 (IA_ENHAACPDEC_NUM_MEMTABS);
816 break;
817 }
818 case IA_API_CMD_SET_MEMTABS_PTR: {
819 if (pv_value == NULL) return IA_ENHAACPLUS_DEC_API_FATAL_MEM_ALLOC;
820 memset(pv_value, 0, (sizeof(ia_mem_info_struct) + sizeof(pVOID *)) *
821 (IA_ENHAACPDEC_NUM_MEMTABS));
822
823 p_obj_exhaacplus_dec->p_mem_info_aac = pv_value;
824 p_obj_exhaacplus_dec->pp_mem_aac =
825 (pVOID *)((WORD8 *)pv_value +
826 sizeof(ia_mem_info_struct) * IA_ENHAACPDEC_NUM_MEMTABS);
827
828 break;
829 }
830 case IA_API_CMD_GET_N_MEMTABS: {
831 *pui_value = IA_ENHAACPDEC_NUM_MEMTABS;
832 break;
833 }
834
835 case IA_API_CMD_GET_N_TABLES: {
836 *pui_value = NUM_AAC_TABLES;
837 break;
838 }
839 case IA_API_CMD_EXECUTE: {
840 switch (i_idx) {
841 case IA_CMD_TYPE_DO_EXECUTE: {
842 WORD32 err_code = 0;
843 if (!p_obj_exhaacplus_dec->p_state_aac->ui_init_done ||
844 p_obj_exhaacplus_dec->p_state_aac->fatal_err_present) {
845 err_code = IA_FATAL_ERROR;
846 } else {
847 err_code = ixheaacd_dec_execute(p_obj_exhaacplus_dec);
848 }
849 if (err_code != IA_NO_ERROR) {
850 if (err_code < 0)
851 p_obj_exhaacplus_dec->p_state_aac->fatal_err_present = 1;
852 p_obj_exhaacplus_dec->p_state_aac->i_bytes_consumed =
853 p_obj_exhaacplus_dec->p_state_aac->ui_in_bytes;
854 }
855 return err_code;
856 break;
857 }
858 case IA_CMD_TYPE_DONE_QUERY: {
859 if (p_obj_exhaacplus_dec->p_state_aac->ui_input_over == 1) {
860 *pui_value = 1;
861 } else {
862 *pui_value = 0;
863 }
864
865 break;
866 }
867 default: { return IA_ENHAACPLUS_DEC_API_FATAL_INVALID_EXECUTE_TYPE; }
868 };
869 break;
870 }
871 case IA_API_CMD_GET_CURIDX_INPUT_BUF: {
872 *pui_value = p_obj_exhaacplus_dec->p_state_aac->i_bytes_consumed;
873 break;
874 }
875 case IA_API_CMD_SET_INPUT_BYTES: {
876 p_obj_exhaacplus_dec->p_state_aac->ui_in_bytes = *pui_value;
877 break;
878 }
879 case IA_API_CMD_GET_OUTPUT_BYTES: {
880 if (p_obj_exhaacplus_dec->p_state_aac->audio_object_type == AOT_USAC) {
881 ia_audio_specific_config_struct *ptr_audio_specific_config =
882 ((ia_audio_specific_config_struct *)
883 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config);
884
885 WORD32 preroll_counter = ptr_audio_specific_config->str_usac_config
886 .str_usac_dec_config.preroll_counter;
887
888 *pui_value = ptr_audio_specific_config->str_usac_config
889 .str_usac_dec_config.preroll_bytes[preroll_counter];
890
891 preroll_counter++;
892 if (preroll_counter > (MAX_AUDIO_PREROLLS + 1)) return IA_FATAL_ERROR;
893 ptr_audio_specific_config->str_usac_config.str_usac_dec_config
894 .preroll_counter = preroll_counter;
895 } else {
896 *pui_value = p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes;
897 }
898 break;
899 }
900 case IA_API_CMD_INPUT_OVER: {
901 p_obj_exhaacplus_dec->p_state_aac->ui_input_over = 1;
902 break;
903 }
904 default: { return IA_ENHAACPLUS_DEC_API_FATAL_INVALID_CMD; }
905 };
906 return IA_NO_ERROR;
907 }
908
ixheaacd_decoder_2_ga_hdr(ia_exhaacplus_dec_api_struct * p_obj_exhaacplus_dec)909 IA_ERRORCODE ixheaacd_decoder_2_ga_hdr(
910 ia_exhaacplus_dec_api_struct *p_obj_exhaacplus_dec) {
911 if (p_obj_exhaacplus_dec->aac_config.ui_flush_cmd == 0) {
912 p_obj_exhaacplus_dec->aac_config.ui_pcm_wdsz = 16;
913 p_obj_exhaacplus_dec->aac_config.flag_downmix = 0;
914 p_obj_exhaacplus_dec->aac_config.flag_08khz_out = 0;
915 p_obj_exhaacplus_dec->aac_config.flag_16khz_out = 0;
916 p_obj_exhaacplus_dec->aac_config.flag_to_stereo = 0;
917 p_obj_exhaacplus_dec->aac_config.down_sample_flag = 0;
918 p_obj_exhaacplus_dec->aac_config.header_dec_done = 0;
919 p_obj_exhaacplus_dec->aac_config.frame_status = 1;
920 p_obj_exhaacplus_dec->aac_config.ui_mp4_flag = 1;
921 p_obj_exhaacplus_dec->aac_config.ui_disable_sync = 0;
922 p_obj_exhaacplus_dec->aac_config.ui_auto_sbr_upsample = 1;
923 p_obj_exhaacplus_dec->aac_config.ui_samp_freq = 0;
924 p_obj_exhaacplus_dec->aac_config.ui_channel_mode = 3;
925 p_obj_exhaacplus_dec->aac_config.ui_sbr_mode = 2;
926 p_obj_exhaacplus_dec->aac_config.ui_pce_found_in_hdr = 0;
927 p_obj_exhaacplus_dec->aac_config.loas_present = 0;
928
929 p_obj_exhaacplus_dec->aac_config.ui_drc_enable = 1;
930 p_obj_exhaacplus_dec->aac_config.ui_drc_boost = 0;
931 p_obj_exhaacplus_dec->aac_config.ui_drc_cut = 0;
932 p_obj_exhaacplus_dec->aac_config.ui_drc_target_level = 108;
933 p_obj_exhaacplus_dec->aac_config.ui_drc_set = 0;
934 p_obj_exhaacplus_dec->aac_config.ui_flush_cmd = 1;
935
936 p_obj_exhaacplus_dec->aac_config.ui_max_channels = 6;
937
938 p_obj_exhaacplus_dec->aac_config.ui_coupling_channel = 0;
939 p_obj_exhaacplus_dec->aac_config.downmix = 0;
940
941 {
942 ia_aac_dec_tables_struct *pstr_aac_tables =
943 &p_obj_exhaacplus_dec->aac_tables;
944 pstr_aac_tables->pstr_huffmann_tables =
945 (ia_aac_dec_huffman_tables_struct *)&ixheaacd_aac_huffmann_tables;
946 pstr_aac_tables->pstr_block_tables =
947 (ia_aac_dec_block_tables_struct *)&ixheaacd_aac_block_tables;
948 pstr_aac_tables->pstr_imdct_tables =
949 (ia_aac_dec_imdct_tables_struct *)&ixheaacd_imdct_tables;
950
951 ixheaacd_huff_tables_create(pstr_aac_tables);
952 }
953 ixheaacd_init_sbr_tables(&p_obj_exhaacplus_dec->str_sbr_tables);
954 p_obj_exhaacplus_dec->common_tables =
955 (ixheaacd_misc_tables *)&ixheaacd_str_fft_n_transcendent_tables;
956 p_obj_exhaacplus_dec->aac_config.ui_qmf_bands = 64;
957 p_obj_exhaacplus_dec->p_state_aac->ui_init_done = 0;
958
959 return ixheaacd_dec_init(p_obj_exhaacplus_dec);
960 } else {
961 p_obj_exhaacplus_dec->aac_config.ui_flush_cmd = 0;
962 return ixheaacd_dec_init(p_obj_exhaacplus_dec);
963 }
964 }
965
ixheaacd_decoder_flush_api(ia_exhaacplus_dec_api_struct * p_obj_exhaacplus_dec)966 IA_ERRORCODE ixheaacd_decoder_flush_api(
967 ia_exhaacplus_dec_api_struct *p_obj_exhaacplus_dec) {
968 UWORD8 *header_temp_ptr;
969 WORD32 header_length;
970 if (p_obj_exhaacplus_dec->aac_config.ui_flush_cmd == 0) {
971 header_temp_ptr = p_obj_exhaacplus_dec->p_state_aac->header_ptr;
972 header_length = p_obj_exhaacplus_dec->p_state_aac->header_length;
973 memset(p_obj_exhaacplus_dec->p_state_aac, 0,
974 sizeof(ia_aac_dec_state_struct));
975 {
976 pUWORD8 p_temp = (pUWORD8)p_obj_exhaacplus_dec->p_state_aac;
977 UWORD32 *meminfo = (UWORD32 *)p_obj_exhaacplus_dec->p_mem_info_aac;
978 UWORD32 pers_size = meminfo[0];
979 p_temp = p_temp + pers_size -
980 (sizeof(ia_dec_data_struct) +
981 sizeof(ia_audio_specific_config_struct) + (8300));
982
983 p_obj_exhaacplus_dec->p_state_aac->pstr_dec_data = p_temp;
984 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config =
985 p_temp + sizeof(ia_dec_data_struct);
986 p_obj_exhaacplus_dec->p_state_aac->header_ptr =
987 p_temp + sizeof(ia_dec_data_struct) +
988 sizeof(ia_audio_specific_config_struct);
989 }
990 memset(&(p_obj_exhaacplus_dec->aac_config), 0,
991 sizeof(ia_aac_dec_config_struct));
992
993 p_obj_exhaacplus_dec->aac_config.ui_pcm_wdsz = 16;
994 p_obj_exhaacplus_dec->aac_config.flag_downmix = 0;
995 p_obj_exhaacplus_dec->aac_config.flag_08khz_out = 0;
996 p_obj_exhaacplus_dec->aac_config.flag_16khz_out = 0;
997 p_obj_exhaacplus_dec->aac_config.flag_to_stereo = 0;
998 p_obj_exhaacplus_dec->aac_config.down_sample_flag = 0;
999 p_obj_exhaacplus_dec->aac_config.header_dec_done = 0;
1000 p_obj_exhaacplus_dec->aac_config.frame_status = 1;
1001 p_obj_exhaacplus_dec->aac_config.ui_mp4_flag = 1;
1002 p_obj_exhaacplus_dec->aac_config.ui_disable_sync = 0;
1003 p_obj_exhaacplus_dec->aac_config.ui_auto_sbr_upsample = 1;
1004 p_obj_exhaacplus_dec->aac_config.ui_samp_freq = 0;
1005 p_obj_exhaacplus_dec->aac_config.ui_channel_mode = 3;
1006 p_obj_exhaacplus_dec->aac_config.ui_sbr_mode = 2;
1007 p_obj_exhaacplus_dec->aac_config.ui_pce_found_in_hdr = 0;
1008 p_obj_exhaacplus_dec->aac_config.loas_present = 0;
1009
1010 p_obj_exhaacplus_dec->aac_config.ui_drc_enable = 1;
1011 p_obj_exhaacplus_dec->aac_config.ui_drc_boost = 0;
1012 p_obj_exhaacplus_dec->aac_config.ui_drc_cut = 0;
1013 p_obj_exhaacplus_dec->aac_config.ui_drc_target_level = 108;
1014 p_obj_exhaacplus_dec->aac_config.ui_drc_set = 0;
1015 p_obj_exhaacplus_dec->aac_config.ui_flush_cmd = 1;
1016
1017 p_obj_exhaacplus_dec->aac_config.ui_max_channels = 6;
1018
1019 p_obj_exhaacplus_dec->aac_config.ui_coupling_channel = 0;
1020 p_obj_exhaacplus_dec->aac_config.downmix = 0;
1021
1022 {
1023 ia_aac_dec_tables_struct *pstr_aac_tables =
1024 &p_obj_exhaacplus_dec->aac_tables;
1025 pstr_aac_tables->pstr_huffmann_tables =
1026 (ia_aac_dec_huffman_tables_struct *)&ixheaacd_aac_huffmann_tables;
1027 pstr_aac_tables->pstr_block_tables =
1028 (ia_aac_dec_block_tables_struct *)&ixheaacd_aac_block_tables;
1029 pstr_aac_tables->pstr_imdct_tables =
1030 (ia_aac_dec_imdct_tables_struct *)&ixheaacd_imdct_tables;
1031
1032 ixheaacd_huff_tables_create(pstr_aac_tables);
1033 }
1034 ixheaacd_init_sbr_tables(&p_obj_exhaacplus_dec->str_sbr_tables);
1035 p_obj_exhaacplus_dec->common_tables =
1036 (ixheaacd_misc_tables *)&ixheaacd_str_fft_n_transcendent_tables;
1037 p_obj_exhaacplus_dec->aac_config.ui_qmf_bands = 64;
1038 p_obj_exhaacplus_dec->p_state_aac->header_ptr = header_temp_ptr;
1039 p_obj_exhaacplus_dec->p_state_aac->ui_in_bytes = header_length;
1040 p_obj_exhaacplus_dec->p_state_aac->header_length = header_length;
1041
1042 return ixheaacd_dec_init(p_obj_exhaacplus_dec);
1043
1044 } else {
1045 p_obj_exhaacplus_dec->aac_config.ui_flush_cmd = 0;
1046 return ixheaacd_dec_init(p_obj_exhaacplus_dec);
1047 }
1048 }
1049
1050 static PLATFORM_INLINE WORD32
ixheaacd_persistent_buffer_sizes(WORD32 num_channel)1051 ixheaacd_persistent_buffer_sizes(WORD32 num_channel) {
1052 WORD32 size_buffers = 0;
1053
1054 WORD32 temp;
1055 WORD32 max_channels;
1056
1057 size_buffers += 4 * 512 * num_channel * sizeof(WORD32);
1058
1059 size_buffers += (ltp_buffer_size * num_channel * sizeof(WORD16));
1060
1061 if (num_channel > 2) {
1062 max_channels = MAX_BS_ELEMENT;
1063 } else {
1064 max_channels = 2;
1065 }
1066 size_buffers +=
1067 (max_channels)*2 * ALIGN_SIZE64(sizeof(ia_aac_dec_sbr_bitstream_struct));
1068
1069 size_buffers += ALIGN_SIZE64(MAXSBRBYTES) * num_channel * sizeof(WORD8);
1070
1071 size_buffers += num_channel *
1072 (QMF_FILTER_STATE_ANA_SIZE + 2 * NO_ANALYSIS_CHANNELS) *
1073 sizeof(WORD16);
1074
1075 size_buffers += num_channel *
1076 (QMF_FILTER_STATE_ANA_SIZE + 2 * NO_ANALYSIS_CHANNELS) *
1077 sizeof(WORD32);
1078
1079 size_buffers += num_channel *
1080 (QMF_FILTER_STATE_SYN_SIZE + 2 * NO_SYNTHESIS_CHANNELS) *
1081 sizeof(WORD16);
1082
1083 size_buffers += num_channel *
1084 (QMF_FILTER_STATE_SYN_SIZE + 2 * NO_SYNTHESIS_CHANNELS) *
1085 sizeof(WORD32);
1086
1087 if (num_channel <= 2) {
1088 size_buffers +=
1089 num_channel * 2 * MAX_OV_COLS * NO_SYNTHESIS_CHANNELS * sizeof(WORD32);
1090 } else {
1091 size_buffers +=
1092 num_channel * MAX_OV_COLS * NO_SYNTHESIS_CHANNELS * sizeof(WORD32);
1093 }
1094
1095 size_buffers +=
1096 LPC_ORDER * num_channel * NO_ANALYSIS_CHANNELS * sizeof(WORD32);
1097
1098 if (num_channel <= 2) {
1099 size_buffers +=
1100 LPC_ORDER * num_channel * NO_ANALYSIS_CHANNELS * sizeof(WORD32);
1101 }
1102
1103 size_buffers += num_channel * 3 * MAX_FREQ_COEFFS * sizeof(WORD16);
1104
1105 temp = sizeof(ia_freq_band_data_struct) +
1106 sizeof(ia_sbr_prev_frame_data_struct) + sizeof(ia_sbr_channel_struct) +
1107 sizeof(ia_sbr_header_data_struct);
1108 size_buffers += num_channel * ALIGN_SIZE64(temp);
1109
1110 size_buffers += MAX_BS_ELEMENT * sizeof(ixheaac_drc_bs_data_struct *);
1111
1112 if (num_channel <= 2) {
1113 size_buffers += sizeof(ia_ps_dec_struct);
1114 }
1115
1116 {
1117 WORD32 temp_size = 0;
1118 size_buffers +=
1119 MAXNRSBRCHANNELS * (sizeof(ia_sbr_frame_info_data_struct) +
1120 MAX_FREQ_COEFFS * sizeof(WORD32) * 2 + 8);
1121 temp_size += sizeof(ia_pvc_data_struct);
1122 temp_size += sizeof(ia_esbr_hbe_txposer_struct) * 2;
1123 temp_size += (MAX_HBE_PERSISTENT_SIZE * 2);
1124 temp_size += (MAX_QMF_BUF_LEN * 2 * 2 * sizeof(FLOAT32 *));
1125 temp_size += (MAX_QMF_BUF_LEN * MAX_QMF_BUF_LEN * 2 * 2 * sizeof(FLOAT32));
1126 size_buffers += temp_size * num_channel;
1127 }
1128
1129 return (size_buffers);
1130 }
1131
ixheaacd_fill_aac_mem_tables(ia_exhaacplus_dec_api_struct * p_obj_exhaacplus_dec)1132 VOID ixheaacd_fill_aac_mem_tables(
1133 ia_exhaacplus_dec_api_struct *p_obj_exhaacplus_dec) {
1134 ia_mem_info_struct *p_mem_info_aac;
1135
1136 WORD32 num_channels;
1137 WORD32 channels;
1138 WORD32 buffer_size;
1139
1140 if (p_obj_exhaacplus_dec->aac_config.ui_max_channels > 2) {
1141 num_channels = (p_obj_exhaacplus_dec->aac_config.ui_max_channels + 1);
1142 } else
1143
1144 {
1145 num_channels = p_obj_exhaacplus_dec->aac_config.ui_max_channels;
1146 }
1147
1148 channels = num_channels;
1149 buffer_size = ixheaacd_persistent_buffer_sizes(num_channels);
1150
1151 {
1152 p_mem_info_aac =
1153 &p_obj_exhaacplus_dec->p_mem_info_aac[IA_ENHAACPLUS_DEC_PERSIST_IDX];
1154 p_mem_info_aac->ui_size =
1155 sizeof(ia_aac_dec_state_struct) +
1156 channels * sizeof(struct ia_aac_persistent_struct) +
1157
1158 buffer_size + channels * ixheaacd_getsize_sbr_persistent() +
1159 channels * 16;
1160
1161 p_mem_info_aac->ui_size += sizeof(ia_dec_data_struct);
1162 p_mem_info_aac->ui_size += sizeof(ia_audio_specific_config_struct);
1163 p_mem_info_aac->ui_size += 8300;
1164
1165 p_mem_info_aac->ui_alignment = 8;
1166 p_mem_info_aac->ui_type = IA_MEMTYPE_PERSIST;
1167 }
1168
1169 {
1170 p_mem_info_aac =
1171 &p_obj_exhaacplus_dec->p_mem_info_aac[IA_ENHAACPLUS_DEC_SCRATCH_IDX];
1172
1173 {
1174 if (num_channels > 2) {
1175 WORD32 other_scr1;
1176 WORD32 other_scr2 = 0;
1177
1178 p_mem_info_aac->ui_size =
1179 2 * sizeof(WORD32) * IA_ENHAACPLUS_DEC_SAMPLES_PER_FRAME;
1180
1181 other_scr2 = 2 * sizeof(WORD32) * IA_ENHAACPLUS_DEC_SAMPLES_PER_FRAME;
1182
1183 other_scr1 = (4 * 1024);
1184
1185 if (MAX_CC_CHANNEL_NUM > 0) {
1186 other_scr1 +=
1187 sizeof(WORD16) * IA_ENHAACPLUS_DEC_SAMPLES_PER_FRAME * 2;
1188 other_scr1 += (4 * 1024);
1189
1190 other_scr1 += 4 * 12;
1191 }
1192
1193 p_mem_info_aac->ui_size += max(other_scr1, other_scr2);
1194
1195 } else {
1196 p_mem_info_aac->ui_size =
1197 2 * sizeof(WORD32) * IA_ENHAACPLUS_DEC_SAMPLES_PER_FRAME;
1198
1199 p_mem_info_aac->ui_size +=
1200 2 * sizeof(WORD32) * IA_ENHAACPLUS_DEC_SAMPLES_PER_FRAME;
1201
1202 p_mem_info_aac->ui_size +=
1203 sizeof(WORD32) * IA_ENHAACPLUS_DEC_SAMPLES_PER_FRAME;
1204 p_mem_info_aac->ui_size += 4 * 12;
1205
1206 p_mem_info_aac->ui_size +=
1207 ((IA_ENHAACPLUS_DEC_SAMPLES_PER_FRAME << 1) * sizeof(WORD32));
1208 p_mem_info_aac->ui_size +=
1209 ((IA_ENHAACPLUS_DEC_SAMPLES_PER_FRAME << 1) * sizeof(WORD32));
1210 p_mem_info_aac->ui_size +=
1211 2 * (sizeof(ia_sbr_frame_info_data_struct) + 232);
1212 }
1213 }
1214
1215 p_mem_info_aac->ui_size += 2200000 + 2048;
1216 p_mem_info_aac->ui_alignment = 8;
1217 p_mem_info_aac->ui_type = IA_MEMTYPE_SCRATCH;
1218 }
1219 {
1220 p_mem_info_aac =
1221 &p_obj_exhaacplus_dec->p_mem_info_aac[IA_ENHAACPLUS_DEC_INPUT_IDX];
1222
1223 p_mem_info_aac->ui_size = 8 * 1024 + 11;
1224
1225 p_mem_info_aac->ui_alignment = 8;
1226 p_mem_info_aac->ui_type = IA_MEMTYPE_INPUT;
1227 }
1228 {
1229 p_mem_info_aac =
1230 &p_obj_exhaacplus_dec->p_mem_info_aac[IA_ENHAACPLUS_DEC_OUTPUT_IDX];
1231 p_mem_info_aac->ui_size = IA_ENHAACPLUS_DEC_OUT_BUF_SIZE;
1232 p_mem_info_aac->ui_alignment = 8;
1233 p_mem_info_aac->ui_type = IA_MEMTYPE_OUTPUT;
1234 }
1235 return;
1236 }
1237
ixheaacd_dec_table_api(ia_exhaacplus_dec_api_struct * p_obj_exhaacplus_dec,WORD32 i_cmd,WORD32 i_idx,pVOID pv_value)1238 IA_ERRORCODE ixheaacd_dec_table_api(
1239 ia_exhaacplus_dec_api_struct *p_obj_exhaacplus_dec, WORD32 i_cmd,
1240 WORD32 i_idx, pVOID pv_value) {
1241 pUWORD32 pui_value = pv_value;
1242 pUWORD32 *p_pui_value = pv_value;
1243 SIZE_T ui_get_vals[5];
1244
1245 pVOID *table_ptrs[8];
1246 UWORD32 table_sizes[8] = {sizeof(ixheaacd_aac_huffmann_tables),
1247 sizeof(ixheaacd_aac_block_tables),
1248 sizeof(ixheaacd_imdct_tables),
1249 sizeof(ixheaacd_str_fft_n_transcendent_tables),
1250 sizeof(ixheaacd_aac_dec_env_calc_tables),
1251 sizeof(ixheaacd_aac_qmf_dec_tables),
1252 sizeof(ixheaacd_aac_dec_env_extr_tables),
1253 sizeof(ixheaacd_aac_dec_ps_tables)};
1254
1255 table_ptrs[0] =
1256 (pVOID *)&(p_obj_exhaacplus_dec->aac_tables.pstr_huffmann_tables);
1257 table_ptrs[1] =
1258 (pVOID *)&(p_obj_exhaacplus_dec->aac_tables.pstr_block_tables);
1259 table_ptrs[2] =
1260 (pVOID *)&(p_obj_exhaacplus_dec->aac_tables.pstr_imdct_tables);
1261 table_ptrs[3] = (pVOID *)&(p_obj_exhaacplus_dec->common_tables);
1262 table_ptrs[4] =
1263 (pVOID *)&p_obj_exhaacplus_dec->str_sbr_tables.env_calc_tables_ptr;
1264 table_ptrs[5] =
1265 (pVOID *)&p_obj_exhaacplus_dec->str_sbr_tables.qmf_dec_tables_ptr;
1266 table_ptrs[6] =
1267 (pVOID *)&p_obj_exhaacplus_dec->str_sbr_tables.env_extr_tables_ptr;
1268 table_ptrs[7] = (pVOID *)&p_obj_exhaacplus_dec->str_sbr_tables.ps_tables_ptr;
1269
1270 if (i_idx < 0 || i_idx >= NUM_AAC_TABLES) {
1271 return IA_ENHAACPLUS_DEC_API_FATAL_INVALID_MEMTAB_INDEX;
1272 }
1273
1274 ui_get_vals[0] = table_sizes[i_idx];
1275 ui_get_vals[1] = 4;
1276 ui_get_vals[4] = (SIZE_T)(*table_ptrs[i_idx]);
1277
1278 if (i_cmd == IA_API_CMD_SET_TABLE_PTR) {
1279 if (pv_value == 0) {
1280 return (IA_ENHAACPLUS_DEC_API_FATAL_MEM_ALLOC);
1281 }
1282 if (((SIZE_T)pv_value) & 3) {
1283 return IA_ENHAACPLUS_DEC_API_FATAL_MEM_ALIGN;
1284 }
1285
1286 *table_ptrs[i_idx] = pv_value;
1287
1288 if (i_idx == 0) {
1289 ixheaacd_huff_tables_create(&p_obj_exhaacplus_dec->aac_tables);
1290 }
1291
1292 }
1293
1294 else if (i_cmd == IA_API_CMD_GET_TABLE_PTR) {
1295 *p_pui_value = (UWORD32 *)((SIZE_T)(
1296 ui_get_vals[i_cmd - IA_API_CMD_GET_TABLE_INFO_SIZE]));
1297 } else {
1298 *pui_value = (WORD32)(ui_get_vals[i_cmd - IA_API_CMD_GET_TABLE_INFO_SIZE]);
1299 }
1300
1301 return IA_NO_ERROR;
1302 }
1303
ixheaacd_dec_init(ia_exhaacplus_dec_api_struct * p_obj_exhaacplus_dec)1304 IA_ERRORCODE ixheaacd_dec_init(
1305 ia_exhaacplus_dec_api_struct *p_obj_exhaacplus_dec) {
1306 FLAG frame_status = 1;
1307 WORD32 frame_size_1;
1308 WORD32 sample_rate_1;
1309 WORD16 num_channels_1;
1310 WORD32 ps_detected = 0;
1311 UWORD8 *in_buffer;
1312 WORD16 *time_data;
1313 WORD ch_idx;
1314 WORD sbr_present_flag = 0;
1315 ia_aac_dec_state_struct *p_state_enhaacplus_dec;
1316
1317 WORD32 error_code = IA_NO_ERROR;
1318 WORD32 persistent_used = 0;
1319 IA_ERRORCODE err_code = IA_NO_ERROR;
1320 struct ia_aac_persistent_struct *aac_persistent_mem;
1321 struct ia_sbr_pers_struct *sbr_persistent_mem;
1322 WORD32 ret_val;
1323
1324 p_obj_exhaacplus_dec->p_state_aac =
1325 p_obj_exhaacplus_dec->pp_mem_aac[IA_ENHAACPLUS_DEC_PERSIST_IDX];
1326
1327 if (p_obj_exhaacplus_dec->p_state_aac != NULL) {
1328 ret_val = setjmp(p_obj_exhaacplus_dec->p_state_aac->xaac_jmp_buf);
1329 if (ret_val != 0) {
1330 p_obj_exhaacplus_dec->p_state_aac->i_bytes_consumed =
1331 p_obj_exhaacplus_dec->p_state_aac->ui_in_bytes;
1332 p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes = 0;
1333 return IA_NO_ERROR;
1334 }
1335 }
1336
1337 time_data = (WORD16 *)(p_obj_exhaacplus_dec
1338 ->pp_mem_aac[IA_ENHAACPLUS_DEC_OUTPUT_IDX]);
1339
1340 if (p_obj_exhaacplus_dec->aac_config.ui_flush_cmd == 0) {
1341 in_buffer = p_obj_exhaacplus_dec->pp_mem_aac[IA_ENHAACPLUS_DEC_INPUT_IDX];
1342 } else {
1343 in_buffer = p_obj_exhaacplus_dec->p_state_aac->header_ptr;
1344 }
1345
1346 p_state_enhaacplus_dec = p_obj_exhaacplus_dec->p_state_aac;
1347
1348 p_state_enhaacplus_dec->aac_scratch_mem_v =
1349 p_obj_exhaacplus_dec->pp_mem_aac[IA_ENHAACPLUS_DEC_SCRATCH_IDX];
1350 p_obj_exhaacplus_dec->p_state_aac->huffman_code_book_scl =
1351 p_obj_exhaacplus_dec->aac_tables.pstr_huffmann_tables
1352 ->huffman_code_book_scl;
1353 p_obj_exhaacplus_dec->p_state_aac->huffman_code_book_scl_index =
1354 p_obj_exhaacplus_dec->aac_tables.pstr_huffmann_tables
1355 ->huffman_code_book_scl_index;
1356
1357 p_state_enhaacplus_dec->pstr_aac_tables = &p_obj_exhaacplus_dec->aac_tables;
1358 if (p_obj_exhaacplus_dec->aac_config.header_dec_done == 0) {
1359 WORD32 channels;
1360
1361 p_obj_exhaacplus_dec->p_state_aac->p_config =
1362 &p_obj_exhaacplus_dec->aac_config;
1363
1364 p_obj_exhaacplus_dec->p_state_aac->pstr_stream_sbr =
1365 (pVOID)((SIZE_T)((pWORD8)p_obj_exhaacplus_dec->p_state_aac +
1366 sizeof(ia_aac_dec_state_struct) + sizeof(SIZE_T) - 1) &
1367 (SIZE_T)(~(sizeof(SIZE_T) - 1)));
1368 if (p_obj_exhaacplus_dec->aac_config.ui_max_channels > 2) {
1369 p_state_enhaacplus_dec->aac_persistent_mem_v =
1370 (pVOID)((pWORD8)p_obj_exhaacplus_dec->p_state_aac->pstr_stream_sbr +
1371 (MAX_BS_ELEMENT)*2 *
1372 ALIGN_SIZE64(sizeof(ia_aac_dec_sbr_bitstream_struct)));
1373
1374 memset(p_obj_exhaacplus_dec->p_state_aac->pstr_stream_sbr, 0,
1375 (MAX_BS_ELEMENT)*2 *
1376 ALIGN_SIZE64(sizeof(ia_aac_dec_sbr_bitstream_struct)));
1377 } else {
1378 p_state_enhaacplus_dec->aac_persistent_mem_v = (pVOID)(
1379 (pWORD8)p_obj_exhaacplus_dec->p_state_aac->pstr_stream_sbr +
1380 (2) * 2 * ALIGN_SIZE64(sizeof(ia_aac_dec_sbr_bitstream_struct)));
1381
1382 memset(p_obj_exhaacplus_dec->p_state_aac->pstr_stream_sbr, 0,
1383 (2) * 2 * ALIGN_SIZE64(sizeof(ia_aac_dec_sbr_bitstream_struct)));
1384 }
1385 if (1 == p_obj_exhaacplus_dec->aac_config.ui_max_channels)
1386 channels = 1;
1387 else
1388 channels = 2;
1389
1390 persistent_used = ixheaacd_set_aac_persistent_buffers(
1391 p_state_enhaacplus_dec->aac_persistent_mem_v, channels);
1392
1393 p_state_enhaacplus_dec->sbr_persistent_mem_v =
1394 (pVOID)((SIZE_T)((pWORD8)p_state_enhaacplus_dec->aac_persistent_mem_v +
1395 persistent_used + sizeof(SIZE_T) - 1) &
1396 (SIZE_T)(~(sizeof(SIZE_T) - 1)));
1397
1398 persistent_used = ixheaacd_getsize_sbr_persistent();
1399 ixheaacd_set_sbr_persistent_buffers(
1400 p_state_enhaacplus_dec->sbr_persistent_mem_v, &persistent_used,
1401 channels, 1);
1402
1403 aac_persistent_mem = (struct ia_aac_persistent_struct *)
1404 p_state_enhaacplus_dec->aac_persistent_mem_v;
1405 if (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD ||
1406 p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD)
1407 p_state_enhaacplus_dec->frame_len_flag =
1408 p_obj_exhaacplus_dec->aac_config.framesize_480;
1409
1410 p_state_enhaacplus_dec->ptr_overlap_buf =
1411 aac_persistent_mem->overlap_buffer;
1412
1413 p_state_enhaacplus_dec->bit_count = 0;
1414 p_state_enhaacplus_dec->sync_status = 0;
1415 p_state_enhaacplus_dec->bs_format = ADTS_BSFORMAT;
1416 p_state_enhaacplus_dec->latm_initialized = 0;
1417 p_state_enhaacplus_dec->frame_size = 0;
1418 memset(&p_state_enhaacplus_dec->latm_struct_element, 0,
1419 sizeof(ixheaacd_latm_struct));
1420 memset(&p_state_enhaacplus_dec->b_n_raw_data_blk, 0,
1421 sizeof(WORD32) * (9 + MAX_BS_ELEMENT));
1422
1423 p_state_enhaacplus_dec->sbr_present_flag = 0;
1424
1425 for (ch_idx = 0; ch_idx < MAX_BS_ELEMENT; ch_idx++) {
1426 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] = 0;
1427 }
1428
1429 memset(&p_state_enhaacplus_dec->ind_cc_info, 0,
1430 sizeof(ia_enhaacplus_dec_ind_cc));
1431
1432 p_state_enhaacplus_dec->last_frame_ok = 1;
1433 p_obj_exhaacplus_dec->aac_config.header_dec_done = 1;
1434
1435 aac_persistent_mem->str_aac_decoder.pstr_aac_tables =
1436 &p_obj_exhaacplus_dec->aac_tables;
1437 aac_persistent_mem->str_aac_decoder.pstr_common_tables =
1438 p_obj_exhaacplus_dec->common_tables;
1439
1440 p_obj_exhaacplus_dec->p_state_aac->sbr_persistent_mem_u =
1441 p_obj_exhaacplus_dec->p_state_aac->sbr_persistent_mem_v;
1442
1443 p_obj_exhaacplus_dec->p_state_aac->sbr_scratch_mem_u =
1444 p_obj_exhaacplus_dec->p_state_aac->aac_scratch_mem_v;
1445
1446 ixheaacd_set_sbr_persistent_table_pointer(
1447 p_obj_exhaacplus_dec->p_state_aac->sbr_persistent_mem_v,
1448 &p_obj_exhaacplus_dec->str_sbr_tables,
1449 p_obj_exhaacplus_dec->common_tables);
1450 }
1451
1452 if (p_obj_exhaacplus_dec->p_state_aac->ui_input_over == 1) {
1453 return IA_ENHAACPLUS_DEC_INIT_FATAL_EO_INPUT_REACHED;
1454 }
1455
1456 if (p_obj_exhaacplus_dec->p_state_aac->header_dec_done == 0) {
1457 if (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD ||
1458 p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD)
1459 p_state_enhaacplus_dec->frame_len_flag =
1460 p_obj_exhaacplus_dec->aac_config.framesize_480;
1461
1462 aac_persistent_mem = (struct ia_aac_persistent_struct *)
1463 p_state_enhaacplus_dec->aac_persistent_mem_v;
1464 sbr_persistent_mem = (struct ia_sbr_pers_struct *)
1465 p_state_enhaacplus_dec->sbr_persistent_mem_v;
1466
1467 if (p_obj_exhaacplus_dec->aac_config.ui_samp_freq == 0) {
1468 WORD32 header_bytes_consumed, return_val;
1469
1470 if (p_state_enhaacplus_dec->ui_in_bytes == 0) {
1471 p_state_enhaacplus_dec->i_bytes_consumed = 0;
1472 return IA_NO_ERROR;
1473 }
1474 p_state_enhaacplus_dec->ui_init_done = 0;
1475 memset(&(p_state_enhaacplus_dec->eld_specific_config), 0,
1476 sizeof(ia_eld_specific_config_struct));
1477 return_val = ixheaacd_aac_headerdecode(
1478 p_obj_exhaacplus_dec, (UWORD8 *)in_buffer, &header_bytes_consumed,
1479 aac_persistent_mem->str_aac_decoder.pstr_aac_tables
1480 ->pstr_huffmann_tables);
1481 if (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD ||
1482 p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD) {
1483 *sbr_persistent_mem->str_sbr_dec_inst.pstr_sbr_header[0] =
1484 p_obj_exhaacplus_dec->p_state_aac->str_sbr_config;
1485 *sbr_persistent_mem->str_sbr_dec_inst.pstr_sbr_header[1] =
1486 p_obj_exhaacplus_dec->p_state_aac->str_sbr_config;
1487 } else {
1488 memset(&(p_state_enhaacplus_dec->eld_specific_config), 0,
1489 sizeof(ia_eld_specific_config_struct));
1490 }
1491
1492 if (return_val < 0) {
1493 if (return_val ==
1494 (WORD32)IA_ENHAACPLUS_DEC_INIT_FATAL_STREAM_CHAN_GT_MAX) {
1495 p_state_enhaacplus_dec->i_bytes_consumed = header_bytes_consumed;
1496 return return_val;
1497 }
1498 p_state_enhaacplus_dec->i_bytes_consumed = 1;
1499
1500 return return_val;
1501 }
1502
1503 if (return_val ==
1504 IA_ENHAACPLUS_DEC_EXE_NONFATAL_INSUFFICIENT_INPUT_BYTES) {
1505 p_state_enhaacplus_dec->i_bytes_consumed = header_bytes_consumed;
1506 return return_val;
1507 }
1508
1509 p_state_enhaacplus_dec->i_bytes_consumed = header_bytes_consumed;
1510
1511 if ((return_val == 0) &&
1512 (p_obj_exhaacplus_dec->p_state_aac->audio_object_type == AOT_USAC)) {
1513 {
1514 WORD32 pcm_size = p_obj_exhaacplus_dec->aac_config.ui_pcm_wdsz;
1515 WORD8 *inbuffer =
1516 p_obj_exhaacplus_dec->pp_mem_aac[IA_ENHAACPLUS_DEC_INPUT_IDX];
1517 WORD8 *outbuffer =
1518 p_obj_exhaacplus_dec->pp_mem_aac[IA_ENHAACPLUS_DEC_OUTPUT_IDX];
1519 WORD32 out_bytes = 0;
1520 WORD32 frames_done = p_obj_exhaacplus_dec->p_state_aac->frame_counter;
1521
1522 if (p_obj_exhaacplus_dec->p_state_aac->ui_input_over == 0) {
1523 error_code = ixheaacd_dec_main(
1524 p_obj_exhaacplus_dec, inbuffer, outbuffer, &out_bytes,
1525 frames_done, pcm_size,
1526 &p_obj_exhaacplus_dec->p_state_aac->num_of_output_ch);
1527 if (error_code) return error_code;
1528 p_obj_exhaacplus_dec->p_state_aac->frame_counter++;
1529 } else {
1530 out_bytes = 0;
1531 }
1532
1533 p_obj_exhaacplus_dec->aac_config.ui_n_channels =
1534 p_obj_exhaacplus_dec->p_state_aac->num_of_output_ch;
1535 }
1536 if (return_val == 0)
1537 p_obj_exhaacplus_dec->p_state_aac->ui_init_done = 1;
1538 return return_val;
1539 }
1540
1541 if (return_val == 0) {
1542 p_obj_exhaacplus_dec->p_state_aac->header_dec_done = 1;
1543 if (p_obj_exhaacplus_dec->aac_config.ui_flush_cmd == 0) {
1544 memcpy(p_state_enhaacplus_dec->header_ptr, in_buffer,
1545 header_bytes_consumed * sizeof(UWORD8));
1546 p_state_enhaacplus_dec->header_length = header_bytes_consumed;
1547 }
1548 }
1549
1550 if (p_obj_exhaacplus_dec->p_state_aac->header_dec_done != 1)
1551 return IA_ENHAACPLUS_DEC_INIT_NONFATAL_HEADER_NOT_AT_START;
1552
1553 if (p_state_enhaacplus_dec->dwnsmp_signal == 1 &&
1554 p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD)
1555 p_obj_exhaacplus_dec->aac_config.down_sample_flag = 1;
1556
1557 if (p_state_enhaacplus_dec->sampling_rate ==
1558 p_state_enhaacplus_dec->extension_samp_rate) {
1559 p_obj_exhaacplus_dec->aac_config.down_sample_flag = 1;
1560 }
1561
1562 } else {
1563 p_obj_exhaacplus_dec->p_state_aac->header_dec_done = 1;
1564 p_state_enhaacplus_dec->i_bytes_consumed = 0;
1565
1566 p_state_enhaacplus_dec->sampling_rate =
1567 p_obj_exhaacplus_dec->aac_config.ui_samp_freq;
1568 }
1569
1570 p_state_enhaacplus_dec->pstr_bit_buf = ixheaacd_create_bit_buf(
1571 &p_state_enhaacplus_dec->str_bit_buf, (UWORD8 *)in_buffer,
1572 p_obj_exhaacplus_dec->p_mem_info_aac[IA_ENHAACPLUS_DEC_INPUT_IDX]
1573 .ui_size);
1574 p_state_enhaacplus_dec->pstr_bit_buf->xaac_jmp_buf =
1575 &(p_state_enhaacplus_dec->xaac_jmp_buf);
1576
1577 p_state_enhaacplus_dec->ptr_bit_stream =
1578 p_state_enhaacplus_dec->pstr_bit_buf;
1579
1580 if (p_state_enhaacplus_dec->s_adts_hdr_present) { // rajat
1581 if (p_obj_exhaacplus_dec->aac_config.ld_decoder == 1)
1582 p_state_enhaacplus_dec->audio_object_type = 23;
1583 }
1584
1585 if ((p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD) ||
1586 (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD))
1587 if (p_state_enhaacplus_dec->s_adts_hdr_present) {
1588 if (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD) {
1589 p_state_enhaacplus_dec->eld_specific_config.ld_sbr_samp_rate = 1;
1590 p_state_enhaacplus_dec->eld_specific_config.ld_sbr_crc_flag = 0;
1591 p_state_enhaacplus_dec->eld_specific_config.ld_sbr_flag_present = 0;
1592
1593 if (p_obj_exhaacplus_dec->aac_config.eld_sbr_present == 1) {
1594 p_state_enhaacplus_dec->eld_specific_config.ld_sbr_flag_present = 1;
1595 }
1596 }
1597 if (p_obj_exhaacplus_dec->aac_config.framesize_480)
1598 p_state_enhaacplus_dec->frame_length = 480;
1599 else
1600 p_state_enhaacplus_dec->frame_length = 512;
1601 }
1602
1603 {
1604 for (ch_idx = 0; ch_idx < MAX_BS_ELEMENT; ch_idx++) {
1605 WORD32 channels;
1606 channels = 2;
1607
1608 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx] =
1609 ixheaacd_aac_decoder_init(
1610 p_state_enhaacplus_dec,
1611
1612 p_state_enhaacplus_dec->pstr_stream_sbr[0], channels,
1613 p_state_enhaacplus_dec->aac_persistent_mem_v,
1614 p_state_enhaacplus_dec->frame_length);
1615
1616 if (!p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]) {
1617 p_state_enhaacplus_dec->i_bytes_consumed = 1;
1618 return IA_ENHAACPLUS_DEC_INIT_FATAL_DEC_INIT_FAIL;
1619 }
1620 }
1621
1622 {
1623 p_state_enhaacplus_dec->pstr_drc_dec =
1624 &p_state_enhaacplus_dec->str_drc_dec_info;
1625 ixheaacd_drc_dec_create(p_state_enhaacplus_dec->pstr_drc_dec, 127, 127);
1626 }
1627 p_state_enhaacplus_dec->pstr_drc_dec->cut_factor =
1628 p_obj_exhaacplus_dec->aac_config.ui_drc_cut;
1629 p_state_enhaacplus_dec->pstr_drc_dec->boost_factor =
1630 p_obj_exhaacplus_dec->aac_config.ui_drc_boost;
1631 p_state_enhaacplus_dec->pstr_drc_dec->target_ref_level =
1632 p_obj_exhaacplus_dec->aac_config.ui_drc_target_level;
1633 p_state_enhaacplus_dec->pstr_drc_dec->prog_ref_level =
1634 p_obj_exhaacplus_dec->aac_config.ui_drc_target_level;
1635
1636 if (1 == p_obj_exhaacplus_dec->aac_config.ui_drc_set) {
1637 if (p_obj_exhaacplus_dec->aac_config.ui_drc_heavy_comp == 1) {
1638 p_state_enhaacplus_dec->pstr_drc_dec->drc_on = 1;
1639 p_state_enhaacplus_dec->pstr_drc_dec->heavy_mode = 1;
1640 } else {
1641 p_state_enhaacplus_dec->pstr_drc_dec->heavy_mode = 0;
1642 if (p_state_enhaacplus_dec->pstr_drc_dec->target_ref_level > 127)
1643 p_state_enhaacplus_dec->pstr_drc_dec->target_ref_level = 127;
1644 if (p_state_enhaacplus_dec->pstr_drc_dec->target_ref_level < 0) {
1645 if (p_state_enhaacplus_dec->pstr_drc_dec->cut_factor > 0 ||
1646 p_state_enhaacplus_dec->pstr_drc_dec->boost_factor > 0)
1647 p_state_enhaacplus_dec->pstr_drc_dec->drc_on = 1;
1648 else
1649 p_state_enhaacplus_dec->pstr_drc_dec->drc_on = 0;
1650 p_state_enhaacplus_dec->pstr_drc_dec->drc_dig_norm = 0;
1651 p_state_enhaacplus_dec->pstr_drc_dec->target_ref_level = 108;
1652 } else {
1653 p_state_enhaacplus_dec->pstr_drc_dec->drc_on = 1;
1654 p_state_enhaacplus_dec->pstr_drc_dec->drc_dig_norm = 1;
1655 }
1656 }
1657 }
1658 }
1659 } else {
1660 struct ia_bit_buf_struct temp_bit_buff = {0};
1661 ia_adts_header_struct adts;
1662 struct ia_bit_buf_struct *it_bit_buff;
1663
1664 WORD16 frame_size_2 = 0;
1665 WORD32 sample_rate_2 = 0;
1666 WORD32 sample_rate = 0;
1667 WORD type, i;
1668 WORD elements_number;
1669
1670 memset(&adts, 0, sizeof(ia_adts_header_struct));
1671
1672 for (i = 0; i < MAX_BS_ELEMENT + 1; i++) {
1673 p_obj_exhaacplus_dec->aac_config.element_type[i] = -1;
1674 }
1675
1676 it_bit_buff = p_state_enhaacplus_dec->pstr_bit_buf;
1677
1678 p_obj_exhaacplus_dec->aac_config.ui_sbr_mode = 0;
1679 p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes = 0;
1680
1681 if (p_state_enhaacplus_dec->ui_in_bytes == 0) {
1682 p_state_enhaacplus_dec->i_bytes_consumed = 0;
1683 return IA_NO_ERROR;
1684 }
1685
1686 if (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD ||
1687 p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD) {
1688 if (p_obj_exhaacplus_dec->aac_config.ui_mp4_flag)
1689 p_state_enhaacplus_dec->frame_size =
1690 p_state_enhaacplus_dec->ui_in_bytes;
1691 }
1692
1693 ixheaacd_create_init_bit_buf(it_bit_buff, in_buffer,
1694 p_state_enhaacplus_dec->ui_in_bytes);
1695 p_state_enhaacplus_dec->pstr_bit_buf->xaac_jmp_buf =
1696 &(p_state_enhaacplus_dec->xaac_jmp_buf);
1697
1698 it_bit_buff->adts_header_present =
1699 p_state_enhaacplus_dec->s_adts_hdr_present;
1700 it_bit_buff->no_raw_data_blocks =
1701 (WORD8)p_state_enhaacplus_dec->b_n_raw_data_blk;
1702 it_bit_buff->protection_absent = p_state_enhaacplus_dec->protection_absent;
1703
1704 memcpy(&temp_bit_buff, it_bit_buff, sizeof(struct ia_bit_buf_struct));
1705
1706 if (p_obj_exhaacplus_dec->aac_config.ui_max_channels > 2)
1707 elements_number = MAX_BS_ELEMENT;
1708 else
1709 elements_number = 2;
1710
1711 for (i = 0; i < elements_number; i++)
1712 p_state_enhaacplus_dec->pstr_stream_sbr[i][0].no_elements = 0;
1713
1714 { it_bit_buff->initial_cnt_bits = it_bit_buff->cnt_bits; }
1715
1716 ixheaacd_byte_align(
1717 p_state_enhaacplus_dec->ptr_bit_stream,
1718 &p_state_enhaacplus_dec->pstr_aac_dec_info[0]->byte_align_bits);
1719
1720 if (p_state_enhaacplus_dec->s_adts_hdr_present) {
1721 WORD32 error;
1722
1723 if (p_state_enhaacplus_dec->b_n_raw_data_blk == 0) {
1724 error = ixheaacd_readifadts(p_state_enhaacplus_dec, it_bit_buff, &adts);
1725
1726 if (error) return error;
1727
1728 p_state_enhaacplus_dec->protection_absent = adts.protection_absent;
1729
1730 if (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD ||
1731 p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD) {
1732 p_state_enhaacplus_dec->frame_size = adts.aac_frame_length;
1733 if (p_obj_exhaacplus_dec->aac_config.framesize_480)
1734 p_state_enhaacplus_dec->frame_length = 480;
1735 else
1736 p_state_enhaacplus_dec->frame_length = 512;
1737 }
1738 }
1739 }
1740
1741 if (p_state_enhaacplus_dec->bs_format == LOAS_BSFORMAT) {
1742 WORD32 result;
1743 WORD32 sync;
1744 WORD32 cnt_bits;
1745
1746 sync = ixheaacd_read_bits_buf(it_bit_buff, 11);
1747 cnt_bits = it_bit_buff->cnt_bits;
1748 if (it_bit_buff->cnt_bits <= 24) {
1749 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_INSUFFICIENT_INPUT_BYTES;
1750 }
1751
1752 while (sync != 0x2b7) {
1753 sync = ((sync & 0x3ff) << 1) | ixheaacd_read_bits_buf(it_bit_buff, 1);
1754 if (it_bit_buff->cnt_bits < 11) {
1755 ixheaacd_read_bidirection(it_bit_buff, -11);
1756 p_state_enhaacplus_dec->i_bytes_consumed =
1757 (cnt_bits - it_bit_buff->cnt_bits) / 8;
1758 return (IA_ENHAACPLUS_DEC_INIT_NONFATAL_HEADER_NOT_AT_START);
1759 }
1760 }
1761
1762 it_bit_buff->audio_mux_align = it_bit_buff->cnt_bits - 13;
1763
1764 if (sync == 0x2b7) {
1765 result = ixheaacd_latm_audio_mux_element(
1766 it_bit_buff, &p_state_enhaacplus_dec->latm_struct_element,
1767 p_state_enhaacplus_dec,
1768 (ia_sampling_rate_info_struct *)&p_obj_exhaacplus_dec->aac_tables
1769 .pstr_huffmann_tables->str_sample_rate_info[0]);
1770 if (result < 0) {
1771 return result;
1772 }
1773 }
1774 }
1775
1776 p_state_enhaacplus_dec->pstr_aac_dec_info[0]->byte_align_bits =
1777 it_bit_buff->cnt_bits;
1778
1779 type = -1;
1780 ch_idx = 0;
1781
1782 while ((type != 7)) {
1783 ia_aac_dec_scratch_struct aac_scratch_struct;
1784
1785 if (ch_idx >= elements_number) {
1786 p_state_enhaacplus_dec->i_bytes_consumed = 1;
1787
1788 return IA_ENHAACPLUS_DEC_INIT_FATAL_STREAM_CHAN_GT_MAX;
1789 }
1790
1791 ixheaacd_allocate_aac_scr(
1792 &aac_scratch_struct, p_state_enhaacplus_dec->aac_scratch_mem_v,
1793 time_data, 1, p_obj_exhaacplus_dec->aac_config.ui_max_channels,
1794 p_state_enhaacplus_dec->audio_object_type);
1795
1796 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]->p_ind_channel_info =
1797 &p_state_enhaacplus_dec->ind_cc_info;
1798
1799 error_code = ixheaacd_aacdec_decodeframe(
1800 p_obj_exhaacplus_dec, &aac_scratch_struct, time_data, frame_status,
1801 &type, &ch_idx, 1, 2,
1802 p_obj_exhaacplus_dec->aac_config.element_instance_order, 0, 1, 0,
1803 p_obj_exhaacplus_dec->aac_config.ui_max_channels, 2,
1804 p_obj_exhaacplus_dec->p_state_aac->frame_length,
1805 p_obj_exhaacplus_dec->p_state_aac->frame_size,
1806 p_state_enhaacplus_dec->pstr_drc_dec,
1807 p_state_enhaacplus_dec->audio_object_type,
1808 p_state_enhaacplus_dec->ch_config,
1809 p_state_enhaacplus_dec->eld_specific_config,
1810 p_state_enhaacplus_dec->s_adts_hdr_present,
1811 &p_state_enhaacplus_dec->drc_dummy);
1812
1813 memset(&(p_obj_exhaacplus_dec->p_state_aac->pstr_aac_dec_info[ch_idx]
1814 ->pstr_aac_dec_ch_info[0]
1815 ->str_ics_info.ltp),
1816 0, sizeof(ltp_info));
1817 memset(&(p_obj_exhaacplus_dec->p_state_aac->pstr_aac_dec_info[ch_idx]
1818 ->pstr_aac_dec_ch_info[0]
1819 ->str_ics_info.ltp2),
1820 0, sizeof(ltp_info));
1821 memset(&(p_obj_exhaacplus_dec->p_state_aac->pstr_aac_dec_info[ch_idx]
1822 ->pstr_aac_dec_ch_info[1]
1823 ->str_ics_info.ltp),
1824 0, sizeof(ltp_info));
1825 memset(&(p_obj_exhaacplus_dec->p_state_aac->pstr_aac_dec_info[ch_idx]
1826 ->pstr_aac_dec_ch_info[1]
1827 ->str_ics_info.ltp2),
1828 0, sizeof(ltp_info));
1829
1830 {
1831 if ((p_state_enhaacplus_dec->audio_object_type != AOT_ER_AAC_LD) &&
1832 (p_state_enhaacplus_dec->audio_object_type != AOT_ER_AAC_ELD))
1833 frame_size_1 = 1024;
1834 else
1835 frame_size_1 = p_state_enhaacplus_dec->frame_length;
1836 sample_rate_1 =
1837 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]->sampling_rate;
1838 num_channels_1 =
1839 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]->channels;
1840 }
1841
1842 if ((p_obj_exhaacplus_dec->aac_config.ui_max_channels <= 2) &&
1843 (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx] == 2)) {
1844 p_state_enhaacplus_dec->i_bytes_consumed = 1;
1845 return IA_ENHAACPLUS_DEC_EXE_FATAL_UNIMPLEMENTED_CCE;
1846 }
1847
1848 if (p_state_enhaacplus_dec->pstr_stream_sbr[0][0].no_elements) {
1849 sbr_present_flag = 1;
1850 p_obj_exhaacplus_dec->aac_config.ui_sbr_mode = 1;
1851 }
1852
1853 if (error_code) {
1854 if (p_state_enhaacplus_dec->ui_input_over) {
1855 return IA_ENHAACPLUS_DEC_INIT_FATAL_EO_INPUT_REACHED;
1856 }
1857
1858 ixheaacd_updatebytesconsumed(p_state_enhaacplus_dec, it_bit_buff);
1859 return error_code;
1860 }
1861
1862 if (p_state_enhaacplus_dec->s_adts_hdr_present) {
1863 if (adts.no_raw_data_blocks != 0) {
1864 if (adts.protection_absent == 0) {
1865 adts.crc_check = ixheaacd_read_bits_buf(it_bit_buff, 16);
1866 }
1867 }
1868 p_state_enhaacplus_dec->b_n_raw_data_blk--;
1869 }
1870
1871 sample_rate_2 = sample_rate_1;
1872 frame_size_2 = frame_size_1;
1873
1874 if (!p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] &&
1875 p_state_enhaacplus_dec->pstr_stream_sbr[0][0].no_elements) {
1876 if ((p_obj_exhaacplus_dec->aac_config.flag_16khz_out == 1) &&
1877 (sample_rate_1 == 8000)) {
1878 p_obj_exhaacplus_dec->aac_config.flag_16khz_out = 0;
1879 }
1880
1881 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] = ixheaacd_init_sbr(
1882 sample_rate_1, frame_size_1,
1883 (FLAG *)&p_obj_exhaacplus_dec->aac_config.down_sample_flag,
1884 p_state_enhaacplus_dec->sbr_persistent_mem_v,
1885 p_state_enhaacplus_dec->ptr_overlap_buf, MAXNRSBRCHANNELS, (WORD)1,
1886 1, frame_size_1 * 2, NULL, NULL,
1887 p_state_enhaacplus_dec->str_sbr_config,
1888 p_state_enhaacplus_dec->audio_object_type);
1889 if (p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx]) {
1890 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx]->xaac_jmp_buf =
1891 &(p_state_enhaacplus_dec->xaac_jmp_buf);
1892 }
1893 } else {
1894 }
1895
1896 if (p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] &&
1897 p_state_enhaacplus_dec->pstr_stream_sbr[0][0].no_elements) {
1898 ia_sbr_scr_struct sbr_scratch_struct;
1899 WORD16 num_channels_1_t = num_channels_1;
1900 ixheaacd_allocate_sbr_scr(
1901 &sbr_scratch_struct, p_state_enhaacplus_dec->aac_scratch_mem_v,
1902 time_data, 1, 1, p_state_enhaacplus_dec->audio_object_type);
1903
1904 if (ixheaacd_applysbr(
1905 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx],
1906 &p_state_enhaacplus_dec->pstr_stream_sbr[0][0], time_data,
1907 &num_channels_1, frame_status,
1908 p_obj_exhaacplus_dec->aac_config.down_sample_flag, 0,
1909 &sbr_scratch_struct, 1, 1, 0, NULL, NULL,
1910 p_state_enhaacplus_dec->eld_specific_config.ld_sbr_flag_present,
1911 p_state_enhaacplus_dec->audio_object_type) != SBRDEC_OK) {
1912 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] = 0;
1913 return -1;
1914 } else {
1915 if (!p_obj_exhaacplus_dec->aac_config.down_sample_flag) {
1916 sample_rate_1 *= 2;
1917 }
1918 }
1919
1920 if (p_obj_exhaacplus_dec->aac_config.flag_downmix) {
1921 num_channels_1 = 1;
1922 }
1923 if (num_channels_1_t == 1 && num_channels_1 == 2) ps_detected = 1;
1924 }
1925
1926 p_state_enhaacplus_dec->i_bytes_consumed = 0;
1927 p_state_enhaacplus_dec->pstr_bit_buf = it_bit_buff;
1928
1929 {
1930 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx] =
1931 ixheaacd_aac_decoder_init(
1932 p_state_enhaacplus_dec,
1933 p_state_enhaacplus_dec->pstr_stream_sbr[0], 2,
1934 p_state_enhaacplus_dec->aac_persistent_mem_v,
1935 p_state_enhaacplus_dec->frame_length);
1936
1937 if (!p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]) {
1938 p_state_enhaacplus_dec->i_bytes_consumed = 1;
1939 return IA_ENHAACPLUS_DEC_INIT_FATAL_DEC_INIT_FAIL;
1940 }
1941
1942 if (p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx]) {
1943 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] = ixheaacd_init_sbr(
1944 sample_rate_2, frame_size_2,
1945 (FLAG *)&p_obj_exhaacplus_dec->aac_config.down_sample_flag,
1946 p_state_enhaacplus_dec->sbr_persistent_mem_v,
1947 p_state_enhaacplus_dec->ptr_overlap_buf, MAXNRSBRCHANNELS, 1, 1,
1948 frame_size_2 * 2, NULL, NULL,
1949 p_state_enhaacplus_dec->str_sbr_config,
1950 p_state_enhaacplus_dec->audio_object_type);
1951 }
1952 if (p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx]) {
1953 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx]->xaac_jmp_buf =
1954 &(p_state_enhaacplus_dec->xaac_jmp_buf);
1955 }
1956 }
1957
1958 if (sample_rate < sample_rate_1) sample_rate = sample_rate_1;
1959
1960 ch_idx++;
1961
1962 if (p_state_enhaacplus_dec->audio_object_type >= ER_OBJECT_START &&
1963 (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD ||
1964 p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD))
1965 break;
1966 }
1967
1968 {
1969 ia_adts_crc_info_struct *ptr_adts_crc_info =
1970 p_state_enhaacplus_dec->ptr_bit_stream->pstr_adts_crc_info;
1971 if (ptr_adts_crc_info->crc_active == 1) {
1972 if ((error_code = ixheaacd_adts_crc_check_crc(ptr_adts_crc_info))) {
1973 return error_code;
1974 }
1975 }
1976 }
1977
1978 {
1979 VOID *temp;
1980 WORD prev_persistent_used_t;
1981 WORD prev_sbrpersistent_used_t;
1982 WORD ps_enable;
1983 WORD ch_idx_err = 0;
1984 WORD persistent_used_t = 0;
1985 WORD channel_check = 0;
1986 WORD cc_channel_check = 0;
1987 WORD max_ch_num = p_obj_exhaacplus_dec->aac_config.ui_max_channels;
1988 i = 0;
1989
1990 p_obj_exhaacplus_dec->aac_config.ui_n_channels = ch_idx;
1991 while (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx_err] <= 3 &&
1992 p_obj_exhaacplus_dec->aac_config.element_type[ch_idx_err] >= 0) {
1993 ch_idx_err++;
1994 }
1995
1996 if (ch_idx_err == 0) {
1997 p_obj_exhaacplus_dec->p_state_aac->header_dec_done = 0;
1998 p_state_enhaacplus_dec->i_bytes_consumed =
1999 it_bit_buff->ptr_read_next - it_bit_buff->ptr_bit_buf_base;
2000 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_DECODE_FRAME_ERROR;
2001 }
2002
2003 if (ch_idx == 1)
2004 ps_enable = 1;
2005 else
2006 ps_enable = 0;
2007
2008 while (p_obj_exhaacplus_dec->aac_config.element_type[i] >= 0 &&
2009 p_obj_exhaacplus_dec->aac_config.element_type[i] <= 3) {
2010 WORD32 channel = 0;
2011 switch (p_obj_exhaacplus_dec->aac_config.element_type[i]) {
2012 case 0:
2013 case 3:
2014 channel = 1;
2015 break;
2016 case 1:
2017 channel = 2;
2018 break;
2019 case 2:
2020 if (max_ch_num > 2) {
2021 if (p_obj_exhaacplus_dec->aac_config.element_instance_order[i] !=
2022 p_obj_exhaacplus_dec->aac_config.ui_coupling_channel) {
2023 i++;
2024 continue;
2025 }
2026 channel = 1;
2027 } else {
2028 i++;
2029 continue;
2030 }
2031 cc_channel_check++;
2032 break;
2033 default:
2034 assert(0);
2035 }
2036
2037 if (cc_channel_check > MAX_CC_CHANNEL_NUM)
2038 return IA_ENHAACPLUS_DEC_EXE_FATAL_UNIMPLEMENTED_CCE;
2039 if (ps_enable == 1) {
2040 channel = 2;
2041 }
2042
2043 if (p_obj_exhaacplus_dec->aac_config.element_type[i] != 2) {
2044 channel_check += channel;
2045 }
2046
2047 if (channel_check > max_ch_num) {
2048 p_state_enhaacplus_dec->i_bytes_consumed = 1;
2049 return IA_ENHAACPLUS_DEC_INIT_FATAL_STREAM_CHAN_GT_MAX;
2050 }
2051
2052 temp = p_state_enhaacplus_dec->aac_persistent_mem_v;
2053
2054 prev_persistent_used_t = persistent_used_t;
2055
2056 ixheaacd_allocate_mem_persistent(
2057 p_obj_exhaacplus_dec, p_state_enhaacplus_dec, channel,
2058 &persistent_used_t, &prev_sbrpersistent_used_t, ps_enable);
2059
2060 p_state_enhaacplus_dec->aac_persistent_mem_v = temp;
2061 p_state_enhaacplus_dec->last_frame_ok = 1;
2062
2063 p_state_enhaacplus_dec->num_channel_last = 0;
2064 p_state_enhaacplus_dec->ui_init_done = 0;
2065 p_state_enhaacplus_dec->ui_input_over = 0;
2066 p_state_enhaacplus_dec->ptr_bit_stream =
2067 p_state_enhaacplus_dec->pstr_bit_buf;
2068
2069 p_state_enhaacplus_dec->pstr_aac_dec_info[i] = 0;
2070
2071 p_state_enhaacplus_dec->pstr_aac_dec_info[i] =
2072 ixheaacd_aac_decoder_init(
2073 p_state_enhaacplus_dec,
2074 p_state_enhaacplus_dec->pstr_stream_sbr[i], channel,
2075 (WORD8 *)p_state_enhaacplus_dec->aac_persistent_mem_v +
2076 prev_persistent_used_t,
2077 p_state_enhaacplus_dec->frame_length);
2078
2079 if (!p_state_enhaacplus_dec->pstr_aac_dec_info[i]) {
2080 p_state_enhaacplus_dec->i_bytes_consumed = 1;
2081 return IA_ENHAACPLUS_DEC_INIT_FATAL_DEC_INIT_FAIL;
2082 }
2083
2084 p_state_enhaacplus_dec->str_sbr_dec_info[i] = ixheaacd_init_sbr(
2085 sample_rate_2, frame_size_2,
2086 (FLAG *)&p_obj_exhaacplus_dec->aac_config.down_sample_flag,
2087 p_state_enhaacplus_dec->sbr_persistent_mem_v,
2088 p_state_enhaacplus_dec->ptr_overlap_buf, channel, ps_enable, 1,
2089 frame_size_2 * 2, NULL, NULL,
2090 p_state_enhaacplus_dec->str_sbr_config,
2091 p_state_enhaacplus_dec->audio_object_type);
2092 if (p_state_enhaacplus_dec->str_sbr_dec_info[i]) {
2093 p_state_enhaacplus_dec->str_sbr_dec_info[i]->xaac_jmp_buf =
2094 &(p_state_enhaacplus_dec->xaac_jmp_buf);
2095 }
2096 if (sbr_present_flag &&
2097 ((p_obj_exhaacplus_dec->p_state_aac->audio_object_type ==
2098 AOT_AAC_LC) ||
2099 (p_obj_exhaacplus_dec->p_state_aac->audio_object_type ==
2100 AOT_SBR) ||
2101 (p_obj_exhaacplus_dec->p_state_aac->audio_object_type == AOT_PS)))
2102 p_obj_exhaacplus_dec->aac_config.flag_to_stereo = 1;
2103
2104 i++;
2105 }
2106 p_state_enhaacplus_dec->pers_mem_ptr =
2107 (WORD8 *)p_state_enhaacplus_dec->aac_persistent_mem_v +
2108 persistent_used_t;
2109
2110 p_obj_exhaacplus_dec->aac_config.i_channel_mask =
2111 ixheaacd_get_channel_mask(p_obj_exhaacplus_dec);
2112
2113 {
2114 num_channels_1 = 0;
2115 ch_idx = 0;
2116 while (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx] >= 0 &&
2117 p_obj_exhaacplus_dec->aac_config.element_type[ch_idx] <= 3) {
2118 if (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx] == 0 ||
2119 p_obj_exhaacplus_dec->aac_config.element_type[ch_idx] == 3)
2120 num_channels_1 += 1;
2121 if (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx] == 1)
2122 num_channels_1 += 2;
2123 ch_idx++;
2124 }
2125
2126 if (ch_idx == 2 && num_channels_1 == 2) {
2127 p_obj_exhaacplus_dec->aac_config.ui_channel_mode = 2;
2128 }
2129 if (ch_idx == 1) {
2130 if (num_channels_1 == 1)
2131 p_obj_exhaacplus_dec->aac_config.ui_channel_mode = 0;
2132 if (num_channels_1 == 2)
2133 p_obj_exhaacplus_dec->aac_config.ui_channel_mode = 1;
2134 }
2135
2136 if (ps_detected == 1 && num_channels_1 == 1) num_channels_1 = 2;
2137 }
2138 }
2139 if (1 == p_obj_exhaacplus_dec->aac_config.downmix) num_channels_1 = 2;
2140
2141 if (p_obj_exhaacplus_dec->aac_config.flag_downmix == 1) {
2142 num_channels_1 = 1;
2143 }
2144
2145 if ((p_obj_exhaacplus_dec->aac_config.flag_to_stereo == 1) &&
2146 (ch_idx == 1 || num_channels_1 <= 2)) {
2147 num_channels_1 = 2;
2148 }
2149
2150 p_obj_exhaacplus_dec->aac_config.ui_n_channels = num_channels_1;
2151 p_obj_exhaacplus_dec->aac_config.ui_samp_freq = sample_rate;
2152 p_state_enhaacplus_dec->ui_init_done = 1;
2153
2154 memcpy(it_bit_buff, &temp_bit_buff, sizeof(struct ia_bit_buf_struct));
2155
2156 p_state_enhaacplus_dec->b_n_raw_data_blk = 0;
2157
2158 if (p_obj_exhaacplus_dec->p_state_aac->header_dec_done == 1) {
2159 p_obj_exhaacplus_dec->p_state_aac->header_dec_done = 0;
2160 }
2161 }
2162 return err_code;
2163 }
2164
ixheaacd_fill_slot_order(ia_aac_dec_state_struct * p_state_enhaacplus_dec,WORD32 ch,WORD8 * ptr_is_cpe,WORD8 * ptr_tag_select,WORD32 * ptr_idx_no)2165 VOID ixheaacd_fill_slot_order(ia_aac_dec_state_struct *p_state_enhaacplus_dec,
2166 WORD32 ch, WORD8 *ptr_is_cpe,
2167 WORD8 *ptr_tag_select, WORD32 *ptr_idx_no) {
2168 WORD32 i;
2169 WORD32 idx_no = *ptr_idx_no;
2170 WORD *p_slot_element = p_state_enhaacplus_dec->p_config->slot_element;
2171 WORD *p_element_type = p_state_enhaacplus_dec->p_config->element_type;
2172 WORD *p_element_instance_order =
2173 p_state_enhaacplus_dec->p_config->element_instance_order;
2174
2175 for (i = 0; i < ch; i++) {
2176 if (ptr_is_cpe[i] == 0) {
2177 *p_slot_element++ = idx_no++;
2178 *p_element_type++ = 0;
2179 *p_element_instance_order++ = ptr_tag_select[i];
2180 }
2181 }
2182 *ptr_idx_no = idx_no;
2183 }
2184
ixheaacd_fill_prog_config_slots(ia_aac_dec_state_struct * p_state_enhaacplus_dec)2185 VOID ixheaacd_fill_prog_config_slots(
2186 ia_aac_dec_state_struct *p_state_enhaacplus_dec) {
2187 WORD32 idx_no = 0;
2188
2189 ixheaacd_fill_slot_order(
2190 p_state_enhaacplus_dec, p_state_enhaacplus_dec->p_config->str_prog_config
2191 .num_front_channel_elements,
2192 p_state_enhaacplus_dec->p_config->str_prog_config.front_element_is_cpe,
2193 p_state_enhaacplus_dec->p_config->str_prog_config
2194 .front_element_tag_select,
2195 &idx_no);
2196
2197 ixheaacd_fill_slot_order(
2198 p_state_enhaacplus_dec, p_state_enhaacplus_dec->p_config->str_prog_config
2199 .num_side_channel_elements,
2200 p_state_enhaacplus_dec->p_config->str_prog_config.side_element_is_cpe,
2201 p_state_enhaacplus_dec->p_config->str_prog_config.side_element_tag_select,
2202 &idx_no);
2203
2204 ixheaacd_fill_slot_order(
2205 p_state_enhaacplus_dec, p_state_enhaacplus_dec->p_config->str_prog_config
2206 .num_back_channel_elements,
2207 p_state_enhaacplus_dec->p_config->str_prog_config.back_element_is_cpe,
2208 p_state_enhaacplus_dec->p_config->str_prog_config.back_element_tag_select,
2209 &idx_no);
2210 }
2211
ixheaacd_dec_execute(ia_exhaacplus_dec_api_struct * p_obj_exhaacplus_dec)2212 IA_ERRORCODE ixheaacd_dec_execute(
2213 ia_exhaacplus_dec_api_struct *p_obj_exhaacplus_dec) {
2214 ia_adts_header_struct adts = {0};
2215 ia_aac_dec_state_struct *p_state_enhaacplus_dec;
2216
2217 UWORD8 *in_buffer;
2218 WORD16 *time_data;
2219 WORD16 num_of_out_samples = 0;
2220 WORD16 frame_size = 0;
2221 WORD32 sample_rate_dec = 0;
2222 WORD32 sample_rate = 0;
2223 WORD16 num_ch = 0;
2224 struct ia_bit_buf_struct *it_bit_buff;
2225 WORD32 error_code = IA_NO_ERROR;
2226 WORD ch_idx1;
2227 WORD type;
2228 WORD total_channels = 0;
2229 WORD total_elements = 0;
2230 WORD16 *actual_out_buffer;
2231 WORD ps_enable;
2232 WORD esbr_mono_downmix = 0;
2233 WORD8 element_used[MAX_BS_ELEMENT];
2234 WORD32 channel_coupling_flag = 0;
2235
2236 SIZE_T bytes_for_sync;
2237 WORD32 audio_mux_length_bytes_last = 0;
2238 WORD32 ret_val;
2239
2240 p_obj_exhaacplus_dec->aac_config.ui_sbr_mode = 0;
2241
2242 if (p_obj_exhaacplus_dec->p_state_aac != NULL) {
2243 ret_val = setjmp(p_obj_exhaacplus_dec->p_state_aac->xaac_jmp_buf);
2244 if (ret_val != 0) {
2245 p_obj_exhaacplus_dec->p_state_aac->i_bytes_consumed =
2246 p_obj_exhaacplus_dec->p_state_aac->ui_in_bytes;
2247 p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes = 0;
2248 return IA_NO_ERROR;
2249 }
2250 }
2251
2252 time_data = (WORD16 *)(p_obj_exhaacplus_dec
2253 ->pp_mem_aac[IA_ENHAACPLUS_DEC_OUTPUT_IDX]);
2254 in_buffer = p_obj_exhaacplus_dec->pp_mem_aac[IA_ENHAACPLUS_DEC_INPUT_IDX];
2255 p_state_enhaacplus_dec = p_obj_exhaacplus_dec->p_state_aac;
2256 p_state_enhaacplus_dec->aac_scratch_mem_v =
2257 p_obj_exhaacplus_dec->pp_mem_aac[IA_ENHAACPLUS_DEC_SCRATCH_IDX];
2258
2259 it_bit_buff = p_state_enhaacplus_dec->pstr_bit_buf;
2260
2261 ch_idx1 = 0;
2262 p_state_enhaacplus_dec->i_bytes_consumed = 0;
2263
2264 if (p_state_enhaacplus_dec->audio_object_type == AOT_USAC) {
2265 WORD32 pcm_size = p_obj_exhaacplus_dec->aac_config.ui_pcm_wdsz;
2266 WORD8 *inbuffer = (WORD8 *)(p_obj_exhaacplus_dec
2267 ->pp_mem_aac[IA_ENHAACPLUS_DEC_INPUT_IDX]);
2268 WORD8 *outbuffer =
2269 (WORD8 *)(p_obj_exhaacplus_dec
2270 ->pp_mem_aac[IA_ENHAACPLUS_DEC_OUTPUT_IDX]);
2271 WORD32 out_bytes = 0;
2272
2273 WORD32 frames_done = p_obj_exhaacplus_dec->p_state_aac->frame_counter;
2274
2275 ia_dec_data_struct *pstr_dec_data =
2276 (ia_dec_data_struct *)(p_obj_exhaacplus_dec->p_state_aac
2277 ->pstr_dec_data);
2278
2279 if (pstr_dec_data->str_usac_data.down_samp_sbr != 0) return IA_FATAL_ERROR;
2280
2281 if (p_obj_exhaacplus_dec->p_state_aac->ui_input_over == 0) {
2282 ia_audio_specific_config_struct *ptr_audio_specific_config =
2283 ((ia_audio_specific_config_struct *)
2284 p_obj_exhaacplus_dec->p_state_aac->ia_audio_specific_config);
2285
2286 ptr_audio_specific_config->str_usac_config.str_usac_dec_config
2287 .preroll_counter = 0;
2288 {
2289 WORD32 iii = 0;
2290 for (iii = 0; iii < (MAX_AUDIO_PREROLLS + 1); iii++) {
2291 ((ia_dec_data_struct *)(p_obj_exhaacplus_dec->p_state_aac
2292 ->pstr_dec_data))
2293 ->str_frame_data.str_audio_specific_config.str_usac_config
2294 .str_usac_dec_config.usac_ext_gain_payload_len[iii] = 0;
2295 ptr_audio_specific_config->str_usac_config.str_usac_dec_config
2296 .usac_ext_gain_payload_len[iii] =
2297 0; // reinitilize the payload len buff
2298 ptr_audio_specific_config->str_usac_config.str_usac_dec_config
2299 .preroll_bytes[iii] = 0;
2300 }
2301 }
2302
2303 ((ia_dec_data_struct *)(p_obj_exhaacplus_dec->p_state_aac->pstr_dec_data))
2304 ->str_frame_data.str_audio_specific_config.str_usac_config
2305 .str_usac_dec_config.preroll_counter = 0;
2306 error_code = ixheaacd_dec_main(
2307 p_obj_exhaacplus_dec, inbuffer, outbuffer, &out_bytes, frames_done,
2308 pcm_size, &p_obj_exhaacplus_dec->p_state_aac->num_of_output_ch);
2309 if (error_code == -1) return error_code;
2310 p_obj_exhaacplus_dec->p_state_aac->frame_counter++;
2311 } else {
2312 out_bytes = 0;
2313 }
2314
2315 p_obj_exhaacplus_dec->p_state_aac->i_bytes_consumed =
2316 p_obj_exhaacplus_dec->p_state_aac->ui_in_bytes;
2317 p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes = out_bytes;
2318 p_obj_exhaacplus_dec->aac_config.ui_n_channels =
2319 p_obj_exhaacplus_dec->p_state_aac->num_of_output_ch;
2320
2321 return 0;
2322 }
2323
2324 while (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx1] <= 3 &&
2325 p_obj_exhaacplus_dec->aac_config.element_type[ch_idx1] >= 0) {
2326 if (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx1] == 0 ||
2327 p_obj_exhaacplus_dec->aac_config.element_type[ch_idx1] == 3) {
2328 total_channels += 1;
2329 total_elements += 1;
2330 }
2331 if (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx1] == 1) {
2332 total_elements += 1;
2333 total_channels += 2;
2334 }
2335 if (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx1] == 2) {
2336 total_elements += 1;
2337 }
2338
2339 ch_idx1++;
2340 }
2341
2342 if (ch_idx1 != 1) {
2343 ps_enable = 0;
2344 if (p_obj_exhaacplus_dec->aac_config.ui_max_channels > 2) {
2345 WORD32 scratch_pointer;
2346
2347 scratch_pointer = 12 * 1024;
2348
2349 p_state_enhaacplus_dec->coup_ch_output =
2350 (WORD16 *)((WORD8 *)
2351 p_obj_exhaacplus_dec->p_state_aac->aac_scratch_mem_v +
2352 scratch_pointer);
2353 }
2354
2355 }
2356
2357 else {
2358 if (total_channels < (WORD)p_obj_exhaacplus_dec->aac_config.ui_n_channels)
2359 total_channels = p_obj_exhaacplus_dec->aac_config.ui_n_channels;
2360 ps_enable = 1;
2361 }
2362
2363 p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes = 0;
2364
2365 if (p_state_enhaacplus_dec->ui_in_bytes == 0) {
2366 p_state_enhaacplus_dec->i_bytes_consumed = 0;
2367 return IA_NO_ERROR;
2368 }
2369
2370 if (ch_idx1 == 0) {
2371 p_state_enhaacplus_dec->i_bytes_consumed = 1;
2372 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_DECODE_FRAME_ERROR;
2373 }
2374 if (total_channels > (WORD)p_obj_exhaacplus_dec->aac_config.ui_max_channels) {
2375 p_state_enhaacplus_dec->i_bytes_consumed = 1;
2376 return IA_ENHAACPLUS_DEC_CONFIG_NONFATAL_INVALID_MAX_CHANNEL;
2377 }
2378
2379 if (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD ||
2380 p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD) {
2381 if (p_obj_exhaacplus_dec->aac_config.ui_mp4_flag)
2382 p_state_enhaacplus_dec->frame_size = p_state_enhaacplus_dec->ui_in_bytes;
2383 }
2384
2385 {
2386 ixheaacd_create_init_bit_buf(it_bit_buff, in_buffer,
2387 p_state_enhaacplus_dec->ui_in_bytes);
2388 it_bit_buff->xaac_jmp_buf = &(p_state_enhaacplus_dec->xaac_jmp_buf);
2389
2390 it_bit_buff->adts_header_present =
2391 p_state_enhaacplus_dec->s_adts_hdr_present;
2392 it_bit_buff->no_raw_data_blocks =
2393 (WORD8)p_state_enhaacplus_dec->b_n_raw_data_blk;
2394 it_bit_buff->protection_absent = p_state_enhaacplus_dec->protection_absent;
2395
2396 if (p_state_enhaacplus_dec->s_adts_hdr_present) {
2397 if (p_state_enhaacplus_dec->b_n_raw_data_blk == 0) {
2398 WORD32 error;
2399
2400 error = ixheaacd_readifadts(p_state_enhaacplus_dec, it_bit_buff, &adts);
2401
2402 if (error) return error;
2403
2404 if ((WORD32)p_state_enhaacplus_dec->sampling_rate !=
2405 (WORD32)((p_obj_exhaacplus_dec->aac_tables.pstr_huffmann_tables
2406 ->str_sample_rate_info[adts.samp_freq_index]
2407 .sampling_frequency))) {
2408 p_state_enhaacplus_dec->i_bytes_consumed = 0;
2409 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_CHANGED_ADTS_SF;
2410 }
2411 }
2412 }
2413
2414 bytes_for_sync = (SIZE_T)it_bit_buff->ptr_read_next;
2415
2416 if (p_state_enhaacplus_dec->bs_format == LOAS_BSFORMAT) {
2417 WORD32 result, audio_mux_len_bytes_last;
2418 WORD32 cnt_bits = it_bit_buff->cnt_bits;
2419 WORD32 sync = ixheaacd_read_bits_buf(it_bit_buff, 11);
2420 UWORD32 curr_samp_rate = 0;
2421
2422 if (p_state_enhaacplus_dec->latm_initialized)
2423 curr_samp_rate =
2424 p_state_enhaacplus_dec->latm_struct_element.layer_info[0][0]
2425 .asc.sampling_freq;
2426
2427 while (sync != 0x2b7) {
2428 sync = ((sync & 0x3ff) << 1) | ixheaacd_read_bits_buf(it_bit_buff, 1);
2429 if (it_bit_buff->cnt_bits < 13) {
2430 ixheaacd_read_bidirection(it_bit_buff, -11);
2431 p_state_enhaacplus_dec->i_bytes_consumed =
2432 (cnt_bits - it_bit_buff->cnt_bits) / 8;
2433
2434 if (p_state_enhaacplus_dec->i_bytes_consumed == 0)
2435 p_state_enhaacplus_dec->i_bytes_consumed = 1;
2436
2437 return (IA_ENHAACPLUS_DEC_INIT_NONFATAL_HEADER_NOT_AT_START);
2438 }
2439 }
2440
2441 it_bit_buff->audio_mux_align = it_bit_buff->cnt_bits - 13;
2442
2443 audio_mux_len_bytes_last = ixheaacd_read_bits_buf(it_bit_buff, 13);
2444
2445 audio_mux_length_bytes_last = audio_mux_len_bytes_last;
2446
2447 bytes_for_sync = (SIZE_T)it_bit_buff->ptr_read_next - bytes_for_sync;
2448
2449 if (it_bit_buff->cnt_bits < (audio_mux_len_bytes_last << 3)) {
2450 ixheaacd_read_bidirection(it_bit_buff, -(13 + 11));
2451 p_state_enhaacplus_dec->i_bytes_consumed =
2452 (cnt_bits - it_bit_buff->cnt_bits) / 8;
2453 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_INSUFFICIENT_INPUT_BYTES;
2454 } else {
2455 ixheaacd_read_bidirection(it_bit_buff, -(13));
2456 }
2457
2458 if (sync == 0x2b7) {
2459 result = ixheaacd_latm_audio_mux_element(
2460 it_bit_buff, &p_state_enhaacplus_dec->latm_struct_element,
2461 p_state_enhaacplus_dec,
2462 (ia_sampling_rate_info_struct *)&p_obj_exhaacplus_dec->aac_tables
2463 .pstr_huffmann_tables->str_sample_rate_info[0]);
2464 if (result) return result;
2465 if (!p_state_enhaacplus_dec->latm_initialized) {
2466 p_state_enhaacplus_dec->sampling_rate =
2467 p_state_enhaacplus_dec->latm_struct_element.layer_info[0][0]
2468 .asc.sampling_freq;
2469 p_state_enhaacplus_dec->latm_initialized = 1;
2470 } else {
2471 if (p_state_enhaacplus_dec->sampling_rate != curr_samp_rate) {
2472 p_state_enhaacplus_dec->i_bytes_consumed = 0;
2473 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_CHANGED_ADTS_SF;
2474 }
2475 }
2476 }
2477 }
2478 }
2479
2480 if (total_elements == 2 && total_channels == 2 &&
2481 (p_state_enhaacplus_dec->p_config->ui_pce_found_in_hdr == 1 ||
2482 p_state_enhaacplus_dec->p_config->ui_pce_found_in_hdr == 3)) {
2483 ixheaacd_fill_prog_config_slots(p_state_enhaacplus_dec);
2484 }
2485
2486 memset(element_used, 0, sizeof(WORD8) * MAX_BS_ELEMENT);
2487
2488 if (it_bit_buff->cnt_bits <= 0) {
2489 it_bit_buff->cnt_bits = -1;
2490 ixheaacd_updatebytesconsumed(p_state_enhaacplus_dec, it_bit_buff);
2491 return (WORD16)(
2492 (WORD32)IA_ENHAACPLUS_DEC_EXE_NONFATAL_INSUFFICIENT_INPUT_BYTES);
2493 }
2494
2495 { it_bit_buff->initial_cnt_bits = it_bit_buff->cnt_bits; }
2496
2497 if (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD) {
2498 if (p_state_enhaacplus_dec->s_adts_hdr_present)
2499 p_state_enhaacplus_dec->frame_size = adts.aac_frame_length;
2500 }
2501
2502 if (p_state_enhaacplus_dec->pstr_drc_dec) {
2503 p_state_enhaacplus_dec->pstr_drc_dec->num_drc_elements = 0;
2504
2505 p_state_enhaacplus_dec->pstr_drc_dec->state = 1;
2506 }
2507
2508 for (ch_idx1 = 0; ch_idx1 < total_elements; ch_idx1++) {
2509 WORD32 skip_full_decode = 0;
2510 WORD32 ch_idx = ch_idx1;
2511 WORD32 channel;
2512 WORD ch_fac, slot_ele;
2513
2514 if (p_state_enhaacplus_dec->audio_object_type < ER_OBJECT_START ||
2515 (p_state_enhaacplus_dec->audio_object_type != AOT_ER_AAC_LD &&
2516 p_state_enhaacplus_dec->audio_object_type != AOT_ER_AAC_ELD)) {
2517 error_code = ixheaacd_get_element_index_tag(
2518 p_obj_exhaacplus_dec, ch_idx1, &ch_idx, &channel,
2519 p_obj_exhaacplus_dec->aac_config.element_instance_order,
2520 total_elements, element_used, total_channels,
2521 p_state_enhaacplus_dec->pstr_drc_dec,
2522 &p_state_enhaacplus_dec->drc_dummy);
2523
2524 if (error_code) {
2525 ixheaacd_updatebytesconsumed(p_state_enhaacplus_dec, it_bit_buff);
2526 p_state_enhaacplus_dec->i_bytes_consumed = 1;
2527 p_state_enhaacplus_dec->b_n_raw_data_blk = 0;
2528 return error_code;
2529 }
2530 } else {
2531 if (p_obj_exhaacplus_dec->aac_config.element_type[0] == ID_SCE)
2532 channel = 1;
2533 else
2534 channel = 2;
2535 }
2536
2537 ch_fac = total_channels;
2538 slot_ele = p_obj_exhaacplus_dec->aac_config.slot_element[ch_idx];
2539 actual_out_buffer = time_data;
2540 if (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx] == 2) {
2541 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]->p_ind_channel_info =
2542 &p_state_enhaacplus_dec->ind_cc_info;
2543 if (p_obj_exhaacplus_dec->aac_config.element_instance_order[ch_idx] !=
2544 p_obj_exhaacplus_dec->aac_config.ui_coupling_channel) {
2545 WORD32 pers_used = 0;
2546 skip_full_decode = 1;
2547 pers_used = ixheaacd_set_aac_persistent_buffers(
2548 p_state_enhaacplus_dec->pers_mem_ptr, channel);
2549
2550 {
2551 struct ia_aac_persistent_struct *aac_persistent_mem =
2552 (struct ia_aac_persistent_struct *)
2553 p_state_enhaacplus_dec->pers_mem_ptr;
2554 aac_persistent_mem->str_aac_decoder.pstr_aac_tables =
2555 &p_obj_exhaacplus_dec->aac_tables;
2556 aac_persistent_mem->str_aac_decoder.pstr_common_tables =
2557 p_obj_exhaacplus_dec->common_tables;
2558 }
2559
2560 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx] = 0;
2561
2562 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] = 0;
2563
2564 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx] =
2565 ixheaacd_aac_decoder_init(
2566 p_state_enhaacplus_dec,
2567
2568 p_state_enhaacplus_dec->pstr_stream_sbr[ch_idx],
2569
2570 channel, p_state_enhaacplus_dec->pers_mem_ptr,
2571 p_state_enhaacplus_dec->frame_length
2572
2573 );
2574 if (!p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]) {
2575 p_state_enhaacplus_dec->i_bytes_consumed = 1;
2576 return IA_ENHAACPLUS_DEC_INIT_FATAL_DEC_INIT_FAIL;
2577 }
2578 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]->p_ind_channel_info =
2579 (WORD8 *)p_state_enhaacplus_dec->aac_scratch_mem_v + (8 * 1024) +
2580 pers_used;
2581 }
2582 if (p_obj_exhaacplus_dec->aac_config.element_type[1] < 3 &&
2583 p_obj_exhaacplus_dec->aac_config.element_type[1] > 0 &&
2584 p_obj_exhaacplus_dec->aac_config.ui_max_channels > 2) {
2585 actual_out_buffer = p_state_enhaacplus_dec->coup_ch_output;
2586 }
2587 ch_fac = 1;
2588 slot_ele = 0;
2589 }
2590
2591 type = -1;
2592 p_state_enhaacplus_dec->pstr_stream_sbr[ch_idx][0].no_elements = 0;
2593
2594 {
2595 WORD element_index_order1[MAX_BS_ELEMENT];
2596 ia_aac_dec_scratch_struct aac_scratch_struct;
2597 ixheaacd_allocate_aac_scr(
2598 &aac_scratch_struct, p_state_enhaacplus_dec->aac_scratch_mem_v,
2599 time_data, channel, p_obj_exhaacplus_dec->aac_config.ui_max_channels,
2600 p_state_enhaacplus_dec->audio_object_type);
2601
2602 if(p_state_enhaacplus_dec->ch_config == 2 && channel == 1)
2603 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_DECODE_FRAME_ERROR;
2604
2605 error_code = ixheaacd_aacdec_decodeframe(
2606 p_obj_exhaacplus_dec, &aac_scratch_struct, actual_out_buffer,
2607 p_obj_exhaacplus_dec->aac_config.frame_status, &type, &ch_idx, 0,
2608 channel, element_index_order1, skip_full_decode, ch_fac, slot_ele,
2609 p_obj_exhaacplus_dec->aac_config.ui_max_channels, total_channels,
2610 p_obj_exhaacplus_dec->p_state_aac->frame_length,
2611 p_obj_exhaacplus_dec->p_state_aac->frame_size,
2612 p_state_enhaacplus_dec->pstr_drc_dec,
2613 p_state_enhaacplus_dec->audio_object_type,
2614 p_state_enhaacplus_dec->ch_config,
2615 p_state_enhaacplus_dec->eld_specific_config,
2616 p_state_enhaacplus_dec->s_adts_hdr_present,
2617 &p_state_enhaacplus_dec->drc_dummy);
2618
2619 if (p_state_enhaacplus_dec->audio_object_type < ER_OBJECT_START ||
2620 (p_state_enhaacplus_dec->audio_object_type != AOT_ER_AAC_LD &&
2621 p_state_enhaacplus_dec->audio_object_type != AOT_ER_AAC_ELD)) {
2622 if ((error_code == 0) && ((ch_idx1 + 1) == total_elements) &&
2623 (type != ID_END)) {
2624 {
2625 p_state_enhaacplus_dec->i_bytes_consumed =
2626 it_bit_buff->ptr_read_next - it_bit_buff->ptr_bit_buf_base;
2627 p_state_enhaacplus_dec->b_n_raw_data_blk = 0;
2628 return IA_ENHAACPLUS_DEC_EXE_NONFATAL_ELE_INSTANCE_TAG_NOT_FOUND;
2629 }
2630 }
2631 }
2632
2633 num_ch = p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]->channels;
2634 if (skip_full_decode == 0) {
2635 if (p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_ELD ||
2636 p_state_enhaacplus_dec->audio_object_type == AOT_ER_AAC_LD)
2637 frame_size = p_state_enhaacplus_dec->frame_length;
2638 else
2639 frame_size = 1024;
2640
2641 sample_rate_dec =
2642 p_state_enhaacplus_dec->pstr_aac_dec_info[ch_idx]->sampling_rate;
2643 }
2644 }
2645
2646 if (skip_full_decode == 1) {
2647 p_state_enhaacplus_dec->pstr_stream_sbr[ch_idx][0].no_elements = 0;
2648 }
2649
2650 if (p_state_enhaacplus_dec->pstr_stream_sbr[ch_idx][0].no_elements != 0) {
2651 p_obj_exhaacplus_dec->aac_config.ui_sbr_mode = 1;
2652 }
2653
2654 if (error_code) {
2655 if (p_state_enhaacplus_dec->ui_input_over) {
2656 return IA_ENHAACPLUS_DEC_INIT_FATAL_EO_INPUT_REACHED;
2657 }
2658 ixheaacd_updatebytesconsumed(p_state_enhaacplus_dec, it_bit_buff);
2659 p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes +=
2660 p_state_enhaacplus_dec->num_of_out_samples * num_ch * sizeof(WORD16);
2661 return error_code;
2662 }
2663
2664 error_code = IA_NO_ERROR;
2665
2666 if (p_obj_exhaacplus_dec->aac_config.ui_auto_sbr_upsample == 0) {
2667 if (p_state_enhaacplus_dec->pstr_stream_sbr[ch_idx][0].no_elements == 0 &&
2668 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx]) {
2669 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] = 0;
2670 error_code = IA_ENHAACPLUS_DEC_EXE_NONFATAL_SBR_TURNED_OFF;
2671 }
2672 }
2673 if ((!p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx]) &&
2674 p_state_enhaacplus_dec->pstr_stream_sbr[ch_idx][0].no_elements) {
2675 error_code = IA_ENHAACPLUS_DEC_EXE_NONFATAL_SBR_TURNED_ON;
2676
2677 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] = ixheaacd_init_sbr(
2678 sample_rate_dec, frame_size,
2679 (FLAG *)&p_obj_exhaacplus_dec->aac_config.down_sample_flag,
2680 p_state_enhaacplus_dec->sbr_persistent_mem_v,
2681 p_state_enhaacplus_dec->ptr_overlap_buf, ps_enable ? 2 : channel,
2682 ps_enable, 1, frame_size * 2, NULL, NULL,
2683 p_state_enhaacplus_dec->str_sbr_config,
2684 p_state_enhaacplus_dec->audio_object_type);
2685 if (p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx]) {
2686 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx]->xaac_jmp_buf =
2687 &(p_state_enhaacplus_dec->xaac_jmp_buf);
2688 }
2689 }
2690
2691 {
2692 if (p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] &&
2693 p_state_enhaacplus_dec->pstr_stream_sbr[0][0].no_elements) {
2694 ia_sbr_scr_struct sbr_scratch_struct;
2695 ixheaacd_allocate_sbr_scr(&sbr_scratch_struct,
2696 p_state_enhaacplus_dec->aac_scratch_mem_v,
2697 time_data, total_elements, ch_fac,
2698 p_state_enhaacplus_dec->audio_object_type);
2699
2700 if (ixheaacd_applysbr(
2701 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx],
2702 &p_state_enhaacplus_dec->pstr_stream_sbr[ch_idx][0],
2703 actual_out_buffer, &num_ch,
2704 p_obj_exhaacplus_dec->aac_config.frame_status,
2705 p_obj_exhaacplus_dec->aac_config.down_sample_flag,
2706 esbr_mono_downmix, &sbr_scratch_struct, ps_enable, ch_fac,
2707 slot_ele, NULL, &p_state_enhaacplus_dec->str_drc_dec_info,
2708 p_state_enhaacplus_dec->eld_specific_config.ld_sbr_flag_present,
2709 p_state_enhaacplus_dec->audio_object_type) != SBRDEC_OK) {
2710 p_state_enhaacplus_dec->str_sbr_dec_info[ch_idx] = 0;
2711 return -1;
2712 } else {
2713 if (!p_obj_exhaacplus_dec->aac_config.down_sample_flag) {
2714 frame_size = (WORD16)(frame_size * 2);
2715 sample_rate_dec *= 2;
2716 }
2717 }
2718 }
2719 }
2720 if (sample_rate < sample_rate_dec) {
2721 sample_rate = sample_rate_dec;
2722 }
2723
2724 p_obj_exhaacplus_dec->aac_config.ui_samp_freq = sample_rate;
2725 num_of_out_samples = frame_size;
2726
2727 p_state_enhaacplus_dec->num_channel_last = num_ch;
2728 p_state_enhaacplus_dec->num_of_out_samples = num_of_out_samples;
2729
2730 if (p_obj_exhaacplus_dec->aac_config.element_type[ch_idx] != 2)
2731
2732 {
2733 if (p_obj_exhaacplus_dec->aac_config.flag_to_stereo == 1 &&
2734 channel == 1 && total_elements == 1 && num_ch == 1) {
2735 WORD i;
2736 num_ch = 2;
2737
2738 for (i = 0; i < frame_size; i++) {
2739 actual_out_buffer[2 * i + 1] = actual_out_buffer[2 * i + 0];
2740 }
2741 }
2742
2743 p_obj_exhaacplus_dec->aac_config.ui_n_channels = num_ch;
2744
2745 p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes +=
2746 p_state_enhaacplus_dec->num_of_out_samples * num_ch * sizeof(WORD16);
2747
2748 }
2749
2750 else {
2751 channel_coupling_flag = 1;
2752 }
2753 }
2754
2755 {
2756 ia_adts_crc_info_struct *ptr_adts_crc_info =
2757 p_state_enhaacplus_dec->ptr_bit_stream->pstr_adts_crc_info;
2758 if (ptr_adts_crc_info->crc_active == 1) {
2759 if ((error_code = ixheaacd_adts_crc_check_crc(ptr_adts_crc_info))) {
2760 return error_code;
2761 }
2762 }
2763 }
2764
2765 p_obj_exhaacplus_dec->aac_config.ui_n_channels = total_channels;
2766
2767 p_state_enhaacplus_dec->frame_counter++;
2768
2769 if (channel_coupling_flag) {
2770 ixheaacd_dec_ind_coupling(p_obj_exhaacplus_dec,
2771 p_state_enhaacplus_dec->coup_ch_output,
2772 num_of_out_samples, total_channels, time_data);
2773 }
2774
2775 if ((total_channels > 2) && (1 == p_obj_exhaacplus_dec->aac_config.downmix)) {
2776 ixheaacd_dec_downmix_to_stereo(p_obj_exhaacplus_dec, num_of_out_samples,
2777 total_elements, time_data, total_channels);
2778
2779 total_channels = 2;
2780 p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes =
2781 p_state_enhaacplus_dec->num_of_out_samples * 2 * sizeof(WORD16);
2782 }
2783
2784 if (p_obj_exhaacplus_dec->aac_config.flag_downmix && total_channels == 2) {
2785 WORD32 out_ch = 1;
2786 WORD i;
2787 if (p_obj_exhaacplus_dec->aac_config.flag_to_stereo == 1) {
2788 out_ch = 2;
2789 }
2790
2791 p_obj_exhaacplus_dec->aac_config.ui_n_channels = out_ch;
2792 p_obj_exhaacplus_dec->p_state_aac->ui_out_bytes =
2793 p_state_enhaacplus_dec->num_of_out_samples * out_ch * sizeof(WORD16);
2794
2795 for (i = 0; i < num_of_out_samples; i++) {
2796 WORD16 temp;
2797
2798 temp = (time_data[2 * i + 0] >> 1) + (time_data[2 * i + 1] >> 1);
2799
2800 if (out_ch == 2) {
2801 time_data[2 * i + 0] = temp;
2802 time_data[2 * i + 1] = time_data[2 * i + 0];
2803 } else {
2804 time_data[i] = temp;
2805 }
2806 }
2807 }
2808
2809 if (p_state_enhaacplus_dec->s_adts_hdr_present) {
2810 if (adts.no_raw_data_blocks != 0) {
2811 if (adts.protection_absent == 0) {
2812 adts.crc_check = ixheaacd_read_bits_buf(it_bit_buff, 16);
2813 }
2814 }
2815 p_state_enhaacplus_dec->b_n_raw_data_blk--;
2816 }
2817
2818 ixheaacd_updatebytesconsumed(p_state_enhaacplus_dec, it_bit_buff);
2819
2820 if (p_state_enhaacplus_dec->bs_format == LOAS_BSFORMAT)
2821 p_state_enhaacplus_dec->i_bytes_consumed =
2822 (audio_mux_length_bytes_last + (SIZE_T)bytes_for_sync);
2823
2824 return error_code;
2825 }
2826