1 /* -----------------------------------------------------------------------------
2 Software License for The Fraunhofer FDK AAC Codec Library for Android
3
4 © Copyright 1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
5 Forschung e.V. All rights reserved.
6
7 1. INTRODUCTION
8 The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software
9 that implements the MPEG Advanced Audio Coding ("AAC") encoding and decoding
10 scheme for digital audio. This FDK AAC Codec software is intended to be used on
11 a wide variety of Android devices.
12
13 AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient
14 general perceptual audio codecs. AAC-ELD is considered the best-performing
15 full-bandwidth communications codec by independent studies and is widely
16 deployed. AAC has been standardized by ISO and IEC as part of the MPEG
17 specifications.
18
19 Patent licenses for necessary patent claims for the FDK AAC Codec (including
20 those of Fraunhofer) may be obtained through Via Licensing
21 (www.vialicensing.com) or through the respective patent owners individually for
22 the purpose of encoding or decoding bit streams in products that are compliant
23 with the ISO/IEC MPEG audio standards. Please note that most manufacturers of
24 Android devices already license these patent claims through Via Licensing or
25 directly from the patent owners, and therefore FDK AAC Codec software may
26 already be covered under those patent licenses when it is used for those
27 licensed purposes only.
28
29 Commercially-licensed AAC software libraries, including floating-point versions
30 with enhanced sound quality, are also available from Fraunhofer. Users are
31 encouraged to check the Fraunhofer website for additional applications
32 information and documentation.
33
34 2. COPYRIGHT LICENSE
35
36 Redistribution and use in source and binary forms, with or without modification,
37 are permitted without payment of copyright license fees provided that you
38 satisfy the following conditions:
39
40 You must retain the complete text of this software license in redistributions of
41 the FDK AAC Codec or your modifications thereto in source code form.
42
43 You must retain the complete text of this software license in the documentation
44 and/or other materials provided with redistributions of the FDK AAC Codec or
45 your modifications thereto in binary form. You must make available free of
46 charge copies of the complete source code of the FDK AAC Codec and your
47 modifications thereto to recipients of copies in binary form.
48
49 The name of Fraunhofer may not be used to endorse or promote products derived
50 from this library without prior written permission.
51
52 You may not charge copyright license fees for anyone to use, copy or distribute
53 the FDK AAC Codec software or your modifications thereto.
54
55 Your modified versions of the FDK AAC Codec must carry prominent notices stating
56 that you changed the software and the date of any change. For modified versions
57 of the FDK AAC Codec, the term "Fraunhofer FDK AAC Codec Library for Android"
58 must be replaced by the term "Third-Party Modified Version of the Fraunhofer FDK
59 AAC Codec Library for Android."
60
61 3. NO PATENT LICENSE
62
63 NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without
64 limitation the patents of Fraunhofer, ARE GRANTED BY THIS SOFTWARE LICENSE.
65 Fraunhofer provides no warranty of patent non-infringement with respect to this
66 software.
67
68 You may use this FDK AAC Codec software or modifications thereto only for
69 purposes that are authorized by appropriate patent licenses.
70
71 4. DISCLAIMER
72
73 This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright
74 holders and contributors "AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES,
75 including but not limited to the implied warranties of merchantability and
76 fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
77 CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary,
78 or consequential damages, including but not limited to procurement of substitute
79 goods or services; loss of use, data, or profits, or business interruption,
80 however caused and on any theory of liability, whether in contract, strict
81 liability, or tort (including negligence), arising in any way out of the use of
82 this software, even if advised of the possibility of such damage.
83
84 5. CONTACT INFORMATION
85
86 Fraunhofer Institute for Integrated Circuits IIS
87 Attention: Audio and Multimedia Departments - FDK AAC LL
88 Am Wolfsmantel 33
89 91058 Erlangen, Germany
90
91 www.iis.fraunhofer.de/amm
92 amm-info@iis.fraunhofer.de
93 ----------------------------------------------------------------------------- */
94
95 /*********************** MPEG surround decoder library *************************
96
97 Author(s):
98
99 Description: SAC Decoder Library
100
101 *******************************************************************************/
102
103 #include "sac_dec_errorcodes.h"
104 #include "sac_dec.h"
105
106 #include "sac_process.h"
107 #include "sac_bitdec.h"
108 #include "sac_smoothing.h"
109 #include "sac_calcM1andM2.h"
110 #include "sac_reshapeBBEnv.h"
111 #include "sac_stp.h"
112 #include "sac_rom.h"
113
114 #include "FDK_decorrelate.h"
115
116 #include "FDK_trigFcts.h"
117 #include "FDK_matrixCalloc.h"
118
119 /* static int pbStrideTable[] = {1, 2, 5, 28}; see sac_rom.cpp */
120
121 enum {
122 APPLY_M2_NONE = 0, /* init value */
123 APPLY_M2 = 1, /* apply m2 fallback implementation */
124 APPLY_M2_MODE212 = 2, /* apply m2 for 212 mode */
125 APPLY_M2_MODE212_Res_PhaseCoding =
126 3 /* apply m2 for 212 mode with residuals and phase coding */
127 };
128
129 /******************************************************************************************/
130 /* function: FDK_SpatialDecInitDefaultSpatialSpecificConfig */
131 /* output: struct of type SPATIAL_SPECIFIC_CONFIG */
132 /* input: core coder audio object type */
133 /* input: nr of core channels */
134 /* input: sampling rate */
135 /* input: nr of time slots */
136 /* input: decoder level */
137 /* input: flag indicating upmix type blind */
138 /* */
139 /* returns: error code */
140 /******************************************************************************************/
FDK_SpatialDecInitDefaultSpatialSpecificConfig(SPATIAL_SPECIFIC_CONFIG * pSpatialSpecificConfig,AUDIO_OBJECT_TYPE coreCodec,int coreChannels,int samplingFreq,int nTimeSlots,int decoderLevel,int isBlind)141 int FDK_SpatialDecInitDefaultSpatialSpecificConfig(
142 SPATIAL_SPECIFIC_CONFIG *pSpatialSpecificConfig,
143 AUDIO_OBJECT_TYPE coreCodec, int coreChannels, int samplingFreq,
144 int nTimeSlots, int decoderLevel, int isBlind) {
145 return SpatialDecDefaultSpecificConfig(pSpatialSpecificConfig, coreCodec,
146 samplingFreq, nTimeSlots, decoderLevel,
147 isBlind, coreChannels);
148 }
149
150 /******************************************************************************************/
151 /* function: FDK_SpatialDecCompareSpatialSpecificConfigHeader */
152 /* input: 2 pointers to a ssc */
153 /* */
154 /* output: - */
155 /* returns: error code (0 = equal, <>0 unequal) */
156 /******************************************************************************************/
FDK_SpatialDecCompareSpatialSpecificConfigHeader(SPATIAL_SPECIFIC_CONFIG * pSsc1,SPATIAL_SPECIFIC_CONFIG * pSsc2)157 int FDK_SpatialDecCompareSpatialSpecificConfigHeader(
158 SPATIAL_SPECIFIC_CONFIG *pSsc1, SPATIAL_SPECIFIC_CONFIG *pSsc2) {
159 int result = MPS_OK;
160
161 /* we assume: every bit must be equal */
162 if (FDKmemcmp(pSsc1, pSsc2, sizeof(SPATIAL_SPECIFIC_CONFIG)) != 0) {
163 result = MPS_UNEQUAL_SSC;
164 }
165 return result;
166 }
167
168 /*******************************************************************************
169 Functionname: SpatialDecClearFrameData
170 *******************************************************************************
171
172 Description: Clear/Fake frame data to avoid misconfiguration and allow proper
173 error concealment.
174 Arguments:
175 Input: self (frame data)
176 Output: No return value.
177
178 *******************************************************************************/
SpatialDecClearFrameData(spatialDec * self,SPATIAL_BS_FRAME * bsFrame,const SACDEC_CREATION_PARAMS * const setup)179 static void SpatialDecClearFrameData(
180 spatialDec *self, /* Shall be removed */
181 SPATIAL_BS_FRAME *bsFrame, const SACDEC_CREATION_PARAMS *const setup) {
182 int i;
183
184 FDK_ASSERT(self != NULL);
185 FDK_ASSERT(bsFrame != NULL);
186 FDK_ASSERT(setup != NULL);
187
188 /* do not apply shaping tools (GES or STP) */
189 for (i = 0; i < setup->maxNumOutputChannels;
190 i += 1) { /* MAX_OUTPUT_CHANNELS */
191 bsFrame->tempShapeEnableChannelSTP[i] = 0;
192 bsFrame->tempShapeEnableChannelGES[i] = 0;
193 }
194
195 bsFrame->TsdData->bsTsdEnable = 0;
196
197 /* use only 1 parameter set at the end of the frame */
198 bsFrame->numParameterSets = 1;
199 bsFrame->paramSlot[0] = self->timeSlots - 1;
200
201 /* parameter smoothing tool set to off */
202 bsFrame->bsSmoothMode[0] = 0;
203
204 /* reset residual data */
205 {
206 int resQmfBands, resTimeSlots = (1);
207
208 resQmfBands = setup->maxNumQmfBands;
209
210 for (i = 0; i < setup->bProcResidual
211 ? fMin(setup->maxNumResChannels,
212 setup->maxNumOttBoxes + setup->maxNumInputChannels)
213 : 0;
214 i += 1) {
215 for (int j = 0; j < resTimeSlots; j += 1) {
216 for (int k = 0; k < resQmfBands; k += 1) {
217 self->qmfResidualReal__FDK[i][j][k] = FL2FXCONST_DBL(0.0f);
218 self->qmfResidualImag__FDK[i][j][k] = FL2FXCONST_DBL(0.0f);
219 }
220 }
221 }
222 }
223
224 return;
225 }
226
227 /*******************************************************************************
228 Functionname: FDK_SpatialDecOpen
229 *******************************************************************************
230
231 Description:
232
233 Arguments:
234
235 Return:
236
237 *******************************************************************************/
FDK_SpatialDecOpen(const SPATIAL_DEC_CONFIG * config,int stereoConfigIndex)238 spatialDec *FDK_SpatialDecOpen(const SPATIAL_DEC_CONFIG *config,
239 int stereoConfigIndex) {
240 int i;
241 int lfSize, hfSize;
242 spatialDec *self = NULL;
243 SACDEC_CREATION_PARAMS setup;
244
245 switch (config->decoderLevel) {
246 case DECODER_LEVEL_0: /* 212 maxNumOutputChannels== 2 */
247 setup.maxNumInputChannels = 1;
248 setup.maxNumOutputChannels = 2;
249 setup.maxNumQmfBands = 64;
250 setup.maxNumXChannels = 2;
251 setup.maxNumVChannels = 2;
252 setup.maxNumDecorChannels = 1;
253 setup.bProcResidual = 1;
254 setup.maxNumResidualChannels = 0;
255 setup.maxNumOttBoxes = 1;
256 setup.maxNumParams = setup.maxNumInputChannels + setup.maxNumOttBoxes;
257 break;
258 default:
259 return NULL;
260 }
261
262 setup.maxNumResChannels = 1;
263
264 {
265 switch (config->maxNumOutputChannels) {
266 case OUTPUT_CHANNELS_2_0:
267 setup.maxNumOutputChannels = fMin(setup.maxNumOutputChannels, 2);
268 break;
269 case OUTPUT_CHANNELS_DEFAULT:
270 default:
271 break;
272 }
273 }
274
275 setup.maxNumHybridBands = SacGetHybridSubbands(setup.maxNumQmfBands);
276
277 switch (config->decoderMode) {
278 case EXT_HQ_ONLY:
279 setup.maxNumCmplxQmfBands = setup.maxNumQmfBands;
280 setup.maxNumCmplxHybBands = setup.maxNumHybridBands;
281 break;
282 default:
283 setup.maxNumCmplxQmfBands = fixMax(PC_NUM_BANDS, setup.maxNumQmfBands);
284 setup.maxNumCmplxHybBands =
285 fixMax(PC_NUM_HYB_BANDS, setup.maxNumHybridBands);
286 break;
287 } /* switch config->decoderMode */
288
289 FDK_ALLOCATE_MEMORY_1D_INT(self, 1, spatialDec, SECT_DATA_L2)
290
291 self->createParams = setup;
292
293 FDK_ALLOCATE_MEMORY_1D(self->param2hyb, MAX_PARAMETER_BANDS + 1, int)
294
295 FDK_ALLOCATE_MEMORY_1D(self->numOttBands, setup.maxNumOttBoxes, int)
296
297 /* allocate arrays */
298
299 FDK_ALLOCATE_MEMORY_1D(self->smgTime, MAX_PARAMETER_SETS, int)
300 FDK_ALLOCATE_MEMORY_2D(self->smgData, MAX_PARAMETER_SETS, MAX_PARAMETER_BANDS,
301 UCHAR)
302
303 FDK_ALLOCATE_MEMORY_3D(self->ottCLD__FDK, setup.maxNumOttBoxes,
304 MAX_PARAMETER_SETS, MAX_PARAMETER_BANDS, SCHAR)
305 FDK_ALLOCATE_MEMORY_3D(self->ottICC__FDK, setup.maxNumOttBoxes,
306 MAX_PARAMETER_SETS, MAX_PARAMETER_BANDS, SCHAR)
307 FDK_ALLOCATE_MEMORY_3D(self->ottIPD__FDK, setup.maxNumOttBoxes,
308 MAX_PARAMETER_SETS, MAX_PARAMETER_BANDS, SCHAR)
309
310 /* Last parameters from prev frame */
311 FDK_ALLOCATE_MEMORY_2D(self->ottCLDidxPrev, setup.maxNumOttBoxes,
312 MAX_PARAMETER_BANDS, SCHAR)
313 FDK_ALLOCATE_MEMORY_2D(self->ottICCidxPrev, setup.maxNumOttBoxes,
314 MAX_PARAMETER_BANDS, SCHAR)
315 FDK_ALLOCATE_MEMORY_3D(self->ottICCdiffidx, setup.maxNumOttBoxes,
316 MAX_PARAMETER_SETS, MAX_PARAMETER_BANDS, SCHAR)
317 FDK_ALLOCATE_MEMORY_2D(self->ottIPDidxPrev, setup.maxNumOttBoxes,
318 MAX_PARAMETER_BANDS, SCHAR)
319 FDK_ALLOCATE_MEMORY_2D(self->arbdmxGainIdxPrev, setup.maxNumInputChannels,
320 MAX_PARAMETER_BANDS, SCHAR)
321 FDK_ALLOCATE_MEMORY_2D(self->cmpOttCLDidxPrev, setup.maxNumOttBoxes,
322 MAX_PARAMETER_BANDS, SCHAR)
323 FDK_ALLOCATE_MEMORY_2D(self->cmpOttICCidxPrev, setup.maxNumOttBoxes,
324 MAX_PARAMETER_BANDS, SCHAR)
325 FDK_ALLOCATE_MEMORY_3D(self->outIdxData, setup.maxNumOttBoxes,
326 MAX_PARAMETER_SETS, MAX_PARAMETER_BANDS, SCHAR)
327
328 FDK_ALLOCATE_MEMORY_3D(self->arbdmxGain__FDK, setup.maxNumInputChannels,
329 MAX_PARAMETER_SETS, MAX_PARAMETER_BANDS, SCHAR)
330 FDK_ALLOCATE_MEMORY_1D(self->arbdmxAlpha__FDK, setup.maxNumInputChannels,
331 FIXP_DBL)
332 FDK_ALLOCATE_MEMORY_1D(self->arbdmxAlphaPrev__FDK, setup.maxNumInputChannels,
333 FIXP_DBL)
334 FDK_ALLOCATE_MEMORY_2D(self->cmpArbdmxGainIdxPrev, setup.maxNumInputChannels,
335 MAX_PARAMETER_BANDS, SCHAR)
336
337 FDK_ALLOCATE_MEMORY_2D(self->cmpOttIPDidxPrev, setup.maxNumOttBoxes,
338 MAX_PARAMETER_BANDS, SCHAR)
339
340 FDK_ALLOCATE_MEMORY_3D_INT(self->M2Real__FDK, setup.maxNumOutputChannels,
341 setup.maxNumVChannels, MAX_PARAMETER_BANDS,
342 FIXP_DBL, SECT_DATA_L2)
343 FDK_ALLOCATE_MEMORY_3D(self->M2Imag__FDK, setup.maxNumOutputChannels,
344 setup.maxNumVChannels, MAX_PARAMETER_BANDS, FIXP_DBL)
345
346 FDK_ALLOCATE_MEMORY_3D_INT(self->M2RealPrev__FDK, setup.maxNumOutputChannels,
347 setup.maxNumVChannels, MAX_PARAMETER_BANDS,
348 FIXP_DBL, SECT_DATA_L2)
349 FDK_ALLOCATE_MEMORY_3D(self->M2ImagPrev__FDK, setup.maxNumOutputChannels,
350 setup.maxNumVChannels, MAX_PARAMETER_BANDS, FIXP_DBL)
351
352 FDK_ALLOCATE_MEMORY_2D_INT_ALIGNED(
353 self->qmfInputReal__FDK, setup.maxNumInputChannels, setup.maxNumQmfBands,
354 FIXP_DBL, SECT_DATA_L2)
355 FDK_ALLOCATE_MEMORY_2D_INT_ALIGNED(
356 self->qmfInputImag__FDK, setup.maxNumInputChannels,
357 setup.maxNumCmplxQmfBands, FIXP_DBL, SECT_DATA_L2)
358
359 FDK_ALLOCATE_MEMORY_2D_INT(self->hybInputReal__FDK, setup.maxNumInputChannels,
360 setup.maxNumHybridBands, FIXP_DBL, SECT_DATA_L2)
361 FDK_ALLOCATE_MEMORY_2D_INT(self->hybInputImag__FDK, setup.maxNumInputChannels,
362 setup.maxNumCmplxHybBands, FIXP_DBL, SECT_DATA_L2)
363
364 if (setup.bProcResidual) {
365 FDK_ALLOCATE_MEMORY_1D(self->qmfResidualReal__FDK, setup.maxNumResChannels,
366 FIXP_DBL **)
367 FDK_ALLOCATE_MEMORY_1D(self->qmfResidualImag__FDK, setup.maxNumResChannels,
368 FIXP_DBL **)
369
370 FDK_ALLOCATE_MEMORY_1D(self->hybResidualReal__FDK, setup.maxNumResChannels,
371 FIXP_DBL *)
372 FDK_ALLOCATE_MEMORY_1D(self->hybResidualImag__FDK, setup.maxNumResChannels,
373 FIXP_DBL *)
374
375 for (i = 0; i < setup.maxNumResChannels; i++) {
376 int resQmfBands = (config->decoderMode == EXT_LP_ONLY)
377 ? PC_NUM_BANDS
378 : setup.maxNumQmfBands;
379 int resHybBands = (config->decoderMode == EXT_LP_ONLY)
380 ? PC_NUM_HYB_BANDS
381 : setup.maxNumHybridBands;
382 /* Alignment is needed for USAC residuals because QMF analysis directly
383 * writes to this buffer. */
384 FDK_ALLOCATE_MEMORY_2D_INT_ALIGNED(self->qmfResidualReal__FDK[i], (1),
385 resQmfBands, FIXP_DBL, SECT_DATA_L1)
386 FDK_ALLOCATE_MEMORY_2D_INT_ALIGNED(self->qmfResidualImag__FDK[i], (1),
387 resQmfBands, FIXP_DBL, SECT_DATA_L1)
388
389 FDK_ALLOCATE_MEMORY_1D(self->hybResidualReal__FDK[i],
390 setup.maxNumHybridBands, FIXP_DBL)
391 FDK_ALLOCATE_MEMORY_1D(self->hybResidualImag__FDK[i], resHybBands,
392 FIXP_DBL)
393 }
394 } /* if (setup.bProcResidual) */
395
396 FDK_ALLOCATE_MEMORY_2D_INT(self->wReal__FDK, setup.maxNumVChannels,
397 setup.maxNumHybridBands, FIXP_DBL, SECT_DATA_L2)
398 FDK_ALLOCATE_MEMORY_2D_INT(self->wImag__FDK, setup.maxNumVChannels,
399 setup.maxNumCmplxHybBands, FIXP_DBL, SECT_DATA_L2)
400
401 FDK_ALLOCATE_MEMORY_2D_INT(self->hybOutputRealDry__FDK,
402 setup.maxNumOutputChannels,
403 setup.maxNumHybridBands, FIXP_DBL, SECT_DATA_L2)
404 FDK_ALLOCATE_MEMORY_2D_INT(self->hybOutputImagDry__FDK,
405 setup.maxNumOutputChannels,
406 setup.maxNumCmplxHybBands, FIXP_DBL, SECT_DATA_L2)
407
408 FDK_ALLOCATE_MEMORY_2D_INT(self->hybOutputRealWet__FDK,
409 setup.maxNumOutputChannels,
410 setup.maxNumHybridBands, FIXP_DBL, SECT_DATA_L2)
411 FDK_ALLOCATE_MEMORY_2D_INT(self->hybOutputImagWet__FDK,
412 setup.maxNumOutputChannels,
413 setup.maxNumCmplxHybBands, FIXP_DBL, SECT_DATA_L2)
414
415 FDK_ALLOCATE_MEMORY_1D(self->hybridSynthesis, setup.maxNumOutputChannels,
416 FDK_SYN_HYB_FILTER)
417
418 FDK_ALLOCATE_MEMORY_1D(
419 self->hybridAnalysis,
420 setup.bProcResidual ? setup.maxNumInputChannels + setup.maxNumResChannels
421 : setup.maxNumInputChannels,
422 FDK_ANA_HYB_FILTER)
423
424 lfSize = 2 * BUFFER_LEN_LF * MAX_QMF_BANDS_TO_HYBRID;
425 {
426 hfSize =
427 BUFFER_LEN_HF * ((setup.maxNumQmfBands - MAX_QMF_BANDS_TO_HYBRID) +
428 (setup.maxNumCmplxQmfBands - MAX_QMF_BANDS_TO_HYBRID));
429 }
430
431 FDK_ALLOCATE_MEMORY_2D_INT(self->pHybridAnaStatesLFdmx,
432 setup.maxNumInputChannels, lfSize, FIXP_DBL,
433 SECT_DATA_L2) {
434 FDK_ALLOCATE_MEMORY_2D(self->pHybridAnaStatesHFdmx,
435 setup.maxNumInputChannels, hfSize, FIXP_DBL)
436 }
437
438 for (i = 0; i < setup.maxNumInputChannels; i++) {
439 FIXP_DBL *pHybridAnaStatesHFdmx;
440
441 pHybridAnaStatesHFdmx = self->pHybridAnaStatesHFdmx[i];
442
443 FDKhybridAnalysisOpen(&self->hybridAnalysis[i],
444 self->pHybridAnaStatesLFdmx[i],
445 lfSize * sizeof(FIXP_DBL), pHybridAnaStatesHFdmx,
446 hfSize * sizeof(FIXP_DBL));
447 }
448 if (setup.bProcResidual) {
449 lfSize = 2 * BUFFER_LEN_LF * MAX_QMF_BANDS_TO_HYBRID;
450 hfSize = BUFFER_LEN_HF *
451 ((((config->decoderMode == EXT_LP_ONLY) ? PC_NUM_BANDS
452 : setup.maxNumQmfBands) -
453 MAX_QMF_BANDS_TO_HYBRID) +
454 (setup.maxNumCmplxQmfBands - MAX_QMF_BANDS_TO_HYBRID));
455
456 FDK_ALLOCATE_MEMORY_2D_INT(self->pHybridAnaStatesLFres,
457 setup.maxNumResChannels, lfSize, FIXP_DBL,
458 SECT_DATA_L2)
459 FDK_ALLOCATE_MEMORY_2D(self->pHybridAnaStatesHFres, setup.maxNumResChannels,
460 hfSize, FIXP_DBL)
461
462 for (i = setup.maxNumInputChannels;
463 i < (setup.maxNumInputChannels + setup.maxNumResChannels); i++) {
464 FDKhybridAnalysisOpen(
465 &self->hybridAnalysis[i],
466 self->pHybridAnaStatesLFres[i - setup.maxNumInputChannels],
467 lfSize * sizeof(FIXP_DBL),
468 self->pHybridAnaStatesHFres[i - setup.maxNumInputChannels],
469 hfSize * sizeof(FIXP_DBL));
470 }
471 }
472
473 FDK_ALLOCATE_MEMORY_1D(self->smoothState, 1, SMOOTHING_STATE)
474 FDK_ALLOCATE_MEMORY_1D(self->reshapeBBEnvState, 1, RESHAPE_BBENV_STATE)
475
476 FDK_ALLOCATE_MEMORY_1D(self->apDecor, setup.maxNumDecorChannels, DECORR_DEC)
477 FDK_ALLOCATE_MEMORY_2D_INT(self->pDecorBufferCplx, setup.maxNumDecorChannels,
478 (2 * ((825) + (373))), FIXP_DBL, SECT_DATA_L2)
479
480 for (i = 0; i < setup.maxNumDecorChannels; i++) {
481 if (FDKdecorrelateOpen(&self->apDecor[i], self->pDecorBufferCplx[i],
482 (2 * ((825) + (373))))) {
483 goto bail;
484 }
485 }
486
487 if (subbandTPCreate(&self->hStpDec) != MPS_OK) {
488 goto bail;
489 }
490
491 /* save general decoder configuration */
492 self->decoderLevel = config->decoderLevel;
493 self->decoderMode = config->decoderMode;
494 self->binauralMode = config->binauralMode;
495
496 /* preinitialize configuration */
497 self->partiallyComplex = (config->decoderMode != EXT_HQ_ONLY) ? 1 : 0;
498
499 /* Set to default state */
500 SpatialDecConcealment_Init(&self->concealInfo, MPEGS_CONCEAL_RESET_ALL);
501
502 /* Everything is fine so return the handle */
503 return self;
504
505 bail:
506 /* Collector for all errors.
507 Deallocate all memory and return a invalid handle. */
508 FDK_SpatialDecClose(self);
509
510 return NULL;
511 }
512
513 /*******************************************************************************
514 Functionname: isValidConfig
515 *******************************************************************************
516
517 Description: Validate if configuration is supported in present instance
518
519 Arguments:
520
521 Return: 1: all okay
522 0: configuration not supported
523 *******************************************************************************/
isValidConfig(spatialDec const * const self,const SPATIAL_DEC_UPMIX_TYPE upmixType,SPATIALDEC_PARAM const * const pUserParams,const AUDIO_OBJECT_TYPE coreAot)524 static int isValidConfig(spatialDec const *const self,
525 const SPATIAL_DEC_UPMIX_TYPE upmixType,
526 SPATIALDEC_PARAM const *const pUserParams,
527 const AUDIO_OBJECT_TYPE coreAot) {
528 UPMIXTYPE nUpmixType;
529
530 FDK_ASSERT(self != NULL);
531 FDK_ASSERT(pUserParams != NULL);
532
533 nUpmixType = (UPMIXTYPE)upmixType;
534
535 switch (nUpmixType) {
536 case UPMIXTYPE_BYPASS: /* UPMIX_TYPE_BYPASS */
537 break;
538 case UPMIXTYPE_NORMAL: /* UPMIX_TYPE_NORMAL */
539 break;
540 default:
541 return 0; /* unsupported upmixType */
542 }
543
544 return 1; /* upmixType supported */
545 }
546
CheckLevelTreeUpmixType(const SACDEC_CREATION_PARAMS * const pCreateParams,const SPATIAL_SPECIFIC_CONFIG * const pSsc,const int decoderLevel,const UPMIXTYPE upmixType)547 static SACDEC_ERROR CheckLevelTreeUpmixType(
548 const SACDEC_CREATION_PARAMS *const pCreateParams,
549 const SPATIAL_SPECIFIC_CONFIG *const pSsc, const int decoderLevel,
550 const UPMIXTYPE upmixType) {
551 SACDEC_ERROR err = MPS_OK;
552 int nOutputChannels, treeConfig;
553
554 FDK_ASSERT(pCreateParams != NULL);
555 FDK_ASSERT(pSsc != NULL);
556
557 treeConfig = pSsc->treeConfig;
558
559 switch (decoderLevel) {
560 case 0: {
561 if (treeConfig != SPATIALDEC_MODE_RSVD7) {
562 err = MPS_INVALID_TREECONFIG;
563 goto bail;
564 }
565 break;
566 }
567 default:
568 err = MPS_INVALID_PARAMETER /* MPS_UNIMPLEMENTED */;
569 goto bail;
570 }
571
572 switch (upmixType) {
573 case UPMIXTYPE_BYPASS:
574 nOutputChannels = pSsc->nInputChannels;
575 break;
576 default:
577 nOutputChannels = pSsc->nOutputChannels;
578 break;
579 }
580
581 /* Is sufficient memory allocated. */
582 if ((pSsc->nInputChannels > pCreateParams->maxNumInputChannels) ||
583 (nOutputChannels > pCreateParams->maxNumOutputChannels) ||
584 (pSsc->nOttBoxes > pCreateParams->maxNumOttBoxes)) {
585 err = MPS_INVALID_PARAMETER;
586 }
587
588 bail:
589 return err;
590 }
591
SpatialDecInitParserContext(spatialDec * self)592 void SpatialDecInitParserContext(spatialDec *self) {
593 int i, j;
594
595 for (i = 0; i < self->createParams.maxNumOttBoxes; i += 1) {
596 for (j = 0; j < MAX_PARAMETER_BANDS; j++) {
597 self->ottCLDidxPrev[i][j] = 0;
598 self->ottICCidxPrev[i][j] = 0;
599 self->cmpOttCLDidxPrev[i][j] = 0;
600 self->cmpOttICCidxPrev[i][j] = 0;
601 }
602 }
603 for (i = 0; i < self->createParams.maxNumInputChannels; i++) {
604 for (j = 0; j < MAX_PARAMETER_BANDS; j++) {
605 self->arbdmxGainIdxPrev[i][j] = 0;
606 self->cmpArbdmxGainIdxPrev[i][j] = 0;
607 }
608 }
609 }
610
611 /*******************************************************************************
612 Functionname: FDK_SpatialDecInit
613 *******************************************************************************
614
615 Description:
616
617 Arguments:
618
619 Return:
620
621 *******************************************************************************/
622
FDK_SpatialDecInit(spatialDec * self,SPATIAL_BS_FRAME * frame,SPATIAL_SPECIFIC_CONFIG * pSpatialSpecificConfig,int nQmfBands,SPATIAL_DEC_UPMIX_TYPE const upmixType,SPATIALDEC_PARAM * pUserParams,UINT initFlags)623 SACDEC_ERROR FDK_SpatialDecInit(spatialDec *self, SPATIAL_BS_FRAME *frame,
624 SPATIAL_SPECIFIC_CONFIG *pSpatialSpecificConfig,
625 int nQmfBands,
626 SPATIAL_DEC_UPMIX_TYPE const upmixType,
627 SPATIALDEC_PARAM *pUserParams, UINT initFlags) {
628 SACDEC_ERROR err = MPS_OK;
629 int nCh, i, j, k;
630 int maxQmfBands;
631 int bypassMode = 0;
632
633 self->useFDreverb = 0;
634
635 /* check configuration parameter */
636 if (!isValidConfig(self, upmixType, pUserParams,
637 pSpatialSpecificConfig->coreCodec)) {
638 return MPS_INVALID_PARAMETER;
639 }
640
641 /* check tree configuration */
642 err = CheckLevelTreeUpmixType(&self->createParams, pSpatialSpecificConfig,
643 self->decoderLevel, (UPMIXTYPE)upmixType);
644 if (err != MPS_OK) {
645 goto bail;
646 }
647
648 /* Store and update instance after all checks passed successfully: */
649 self->upmixType = (UPMIXTYPE)upmixType;
650
651 if (initFlags & MPEGS_INIT_PARAMS_ERROR_CONCEALMENT) { /* At least one error
652 concealment
653 parameter changed */
654 err = SpatialDecConcealment_SetParam(
655 &self->concealInfo, SAC_DEC_CONCEAL_METHOD, pUserParams->concealMethod);
656 if (err != MPS_OK) {
657 goto bail;
658 }
659 err = SpatialDecConcealment_SetParam(&self->concealInfo,
660 SAC_DEC_CONCEAL_NUM_KEEP_FRAMES,
661 pUserParams->concealNumKeepFrames);
662 if (err != MPS_OK) {
663 goto bail;
664 }
665 err = SpatialDecConcealment_SetParam(
666 &self->concealInfo, SAC_DEC_CONCEAL_FADE_OUT_SLOPE_LENGTH,
667 pUserParams->concealFadeOutSlopeLength);
668 if (err != MPS_OK) {
669 goto bail;
670 }
671 err = SpatialDecConcealment_SetParam(&self->concealInfo,
672 SAC_DEC_CONCEAL_FADE_IN_SLOPE_LENGTH,
673 pUserParams->concealFadeInSlopeLength);
674 if (err != MPS_OK) {
675 goto bail;
676 }
677 err = SpatialDecConcealment_SetParam(&self->concealInfo,
678 SAC_DEC_CONCEAL_NUM_RELEASE_FRAMES,
679 pUserParams->concealNumReleaseFrames);
680 if (err != MPS_OK) {
681 goto bail;
682 }
683 }
684
685 if (initFlags &
686 MPEGS_INIT_STATES_ERROR_CONCEALMENT) { /* Set to default state */
687 SpatialDecConcealment_Init(&self->concealInfo, MPEGS_CONCEAL_RESET_STATE);
688 }
689
690 /* determine bypass mode */
691 bypassMode |= pUserParams->bypassMode;
692 bypassMode |= ((self->upmixType == UPMIXTYPE_BYPASS) ? 1 : 0);
693
694 /* static decoder scale depends on number of qmf bands */
695 switch (nQmfBands) {
696 case 16:
697 case 24:
698 case 32:
699 self->staticDecScale = 21;
700 break;
701 case 64:
702 self->staticDecScale = 22;
703 break;
704 default:
705 return MPS_INVALID_PARAMETER;
706 }
707
708 self->numParameterSetsPrev = 1;
709
710 self->qmfBands = nQmfBands;
711 /* self->hybridBands will be updated in SpatialDecDecodeHeader() below. */
712
713 self->bShareDelayWithSBR = 0;
714
715 err = SpatialDecDecodeHeader(self, pSpatialSpecificConfig);
716 if (err != MPS_OK) {
717 goto bail;
718 }
719
720 self->stereoConfigIndex = pSpatialSpecificConfig->stereoConfigIndex;
721
722 if (initFlags & MPEGS_INIT_STATES_ANA_QMF_FILTER) {
723 self->qmfInputDelayBufPos = 0;
724 self->pc_filterdelay = 1; /* Division by 0 not possible */
725 }
726
727 maxQmfBands = self->qmfBands;
728
729 /* init residual decoder */
730
731 /* init tonality smoothing */
732 if (initFlags & MPEGS_INIT_STATES_PARAM) {
733 initParameterSmoothing(self);
734 }
735
736 /* init GES */
737 initBBEnv(self, (initFlags & MPEGS_INIT_STATES_GES) ? 1 : 0);
738
739 /* Clip protection is applied only for normal processing. */
740 if (!isTwoChMode(self->upmixType) && !bypassMode) {
741 self->staticDecScale += self->clipProtectGainSF__FDK;
742 }
743
744 {
745 UINT flags = 0;
746 INT initStatesFlag = (initFlags & MPEGS_INIT_STATES_ANA_QMF_FILTER) ? 1 : 0;
747 INT useLdFilter =
748 (self->pConfigCurrent->syntaxFlags & SACDEC_SYNTAX_LD) ? 1 : 0;
749
750 flags = self->pQmfDomain->globalConf.flags_requested;
751 flags &= (~(UINT)QMF_FLAG_LP);
752
753 if (initStatesFlag)
754 flags &= ~QMF_FLAG_KEEP_STATES;
755 else
756 flags |= QMF_FLAG_KEEP_STATES;
757
758 if (useLdFilter)
759 flags |= QMF_FLAG_MPSLDFB;
760 else
761 flags &= ~QMF_FLAG_MPSLDFB;
762
763 self->pQmfDomain->globalConf.flags_requested = flags;
764 FDK_QmfDomain_Configure(self->pQmfDomain);
765
766 /* output scaling */
767 for (nCh = 0; nCh < self->numOutputChannelsAT; nCh++) {
768 int outputScale = 0, outputGain_e = 0, scale = 0;
769 FIXP_DBL outputGain_m = getChGain(self, nCh, &outputGain_e);
770
771 if (!isTwoChMode(self->upmixType) && !bypassMode) {
772 outputScale +=
773 self->clipProtectGainSF__FDK; /* consider clip protection scaling at
774 synthesis qmf */
775 }
776
777 scale = outputScale;
778
779 qmfChangeOutScalefactor(&self->pQmfDomain->QmfDomainOut[nCh].fb, scale);
780 qmfChangeOutGain(&self->pQmfDomain->QmfDomainOut[nCh].fb, outputGain_m,
781 outputGain_e);
782 }
783 }
784
785 for (nCh = 0; nCh < self->numOutputChannelsAT; nCh++) {
786 FDKhybridSynthesisInit(&self->hybridSynthesis[nCh], THREE_TO_TEN,
787 self->qmfBands, maxQmfBands);
788 }
789
790 /* for input, residual channels and arbitrary down-mix residual channels */
791 for (nCh = 0; nCh < self->createParams.maxNumInputChannels; nCh++) {
792 FDKhybridAnalysisInit(
793 &self->hybridAnalysis[nCh], THREE_TO_TEN, self->qmfBands, maxQmfBands,
794 (initFlags & MPEGS_INIT_STATES_ANA_HYB_FILTER) ? 1 : 0);
795 }
796 for (; nCh < (self->createParams.bProcResidual
797 ? (self->createParams.maxNumInputChannels +
798 self->createParams.maxNumResChannels)
799 : self->createParams.maxNumInputChannels);
800 nCh++) {
801 FDKhybridAnalysisInit(&self->hybridAnalysis[nCh], THREE_TO_TEN, maxQmfBands,
802 maxQmfBands, 0);
803 }
804
805 {
806 for (k = 0; k < self->numDecorSignals; k++) {
807 int errCode, idec;
808 FDK_DECORR_TYPE decorrType = DECORR_PS;
809 decorrType = DECORR_LD;
810 if (self->pConfigCurrent->syntaxFlags &
811 (SACDEC_SYNTAX_USAC | SACDEC_SYNTAX_RSVD50)) {
812 decorrType =
813 ((self->treeConfig == TREE_212) && (self->decorrType == DECORR_PS))
814 ? DECORR_PS
815 : DECORR_USAC;
816 }
817 {
818 idec = k;
819 if (self->pConfigCurrent->syntaxFlags & SACDEC_SYNTAX_LD) {
820 if (self->treeConfig == TREE_212 && k == 0) {
821 idec = 2;
822 }
823 }
824 }
825 errCode = FDKdecorrelateInit(
826 &self->apDecor[k], self->hybridBands, decorrType, DUCKER_AUTOMATIC,
827 self->decorrConfig, idec, 0, /* self->partiallyComplex */
828 0, 0, /* isLegacyPS */
829 (initFlags & MPEGS_INIT_STATES_DECORRELATOR) ? 1 : 0);
830 if (errCode) return MPS_NOTOK;
831 }
832 } /* !self->partiallyComplex */
833
834 err = initM1andM2(self, (initFlags & MPEGS_INIT_STATES_M1M2) ? 1 : 0,
835 (initFlags & MPEGS_INIT_CONFIG) ? 1 : 0);
836 if (err != MPS_OK) return err;
837
838 /* Initialization of previous frame data */
839 if (initFlags & MPEGS_INIT_STATES_PARAM) {
840 for (i = 0; i < self->createParams.maxNumOttBoxes; i += 1) {
841 /* reset icc diff data */
842 for (k = 0; k < MAX_PARAMETER_SETS; k += 1) {
843 for (j = 0; j < MAX_PARAMETER_BANDS; j += 1) {
844 self->ottICCdiffidx[i][k][j] = 0;
845 }
846 }
847 }
848 /* Parameter Smoothing */
849 /* robustness: init with one of the values of smgTimeTable[] = {64, 128,
850 256, 512} to avoid division by zero in calcFilterCoeff__FDK() */
851 self->smoothState->prevSmgTime = smgTimeTable[2]; /* == 256 */
852 FDKmemclear(self->smoothState->prevSmgData,
853 MAX_PARAMETER_BANDS * sizeof(UCHAR));
854 FDKmemclear(self->smoothState->opdLeftState__FDK,
855 MAX_PARAMETER_BANDS * sizeof(FIXP_DBL));
856 FDKmemclear(self->smoothState->opdRightState__FDK,
857 MAX_PARAMETER_BANDS * sizeof(FIXP_DBL));
858 }
859
860 self->prevTimeSlot = -1;
861 self->curTimeSlot =
862 MAX_TIME_SLOTS + 1; /* Initialize with a invalid value to trigger
863 concealment if first frame has no valid data. */
864 self->curPs = 0;
865
866 subbandTPInit(self->hStpDec);
867
868 bail:
869 return err;
870 }
871
SpatialDecChannelProperties(spatialDec * self,AUDIO_CHANNEL_TYPE channelType[],UCHAR channelIndices[],const FDK_channelMapDescr * const mapDescr)872 void SpatialDecChannelProperties(spatialDec *self,
873 AUDIO_CHANNEL_TYPE channelType[],
874 UCHAR channelIndices[],
875 const FDK_channelMapDescr *const mapDescr) {
876 if ((self == NULL) || (channelType == NULL) || (channelIndices == NULL) ||
877 (mapDescr == NULL)) {
878 return; /* no extern buffer to be filled */
879 }
880
881 if (self->numOutputChannelsAT !=
882 treePropertyTable[self->treeConfig].numOutputChannels) {
883 int ch;
884 /* Declare all channels to be front channels: */
885 for (ch = 0; ch < self->numOutputChannelsAT; ch += 1) {
886 channelType[ch] = ACT_FRONT;
887 channelIndices[ch] = ch;
888 }
889 } else {
890 /* ISO/IEC FDIS 23003-1:2006(E), page 46, Table 40 bsTreeConfig */
891 switch (self->treeConfig) {
892 case TREE_212:
893 channelType[0] = ACT_FRONT;
894 channelIndices[0] = 0;
895 channelType[1] = ACT_FRONT;
896 channelIndices[1] = 1;
897 break;
898 default:;
899 }
900 }
901 }
902
903 /*******************************************************************************
904 Functionname: FDK_SpatialDecClose
905 *******************************************************************************
906
907 Description:
908
909 Arguments:
910
911 Return:
912
913 *******************************************************************************/
914
FDK_SpatialDecClose(spatialDec * self)915 void FDK_SpatialDecClose(spatialDec *self) {
916 if (self) {
917 int k;
918
919 if (self->apDecor != NULL) {
920 for (k = 0; k < self->createParams.maxNumDecorChannels; k++) {
921 FDKdecorrelateClose(&(self->apDecor[k]));
922 }
923 FDK_FREE_MEMORY_1D(self->apDecor);
924 }
925 if (self->pDecorBufferCplx != NULL) {
926 FDK_FREE_MEMORY_2D(self->pDecorBufferCplx);
927 }
928
929 subbandTPDestroy(&self->hStpDec);
930
931 FDK_FREE_MEMORY_1D(self->reshapeBBEnvState);
932 FDK_FREE_MEMORY_1D(self->smoothState);
933
934 FDK_FREE_MEMORY_2D(self->pHybridAnaStatesLFdmx);
935 FDK_FREE_MEMORY_2D(self->pHybridAnaStatesHFdmx);
936 FDK_FREE_MEMORY_2D(self->pHybridAnaStatesLFres);
937 FDK_FREE_MEMORY_2D(self->pHybridAnaStatesHFres);
938 FDK_FREE_MEMORY_1D(self->hybridAnalysis);
939
940 FDK_FREE_MEMORY_1D(self->hybridSynthesis);
941
942 /* The time buffer is passed to the decoder from outside to avoid copying
943 * (zero copy). */
944 /* FDK_FREE_MEMORY_2D(self->timeOut__FDK); */
945
946 FDK_FREE_MEMORY_2D(self->hybOutputImagWet__FDK);
947 FDK_FREE_MEMORY_2D(self->hybOutputRealWet__FDK);
948
949 FDK_FREE_MEMORY_2D(self->hybOutputImagDry__FDK);
950 FDK_FREE_MEMORY_2D(self->hybOutputRealDry__FDK);
951
952 FDK_FREE_MEMORY_2D(self->wImag__FDK);
953 FDK_FREE_MEMORY_2D(self->wReal__FDK);
954
955 if (self->createParams.bProcResidual) {
956 int i;
957
958 for (i = 0; i < self->createParams.maxNumResChannels; i++) {
959 if (self->hybResidualImag__FDK != NULL)
960 FDK_FREE_MEMORY_1D(self->hybResidualImag__FDK[i]);
961 if (self->hybResidualReal__FDK != NULL)
962 FDK_FREE_MEMORY_1D(self->hybResidualReal__FDK[i]);
963 if (self->qmfResidualImag__FDK != NULL)
964 FDK_FREE_MEMORY_2D_ALIGNED(self->qmfResidualImag__FDK[i]);
965 if (self->qmfResidualReal__FDK != NULL)
966 FDK_FREE_MEMORY_2D_ALIGNED(self->qmfResidualReal__FDK[i]);
967 }
968
969 FDK_FREE_MEMORY_1D(self->hybResidualImag__FDK);
970 FDK_FREE_MEMORY_1D(self->hybResidualReal__FDK);
971
972 FDK_FREE_MEMORY_1D(self->qmfResidualImag__FDK);
973 FDK_FREE_MEMORY_1D(self->qmfResidualReal__FDK);
974
975 } /* self->createParams.bProcResidual */
976
977 FDK_FREE_MEMORY_2D(self->hybInputImag__FDK);
978 FDK_FREE_MEMORY_2D(self->hybInputReal__FDK);
979
980 FDK_FREE_MEMORY_2D_ALIGNED(self->qmfInputImag__FDK);
981 FDK_FREE_MEMORY_2D_ALIGNED(self->qmfInputReal__FDK);
982
983 FDK_FREE_MEMORY_3D(self->M2ImagPrev__FDK);
984
985 FDK_FREE_MEMORY_3D(self->M2RealPrev__FDK);
986
987 FDK_FREE_MEMORY_3D(self->M2Imag__FDK);
988
989 FDK_FREE_MEMORY_3D(self->M2Real__FDK);
990
991 FDK_FREE_MEMORY_1D(self->arbdmxAlphaPrev__FDK);
992 FDK_FREE_MEMORY_1D(self->arbdmxAlpha__FDK);
993
994 FDK_FREE_MEMORY_3D(self->arbdmxGain__FDK);
995
996 FDK_FREE_MEMORY_3D(self->ottIPD__FDK);
997 FDK_FREE_MEMORY_3D(self->ottICC__FDK);
998 FDK_FREE_MEMORY_3D(self->ottCLD__FDK);
999
1000 /* Last parameters from prev frame */
1001 FDK_FREE_MEMORY_2D(self->ottCLDidxPrev);
1002 FDK_FREE_MEMORY_2D(self->ottICCidxPrev);
1003 FDK_FREE_MEMORY_3D(self->ottICCdiffidx);
1004 FDK_FREE_MEMORY_2D(self->ottIPDidxPrev);
1005 FDK_FREE_MEMORY_2D(self->arbdmxGainIdxPrev);
1006
1007 FDK_FREE_MEMORY_2D(self->cmpOttCLDidxPrev);
1008 FDK_FREE_MEMORY_2D(self->cmpOttICCidxPrev);
1009 FDK_FREE_MEMORY_3D(self->outIdxData);
1010 FDK_FREE_MEMORY_2D(self->cmpOttIPDidxPrev);
1011 FDK_FREE_MEMORY_2D(self->cmpArbdmxGainIdxPrev);
1012
1013 FDK_FREE_MEMORY_2D(self->smgData);
1014 FDK_FREE_MEMORY_1D(self->smgTime);
1015
1016 FDK_FREE_MEMORY_1D(self->numOttBands);
1017
1018 FDK_FREE_MEMORY_1D(self->param2hyb);
1019
1020 FDK_FREE_MEMORY_1D(self);
1021 }
1022
1023 return;
1024 }
1025
1026 /**
1027 * \brief Apply Surround bypass buffer copies
1028 * \param self spatialDec handle
1029 * \param hybInputReal
1030 * \param hybInputImag
1031 * \param hybOutputReal
1032 * \param hybOutputImag
1033 * \param numInputChannels amount if input channels available in hybInputReal
1034 * and hybInputImag, which may differ from self->numInputChannels.
1035 */
SpatialDecApplyBypass(spatialDec * self,FIXP_DBL ** hybInputReal,FIXP_DBL ** hybInputImag,FIXP_DBL ** hybOutputReal,FIXP_DBL ** hybOutputImag,const int numInputChannels)1036 static void SpatialDecApplyBypass(spatialDec *self, FIXP_DBL **hybInputReal,
1037 FIXP_DBL **hybInputImag,
1038 FIXP_DBL **hybOutputReal,
1039 FIXP_DBL **hybOutputImag,
1040 const int numInputChannels) {
1041 int complexHybBands;
1042
1043 complexHybBands = self->hybridBands;
1044
1045 {
1046 int ch;
1047 int rf = -1, lf = -1, cf = -1; /* Right Front, Left Front, Center Front */
1048
1049 /* Determine output channel indices according to tree config */
1050 switch (self->treeConfig) {
1051 case TREE_212: /* 212 */
1052 lf = 0;
1053 rf = 1;
1054 break;
1055 default:;
1056 }
1057
1058 /* Note: numInputChannels might not match the tree config ! */
1059 switch (numInputChannels) {
1060 case 1:
1061 if (cf > 0) {
1062 FDKmemcpy(hybOutputReal[cf], hybInputReal[0],
1063 self->hybridBands * sizeof(FIXP_DBL));
1064 FDKmemcpy(hybOutputImag[cf], hybInputImag[0],
1065 complexHybBands * sizeof(FIXP_DBL));
1066 } else {
1067 FDKmemcpy(hybOutputReal[lf], hybInputReal[0],
1068 self->hybridBands * sizeof(FIXP_DBL));
1069 FDKmemcpy(hybOutputReal[rf], hybInputReal[0],
1070 self->hybridBands * sizeof(FIXP_DBL));
1071 FDKmemcpy(hybOutputImag[lf], hybInputImag[0],
1072 complexHybBands * sizeof(FIXP_DBL));
1073 FDKmemcpy(hybOutputImag[rf], hybInputImag[0],
1074 complexHybBands * sizeof(FIXP_DBL));
1075 }
1076 break;
1077 case 2:
1078 FDK_ASSERT(lf != -1);
1079 FDK_ASSERT(rf != -1);
1080 FDKmemcpy(hybOutputReal[lf], hybInputReal[0],
1081 self->hybridBands * sizeof(FIXP_DBL));
1082 FDKmemcpy(hybOutputReal[rf], hybInputReal[1],
1083 self->hybridBands * sizeof(FIXP_DBL));
1084 FDKmemcpy(hybOutputImag[lf], hybInputImag[0],
1085 complexHybBands * sizeof(FIXP_DBL));
1086 FDKmemcpy(hybOutputImag[rf], hybInputImag[1],
1087 complexHybBands * sizeof(FIXP_DBL));
1088 break;
1089 }
1090 for (ch = 0; ch < self->numOutputChannelsAT; ch++) {
1091 if (ch == lf || ch == rf || ch == cf) {
1092 continue; /* Skip bypassed channels */
1093 }
1094 FDKmemclear(hybOutputReal[ch], self->hybridBands * sizeof(FIXP_DBL));
1095 FDKmemclear(hybOutputImag[ch], complexHybBands * sizeof(FIXP_DBL));
1096 }
1097 }
1098 }
1099
1100 /*******************************************************************************
1101 Functionname: SpatialDecApplyParameterSets
1102 *******************************************************************************
1103
1104 Description:
1105
1106 Arguments:
1107
1108 Return:
1109
1110 *******************************************************************************/
SpatialDecApplyParameterSets(spatialDec * self,const SPATIAL_BS_FRAME * frame,SPATIALDEC_INPUT_MODE mode,PCM_MPS * inData,FIXP_DBL ** qmfInDataReal,FIXP_DBL ** qmfInDataImag,UINT nSamples,UINT controlFlags,int numInputChannels,const FDK_channelMapDescr * const mapDescr)1111 static SACDEC_ERROR SpatialDecApplyParameterSets(
1112 spatialDec *self, const SPATIAL_BS_FRAME *frame, SPATIALDEC_INPUT_MODE mode,
1113 PCM_MPS *inData, /* Time domain input */
1114 FIXP_DBL **qmfInDataReal, /* QMF domain data l/r */
1115 FIXP_DBL **qmfInDataImag, /* QMF domain data l/r */
1116 UINT nSamples, UINT controlFlags, int numInputChannels,
1117 const FDK_channelMapDescr *const mapDescr) {
1118 SACDEC_ERROR err = MPS_OK;
1119
1120 FIXP_SGL alpha;
1121
1122 int ts;
1123 int ch;
1124 int hyb;
1125
1126 int prevSlot = self->prevTimeSlot;
1127 int ps = self->curPs;
1128 int ts_io = 0; /* i/o dependent slot */
1129 int bypassMode = (controlFlags & MPEGS_BYPASSMODE) ? 1 : 0;
1130
1131 /* Bypass can be triggered by the upmixType, too. */
1132 bypassMode |= ((self->upmixType == UPMIXTYPE_BYPASS) ? 1 : 0);
1133
1134 /*
1135 * Decode available slots
1136 */
1137 for (ts = self->curTimeSlot;
1138 ts <= fixMin(self->curTimeSlot + (int)nSamples / self->qmfBands - 1,
1139 self->timeSlots - 1);
1140 ts++, ts_io++) {
1141 int currSlot = frame->paramSlot[ps];
1142
1143 /*
1144 * Get new parameter set
1145 */
1146 if (ts == prevSlot + 1) {
1147 err = SpatialDecCalculateM1andM2(self, ps,
1148 frame); /* input: ottCLD, ottICC, ... */
1149 /* output: M1param(Real/Imag), M2(Real/Imag) */
1150 if (err != MPS_OK) {
1151 bypassMode = 1;
1152 if (self->errInt == MPS_OK) {
1153 /* store internal error befor it gets overwritten */
1154 self->errInt = err;
1155 }
1156 err = MPS_OK;
1157 }
1158
1159 if ((ps == 0) && (self->bOverwriteM1M2prev != 0)) {
1160 /* copy matrix entries of M1/M2 of the first parameter set to the
1161 previous matrices (of the last frame). This avoids the interpolation
1162 of incompatible values. E.g. for residual bands the coefficients are
1163 calculated differently compared to non-residual bands.
1164 */
1165 SpatialDecBufferMatrices(self); /* input: M(1/2)param(Real/Imag) */
1166 /* output: M(1/2)param(Real/Imag)Prev */
1167 self->bOverwriteM1M2prev = 0;
1168 }
1169
1170 SpatialDecSmoothM1andM2(
1171 self, frame,
1172 ps); /* input: M1param(Real/Imag)(Prev), M2(Real/Imag)(Prev) */
1173 /* output: M1param(Real/Imag), M2(Real/Imag) */
1174 }
1175
1176 alpha = FX_DBL2FX_SGL(fDivNorm(ts - prevSlot, currSlot - prevSlot));
1177
1178 switch (mode) {
1179 case INPUTMODE_QMF_SBR:
1180 if (self->pConfigCurrent->syntaxFlags & SACDEC_SYNTAX_LD)
1181 self->bShareDelayWithSBR = 0; /* We got no hybrid delay */
1182 else
1183 self->bShareDelayWithSBR = 1;
1184 SpatialDecFeedQMF(self, qmfInDataReal, qmfInDataImag, ts_io, bypassMode,
1185 self->qmfInputReal__FDK, self->qmfInputImag__FDK,
1186 self->numInputChannels);
1187 break;
1188 case INPUTMODE_TIME:
1189 self->bShareDelayWithSBR = 0;
1190 SpatialDecQMFAnalysis(self, inData, ts_io, bypassMode,
1191 self->qmfInputReal__FDK, self->qmfInputImag__FDK,
1192 self->numInputChannels);
1193 break;
1194 default:
1195 break;
1196 }
1197
1198 if ((self->pConfigCurrent->syntaxFlags & SACDEC_SYNTAX_USAC) &&
1199 self->residualCoding) {
1200 int offset;
1201 ch = 1;
1202
1203 offset = self->pQmfDomain->globalConf.nBandsSynthesis *
1204 self->pQmfDomain->globalConf.nQmfTimeSlots;
1205
1206 {
1207 const PCM_MPS *inSamples =
1208 &inData[ts * self->pQmfDomain->globalConf.nBandsAnalysis];
1209
1210 CalculateSpaceAnalysisQmf(
1211 &self->pQmfDomain->QmfDomainIn[ch].fb, inSamples + (ch * offset),
1212 self->qmfResidualReal__FDK[0][0], self->qmfResidualImag__FDK[0][0]);
1213
1214 if (!isTwoChMode(self->upmixType) && !bypassMode) {
1215 int i;
1216 FIXP_DBL *RESTRICT self_qmfResidualReal__FDK_0_0 =
1217 &self->qmfResidualReal__FDK[0][0][0];
1218 FIXP_DBL *RESTRICT self_qmfResidualImag__FDK_0_0 =
1219 &self->qmfResidualImag__FDK[0][0][0];
1220
1221 if ((self->pQmfDomain->globalConf.nBandsAnalysis == 24) &&
1222 !(self->stereoConfigIndex == 3)) {
1223 for (i = 0; i < self->qmfBands; i++) {
1224 self_qmfResidualReal__FDK_0_0[i] =
1225 fMult(self_qmfResidualReal__FDK_0_0[i] << 1,
1226 self->clipProtectGain__FDK);
1227 self_qmfResidualImag__FDK_0_0[i] =
1228 fMult(self_qmfResidualImag__FDK_0_0[i] << 1,
1229 self->clipProtectGain__FDK);
1230 }
1231 } else {
1232 for (i = 0; i < self->qmfBands; i++) {
1233 self_qmfResidualReal__FDK_0_0[i] = fMult(
1234 self_qmfResidualReal__FDK_0_0[i], self->clipProtectGain__FDK);
1235 self_qmfResidualImag__FDK_0_0[i] = fMult(
1236 self_qmfResidualImag__FDK_0_0[i], self->clipProtectGain__FDK);
1237 }
1238 }
1239 }
1240 }
1241 }
1242
1243 SpatialDecHybridAnalysis(
1244 self, /* input: qmfInput(Real/Imag), qmfResidual(Real/Imag) */
1245 self->qmfInputReal__FDK, self->qmfInputImag__FDK,
1246 self->hybInputReal__FDK, self->hybInputImag__FDK, ts, numInputChannels);
1247
1248 if (bypassMode) {
1249 SpatialDecApplyBypass(
1250 self, self->hybInputReal__FDK, /* input: hybInput(Real/Imag) */
1251 self->hybInputImag__FDK,
1252 self->hybOutputRealDry__FDK, /* output: hybOutput(Real/Imag)Dry */
1253 self->hybOutputImagDry__FDK, numInputChannels);
1254 } else /* !bypassMode */
1255 {
1256 FIXP_DBL *pxReal[MAX_NUM_XCHANNELS] = {NULL};
1257 FIXP_DBL *pxImag[MAX_NUM_XCHANNELS] = {NULL};
1258
1259 SpatialDecCreateX(self,
1260 self->hybInputReal__FDK, /* input: hybInput(Real/Imag),
1261 hybResidual(Real/Imag) */
1262 self->hybInputImag__FDK, pxReal, pxImag);
1263
1264 {
1265 SpatialDecApplyM1_CreateW_Mode212(
1266 self, frame, pxReal, pxImag,
1267 self->wReal__FDK, /* output: w(Real/Imag) */
1268 self->wImag__FDK);
1269 }
1270 if (err != MPS_OK) goto bail;
1271
1272 int applyM2Config = APPLY_M2_NONE;
1273
1274 applyM2Config = APPLY_M2;
1275 if ((self->pConfigCurrent->syntaxFlags &
1276 (SACDEC_SYNTAX_USAC | SACDEC_SYNTAX_RSVD50)) &&
1277 (self->tempShapeConfig != 1) && (self->tempShapeConfig != 2)) {
1278 if (self->phaseCoding == 3)
1279 applyM2Config = APPLY_M2_MODE212_Res_PhaseCoding;
1280 else
1281 applyM2Config = APPLY_M2_MODE212;
1282 }
1283
1284 switch (applyM2Config) {
1285 case APPLY_M2_MODE212: {
1286 err = SpatialDecApplyM2_Mode212(
1287 self, ps, alpha, self->wReal__FDK, self->wImag__FDK,
1288 self->hybOutputRealDry__FDK, self->hybOutputImagDry__FDK);
1289 } break;
1290 case APPLY_M2_MODE212_Res_PhaseCoding:
1291 err = SpatialDecApplyM2_Mode212_ResidualsPlusPhaseCoding(
1292 self, ps, alpha, self->wReal__FDK, self->wImag__FDK,
1293 self->hybOutputRealDry__FDK, self->hybOutputImagDry__FDK);
1294 break;
1295 case APPLY_M2:
1296 err = SpatialDecApplyM2(
1297 self, ps, alpha, self->wReal__FDK, self->wImag__FDK,
1298 self->hybOutputRealDry__FDK, self->hybOutputImagDry__FDK,
1299 self->hybOutputRealWet__FDK, self->hybOutputImagWet__FDK);
1300 break;
1301 default:
1302 err = MPS_APPLY_M2_ERROR;
1303 goto bail;
1304 }
1305
1306 if (err != MPS_OK) goto bail;
1307
1308 if ((self->tempShapeConfig == 2) && (!isTwoChMode(self->upmixType))) {
1309 SpatialDecReshapeBBEnv(self, frame,
1310 ts); /* input: reshapeBBEnvState,
1311 hybOutput(Real/Imag)(Dry/Wet),
1312 hybInput(Real/Imag) */
1313 } /* output: hybOutput(Real/Imag)Dry */
1314
1315 /* Merge parts of the dry and wet QMF buffers. */
1316 if ((self->tempShapeConfig == 1) && (!isTwoChMode(self->upmixType))) {
1317 for (ch = 0; ch < self->numOutputChannels; ch++) {
1318 for (hyb = 0; hyb < self->tp_hybBandBorder; hyb++) {
1319 self->hybOutputRealDry__FDK[ch][hyb] +=
1320 self->hybOutputRealWet__FDK[ch][hyb];
1321 self->hybOutputImagDry__FDK[ch][hyb] +=
1322 self->hybOutputImagWet__FDK[ch][hyb];
1323 } /* loop hyb */
1324 } /* loop ch */
1325 err = subbandTPApply(
1326 self, frame); /* input: hStpDec, hybOutput(Real/Imag)Dry/Wet */
1327 /* output: hStpDec, hybOutput(Real/Imag)Dry */
1328 if (err != MPS_OK) goto bail;
1329 } /* (self->tempShapeConfig == 1) */
1330 else {
1331 /* The wet signal is added to the dry signal in applyM2 if GES and STP
1332 * are disabled */
1333 if ((self->tempShapeConfig == 1) || (self->tempShapeConfig == 2)) {
1334 int nHybBands;
1335 nHybBands = self->hybridBands;
1336
1337 for (ch = 0; ch < self->numOutputChannels; ch++) {
1338 FIXP_DBL *RESTRICT pRealDry = self->hybOutputRealDry__FDK[ch];
1339 FIXP_DBL *RESTRICT pImagDry = self->hybOutputImagDry__FDK[ch];
1340 FIXP_DBL *RESTRICT pRealWet = self->hybOutputRealWet__FDK[ch];
1341 FIXP_DBL *RESTRICT pImagWet = self->hybOutputImagWet__FDK[ch];
1342 for (hyb = 0; hyb < nHybBands; hyb++) {
1343 pRealDry[hyb] += pRealWet[hyb];
1344 pImagDry[hyb] += pImagWet[hyb];
1345 } /* loop hyb */
1346 for (; hyb < self->hybridBands; hyb++) {
1347 pRealDry[hyb] += pRealWet[hyb];
1348 } /* loop hyb */
1349 } /* loop ch */
1350 } /* ( self->tempShapeConfig == 1 ) || ( self->tempShapeConfig == 2 ) */
1351 } /* !self->tempShapeConfig == 1 */
1352 } /* !bypassMode */
1353
1354 if (self->phaseCoding == 1) {
1355 /* only if bsPhaseCoding == 1 and bsResidualCoding == 0 */
1356
1357 SpatialDecApplyPhase(
1358 self, alpha, (ts == currSlot) /* signal the last slot of the set */
1359 );
1360 }
1361
1362 /*
1363 * Synthesis Filtering
1364 */
1365
1366 err = SpatialDecSynthesis(
1367 self, ts_io,
1368 self->hybOutputRealDry__FDK, /* input: hybOutput(Real/Imag)Dry */
1369 self->hybOutputImagDry__FDK, self->timeOut__FDK, /* output: timeOut */
1370 numInputChannels, mapDescr);
1371
1372 if (err != MPS_OK) goto bail;
1373
1374 /*
1375 * Update parameter buffer
1376 */
1377 if (ts == currSlot) {
1378 SpatialDecBufferMatrices(self); /* input: M(1/2)param(Real/Imag) */
1379 /* output: M(1/2)param(Real/Imag)Prev */
1380
1381 prevSlot = currSlot;
1382 ps++;
1383 } /* if (ts==currSlot) */
1384
1385 } /* ts loop */
1386
1387 /*
1388 * Save parameter states
1389 */
1390 self->prevTimeSlot = prevSlot;
1391 self->curTimeSlot = ts;
1392 self->curPs = ps;
1393
1394 bail:
1395
1396 return err;
1397 }
1398
SpatialDecApplyFrame(spatialDec * self,SPATIAL_BS_FRAME * frame,SPATIALDEC_INPUT_MODE inputMode,PCM_MPS * inData,FIXP_DBL ** qmfInDataReal,FIXP_DBL ** qmfInDataImag,PCM_MPS * pcmOutBuf,UINT nSamples,UINT * pControlFlags,int numInputChannels,const FDK_channelMapDescr * const mapDescr)1399 SACDEC_ERROR SpatialDecApplyFrame(
1400 spatialDec *self,
1401 SPATIAL_BS_FRAME *frame, /* parsed frame data to be applied */
1402 SPATIALDEC_INPUT_MODE inputMode, PCM_MPS *inData, /* Time domain input */
1403 FIXP_DBL **qmfInDataReal, /* QMF domain data l/r */
1404 FIXP_DBL **qmfInDataImag, /* QMF domain data l/r */
1405 PCM_MPS *pcmOutBuf, /* MAX_OUTPUT_CHANNELS*MAX_TIME_SLOTS*NUM_QMF_BANDS] */
1406 UINT nSamples, UINT *pControlFlags, int numInputChannels,
1407 const FDK_channelMapDescr *const mapDescr) {
1408 SACDEC_ERROR err = MPS_OK;
1409
1410 int fDecAndMapFrameData;
1411 int controlFlags;
1412
1413 FDK_ASSERT(self != NULL);
1414 FDK_ASSERT(pControlFlags != NULL);
1415 FDK_ASSERT(pcmOutBuf != NULL);
1416
1417 self->errInt = err; /* Init internal error */
1418
1419 controlFlags = *pControlFlags;
1420
1421 if ((self->pConfigCurrent->syntaxFlags & SACDEC_SYNTAX_USAC) &&
1422 (self->stereoConfigIndex > 1)) {
1423 numInputChannels =
1424 1; /* Do not count residual channel as input channel. It is handled
1425 seperately. */
1426 }
1427
1428 /* Check if input amount of channels is consistent */
1429 if (numInputChannels != self->numInputChannels) {
1430 controlFlags |= MPEGS_CONCEAL;
1431 if (numInputChannels > self->createParams.maxNumInputChannels) {
1432 return MPS_INVALID_PARAMETER;
1433 }
1434 }
1435
1436 self->timeOut__FDK = pcmOutBuf;
1437
1438 /* Determine local function control flags */
1439 fDecAndMapFrameData = frame->newBsData;
1440
1441 if (((fDecAndMapFrameData ==
1442 0) /* assures that conceal flag will not be set for blind mode */
1443 && (self->curTimeSlot + (int)nSamples / self->qmfBands >
1444 self->timeSlots)) ||
1445 (frame->numParameterSets ==
1446 0)) { /* New input samples but missing side info */
1447 fDecAndMapFrameData = 1;
1448 controlFlags |= MPEGS_CONCEAL;
1449 }
1450
1451 if ((fDecAndMapFrameData == 0) &&
1452 (frame->paramSlot[fMax(0, frame->numParameterSets - 1)] !=
1453 (self->timeSlots - 1) ||
1454 self->curTimeSlot >
1455 frame->paramSlot[self->curPs])) { /* Detected faulty parameter slot
1456 data. */
1457 fDecAndMapFrameData = 1;
1458 controlFlags |= MPEGS_CONCEAL;
1459 }
1460
1461 /* Update concealment state machine */
1462 SpatialDecConcealment_UpdateState(
1463 &self->concealInfo,
1464 (controlFlags & MPEGS_CONCEAL)
1465 ? 0
1466 : 1); /* convert from conceal flag to frame ok flag */
1467
1468 if (fDecAndMapFrameData) {
1469 /* Reset spatial framing control vars */
1470 frame->newBsData = 0;
1471 self->prevTimeSlot = -1;
1472 self->curTimeSlot = 0;
1473 self->curPs = 0;
1474
1475 if (controlFlags & MPEGS_CONCEAL) {
1476 /* Reset frame data to avoid misconfiguration. */
1477 SpatialDecClearFrameData(self, frame, &self->createParams);
1478 }
1479
1480 {
1481 err = SpatialDecDecodeFrame(self, frame); /* input: ... */
1482 /* output: decodeAndMapFrameDATA */
1483 }
1484
1485 if (err != MPS_OK) {
1486 /* Rescue strategy is to apply bypass mode in order
1487 to keep at least the downmix channels continuous. */
1488 controlFlags |= MPEGS_CONCEAL;
1489 if (self->errInt == MPS_OK) {
1490 /* store internal error befor it gets overwritten */
1491 self->errInt = err;
1492 }
1493 }
1494 }
1495
1496 err = SpatialDecApplyParameterSets(
1497 self, frame, inputMode, inData, qmfInDataReal, qmfInDataImag, nSamples,
1498 controlFlags | ((err == MPS_OK) ? 0 : MPEGS_BYPASSMODE), numInputChannels,
1499 mapDescr);
1500 if (err != MPS_OK) {
1501 goto bail;
1502 }
1503
1504 bail:
1505
1506 *pControlFlags = controlFlags;
1507
1508 return err;
1509 }
1510