1 /******************************************************************************
2 *
3 * Copyright (C) 2018 The Android Open Source Project
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 *****************************************************************************
18 * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19 */
20 #include <stdio.h>
21 #include <stdlib.h>
22 #include <math.h>
23 #include <string.h>
24 #include "impd_type_def.h"
25 #include "impd_drc_extr_delta_coded_info.h"
26 #include "impd_drc_common.h"
27 #include "impd_drc_struct.h"
28 #include "impd_drc_interface.h"
29 #include "impd_drc_selection_process.h"
30 #include "impd_drc_sel_proc_drc_set_sel.h"
31
impd_drc_uni_selction_proc_init(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc,ia_drc_sel_proc_params_struct * pstr_drc_sel_proc_params_struct,ia_drc_interface_struct * pstr_drc_interface,WORD32 subband_domain_mode)32 WORD32 impd_drc_uni_selction_proc_init(
33 ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc,
34 ia_drc_sel_proc_params_struct* pstr_drc_sel_proc_params_struct,
35 ia_drc_interface_struct* pstr_drc_interface, WORD32 subband_domain_mode) {
36 WORD32 err = 0;
37
38 if (pstr_drc_uni_sel_proc == NULL) {
39 return 1;
40 }
41
42 if (pstr_drc_uni_sel_proc->first_frame == 1) {
43 err = impd_drc_sel_proc_init_dflt(pstr_drc_uni_sel_proc);
44 if (err) return (err);
45 }
46
47 err = impd_drc_sel_proc_init_sel_proc_params(pstr_drc_uni_sel_proc,
48 pstr_drc_sel_proc_params_struct);
49 if (err) return (err);
50 {
51 WORD32 i;
52 pstr_drc_uni_sel_proc->drc_set_id_valid_flag[0] = 1;
53 for (i = 1; i < DRC_INSTRUCTIONS_COUNT_MAX; i++) {
54 pstr_drc_uni_sel_proc->drc_set_id_valid_flag[i] = 0;
55 }
56
57 pstr_drc_uni_sel_proc->eq_set_id_valid_flag[0] = 1;
58 for (i = 1; i < EQ_INSTRUCTIONS_COUNT_MAX; i++) {
59 pstr_drc_uni_sel_proc->eq_set_id_valid_flag[i] = 0;
60 }
61 }
62 impd_drc_sel_proc_init_interface_params(pstr_drc_uni_sel_proc,
63 pstr_drc_interface);
64
65 pstr_drc_uni_sel_proc->subband_domain_mode = subband_domain_mode;
66
67 return 0;
68 }
69
70 WORD32
impd_drc_uni_sel_proc_process(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc,ia_drc_config * pstr_drc_config,ia_drc_loudness_info_set_struct * pstr_loudness_info,ia_drc_sel_proc_output_struct * hia_drc_sel_proc_output_struct)71 impd_drc_uni_sel_proc_process(
72 ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc,
73 ia_drc_config* pstr_drc_config,
74 ia_drc_loudness_info_set_struct* pstr_loudness_info,
75 ia_drc_sel_proc_output_struct* hia_drc_sel_proc_output_struct) {
76 WORD32 i, err, drc_set_id_selected, activeDrcSetIndex;
77 WORD32 eq_set_id_selected;
78 WORD32 loudEqSetIdSelected;
79
80 if (pstr_drc_config != NULL) {
81 if (memcmp(&pstr_drc_uni_sel_proc->drc_config, pstr_drc_config,
82 sizeof(ia_drc_config))) {
83 pstr_drc_uni_sel_proc->drc_config = *pstr_drc_config;
84 pstr_drc_uni_sel_proc->drc_config_flag = 1;
85
86 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.base_channel_count !=
87 pstr_drc_uni_sel_proc->drc_config.channel_layout.base_channel_count) {
88 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.base_channel_count =
89 pstr_drc_uni_sel_proc->drc_config.channel_layout.base_channel_count;
90 }
91 if (pstr_drc_uni_sel_proc->drc_config.channel_layout
92 .layout_signaling_present == 1 &&
93 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.base_layout !=
94 pstr_drc_uni_sel_proc->drc_config.channel_layout.defined_layout) {
95 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.base_layout =
96 pstr_drc_uni_sel_proc->drc_config.channel_layout.defined_layout;
97 }
98 } else {
99 pstr_drc_uni_sel_proc->drc_config_flag = 0;
100 }
101 }
102 if (pstr_loudness_info != NULL) {
103 if (memcmp(&pstr_drc_uni_sel_proc->loudness_info_set, pstr_loudness_info,
104 sizeof(ia_drc_loudness_info_set_struct))) {
105 pstr_drc_uni_sel_proc->loudness_info_set = *pstr_loudness_info;
106 pstr_drc_uni_sel_proc->loudness_info_set_flag = 1;
107 } else {
108 pstr_drc_uni_sel_proc->loudness_info_set_flag = 0;
109 }
110 }
111
112 if ((pstr_drc_uni_sel_proc->drc_config_flag &&
113 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
114 .target_config_request_type != 0) ||
115 (pstr_drc_uni_sel_proc->sel_proc_request_flag &&
116 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
117 .target_config_request_type != 0) ||
118 (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
119 .target_config_request_type == 0 &&
120 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.num_downmix_id_requests ==
121 0)) {
122 err = impd_map_target_config_req_downmix_id(
123 pstr_drc_uni_sel_proc, &pstr_drc_uni_sel_proc->drc_config);
124 if (err) return (err);
125 }
126
127 if (pstr_drc_uni_sel_proc->drc_config_flag ||
128 pstr_drc_uni_sel_proc->loudness_info_set_flag ||
129 pstr_drc_uni_sel_proc->sel_proc_request_flag) {
130 WORD32 repeat_selection = 1;
131
132 err = impd_manage_drc_complexity(pstr_drc_uni_sel_proc, pstr_drc_config);
133 if (err) return (err);
134 err = impd_manage_eq_complexity(pstr_drc_uni_sel_proc, pstr_drc_config);
135 if (err) return (err);
136 while (repeat_selection == 1) {
137 err = impd_select_drc_set(pstr_drc_uni_sel_proc, &drc_set_id_selected,
138 &eq_set_id_selected, &loudEqSetIdSelected);
139 if (err) return (err);
140
141 err =
142 impd_get_selected_drc_set(pstr_drc_uni_sel_proc, drc_set_id_selected);
143 if (err) return (err);
144
145 err = impd_get_dependent_drc_set(pstr_drc_uni_sel_proc);
146 if (err) return (err);
147
148 err = impd_get_fading_drc_set(pstr_drc_uni_sel_proc);
149 if (err) return (err);
150
151 err = impd_get_ducking_drc_set(pstr_drc_uni_sel_proc);
152 if (err) return (err);
153
154 pstr_drc_uni_sel_proc->eq_inst_index[0] = -1;
155 pstr_drc_uni_sel_proc->eq_inst_index[1] = -1;
156
157 err = impd_get_selected_eq_set(pstr_drc_uni_sel_proc, eq_set_id_selected);
158 if (err) return (err);
159
160 err = impd_get_dependent_eq_set(pstr_drc_uni_sel_proc);
161 if (err) return (err);
162
163 err = impd_get_selected_loud_eq_set(pstr_drc_uni_sel_proc,
164 loudEqSetIdSelected);
165 if (err) return (err);
166
167 activeDrcSetIndex = 0;
168 for (i = SUB_DRC_COUNT - 1; i >= 0; i--) {
169 WORD32 drc_instructions_index =
170 pstr_drc_uni_sel_proc->drc_instructions_index[i];
171 ia_drc_instructions_struct* str_drc_instruction_str;
172 if (drc_instructions_index < 0) continue;
173
174 str_drc_instruction_str =
175 &(pstr_drc_uni_sel_proc->drc_config
176 .str_drc_instruction_str[drc_instructions_index]);
177
178 if (str_drc_instruction_str->drc_set_id > 0) {
179 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
180 .sel_drc_set_ids[activeDrcSetIndex] =
181 str_drc_instruction_str->drc_set_id;
182
183 if ((i == 3) && (str_drc_instruction_str->drc_set_effect &
184 (EFFECT_BIT_DUCK_SELF | EFFECT_BIT_DUCK_OTHER))) {
185 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
186 .sel_downmix_ids[activeDrcSetIndex] = 0;
187 } else {
188 if (str_drc_instruction_str->drc_apply_to_dwnmix == 1) {
189 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
190 .sel_downmix_ids[activeDrcSetIndex] =
191 str_drc_instruction_str->downmix_id[0];
192 } else {
193 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
194 .sel_downmix_ids[activeDrcSetIndex] = 0;
195 }
196 }
197
198 activeDrcSetIndex++;
199 }
200 }
201 if (activeDrcSetIndex <= 3) {
202 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.num_sel_drc_sets =
203 activeDrcSetIndex;
204 } else {
205 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.num_sel_drc_sets = -1;
206 return (UNEXPECTED_ERROR);
207 }
208
209 impd_sel_downmix_matrix(pstr_drc_uni_sel_proc,
210 &pstr_drc_uni_sel_proc->drc_config);
211
212 err = impd_manage_complexity(pstr_drc_uni_sel_proc, pstr_drc_config,
213 &repeat_selection);
214 if (err) return (err);
215 }
216
217 pstr_drc_uni_sel_proc->sel_proc_request_flag = 0;
218 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.boost =
219 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.boost;
220 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.compress =
221 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.compress;
222 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.drc_characteristic_target =
223 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
224 .drc_characteristic_target;
225 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
226 .loudness_normalization_gain_db +=
227 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
228 .loudness_norm_gain_modification_db;
229 }
230 for (i = 0; i < 2; i++) {
231 if (pstr_drc_uni_sel_proc->eq_inst_index[i] >= 0) {
232 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_eq_set_ids[i] =
233 pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
234 .str_eq_instructions[pstr_drc_uni_sel_proc->eq_inst_index[i]]
235 .eq_set_id;
236 }
237 }
238 if (pstr_drc_uni_sel_proc->loud_eq_inst_index_sel >= 0) {
239 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_loud_eq_id =
240 pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
241 .loud_eq_instructions[pstr_drc_uni_sel_proc->loud_eq_inst_index_sel]
242 .loud_eq_set_id;
243 } else {
244 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_loud_eq_id = 0;
245 }
246 *hia_drc_sel_proc_output_struct =
247 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output;
248
249 return 0;
250 }
251
impd_map_target_config_req_downmix_id(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc,ia_drc_config * pstr_drc_config)252 WORD32 impd_map_target_config_req_downmix_id(
253 ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc,
254 ia_drc_config* pstr_drc_config) {
255 WORD32 i, dwnmix_instructions_count;
256 WORD32 target_ch_count_prelim =
257 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.base_channel_count;
258
259 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.num_downmix_id_requests = 0;
260 switch (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
261 .target_config_request_type) {
262 case 0:
263 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
264 .num_downmix_id_requests == 0) {
265 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.requested_dwnmix_id[0] =
266 0;
267 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.num_downmix_id_requests =
268 1;
269 }
270 break;
271 case 1:
272 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
273 .requested_target_layout ==
274 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.base_layout) {
275 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.requested_dwnmix_id[0] =
276 0;
277 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.num_downmix_id_requests =
278 1;
279 }
280 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
281 .num_downmix_id_requests == 0) {
282 dwnmix_instructions_count =
283 pstr_drc_uni_sel_proc->drc_config.dwnmix_instructions_count;
284 for (i = 0; i < dwnmix_instructions_count; i++) {
285 ia_downmix_instructions_struct* dwnmix_instructions =
286 &(pstr_drc_config->dwnmix_instructions[i]);
287 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
288 .requested_target_layout ==
289 dwnmix_instructions->target_layout) {
290 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.requested_dwnmix_id
291 [pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
292 .num_downmix_id_requests] =
293 dwnmix_instructions->downmix_id;
294 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
295 .num_downmix_id_requests += 1;
296 target_ch_count_prelim = dwnmix_instructions->target_channel_count;
297 }
298 }
299 }
300
301 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
302 .num_downmix_id_requests == 0) {
303 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.requested_dwnmix_id[0] =
304 0;
305 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.num_downmix_id_requests =
306 1;
307 }
308 break;
309 case 2:
310 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
311 .requested_target_ch_count ==
312 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.base_channel_count) {
313 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.requested_dwnmix_id[0] =
314 0;
315 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.num_downmix_id_requests =
316 1;
317 }
318 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
319 .num_downmix_id_requests == 0) {
320 dwnmix_instructions_count =
321 pstr_drc_uni_sel_proc->drc_config.dwnmix_instructions_count;
322 for (i = 0; i < dwnmix_instructions_count; i++) {
323 ia_downmix_instructions_struct* dwnmix_instructions =
324 &(pstr_drc_config->dwnmix_instructions[i]);
325 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
326 .requested_target_ch_count ==
327 dwnmix_instructions->target_channel_count) {
328 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.requested_dwnmix_id
329 [pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
330 .num_downmix_id_requests] =
331 dwnmix_instructions->downmix_id;
332 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
333 .num_downmix_id_requests += 1;
334 target_ch_count_prelim = dwnmix_instructions->target_channel_count;
335 }
336 }
337 }
338
339 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_params
340 .num_downmix_id_requests == 0) {
341 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.requested_dwnmix_id[0] =
342 0;
343 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.num_downmix_id_requests =
344 1;
345 }
346 break;
347 default:
348 return UNEXPECTED_ERROR;
349 break;
350 }
351 pstr_drc_uni_sel_proc->uni_drc_sel_proc_params.target_ch_count_prelim =
352 target_ch_count_prelim;
353
354 return 0;
355 }
356
impd_sel_downmix_matrix(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc,ia_drc_config * pstr_drc_config)357 VOID impd_sel_downmix_matrix(ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc,
358 ia_drc_config* pstr_drc_config) {
359 WORD32 i, j, n;
360
361 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.base_channel_count =
362 pstr_drc_config->channel_layout.base_channel_count;
363 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.target_channel_count =
364 pstr_drc_config->channel_layout.base_channel_count;
365 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.target_layout = -1;
366 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.downmix_matrix_present = 0;
367 pstr_drc_uni_sel_proc->downmix_inst_index_sel = -1;
368
369 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.active_downmix_id != 0) {
370 for (n = 0; n < pstr_drc_config->dwnmix_instructions_count; n++) {
371 ia_downmix_instructions_struct* dwnmix_instructions =
372 &(pstr_drc_config->dwnmix_instructions[n]);
373
374 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.active_downmix_id ==
375 dwnmix_instructions->downmix_id) {
376 pstr_drc_uni_sel_proc->downmix_inst_index_sel = n;
377 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.target_channel_count =
378 dwnmix_instructions->target_channel_count;
379 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.target_layout =
380 dwnmix_instructions->target_layout;
381 if (dwnmix_instructions->downmix_coefficients_present) {
382 for (i = 0; i < pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
383 .base_channel_count;
384 i++) {
385 for (j = 0; j < pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
386 .target_channel_count;
387 j++) {
388 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
389 .downmix_matrix[i][j] =
390 dwnmix_instructions->downmix_coefficient
391 [i +
392 j *
393 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
394 .base_channel_count];
395 }
396 }
397 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output
398 .downmix_matrix_present = 1;
399 }
400 break;
401 }
402 }
403 }
404 return;
405 }
406
impd_get_selected_eq_set(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc,WORD32 eq_set_id_selected)407 WORD32 impd_get_selected_eq_set(ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc,
408 WORD32 eq_set_id_selected) {
409 WORD32 n;
410
411 pstr_drc_uni_sel_proc->eq_inst_index_sel = -1;
412
413 if (eq_set_id_selected > 0) {
414 for (n = 0; n < pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
415 .eq_instructions_count;
416 n++) {
417 if (pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
418 .str_eq_instructions[n]
419 .eq_set_id == eq_set_id_selected)
420 break;
421 }
422 if (n ==
423 pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
424 .eq_instructions_count) {
425 return (EXTERNAL_ERROR);
426 }
427 pstr_drc_uni_sel_proc->eq_inst_index_sel = n;
428 if (pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
429 .str_eq_instructions[n]
430 .eq_apply_to_downmix == 1) {
431 pstr_drc_uni_sel_proc->eq_inst_index[1] =
432 pstr_drc_uni_sel_proc->eq_inst_index_sel;
433 } else {
434 pstr_drc_uni_sel_proc->eq_inst_index[0] =
435 pstr_drc_uni_sel_proc->eq_inst_index_sel;
436 }
437 }
438 return (0);
439 }
440
impd_get_dependent_eq_set(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc)441 WORD32 impd_get_dependent_eq_set(ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc) {
442 ia_eq_instructions_struct* str_eq_instructions = NULL;
443
444 if (pstr_drc_uni_sel_proc->eq_inst_index_sel >= 0) {
445 str_eq_instructions =
446 &(pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
447 .str_eq_instructions[pstr_drc_uni_sel_proc->eq_inst_index_sel]);
448
449 if (str_eq_instructions->depends_on_eq_set_present == 1) {
450 WORD32 n;
451 WORD32 dependsOnEqSetID = str_eq_instructions->depends_on_eq_set;
452
453 for (n = 0; n < pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
454 .eq_instructions_count;
455 n++) {
456 if (pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
457 .str_eq_instructions[n]
458 .eq_set_id == dependsOnEqSetID)
459 break;
460 }
461 if (n ==
462 pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
463 .eq_instructions_count) {
464 return (UNEXPECTED_ERROR);
465 }
466 if (pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
467 .str_eq_instructions[n]
468 .eq_apply_to_downmix == 1) {
469 pstr_drc_uni_sel_proc->eq_inst_index[1] = n;
470 } else {
471 pstr_drc_uni_sel_proc->eq_inst_index[0] = n;
472 }
473 }
474 }
475 return (0);
476 }
477
impd_get_selected_loud_eq_set(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc,WORD32 loudEqSetIdSelected)478 WORD32 impd_get_selected_loud_eq_set(
479 ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc, WORD32 loudEqSetIdSelected) {
480 WORD32 n;
481
482 pstr_drc_uni_sel_proc->loud_eq_inst_index_sel = -1;
483
484 if (loudEqSetIdSelected > 0) {
485 for (n = 0; n < pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
486 .loud_eq_instructions_count;
487 n++) {
488 if (pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
489 .loud_eq_instructions[n]
490 .loud_eq_set_id == loudEqSetIdSelected)
491 break;
492 }
493 if (n ==
494 pstr_drc_uni_sel_proc->drc_config.str_drc_config_ext
495 .loud_eq_instructions_count) {
496 return (EXTERNAL_ERROR);
497 }
498 pstr_drc_uni_sel_proc->loud_eq_inst_index_sel = n;
499 }
500 return (0);
501 }
502
impd_select_loud_eq(ia_drc_config * pstr_drc_config,WORD32 requested_dwnmix_id,WORD32 drc_set_id_requested,WORD32 eq_set_id_requested,WORD32 * loud_eq_id_sel)503 WORD32 impd_select_loud_eq(ia_drc_config* pstr_drc_config,
504 WORD32 requested_dwnmix_id,
505 WORD32 drc_set_id_requested,
506 WORD32 eq_set_id_requested, WORD32* loud_eq_id_sel) {
507 WORD32 i, c, d, e;
508
509 *loud_eq_id_sel = 0;
510 for (i = 0;
511 i < pstr_drc_config->str_drc_config_ext.loud_eq_instructions_count;
512 i++) {
513 ia_loud_eq_instructions_struct* loud_eq_instructions =
514 &pstr_drc_config->str_drc_config_ext.loud_eq_instructions[i];
515 if (loud_eq_instructions->drc_location == LOCATION_SELECTED) {
516 for (d = 0; d < loud_eq_instructions->dwnmix_id_count; d++) {
517 if ((loud_eq_instructions->downmix_id[d] == requested_dwnmix_id) ||
518 (loud_eq_instructions->downmix_id[d] == ID_FOR_ANY_DOWNMIX)) {
519 for (c = 0; c < loud_eq_instructions->drc_set_id_count; c++) {
520 if ((loud_eq_instructions->drc_set_id[c] == drc_set_id_requested) ||
521 (loud_eq_instructions->drc_set_id[c] == ID_FOR_ANY_DRC)) {
522 for (e = 0; e < loud_eq_instructions->eq_set_id_count; e++) {
523 if ((loud_eq_instructions->eq_set_id[e] ==
524 eq_set_id_requested) ||
525 (loud_eq_instructions->eq_set_id[e] == ID_FOR_ANY_EQ)) {
526 *loud_eq_id_sel = loud_eq_instructions->loud_eq_set_id;
527 }
528 }
529 }
530 }
531 }
532 }
533 }
534 }
535 return (0);
536 }
537
impd_match_eq_set(ia_drc_config * drc_config,WORD32 downmix_id,WORD32 drc_set_id,WORD32 * eq_set_id_valid_flag,WORD32 * matching_eq_set_count,WORD32 * matching_eq_set_idx)538 WORD32 impd_match_eq_set(ia_drc_config* drc_config, WORD32 downmix_id,
539 WORD32 drc_set_id, WORD32* eq_set_id_valid_flag,
540 WORD32* matching_eq_set_count,
541 WORD32* matching_eq_set_idx) {
542 ia_eq_instructions_struct* str_eq_instructions = NULL;
543 WORD32 i, k, n;
544 WORD32 match = 0;
545 *matching_eq_set_count = 0;
546 for (i = 0; i < drc_config->str_drc_config_ext.eq_instructions_count; i++) {
547 str_eq_instructions =
548 &drc_config->str_drc_config_ext.str_eq_instructions[i];
549
550 if (str_eq_instructions->depends_on_eq_set_present == 0) {
551 if (str_eq_instructions->no_independent_eq_use == 1) continue;
552 }
553 if (eq_set_id_valid_flag[str_eq_instructions->eq_set_id] == 0) continue;
554 for (k = 0; k < str_eq_instructions->dwnmix_id_count; k++) {
555 if ((str_eq_instructions->downmix_id[k] == ID_FOR_ANY_DOWNMIX) ||
556 (downmix_id == str_eq_instructions->downmix_id[k])) {
557 for (n = 0; n < str_eq_instructions->drc_set_id_count; n++) {
558 if ((str_eq_instructions->drc_set_id[n] == ID_FOR_ANY_DRC) ||
559 (drc_set_id == str_eq_instructions->drc_set_id[n])) {
560 match = 1;
561 matching_eq_set_idx[*matching_eq_set_count] = i;
562 (*matching_eq_set_count)++;
563 }
564 }
565 }
566 }
567 }
568 return (0);
569 }
570
impd_match_eq_set_purpose(ia_drc_config * drc_config,WORD32 eq_set_purpose_requested,WORD32 * eq_set_id_valid_flag,WORD32 * selection_candidate_count,ia_selection_candidate_info_struct * selection_candidate_info,ia_selection_candidate_info_struct * selection_candidate_info_step_2)571 WORD32 impd_match_eq_set_purpose(
572 ia_drc_config* drc_config, WORD32 eq_set_purpose_requested,
573 WORD32* eq_set_id_valid_flag, WORD32* selection_candidate_count,
574 ia_selection_candidate_info_struct* selection_candidate_info,
575 ia_selection_candidate_info_struct* selection_candidate_info_step_2) {
576 WORD32 i, j, k;
577 WORD32 match_found_flag;
578 WORD32 loop_cnt = 0;
579 ia_eq_instructions_struct* str_eq_instructions = NULL;
580 match_found_flag = 0;
581
582 k = 0;
583 while ((k == 0) && (loop_cnt < 2)) {
584 for (j = 0; j < *selection_candidate_count; j++) {
585 WORD32 eq_set_id_requested = selection_candidate_info[j].eq_set_id;
586
587 for (i = 0; i < drc_config->str_drc_config_ext.eq_instructions_count;
588 i++) {
589 str_eq_instructions =
590 &drc_config->str_drc_config_ext.str_eq_instructions[i];
591
592 if (str_eq_instructions->depends_on_eq_set_present == 0) {
593 if (eq_set_id_valid_flag[str_eq_instructions->eq_set_id] == 0)
594 continue;
595 }
596 if (eq_set_id_valid_flag[str_eq_instructions->eq_set_id] == 0) continue;
597 if ((str_eq_instructions->eq_set_id == eq_set_id_requested) &&
598 (str_eq_instructions->eq_set_purpose & eq_set_purpose_requested)) {
599 match_found_flag = 1;
600 }
601 }
602
603 if (match_found_flag > 0) {
604 memcpy(&selection_candidate_info_step_2[k],
605 &selection_candidate_info[j],
606 sizeof(ia_selection_candidate_info_struct));
607 k++;
608 }
609 }
610 eq_set_purpose_requested = EQ_PURPOSE_DEFAULT;
611 loop_cnt++;
612 }
613
614 if (k > 0) {
615 memcpy(&selection_candidate_info[0], &selection_candidate_info_step_2[0],
616 k * sizeof(ia_selection_candidate_info_struct));
617 *selection_candidate_count = k;
618 }
619
620 return (0);
621 }
622
impd_find_eq_set_no_compression(ia_drc_config * pstr_drc_config,WORD32 requested_dwnmix_id,WORD32 * num_compression_eq_count,WORD32 * num_compression_eq_id)623 WORD32 impd_find_eq_set_no_compression(ia_drc_config* pstr_drc_config,
624 WORD32 requested_dwnmix_id,
625 WORD32* num_compression_eq_count,
626 WORD32* num_compression_eq_id) {
627 WORD32 i, d, k, c;
628 k = 0;
629 for (i = 0; i < pstr_drc_config->str_drc_config_ext.eq_instructions_count;
630 i++) {
631 ia_eq_instructions_struct* str_eq_instructions =
632 &pstr_drc_config->str_drc_config_ext.str_eq_instructions[i];
633 for (d = 0; d < str_eq_instructions->dwnmix_id_count; d++) {
634 if (requested_dwnmix_id == str_eq_instructions->downmix_id[d]) {
635 for (c = 0; c < str_eq_instructions->drc_set_id_count; c++) {
636 if ((str_eq_instructions->drc_set_id[c] == ID_FOR_ANY_DRC) ||
637 (str_eq_instructions->drc_set_id[c] == 0)) {
638 if (k >= MAX_NUM_COMPRESSION_EQ) return UNEXPECTED_ERROR;
639 num_compression_eq_id[k] = str_eq_instructions->eq_set_id;
640 k++;
641 }
642 }
643 }
644 }
645 }
646 *num_compression_eq_count = k;
647 return (0);
648 }
649
impd_select_drc_coeff3(ia_drc_config * drc_config,ia_uni_drc_coeffs_struct ** str_p_loc_drc_coefficients_uni_drc)650 VOID impd_select_drc_coeff3(
651 ia_drc_config* drc_config,
652 ia_uni_drc_coeffs_struct** str_p_loc_drc_coefficients_uni_drc) {
653 WORD32 n;
654 WORD32 cV1 = -1;
655 WORD32 cV0 = -1;
656 for (n = 0; n < drc_config->drc_coefficients_drc_count; n++) {
657 if (drc_config->str_p_loc_drc_coefficients_uni_drc[n].drc_location == 1) {
658 if (drc_config->str_p_loc_drc_coefficients_uni_drc[n].version == 0) {
659 cV0 = n;
660 } else {
661 cV1 = n;
662 }
663 }
664 }
665 if (cV1 >= 0) {
666 *str_p_loc_drc_coefficients_uni_drc =
667 &(drc_config->str_p_loc_drc_coefficients_uni_drc[cV1]);
668 } else if (cV0 >= 0) {
669 *str_p_loc_drc_coefficients_uni_drc =
670 &(drc_config->str_p_loc_drc_coefficients_uni_drc[cV0]);
671 } else {
672 *str_p_loc_drc_coefficients_uni_drc = NULL;
673 }
674 return;
675 }
676
impd_manage_drc_complexity(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc,ia_drc_config * pstr_drc_config)677 WORD32 impd_manage_drc_complexity(ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc,
678 ia_drc_config* pstr_drc_config) {
679 WORD32 i, j, err, channel_count;
680 WORD32 numBandsTooLarge = 0;
681 FLOAT32 complexityDrcPrelim;
682 ia_uni_drc_coeffs_struct* str_p_loc_drc_coefficients_uni_drc;
683 FLOAT32 complexitySupportedTotal =
684 (FLOAT32)(pow(2.0f, pstr_drc_uni_sel_proc->compl_level_supported_total));
685 ia_drc_instructions_struct* str_drc_instruction_str;
686 ia_drc_instructions_struct* drc_inst_uni_drc_dependent;
687 ia_drc_sel_proc_output_struct* uni_drc_sel_proc_output =
688 &pstr_drc_uni_sel_proc->uni_drc_sel_proc_output;
689 ia_drc_sel_proc_params_struct* pstr_drc_sel_proc_params_struct =
690 &pstr_drc_uni_sel_proc->uni_drc_sel_proc_params;
691
692 impd_select_drc_coeff3(pstr_drc_config, &str_p_loc_drc_coefficients_uni_drc);
693 if (str_p_loc_drc_coefficients_uni_drc == NULL) return UNEXPECTED_ERROR;
694 for (i = 0; i < pstr_drc_config->drc_instructions_uni_drc_count; i++) {
695 str_drc_instruction_str = &pstr_drc_config->str_drc_instruction_str[i];
696 if (str_drc_instruction_str->no_independent_use) continue;
697
698 numBandsTooLarge = 0;
699 if (str_drc_instruction_str->drc_apply_to_dwnmix == 1) {
700 channel_count = uni_drc_sel_proc_output->target_channel_count;
701 } else {
702 channel_count = uni_drc_sel_proc_output->base_channel_count;
703 }
704 if (pstr_drc_uni_sel_proc->subband_domain_mode == SUBBAND_DOMAIN_MODE_OFF) {
705 for (j = 0; j < str_drc_instruction_str->num_drc_ch_groups; j++) {
706 ia_gain_set_params_struct* gain_set_params = &(
707 str_p_loc_drc_coefficients_uni_drc->gain_set_params
708 [str_drc_instruction_str->gain_set_index_for_channel_group[j]]);
709 if (gain_set_params->band_count >
710 pstr_drc_sel_proc_params_struct->num_bands_supported) {
711 numBandsTooLarge = 1;
712 } else {
713 if (gain_set_params->band_count > 4) {
714 /* Add complexity for analysis and synthesis QMF bank here, if
715 * supported */
716 }
717 }
718 }
719 }
720 complexityDrcPrelim =
721 (FLOAT32)(channel_count *
722 (1 << str_drc_instruction_str->drc_set_complexity_level));
723
724 if (str_drc_instruction_str->depends_on_drc_set > 0) {
725 err = impd_find_drc_instructions_uni_drc(
726 pstr_drc_config, str_drc_instruction_str->depends_on_drc_set,
727 &drc_inst_uni_drc_dependent);
728 if (err) return (err);
729 if (drc_inst_uni_drc_dependent->drc_apply_to_dwnmix == 1) {
730 channel_count = uni_drc_sel_proc_output->target_channel_count;
731 } else {
732 channel_count = uni_drc_sel_proc_output->base_channel_count;
733 }
734 if (pstr_drc_uni_sel_proc->subband_domain_mode ==
735 SUBBAND_DOMAIN_MODE_OFF) {
736 for (j = 0; j < str_drc_instruction_str->num_drc_ch_groups; j++) {
737 ia_gain_set_params_struct* gain_set_params = &(
738 str_p_loc_drc_coefficients_uni_drc
739 ->gain_set_params[drc_inst_uni_drc_dependent
740 ->gain_set_index_for_channel_group[j]]);
741 if (gain_set_params->band_count >
742 pstr_drc_sel_proc_params_struct->num_bands_supported) {
743 numBandsTooLarge = 1;
744 } else {
745 if (gain_set_params->band_count > 4) {
746 /* Add complexity for analysis and synthesis QMF bank here, if
747 * supported */
748 }
749 }
750 }
751 }
752 complexityDrcPrelim +=
753 channel_count *
754 (1 << drc_inst_uni_drc_dependent->drc_set_complexity_level);
755 }
756
757 complexityDrcPrelim *= pstr_drc_config->sampling_rate / 48000.0f;
758
759 if ((complexityDrcPrelim <= complexitySupportedTotal) &&
760 (numBandsTooLarge == 0)) {
761 pstr_drc_uni_sel_proc
762 ->drc_set_id_valid_flag[str_drc_instruction_str->drc_set_id] = 1;
763 }
764 }
765 return (0);
766 }
767
impd_manage_eq_complexity(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc,ia_drc_config * pstr_drc_config)768 WORD32 impd_manage_eq_complexity(ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc,
769 ia_drc_config* pstr_drc_config) {
770 WORD32 k, n, m, err;
771 WORD32 eqComplexityPrimary = 0;
772 WORD32 eqComplexityDependent = 0;
773 WORD32 eqChannelCountPrimary = 0, eqChannelCountDependent = 0;
774 FLOAT32 complexityTotalEq;
775 ia_drc_config* drc_config = &pstr_drc_uni_sel_proc->drc_config;
776 ia_drc_sel_proc_params_struct* pstr_drc_sel_proc_params_struct =
777 &pstr_drc_uni_sel_proc->uni_drc_sel_proc_params;
778 FLOAT32 complexitySupportedTotal =
779 (FLOAT32)(pow(2.0f, pstr_drc_uni_sel_proc->compl_level_supported_total));
780
781 for (n = 0; n < drc_config->str_drc_config_ext.eq_instructions_count; n++) {
782 ia_eq_instructions_struct* str_eq_instructions =
783 &pstr_drc_config->str_drc_config_ext.str_eq_instructions[n];
784
785 eqChannelCountPrimary = pstr_drc_sel_proc_params_struct->base_channel_count;
786 eqChannelCountDependent =
787 pstr_drc_sel_proc_params_struct->base_channel_count;
788
789 eqComplexityPrimary = 1 << str_eq_instructions->eq_set_complexity_level;
790 if (pstr_drc_uni_sel_proc->subband_domain_mode == SUBBAND_DOMAIN_MODE_OFF) {
791 if (str_eq_instructions->td_filter_cascade_present == 0) {
792 eqComplexityPrimary = 0;
793 }
794 } else {
795 if (str_eq_instructions->td_filter_cascade_present == 1) {
796 eqComplexityPrimary = (WORD32)2.5f;
797 }
798 }
799 if (str_eq_instructions->eq_apply_to_downmix == 1) {
800 if (str_eq_instructions->downmix_id[0] == ID_FOR_ANY_DOWNMIX) {
801 eqChannelCountPrimary =
802 pstr_drc_sel_proc_params_struct->target_ch_count_prelim;
803 } else {
804 for (k = 0; k < pstr_drc_config->dwnmix_instructions_count; k++) {
805 for (m = 0; m < str_eq_instructions->dwnmix_id_count; m++) {
806 if (pstr_drc_config->dwnmix_instructions[k].downmix_id ==
807 str_eq_instructions->downmix_id[m]) {
808 if (eqChannelCountPrimary >
809 pstr_drc_config->dwnmix_instructions[k]
810 .target_channel_count) {
811 eqChannelCountPrimary = pstr_drc_config->dwnmix_instructions[k]
812 .target_channel_count;
813 }
814 }
815 }
816 }
817 }
818 }
819 complexityTotalEq = (FLOAT32)(eqChannelCountPrimary * eqComplexityPrimary);
820
821 if (str_eq_instructions->depends_on_eq_set_present > 0) {
822 ia_eq_instructions_struct* eq_instructionsDependent;
823 err = impd_find_eq_instructions(drc_config,
824 str_eq_instructions->depends_on_eq_set,
825 &eq_instructionsDependent);
826 if (err) return (err);
827 eqComplexityDependent =
828 1 << eq_instructionsDependent->eq_set_complexity_level;
829 if (pstr_drc_uni_sel_proc->subband_domain_mode ==
830 SUBBAND_DOMAIN_MODE_OFF) {
831 if (str_eq_instructions->td_filter_cascade_present == 0) {
832 eqComplexityDependent = 0;
833 }
834 } else {
835 if (str_eq_instructions->td_filter_cascade_present == 1) {
836 eqComplexityDependent = (WORD32)2.5f;
837 }
838 }
839 if (eq_instructionsDependent->eq_apply_to_downmix == 1) {
840 if (eq_instructionsDependent->downmix_id[0] == ID_FOR_ANY_DOWNMIX) {
841 eqChannelCountDependent =
842 pstr_drc_sel_proc_params_struct->target_ch_count_prelim;
843 } else {
844 for (k = 0; k < pstr_drc_config->dwnmix_instructions_count; k++) {
845 for (m = 0; m < str_eq_instructions->dwnmix_id_count; m++) {
846 if (pstr_drc_config->dwnmix_instructions[k].downmix_id ==
847 eq_instructionsDependent->downmix_id[m]) {
848 if (eqChannelCountDependent >
849 pstr_drc_config->dwnmix_instructions[k]
850 .target_channel_count) {
851 eqChannelCountDependent =
852 pstr_drc_config->dwnmix_instructions[k]
853 .target_channel_count;
854 }
855 }
856 }
857 }
858 }
859 }
860 complexityTotalEq += eqChannelCountDependent * eqComplexityDependent;
861 }
862
863 pstr_drc_uni_sel_proc
864 ->eq_set_id_valid_flag[str_eq_instructions->eq_set_id] = 0;
865 complexityTotalEq *= pstr_drc_config->sampling_rate / 48000.0f;
866
867 if (complexityTotalEq <= complexitySupportedTotal) {
868 pstr_drc_uni_sel_proc
869 ->eq_set_id_valid_flag[str_eq_instructions->eq_set_id] = 1;
870 }
871 }
872 return 0;
873 }
874
impd_manage_complexity(ia_drc_sel_pro_struct * pstr_drc_uni_sel_proc,ia_drc_config * pstr_drc_config,WORD32 * repeat_selection)875 WORD32 impd_manage_complexity(ia_drc_sel_pro_struct* pstr_drc_uni_sel_proc,
876 ia_drc_config* pstr_drc_config,
877 WORD32* repeat_selection) {
878 WORD32 i, j, p, err;
879 WORD32 channel_count;
880 WORD32 numBandsTooLarge = 0;
881 WORD32 drcRequiresEq;
882 FLOAT32 complexityEq;
883 FLOAT32 complexityDrcTotal = 0.0f;
884 FLOAT32 complexityEqTotal = 0.0f;
885 FLOAT32 freqNorm = pstr_drc_config->sampling_rate / 48000.0f;
886 ia_uni_drc_coeffs_struct* str_p_loc_drc_coefficients_uni_drc;
887 ia_drc_instructions_struct* str_drc_instruction_str =
888 &pstr_drc_config->str_drc_instruction_str[0];
889 ia_drc_sel_proc_output_struct* uni_drc_sel_proc_output =
890 &pstr_drc_uni_sel_proc->uni_drc_sel_proc_output;
891 ia_drc_sel_proc_params_struct* pstr_drc_sel_proc_params_struct =
892 &pstr_drc_uni_sel_proc->uni_drc_sel_proc_params;
893 FLOAT32 complexitySupportedTotal =
894 (FLOAT32)(pow(2.0f, pstr_drc_uni_sel_proc->compl_level_supported_total));
895
896 impd_select_drc_coeff3(pstr_drc_config, &str_p_loc_drc_coefficients_uni_drc);
897
898 if (str_p_loc_drc_coefficients_uni_drc == NULL) return UNEXPECTED_ERROR;
899
900 for (p = 0; p < 4; p++) {
901 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[p] <= 0)
902 continue;
903 err = impd_find_drc_instructions_uni_drc(
904 pstr_drc_config,
905 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[p],
906 &str_drc_instruction_str);
907 if (err) return (err);
908
909 if (str_drc_instruction_str->drc_apply_to_dwnmix == 1) {
910 channel_count = uni_drc_sel_proc_output->target_channel_count;
911 } else {
912 channel_count = uni_drc_sel_proc_output->base_channel_count;
913 }
914 if (pstr_drc_uni_sel_proc->subband_domain_mode == SUBBAND_DOMAIN_MODE_OFF) {
915 for (j = 0; j < str_drc_instruction_str->num_drc_ch_groups; j++) {
916 ia_gain_set_params_struct* gain_set_params = &(
917 str_p_loc_drc_coefficients_uni_drc->gain_set_params
918 [str_drc_instruction_str->gain_set_index_for_channel_group[j]]);
919 if (gain_set_params->band_count >
920 pstr_drc_sel_proc_params_struct->num_bands_supported) {
921 if (p < 2) {
922 numBandsTooLarge = 1;
923 } else {
924 pstr_drc_uni_sel_proc
925 ->drc_set_id_valid_flag[str_drc_instruction_str->drc_set_id] =
926 0;
927 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[p] =
928 0;
929 }
930 } else {
931 if (gain_set_params->band_count > 4) {
932 /* Add complexity for analysis and synthesis QMF bank here, if
933 * supported */
934 }
935 }
936 }
937 }
938 complexityDrcTotal +=
939 channel_count *
940 (1 << str_drc_instruction_str->drc_set_complexity_level);
941 }
942
943 if (uni_drc_sel_proc_output->active_downmix_id > 0) {
944 FLOAT32 complexityPerCoeff;
945 ia_downmix_instructions_struct* dwnmix_instructions;
946
947 if (pstr_drc_uni_sel_proc->subband_domain_mode == SUBBAND_DOMAIN_MODE_OFF) {
948 complexityPerCoeff = 1.0f;
949 } else {
950 complexityPerCoeff = 2.0f;
951 }
952 err = impd_find_downmix(pstr_drc_config,
953 uni_drc_sel_proc_output->active_downmix_id,
954 &dwnmix_instructions);
955 if (err) return (err);
956 if (dwnmix_instructions->downmix_coefficients_present == 1) {
957 for (i = 0; i < uni_drc_sel_proc_output->base_channel_count; i++) {
958 for (j = 0; j < uni_drc_sel_proc_output->target_channel_count; j++) {
959 if (uni_drc_sel_proc_output->downmix_matrix[i][j] != 0.0f) {
960 complexityDrcTotal += complexityPerCoeff;
961 }
962 }
963 }
964 } else {
965 /* add standard downmix here */
966 }
967 }
968
969 for (p = 0; p < 2; p++) {
970 if (pstr_drc_uni_sel_proc->eq_inst_index[p] >= 0) {
971 ia_eq_instructions_struct* str_eq_instructions =
972 &pstr_drc_config->str_drc_config_ext
973 .str_eq_instructions[pstr_drc_uni_sel_proc->eq_inst_index[p]];
974 if (p == 0) {
975 channel_count = uni_drc_sel_proc_output->base_channel_count;
976 } else {
977 channel_count = uni_drc_sel_proc_output->target_channel_count;
978 }
979
980 complexityEq =
981 (FLOAT32)(1 << str_eq_instructions->eq_set_complexity_level);
982 if (pstr_drc_uni_sel_proc->subband_domain_mode ==
983 SUBBAND_DOMAIN_MODE_OFF) {
984 if (str_eq_instructions->td_filter_cascade_present == 0) {
985 complexityEq = 0.0;
986 }
987 } else {
988 if (str_eq_instructions->td_filter_cascade_present == 1) {
989 complexityEq = 2.5;
990 }
991 }
992
993 complexityEqTotal += channel_count * complexityEq;
994 }
995 }
996
997 complexityDrcTotal *= freqNorm;
998 complexityEqTotal *= freqNorm;
999
1000 if ((complexityDrcTotal > complexitySupportedTotal) ||
1001 (complexityEqTotal > complexitySupportedTotal))
1002 return UNEXPECTED_ERROR;
1003
1004 if (numBandsTooLarge == 1) {
1005 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[0] > 0) {
1006 err = impd_find_drc_instructions_uni_drc(
1007 pstr_drc_config,
1008 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[0],
1009 &str_drc_instruction_str);
1010 if (err) return (err);
1011
1012 pstr_drc_uni_sel_proc
1013 ->drc_set_id_valid_flag[str_drc_instruction_str->drc_set_id] = 0;
1014 }
1015 *repeat_selection = 1;
1016 } else {
1017 if (complexityDrcTotal + complexityEqTotal <= complexitySupportedTotal) {
1018 *repeat_selection = 0;
1019 } else {
1020 drcRequiresEq = 0;
1021 for (p = 0; p < 2; p++) {
1022 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[p] <=
1023 0)
1024 continue;
1025 err = impd_find_drc_instructions_uni_drc(
1026 pstr_drc_config,
1027 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[p],
1028 &str_drc_instruction_str);
1029 if (err) return (err);
1030 if (str_drc_instruction_str->requires_eq == 1) {
1031 drcRequiresEq = 1;
1032 }
1033 }
1034 if ((drcRequiresEq == 0) &&
1035 (complexityDrcTotal <= complexitySupportedTotal)) {
1036 for (p = 0; p < 2; p++) {
1037 pstr_drc_uni_sel_proc->eq_inst_index[p] = 0;
1038 }
1039 *repeat_selection = 0;
1040 } else {
1041 if (pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[0] >
1042 0) {
1043 err = impd_find_drc_instructions_uni_drc(
1044 pstr_drc_config,
1045 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[0],
1046 &str_drc_instruction_str);
1047 if (err) return (err);
1048
1049 pstr_drc_uni_sel_proc
1050 ->drc_set_id_valid_flag[str_drc_instruction_str->drc_set_id] = 0;
1051 } else {
1052 for (p = 2; p < 4; p++) {
1053 pstr_drc_uni_sel_proc
1054 ->drc_set_id_valid_flag[str_drc_instruction_str->drc_set_id] =
1055 0;
1056 pstr_drc_uni_sel_proc->uni_drc_sel_proc_output.sel_drc_set_ids[p] =
1057 0;
1058 }
1059 }
1060 *repeat_selection = 1;
1061 }
1062 }
1063 }
1064
1065 if (*repeat_selection == 1) {
1066 memset(&pstr_drc_uni_sel_proc->uni_drc_sel_proc_output, 0,
1067 sizeof(ia_drc_sel_proc_output_struct));
1068 }
1069 return (0);
1070 }
1071
impd_find_loud_eq_instructions_idx_for_id(ia_drc_config * drc_config,WORD32 loud_eq_set_id_requested,WORD32 * instructions_idx)1072 WORD32 impd_find_loud_eq_instructions_idx_for_id(
1073 ia_drc_config* drc_config, WORD32 loud_eq_set_id_requested,
1074 WORD32* instructions_idx) {
1075 WORD32 i;
1076 if (loud_eq_set_id_requested > 0) {
1077 for (i = 0; i < drc_config->str_drc_config_ext.loud_eq_instructions_count;
1078 i++) {
1079 if (drc_config->str_drc_config_ext.loud_eq_instructions[i]
1080 .loud_eq_set_id == loud_eq_set_id_requested)
1081 break;
1082 }
1083 if (i == drc_config->str_drc_config_ext.loud_eq_instructions_count) {
1084 return (UNEXPECTED_ERROR);
1085 }
1086 *instructions_idx = i;
1087 } else {
1088 *instructions_idx = -1;
1089 }
1090 return (0);
1091 }
1092
impd_find_eq_instructions(ia_drc_config * drc_config,WORD32 eq_set_id_requested,ia_eq_instructions_struct ** str_eq_instructions)1093 WORD32 impd_find_eq_instructions(
1094 ia_drc_config* drc_config, WORD32 eq_set_id_requested,
1095 ia_eq_instructions_struct** str_eq_instructions) {
1096 WORD32 i;
1097 for (i = 0; i < drc_config->str_drc_config_ext.eq_instructions_count; i++) {
1098 if (eq_set_id_requested ==
1099 drc_config->str_drc_config_ext.str_eq_instructions[i].eq_set_id)
1100 break;
1101 }
1102 if (i == drc_config->str_drc_config_ext.eq_instructions_count) {
1103 return (UNEXPECTED_ERROR);
1104 }
1105 *str_eq_instructions = &drc_config->str_drc_config_ext.str_eq_instructions[i];
1106 return (0);
1107 }
1108
impd_find_downmix(ia_drc_config * drc_config,WORD32 requested_dwnmix_id,ia_downmix_instructions_struct ** dwnmix_instructions)1109 WORD32 impd_find_downmix(ia_drc_config* drc_config, WORD32 requested_dwnmix_id,
1110 ia_downmix_instructions_struct** dwnmix_instructions) {
1111 WORD32 i;
1112 for (i = 0; i < drc_config->dwnmix_instructions_count; i++) {
1113 if (requested_dwnmix_id == drc_config->dwnmix_instructions[i].downmix_id)
1114 break;
1115 }
1116 if (i == drc_config->dwnmix_instructions_count) {
1117 return (UNEXPECTED_ERROR);
1118 }
1119 *dwnmix_instructions = &drc_config->dwnmix_instructions[i];
1120 return (0);
1121 }
1122