1 /* -----------------------------------------------------------------------------
2 Software License for The Fraunhofer FDK AAC Codec Library for Android
3
4 © Copyright 1995 - 2019 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 /**************************** AAC decoder library ******************************
96
97 Author(s): Robert Weidner (DSP Solutions)
98
99 Description: HCR Decoder: HCR initialization, preprocess HCR sideinfo,
100 decode priority codewords (PCWs)
101
102 *******************************************************************************/
103
104 #include "aacdec_hcr.h"
105
106 #include "aacdec_hcr_types.h"
107 #include "aacdec_hcr_bit.h"
108 #include "aacdec_hcrs.h"
109 #include "aac_ram.h"
110 #include "aac_rom.h"
111 #include "channel.h"
112 #include "block.h"
113
114 #include "aacdecoder.h" /* for ID_CPE, ID_SCE ... */
115 #include "FDK_bitstream.h"
116
117 extern int mlFileChCurr;
118
119 static void errDetectorInHcrSideinfoShrt(SCHAR cb, SHORT numLine,
120 UINT *errorWord);
121
122 static void errDetectorInHcrLengths(SCHAR lengthOfLongestCodeword,
123 SHORT lengthOfReorderedSpectralData,
124 UINT *errorWord);
125
126 static void HcrCalcNumCodeword(H_HCR_INFO pHcr);
127 static void HcrSortCodebookAndNumCodewordInSection(H_HCR_INFO pHcr);
128 static void HcrPrepareSegmentationGrid(H_HCR_INFO pHcr);
129 static void HcrExtendedSectionInfo(H_HCR_INFO pHcr);
130
131 static void DeriveNumberOfExtendedSortedSectionsInSets(
132 UINT numSegment, USHORT *pNumExtendedSortedCodewordInSection,
133 int numExtendedSortedCodewordInSectionIdx,
134 USHORT *pNumExtendedSortedSectionsInSets,
135 int numExtendedSortedSectionsInSetsIdx);
136
137 static INT DecodeEscapeSequence(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
138 INT quantSpecCoef, INT *pLeftStartOfSegment,
139 SCHAR *pRemainingBitsInSegment,
140 int *pNumDecodedBits, UINT *errorWord);
141
142 static int DecodePCW_Sign(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
143 UINT codebookDim, const SCHAR *pQuantVal,
144 FIXP_DBL *pQuantSpecCoef, int *quantSpecCoefIdx,
145 INT *pLeftStartOfSegment,
146 SCHAR *pRemainingBitsInSegment, int *pNumDecodedBits);
147
148 static const SCHAR *DecodePCW_Body(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
149 const UINT *pCurrentTree,
150 const SCHAR *pQuantValBase,
151 INT *pLeftStartOfSegment,
152 SCHAR *pRemainingBitsInSegment,
153 int *pNumDecodedBits);
154
155 static void DecodePCWs(HANDLE_FDK_BITSTREAM bs, H_HCR_INFO pHcr);
156
157 static void HcrReorderQuantizedSpectralCoefficients(
158 H_HCR_INFO pHcr, CAacDecoderChannelInfo *pAacDecoderChannelInfo,
159 const SamplingRateInfo *pSamplingRateInfo);
160
161 static UCHAR errDetectPcwSegmentation(SCHAR remainingBitsInSegment,
162 H_HCR_INFO pHcr, PCW_TYPE kind,
163 FIXP_DBL *qsc_base_of_cw,
164 UCHAR dimension);
165
166 static void errDetectWithinSegmentationFinal(H_HCR_INFO pHcr);
167
168 /*---------------------------------------------------------------------------------------------
169 description: Check if codebook and numSect are within allowed range
170 (short only)
171 --------------------------------------------------------------------------------------------
172 */
errDetectorInHcrSideinfoShrt(SCHAR cb,SHORT numLine,UINT * errorWord)173 static void errDetectorInHcrSideinfoShrt(SCHAR cb, SHORT numLine,
174 UINT *errorWord) {
175 if (cb < ZERO_HCB || cb >= MAX_CB_CHECK || cb == BOOKSCL) {
176 *errorWord |= CB_OUT_OF_RANGE_SHORT_BLOCK;
177 }
178 if (numLine < 0 || numLine > 1024) {
179 *errorWord |= LINE_IN_SECT_OUT_OF_RANGE_SHORT_BLOCK;
180 }
181 }
182
183 /*---------------------------------------------------------------------------------------------
184 description: Check both HCR lengths
185 --------------------------------------------------------------------------------------------
186 */
errDetectorInHcrLengths(SCHAR lengthOfLongestCodeword,SHORT lengthOfReorderedSpectralData,UINT * errorWord)187 static void errDetectorInHcrLengths(SCHAR lengthOfLongestCodeword,
188 SHORT lengthOfReorderedSpectralData,
189 UINT *errorWord) {
190 if (lengthOfReorderedSpectralData < lengthOfLongestCodeword) {
191 *errorWord |= HCR_SI_LENGTHS_FAILURE;
192 }
193 }
194
195 /*---------------------------------------------------------------------------------------------
196 description: Decode (and adapt if necessary) the two HCR sideinfo
197 components: 'reordered_spectral_data_length' and 'longest_codeword_length'
198 --------------------------------------------------------------------------------------------
199 */
200
CHcr_Read(HANDLE_FDK_BITSTREAM bs,CAacDecoderChannelInfo * pAacDecoderChannelInfo,const MP4_ELEMENT_ID globalHcrType)201 void CHcr_Read(HANDLE_FDK_BITSTREAM bs,
202 CAacDecoderChannelInfo *pAacDecoderChannelInfo,
203 const MP4_ELEMENT_ID globalHcrType) {
204 SHORT lengOfReorderedSpectralData;
205 SCHAR lengOfLongestCodeword;
206
207 pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfReorderedSpectralData =
208 0;
209 pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfLongestCodeword = 0;
210
211 /* ------- SI-Value No 1 ------- */
212 lengOfReorderedSpectralData = FDKreadBits(bs, 14) + ERROR_LORSD;
213 if (globalHcrType == ID_CPE) {
214 if ((lengOfReorderedSpectralData >= 0) &&
215 (lengOfReorderedSpectralData <= CPE_TOP_LENGTH)) {
216 pAacDecoderChannelInfo->pDynData->specificTo.aac
217 .lenOfReorderedSpectralData =
218 lengOfReorderedSpectralData; /* the decoded value is within range */
219 } else {
220 if (lengOfReorderedSpectralData > CPE_TOP_LENGTH) {
221 pAacDecoderChannelInfo->pDynData->specificTo.aac
222 .lenOfReorderedSpectralData =
223 CPE_TOP_LENGTH; /* use valid maximum */
224 }
225 }
226 } else if (globalHcrType == ID_SCE || globalHcrType == ID_LFE ||
227 globalHcrType == ID_CCE) {
228 if ((lengOfReorderedSpectralData >= 0) &&
229 (lengOfReorderedSpectralData <= SCE_TOP_LENGTH)) {
230 pAacDecoderChannelInfo->pDynData->specificTo.aac
231 .lenOfReorderedSpectralData =
232 lengOfReorderedSpectralData; /* the decoded value is within range */
233 } else {
234 if (lengOfReorderedSpectralData > SCE_TOP_LENGTH) {
235 pAacDecoderChannelInfo->pDynData->specificTo.aac
236 .lenOfReorderedSpectralData =
237 SCE_TOP_LENGTH; /* use valid maximum */
238 }
239 }
240 }
241
242 /* ------- SI-Value No 2 ------- */
243 lengOfLongestCodeword = FDKreadBits(bs, 6) + ERROR_LOLC;
244 if ((lengOfLongestCodeword >= 0) &&
245 (lengOfLongestCodeword <= LEN_OF_LONGEST_CW_TOP_LENGTH)) {
246 pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfLongestCodeword =
247 lengOfLongestCodeword; /* the decoded value is within range */
248 } else {
249 if (lengOfLongestCodeword > LEN_OF_LONGEST_CW_TOP_LENGTH) {
250 pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfLongestCodeword =
251 LEN_OF_LONGEST_CW_TOP_LENGTH; /* use valid maximum */
252 }
253 }
254 }
255
256 /*---------------------------------------------------------------------------------------------
257 description: Set up HCR - must be called before every call to
258 HcrDecoder(). For short block a sorting algorithm is applied to get the SI in
259 the order that HCR could assemble the qsc's as if it is a long block.
260 -----------------------------------------------------------------------------------------------
261 return: error log
262 --------------------------------------------------------------------------------------------
263 */
264
HcrInit(H_HCR_INFO pHcr,CAacDecoderChannelInfo * pAacDecoderChannelInfo,const SamplingRateInfo * pSamplingRateInfo,HANDLE_FDK_BITSTREAM bs)265 UINT HcrInit(H_HCR_INFO pHcr, CAacDecoderChannelInfo *pAacDecoderChannelInfo,
266 const SamplingRateInfo *pSamplingRateInfo,
267 HANDLE_FDK_BITSTREAM bs) {
268 CIcsInfo *pIcsInfo = &pAacDecoderChannelInfo->icsInfo;
269 SHORT *pNumLinesInSec;
270 UCHAR *pCodeBk;
271 SHORT numSection;
272 SCHAR cb;
273 int numLine;
274 int i;
275
276 pHcr->decInOut.lengthOfReorderedSpectralData =
277 pAacDecoderChannelInfo->pDynData->specificTo.aac
278 .lenOfReorderedSpectralData;
279 pHcr->decInOut.lengthOfLongestCodeword =
280 pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfLongestCodeword;
281 pHcr->decInOut.pQuantizedSpectralCoefficientsBase =
282 pAacDecoderChannelInfo->pSpectralCoefficient;
283 pHcr->decInOut.quantizedSpectralCoefficientsIdx = 0;
284 pHcr->decInOut.pCodebook =
285 pAacDecoderChannelInfo->pDynData->specificTo.aac.aCodeBooks4Hcr;
286 pHcr->decInOut.pNumLineInSect =
287 pAacDecoderChannelInfo->pDynData->specificTo.aac.aNumLineInSec4Hcr;
288 pHcr->decInOut.numSection =
289 pAacDecoderChannelInfo->pDynData->specificTo.aac.numberSection;
290 pHcr->decInOut.errorLog = 0;
291 pHcr->nonPcwSideinfo.pResultBase =
292 SPEC_LONG(pAacDecoderChannelInfo->pSpectralCoefficient);
293
294 FDKsyncCache(bs);
295 pHcr->decInOut.bitstreamAnchor = (INT)FDKgetValidBits(bs);
296
297 if (!IsLongBlock(&pAacDecoderChannelInfo->icsInfo)) /* short block */
298 {
299 SHORT band;
300 SHORT maxBand;
301 SCHAR group;
302 SCHAR winGroupLen;
303 SCHAR window;
304 SCHAR numUnitInBand;
305 SCHAR cntUnitInBand;
306 SCHAR groupWin;
307 SCHAR cb_prev;
308
309 UCHAR *pCodeBook;
310 const SHORT *BandOffsets;
311 SCHAR numOfGroups;
312
313 pCodeBook = pAacDecoderChannelInfo->pDynData->aCodeBook; /* in */
314 pNumLinesInSec = pHcr->decInOut.pNumLineInSect; /* out */
315 pCodeBk = pHcr->decInOut.pCodebook; /* out */
316 BandOffsets =
317 GetScaleFactorBandOffsets(pIcsInfo, pSamplingRateInfo); /* aux */
318 numOfGroups = GetWindowGroups(pIcsInfo);
319
320 numLine = 0;
321 numSection = 0;
322 cb = pCodeBook[0];
323 cb_prev = pCodeBook[0];
324
325 /* convert HCR-sideinfo into a unitwise manner: When the cb changes, a new
326 * section starts */
327
328 *pCodeBk++ = cb_prev;
329
330 maxBand = GetScaleFactorBandsTransmitted(&pAacDecoderChannelInfo->icsInfo);
331 for (band = 0; band < maxBand;
332 band++) { /* from low to high sfbs i.e. from low to high frequencies */
333 numUnitInBand =
334 ((BandOffsets[band + 1] - BandOffsets[band]) >>
335 FOUR_LOG_DIV_TWO_LOG); /* get the number of units in current sfb */
336 for (cntUnitInBand = numUnitInBand; cntUnitInBand != 0;
337 cntUnitInBand--) { /* for every unit in the band */
338 for (window = 0, group = 0; group < numOfGroups; group++) {
339 winGroupLen = (SCHAR)GetWindowGroupLength(
340 &pAacDecoderChannelInfo->icsInfo, group);
341 for (groupWin = winGroupLen; groupWin != 0; groupWin--, window++) {
342 cb = pCodeBook[group * 16 + band];
343 if (cb != cb_prev) {
344 errDetectorInHcrSideinfoShrt(cb, numLine,
345 &pHcr->decInOut.errorLog);
346 if (pHcr->decInOut.errorLog != 0) {
347 return (pHcr->decInOut.errorLog);
348 }
349 *pCodeBk++ = cb;
350 *pNumLinesInSec++ = numLine;
351 numSection++;
352
353 cb_prev = cb;
354 numLine = LINES_PER_UNIT;
355 } else {
356 numLine += LINES_PER_UNIT;
357 }
358 }
359 }
360 }
361 }
362
363 numSection++;
364
365 errDetectorInHcrSideinfoShrt(cb, numLine, &pHcr->decInOut.errorLog);
366 if (numSection <= 0 || numSection > 1024 / 2) {
367 pHcr->decInOut.errorLog |= NUM_SECT_OUT_OF_RANGE_SHORT_BLOCK;
368 }
369 errDetectorInHcrLengths(pHcr->decInOut.lengthOfLongestCodeword,
370 pHcr->decInOut.lengthOfReorderedSpectralData,
371 &pHcr->decInOut.errorLog);
372 if (pHcr->decInOut.errorLog != 0) {
373 return (pHcr->decInOut.errorLog);
374 }
375
376 *pCodeBk = cb;
377 *pNumLinesInSec = numLine;
378 pHcr->decInOut.numSection = numSection;
379
380 } else /* end short block prepare SI */
381 { /* long block */
382 errDetectorInHcrLengths(pHcr->decInOut.lengthOfLongestCodeword,
383 pHcr->decInOut.lengthOfReorderedSpectralData,
384 &pHcr->decInOut.errorLog);
385 numSection = pHcr->decInOut.numSection;
386 pNumLinesInSec = pHcr->decInOut.pNumLineInSect;
387 pCodeBk = pHcr->decInOut.pCodebook;
388 if (numSection <= 0 || numSection > 64) {
389 pHcr->decInOut.errorLog |= NUM_SECT_OUT_OF_RANGE_LONG_BLOCK;
390 numSection = 0;
391 }
392
393 for (i = numSection; i != 0; i--) {
394 cb = *pCodeBk++;
395
396 if (cb < ZERO_HCB || cb >= MAX_CB_CHECK || cb == BOOKSCL) {
397 pHcr->decInOut.errorLog |= CB_OUT_OF_RANGE_LONG_BLOCK;
398 }
399
400 numLine = *pNumLinesInSec++;
401 /* FDK_ASSERT(numLine > 0); */
402
403 if ((numLine <= 0) || (numLine > 1024)) {
404 pHcr->decInOut.errorLog |= LINE_IN_SECT_OUT_OF_RANGE_LONG_BLOCK;
405 }
406 }
407 if (pHcr->decInOut.errorLog != 0) {
408 return (pHcr->decInOut.errorLog);
409 }
410 }
411
412 pCodeBk = pHcr->decInOut.pCodebook;
413 for (i = 0; i < numSection; i++) {
414 if ((*pCodeBk == NOISE_HCB) || (*pCodeBk == INTENSITY_HCB2) ||
415 (*pCodeBk == INTENSITY_HCB)) {
416 *pCodeBk = 0;
417 }
418 pCodeBk++;
419 }
420
421 /* HCR-sideinfo-input is complete and seems to be valid */
422
423 return (pHcr->decInOut.errorLog);
424 }
425
426 /*---------------------------------------------------------------------------------------------
427 description: This function decodes the codewords of the spectral
428 coefficients from the bitstream according to the HCR algorithm and stores the
429 quantized spectral coefficients in correct order in the output buffer.
430 --------------------------------------------------------------------------------------------
431 */
432
HcrDecoder(H_HCR_INFO pHcr,CAacDecoderChannelInfo * pAacDecoderChannelInfo,const SamplingRateInfo * pSamplingRateInfo,HANDLE_FDK_BITSTREAM bs)433 UINT HcrDecoder(H_HCR_INFO pHcr, CAacDecoderChannelInfo *pAacDecoderChannelInfo,
434 const SamplingRateInfo *pSamplingRateInfo,
435 HANDLE_FDK_BITSTREAM bs) {
436 int pTmp1, pTmp2, pTmp3, pTmp4;
437 int pTmp5;
438
439 INT bitCntOffst;
440 INT saveBitCnt = (INT)FDKgetValidBits(bs); /* save bitstream position */
441
442 HcrCalcNumCodeword(pHcr);
443
444 HcrSortCodebookAndNumCodewordInSection(pHcr);
445
446 HcrPrepareSegmentationGrid(pHcr);
447
448 HcrExtendedSectionInfo(pHcr);
449
450 if ((pHcr->decInOut.errorLog & HCR_FATAL_PCW_ERROR_MASK) != 0) {
451 return (pHcr->decInOut.errorLog); /* sideinfo is massively corrupt, return
452 from HCR without having decoded
453 anything */
454 }
455
456 DeriveNumberOfExtendedSortedSectionsInSets(
457 pHcr->segmentInfo.numSegment,
458 pHcr->sectionInfo.pNumExtendedSortedCodewordInSection,
459 pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx,
460 pHcr->sectionInfo.pNumExtendedSortedSectionsInSets,
461 pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx);
462
463 /* store */
464 pTmp1 = pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx;
465 pTmp2 = pHcr->sectionInfo.extendedSortedCodebookIdx;
466 pTmp3 = pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx;
467 pTmp4 = pHcr->decInOut.quantizedSpectralCoefficientsIdx;
468 pTmp5 = pHcr->sectionInfo.maxLenOfCbInExtSrtSecIdx;
469
470 /* ------- decode meaningful PCWs ------ */
471 DecodePCWs(bs, pHcr);
472
473 if ((pHcr->decInOut.errorLog & HCR_FATAL_PCW_ERROR_MASK) == 0) {
474 /* ------ decode the non-PCWs -------- */
475 DecodeNonPCWs(bs, pHcr);
476 }
477
478 errDetectWithinSegmentationFinal(pHcr);
479
480 /* restore */
481 pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx = pTmp1;
482 pHcr->sectionInfo.extendedSortedCodebookIdx = pTmp2;
483 pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx = pTmp3;
484 pHcr->decInOut.quantizedSpectralCoefficientsIdx = pTmp4;
485 pHcr->sectionInfo.maxLenOfCbInExtSrtSecIdx = pTmp5;
486
487 HcrReorderQuantizedSpectralCoefficients(pHcr, pAacDecoderChannelInfo,
488 pSamplingRateInfo);
489
490 /* restore bitstream position */
491 bitCntOffst = (INT)FDKgetValidBits(bs) - saveBitCnt;
492 if (bitCntOffst) {
493 FDKpushBiDirectional(bs, bitCntOffst);
494 }
495
496 return (pHcr->decInOut.errorLog);
497 }
498
499 /*---------------------------------------------------------------------------------------------
500 description: This function reorders the quantized spectral coefficients
501 sectionwise for long- and short-blocks and compares to the LAV (Largest Absolute
502 Value of the current codebook) -- a counter is incremented if there is an error
503 detected.
504 Additional for short-blocks a unit-based-deinterleaving is
505 applied. Moreover (for short blocks) the scaling is derived (compare plain
506 huffman decoder).
507 --------------------------------------------------------------------------------------------
508 */
509
HcrReorderQuantizedSpectralCoefficients(H_HCR_INFO pHcr,CAacDecoderChannelInfo * pAacDecoderChannelInfo,const SamplingRateInfo * pSamplingRateInfo)510 static void HcrReorderQuantizedSpectralCoefficients(
511 H_HCR_INFO pHcr, CAacDecoderChannelInfo *pAacDecoderChannelInfo,
512 const SamplingRateInfo *pSamplingRateInfo) {
513 INT qsc;
514 UINT abs_qsc;
515 UINT i, j;
516 USHORT numSpectralValuesInSection;
517 FIXP_DBL *pTeVa;
518 USHORT lavErrorCnt = 0;
519
520 UINT numSection = pHcr->decInOut.numSection;
521 SPECTRAL_PTR pQuantizedSpectralCoefficientsBase =
522 pHcr->decInOut.pQuantizedSpectralCoefficientsBase;
523 FIXP_DBL *pQuantizedSpectralCoefficients =
524 SPEC_LONG(pHcr->decInOut.pQuantizedSpectralCoefficientsBase);
525 const UCHAR *pCbDimShift = aDimCbShift;
526 const USHORT *pLargestAbsVal = aLargestAbsoluteValue;
527 UCHAR *pSortedCodebook = pHcr->sectionInfo.pSortedCodebook;
528 USHORT *pNumSortedCodewordInSection =
529 pHcr->sectionInfo.pNumSortedCodewordInSection;
530 USHORT *pReorderOffset = pHcr->sectionInfo.pReorderOffset;
531 FIXP_DBL pTempValues[1024];
532 FIXP_DBL *pBak = pTempValues;
533
534 FDKmemclear(pTempValues, 1024 * sizeof(FIXP_DBL));
535
536 /* long and short: check if decoded huffman-values (quantized spectral
537 * coefficients) are within range */
538 for (i = numSection; i != 0; i--) {
539 numSpectralValuesInSection = *pNumSortedCodewordInSection++
540 << pCbDimShift[*pSortedCodebook];
541 pTeVa = &pTempValues[*pReorderOffset++];
542 for (j = numSpectralValuesInSection; j != 0; j--) {
543 qsc = *pQuantizedSpectralCoefficients++;
544 abs_qsc = fAbs(qsc);
545 if (abs_qsc <= pLargestAbsVal[*pSortedCodebook]) {
546 *pTeVa++ = (FIXP_DBL)qsc; /* the qsc value is within range */
547 } else { /* line is too high .. */
548 if (abs_qsc ==
549 Q_VALUE_INVALID) { /* .. because of previous marking --> dont set
550 LAV flag (would be confusing), just copy out
551 the already marked value */
552 *pTeVa++ = (FIXP_DBL)qsc;
553 } else { /* .. because a too high value was decoded for this cb --> set
554 LAV flag */
555 *pTeVa++ = (FIXP_DBL)Q_VALUE_INVALID;
556 lavErrorCnt += 1;
557 }
558 }
559 }
560 pSortedCodebook++;
561 }
562
563 if (!IsLongBlock(&pAacDecoderChannelInfo->icsInfo)) {
564 FIXP_DBL *pOut;
565 FIXP_DBL locMax;
566 FIXP_DBL tmp;
567 SCHAR groupoffset;
568 SCHAR group;
569 SCHAR band;
570 SCHAR groupwin;
571 SCHAR window;
572 SCHAR numWinGroup;
573 SHORT interm;
574 SCHAR numSfbTransm;
575 SCHAR winGroupLen;
576 SHORT index;
577 INT msb;
578 INT lsb;
579
580 SHORT *pScaleFacHcr = pAacDecoderChannelInfo->pDynData->aScaleFactor;
581 SHORT *pSfbSclHcr = pAacDecoderChannelInfo->pDynData->aSfbScale;
582 const SHORT *BandOffsets = GetScaleFactorBandOffsets(
583 &pAacDecoderChannelInfo->icsInfo, pSamplingRateInfo);
584
585 pBak = pTempValues;
586 /* deinterleave unitwise for short blocks */
587 for (window = 0; window < (8); window++) {
588 pOut = SPEC(pQuantizedSpectralCoefficientsBase, window,
589 pAacDecoderChannelInfo->granuleLength);
590 for (i = 0; i < (LINES_PER_UNIT_GROUP); i++) {
591 pTeVa = pBak + (window << FOUR_LOG_DIV_TWO_LOG) +
592 i * 32; /* distance of lines between unit groups has to be
593 constant for every framelength (32)! */
594 for (j = (LINES_PER_UNIT); j != 0; j--) {
595 *pOut++ = *pTeVa++;
596 }
597 }
598 }
599
600 /* short blocks only */
601 /* derive global scaling-value for every sfb and every window (as it is done
602 * in plain-huffman-decoder at short blocks) */
603 groupoffset = 0;
604
605 numWinGroup = GetWindowGroups(&pAacDecoderChannelInfo->icsInfo);
606 numSfbTransm =
607 GetScaleFactorBandsTransmitted(&pAacDecoderChannelInfo->icsInfo);
608
609 for (group = 0; group < numWinGroup; group++) {
610 winGroupLen =
611 GetWindowGroupLength(&pAacDecoderChannelInfo->icsInfo, group);
612 for (band = 0; band < numSfbTransm; band++) {
613 interm = group * 16 + band;
614 msb = pScaleFacHcr[interm] >> 2;
615 lsb = pScaleFacHcr[interm] & 3;
616 for (groupwin = 0; groupwin < winGroupLen; groupwin++) {
617 window = groupoffset + groupwin;
618 pBak = SPEC(pQuantizedSpectralCoefficientsBase, window,
619 pAacDecoderChannelInfo->granuleLength);
620 locMax = FL2FXCONST_DBL(0.0f);
621 for (index = BandOffsets[band]; index < BandOffsets[band + 1];
622 index += LINES_PER_UNIT) {
623 pTeVa = &pBak[index];
624 for (i = LINES_PER_UNIT; i != 0; i--) {
625 tmp = (*pTeVa < FL2FXCONST_DBL(0.0f)) ? -*pTeVa++ : *pTeVa++;
626 locMax = fixMax(tmp, locMax);
627 }
628 }
629 if (fixp_abs(locMax) > (FIXP_DBL)MAX_QUANTIZED_VALUE) {
630 locMax = (FIXP_DBL)MAX_QUANTIZED_VALUE;
631 }
632 pSfbSclHcr[window * 16 + band] =
633 msb - GetScaleFromValue(
634 locMax, lsb); /* save global scale maxima in this sfb */
635 }
636 }
637 groupoffset +=
638 GetWindowGroupLength(&pAacDecoderChannelInfo->icsInfo, group);
639 }
640 } else {
641 /* copy straight for long-blocks */
642 pQuantizedSpectralCoefficients =
643 SPEC_LONG(pQuantizedSpectralCoefficientsBase);
644 for (i = 1024; i != 0; i--) {
645 *pQuantizedSpectralCoefficients++ = *pBak++;
646 }
647 }
648
649 if (lavErrorCnt != 0) {
650 pHcr->decInOut.errorLog |= LAV_VIOLATION;
651 }
652 }
653
654 /*---------------------------------------------------------------------------------------------
655 description: This function calculates the number of codewords
656 for each section (numCodewordInSection) and the number of
657 codewords for all sections (numCodeword). For zero and intensity codebooks a
658 entry is also done in the variable numCodewordInSection. It is assumed that the
659 codebook is a two tuples codebook. This is needed later for the calculation of
660 the base addresses for the reordering of the quantize spectral coefficients at
661 the end of the hcr tool. The variable numCodeword contain the number of
662 codewords which are really in the bitstream. Zero or intensity codebooks does
663 not increase the variable numCodewords.
664 -----------------------------------------------------------------------------------------------
665 return: -
666 --------------------------------------------------------------------------------------------
667 */
668
HcrCalcNumCodeword(H_HCR_INFO pHcr)669 static void HcrCalcNumCodeword(H_HCR_INFO pHcr) {
670 int hcrSection;
671 UINT numCodeword;
672
673 UINT numSection = pHcr->decInOut.numSection;
674 UCHAR *pCodebook = pHcr->decInOut.pCodebook;
675 SHORT *pNumLineInSection = pHcr->decInOut.pNumLineInSect;
676 const UCHAR *pCbDimShift = aDimCbShift;
677
678 USHORT *pNumCodewordInSection = pHcr->sectionInfo.pNumCodewordInSection;
679
680 numCodeword = 0;
681 for (hcrSection = numSection; hcrSection != 0; hcrSection--) {
682 *pNumCodewordInSection = *pNumLineInSection++ >> pCbDimShift[*pCodebook];
683 if (*pCodebook != 0) {
684 numCodeword += *pNumCodewordInSection;
685 }
686 pNumCodewordInSection++;
687 pCodebook++;
688 }
689 pHcr->sectionInfo.numCodeword = numCodeword;
690 }
691
692 /*---------------------------------------------------------------------------------------------
693 description: This function calculates the number
694 of sorted codebooks and sorts the codebooks and the
695 numCodewordInSection according to the priority.
696 --------------------------------------------------------------------------------------------
697 */
698
HcrSortCodebookAndNumCodewordInSection(H_HCR_INFO pHcr)699 static void HcrSortCodebookAndNumCodewordInSection(H_HCR_INFO pHcr) {
700 UINT i, j, k;
701 UCHAR temp;
702 UINT counter;
703 UINT startOffset;
704 UINT numZeroSection;
705 UCHAR *pDest;
706 UINT numSectionDec;
707
708 UINT numSection = pHcr->decInOut.numSection;
709 UCHAR *pCodebook = pHcr->decInOut.pCodebook;
710 UCHAR *pSortedCodebook = pHcr->sectionInfo.pSortedCodebook;
711 USHORT *pNumCodewordInSection = pHcr->sectionInfo.pNumCodewordInSection;
712 USHORT *pNumSortedCodewordInSection =
713 pHcr->sectionInfo.pNumSortedCodewordInSection;
714 UCHAR *pCodebookSwitch = pHcr->sectionInfo.pCodebookSwitch;
715 USHORT *pReorderOffset = pHcr->sectionInfo.pReorderOffset;
716 const UCHAR *pCbPriority = aCbPriority;
717 const UCHAR *pMinOfCbPair = aMinOfCbPair;
718 const UCHAR *pMaxOfCbPair = aMaxOfCbPair;
719 const UCHAR *pCbDimShift = aDimCbShift;
720
721 UINT searchStart = 0;
722
723 /* calculate *pNumSortedSection and store the priorities in array
724 * pSortedCdebook */
725 pDest = pSortedCodebook;
726 numZeroSection = 0;
727 for (i = numSection; i != 0; i--) {
728 if (pCbPriority[*pCodebook] == 0) {
729 numZeroSection += 1;
730 }
731 *pDest++ = pCbPriority[*pCodebook++];
732 }
733 pHcr->sectionInfo.numSortedSection =
734 numSection - numZeroSection; /* numSortedSection contains no zero or
735 intensity section */
736 pCodebook = pHcr->decInOut.pCodebook;
737
738 /* sort priorities of the codebooks in array pSortedCdebook[] */
739 numSectionDec = numSection - 1;
740 if (numSectionDec > 0) {
741 counter = numSectionDec;
742 for (j = numSectionDec; j != 0; j--) {
743 for (i = 0; i < counter; i++) {
744 /* swap priorities */
745 if (pSortedCodebook[i + 1] > pSortedCodebook[i]) {
746 temp = pSortedCodebook[i];
747 pSortedCodebook[i] = pSortedCodebook[i + 1];
748 pSortedCodebook[i + 1] = temp;
749 }
750 }
751 counter -= 1;
752 }
753 }
754
755 /* clear codebookSwitch array */
756 for (i = numSection; i != 0; i--) {
757 *pCodebookSwitch++ = 0;
758 }
759 pCodebookSwitch = pHcr->sectionInfo.pCodebookSwitch;
760
761 /* sort sectionCodebooks and numCodwordsInSection and calculate
762 * pReorderOffst[j] */
763 for (j = 0; j < numSection; j++) {
764 for (i = searchStart; i < numSection; i++) {
765 if (pCodebookSwitch[i] == 0 &&
766 (pMinOfCbPair[pSortedCodebook[j]] == pCodebook[i] ||
767 pMaxOfCbPair[pSortedCodebook[j]] == pCodebook[i])) {
768 pCodebookSwitch[i] = 1;
769 pSortedCodebook[j] = pCodebook[i]; /* sort codebook */
770 pNumSortedCodewordInSection[j] =
771 pNumCodewordInSection[i]; /* sort NumCodewordInSection */
772
773 startOffset = 0;
774 for (k = 0; k < i; k++) { /* make entry in pReorderOffst */
775 startOffset += pNumCodewordInSection[k] << pCbDimShift[pCodebook[k]];
776 }
777 pReorderOffset[j] =
778 startOffset; /* offset for reordering the codewords */
779
780 if (i == searchStart) {
781 k = i;
782 while (pCodebookSwitch[k++] == 1) searchStart++;
783 }
784 break;
785 }
786 }
787 }
788 }
789
790 /*---------------------------------------------------------------------------------------------
791 description: This function calculates the segmentation, which includes
792 numSegment, leftStartOfSegment, rightStartOfSegment and remainingBitsInSegment.
793 The segmentation could be visualized a as kind of
794 'overlay-grid' for the bitstream-block holding the HCR-encoded
795 quantized-spectral-coefficients.
796 --------------------------------------------------------------------------------------------
797 */
798
HcrPrepareSegmentationGrid(H_HCR_INFO pHcr)799 static void HcrPrepareSegmentationGrid(H_HCR_INFO pHcr) {
800 USHORT i, j;
801 USHORT numSegment = 0;
802 INT segmentStart = 0;
803 UCHAR segmentWidth;
804 UCHAR lastSegmentWidth;
805 UCHAR sortedCodebook;
806 UCHAR endFlag = 0;
807 INT intermediateResult;
808
809 SCHAR lengthOfLongestCodeword = pHcr->decInOut.lengthOfLongestCodeword;
810 SHORT lengthOfReorderedSpectralData =
811 pHcr->decInOut.lengthOfReorderedSpectralData;
812 UINT numSortedSection = pHcr->sectionInfo.numSortedSection;
813 UCHAR *pSortedCodebook = pHcr->sectionInfo.pSortedCodebook;
814 USHORT *pNumSortedCodewordInSection =
815 pHcr->sectionInfo.pNumSortedCodewordInSection;
816 INT *pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment;
817 INT *pRightStartOfSegment = pHcr->segmentInfo.pRightStartOfSegment;
818 SCHAR *pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
819 const UCHAR *pMaxCwLength = aMaxCwLen;
820
821 for (i = numSortedSection; i != 0; i--) {
822 sortedCodebook = *pSortedCodebook++;
823 segmentWidth =
824 fMin((INT)pMaxCwLength[sortedCodebook], (INT)lengthOfLongestCodeword);
825
826 for (j = *pNumSortedCodewordInSection; j != 0; j--) {
827 /* width allows a new segment */
828 intermediateResult = segmentStart;
829 if ((segmentStart + segmentWidth) <= lengthOfReorderedSpectralData) {
830 /* store segment start, segment length and increment the number of
831 * segments */
832 *pLeftStartOfSegment++ = intermediateResult;
833 *pRightStartOfSegment++ = intermediateResult + segmentWidth - 1;
834 *pRemainingBitsInSegment++ = segmentWidth;
835 segmentStart += segmentWidth;
836 numSegment += 1;
837 }
838 /* width does not allow a new segment */
839 else {
840 /* correct the last segment length */
841 pLeftStartOfSegment--;
842 pRightStartOfSegment--;
843 pRemainingBitsInSegment--;
844 segmentStart = *pLeftStartOfSegment;
845
846 lastSegmentWidth = lengthOfReorderedSpectralData - segmentStart;
847 *pRemainingBitsInSegment = lastSegmentWidth;
848 *pRightStartOfSegment = segmentStart + lastSegmentWidth - 1;
849 endFlag = 1;
850 break;
851 }
852 }
853 pNumSortedCodewordInSection++;
854 if (endFlag != 0) {
855 break;
856 }
857 }
858 pHcr->segmentInfo.numSegment = numSegment;
859 }
860
861 /*---------------------------------------------------------------------------------------------
862 description: This function adapts the sorted section boundaries to the
863 boundaries of segmentation. If the section lengths does not fit completely into
864 the current segment, the section is spitted into two so called 'extended
865 sections'. The extended-section-info
866 (pNumExtendedSortedCodewordInSectin and pExtendedSortedCodebook) is updated in
867 this case.
868
869 --------------------------------------------------------------------------------------------
870 */
871
HcrExtendedSectionInfo(H_HCR_INFO pHcr)872 static void HcrExtendedSectionInfo(H_HCR_INFO pHcr) {
873 UINT srtSecCnt = 0; /* counter for sorted sections */
874 UINT xSrtScCnt = 0; /* counter for extended sorted sections */
875 UINT remainNumCwInSortSec;
876 UINT inSegmentRemainNumCW;
877
878 UINT numSortedSection = pHcr->sectionInfo.numSortedSection;
879 UCHAR *pSortedCodebook = pHcr->sectionInfo.pSortedCodebook;
880 USHORT *pNumSortedCodewordInSection =
881 pHcr->sectionInfo.pNumSortedCodewordInSection;
882 UCHAR *pExtendedSortedCoBo = pHcr->sectionInfo.pExtendedSortedCodebook;
883 USHORT *pNumExtSortCwInSect =
884 pHcr->sectionInfo.pNumExtendedSortedCodewordInSection;
885 UINT numSegment = pHcr->segmentInfo.numSegment;
886 UCHAR *pMaxLenOfCbInExtSrtSec = pHcr->sectionInfo.pMaxLenOfCbInExtSrtSec;
887 SCHAR lengthOfLongestCodeword = pHcr->decInOut.lengthOfLongestCodeword;
888 const UCHAR *pMaxCwLength = aMaxCwLen;
889
890 remainNumCwInSortSec = pNumSortedCodewordInSection[srtSecCnt];
891 inSegmentRemainNumCW = numSegment;
892
893 while (srtSecCnt < numSortedSection) {
894 if (inSegmentRemainNumCW < remainNumCwInSortSec) {
895 pNumExtSortCwInSect[xSrtScCnt] = inSegmentRemainNumCW;
896 pExtendedSortedCoBo[xSrtScCnt] = pSortedCodebook[srtSecCnt];
897
898 remainNumCwInSortSec -= inSegmentRemainNumCW;
899 inSegmentRemainNumCW = numSegment;
900 /* data of a sorted section was not integrated in extended sorted section
901 */
902 } else if (inSegmentRemainNumCW == remainNumCwInSortSec) {
903 pNumExtSortCwInSect[xSrtScCnt] = inSegmentRemainNumCW;
904 pExtendedSortedCoBo[xSrtScCnt] = pSortedCodebook[srtSecCnt];
905
906 srtSecCnt++;
907 remainNumCwInSortSec = pNumSortedCodewordInSection[srtSecCnt];
908 inSegmentRemainNumCW = numSegment;
909 /* data of a sorted section was integrated in extended sorted section */
910 } else { /* inSegmentRemainNumCW > remainNumCwInSortSec */
911 pNumExtSortCwInSect[xSrtScCnt] = remainNumCwInSortSec;
912 pExtendedSortedCoBo[xSrtScCnt] = pSortedCodebook[srtSecCnt];
913
914 inSegmentRemainNumCW -= remainNumCwInSortSec;
915 srtSecCnt++;
916 remainNumCwInSortSec = pNumSortedCodewordInSection[srtSecCnt];
917 /* data of a sorted section was integrated in extended sorted section */
918 }
919 pMaxLenOfCbInExtSrtSec[xSrtScCnt] =
920 fMin((INT)pMaxCwLength[pExtendedSortedCoBo[xSrtScCnt]],
921 (INT)lengthOfLongestCodeword);
922
923 xSrtScCnt += 1;
924
925 if (xSrtScCnt >= (MAX_SFB_HCR + MAX_HCR_SETS)) {
926 pHcr->decInOut.errorLog |= EXTENDED_SORTED_COUNTER_OVERFLOW;
927 return;
928 }
929 }
930 pNumExtSortCwInSect[xSrtScCnt] = 0;
931 }
932
933 /*---------------------------------------------------------------------------------------------
934 description: This function calculates the number of extended sorted
935 sections which belong to the sets. Each set from set 0 (one and only set for the
936 PCWs) till to the last set gets a entry in the array to which
937 'pNumExtendedSortedSectinsInSets' points to.
938
939 Calculation: The entrys in
940 pNumExtendedSortedCodewordInSectin are added untill the value numSegment is
941 reached. Then the sum_variable is cleared and the calculation starts from the
942 beginning. As much extended sorted Sections are summed up to reach the value
943 numSegment, as much is the current entry in *pNumExtendedSortedCodewordInSectin.
944 --------------------------------------------------------------------------------------------
945 */
DeriveNumberOfExtendedSortedSectionsInSets(UINT numSegment,USHORT * pNumExtendedSortedCodewordInSection,int numExtendedSortedCodewordInSectionIdx,USHORT * pNumExtendedSortedSectionsInSets,int numExtendedSortedSectionsInSetsIdx)946 static void DeriveNumberOfExtendedSortedSectionsInSets(
947 UINT numSegment, USHORT *pNumExtendedSortedCodewordInSection,
948 int numExtendedSortedCodewordInSectionIdx,
949 USHORT *pNumExtendedSortedSectionsInSets,
950 int numExtendedSortedSectionsInSetsIdx) {
951 USHORT counter = 0;
952 UINT cwSum = 0;
953 USHORT *pNumExSortCwInSec = pNumExtendedSortedCodewordInSection;
954 USHORT *pNumExSortSecInSets = pNumExtendedSortedSectionsInSets;
955
956 while (pNumExSortCwInSec[numExtendedSortedCodewordInSectionIdx] != 0) {
957 cwSum += pNumExSortCwInSec[numExtendedSortedCodewordInSectionIdx];
958 numExtendedSortedCodewordInSectionIdx++;
959 if (numExtendedSortedCodewordInSectionIdx >= (MAX_SFB_HCR + MAX_HCR_SETS)) {
960 return;
961 }
962 if (cwSum > numSegment) {
963 return;
964 }
965 counter++;
966 if (counter > 1024 / 4) {
967 return;
968 }
969 if (cwSum == numSegment) {
970 pNumExSortSecInSets[numExtendedSortedSectionsInSetsIdx] = counter;
971 numExtendedSortedSectionsInSetsIdx++;
972 if (numExtendedSortedSectionsInSetsIdx >= MAX_HCR_SETS) {
973 return;
974 }
975 counter = 0;
976 cwSum = 0;
977 }
978 }
979 pNumExSortSecInSets[numExtendedSortedSectionsInSetsIdx] =
980 counter; /* save last entry for the last - probably shorter - set */
981 }
982
983 /*---------------------------------------------------------------------------------------------
984 description: This function decodes all priority codewords (PCWs) in a
985 spectrum (within set 0). The calculation of the PCWs is managed in two loops.
986 The loopcounter of the outer loop is set to the first value pointer
987 pNumExtendedSortedSectionsInSets points to. This value
988 represents the number of extended sorted sections within set 0. The loopcounter
989 of the inner loop is set to the first value pointer
990 pNumExtendedSortedCodewordInSectin points to. The value
991 represents the number of extended sorted codewords in sections (the original
992 sections have been splitted to go along with the borders of the sets). Each time
993 the number of the extended sorted codewords in sections are de- coded, the
994 pointer 'pNumExtendedSortedCodewordInSectin' is incremented by one.
995 --------------------------------------------------------------------------------------------
996 */
DecodePCWs(HANDLE_FDK_BITSTREAM bs,H_HCR_INFO pHcr)997 static void DecodePCWs(HANDLE_FDK_BITSTREAM bs, H_HCR_INFO pHcr) {
998 UINT i;
999 USHORT extSortSec;
1000 USHORT curExtSortCwInSec;
1001 UCHAR codebook;
1002 UCHAR dimension;
1003 const UINT *pCurrentTree;
1004 const SCHAR *pQuantValBase;
1005 const SCHAR *pQuantVal;
1006
1007 USHORT *pNumExtendedSortedCodewordInSection =
1008 pHcr->sectionInfo.pNumExtendedSortedCodewordInSection;
1009 int numExtendedSortedCodewordInSectionIdx =
1010 pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx;
1011 UCHAR *pExtendedSortedCodebook = pHcr->sectionInfo.pExtendedSortedCodebook;
1012 int extendedSortedCodebookIdx = pHcr->sectionInfo.extendedSortedCodebookIdx;
1013 USHORT *pNumExtendedSortedSectionsInSets =
1014 pHcr->sectionInfo.pNumExtendedSortedSectionsInSets;
1015 int numExtendedSortedSectionsInSetsIdx =
1016 pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx;
1017 FIXP_DBL *pQuantizedSpectralCoefficients =
1018 SPEC_LONG(pHcr->decInOut.pQuantizedSpectralCoefficientsBase);
1019 int quantizedSpectralCoefficientsIdx =
1020 pHcr->decInOut.quantizedSpectralCoefficientsIdx;
1021 INT *pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment;
1022 SCHAR *pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
1023 UCHAR *pMaxLenOfCbInExtSrtSec = pHcr->sectionInfo.pMaxLenOfCbInExtSrtSec;
1024 int maxLenOfCbInExtSrtSecIdx = pHcr->sectionInfo.maxLenOfCbInExtSrtSecIdx;
1025 UCHAR maxAllowedCwLen;
1026 int numDecodedBits;
1027 const UCHAR *pCbDimension = aDimCb;
1028 const UCHAR *pCbSign = aSignCb;
1029
1030 /* clear result array */
1031 FDKmemclear(pQuantizedSpectralCoefficients + quantizedSpectralCoefficientsIdx,
1032 1024 * sizeof(FIXP_DBL));
1033
1034 /* decode all PCWs in the extended sorted section(s) belonging to set 0 */
1035 for (extSortSec =
1036 pNumExtendedSortedSectionsInSets[numExtendedSortedSectionsInSetsIdx];
1037 extSortSec != 0; extSortSec--) {
1038 codebook =
1039 pExtendedSortedCodebook[extendedSortedCodebookIdx]; /* get codebook for
1040 this extended
1041 sorted section
1042 and increment ptr
1043 to cb of next
1044 ext. sort sec */
1045 extendedSortedCodebookIdx++;
1046 if (extendedSortedCodebookIdx >= (MAX_SFB_HCR + MAX_HCR_SETS)) {
1047 return;
1048 }
1049 dimension = pCbDimension[codebook]; /* get dimension of codebook of this
1050 extended sort. sec. */
1051 pCurrentTree =
1052 aHuffTable[codebook]; /* convert codebook to pointer to QSCs */
1053 pQuantValBase =
1054 aQuantTable[codebook]; /* convert codebook to index to table of QSCs */
1055 maxAllowedCwLen = pMaxLenOfCbInExtSrtSec[maxLenOfCbInExtSrtSecIdx];
1056 maxLenOfCbInExtSrtSecIdx++;
1057 if (maxLenOfCbInExtSrtSecIdx >= (MAX_SFB_HCR + MAX_HCR_SETS)) {
1058 return;
1059 }
1060
1061 /* switch for decoding with different codebooks: */
1062 if (pCbSign[codebook] ==
1063 0) { /* no sign bits follow after the codeword-body */
1064 /* PCW_BodyONLY */
1065 /*==============*/
1066
1067 for (curExtSortCwInSec = pNumExtendedSortedCodewordInSection
1068 [numExtendedSortedCodewordInSectionIdx];
1069 curExtSortCwInSec != 0; curExtSortCwInSec--) {
1070 numDecodedBits = 0;
1071
1072 /* decode PCW_BODY */
1073 pQuantVal = DecodePCW_Body(
1074 bs, pHcr->decInOut.bitstreamAnchor, pCurrentTree, pQuantValBase,
1075 pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits);
1076
1077 /* result is written out here because NO sign bits follow the body */
1078 for (i = dimension; i != 0; i--) {
1079 pQuantizedSpectralCoefficients[quantizedSpectralCoefficientsIdx] =
1080 (FIXP_DBL)*pQuantVal++; /* write quant. spec. coef. into
1081 spectrum; sign is already valid */
1082 quantizedSpectralCoefficientsIdx++;
1083 if (quantizedSpectralCoefficientsIdx >= 1024) {
1084 return;
1085 }
1086 }
1087
1088 /* one more PCW should be decoded */
1089
1090 if (maxAllowedCwLen < (numDecodedBits + ERROR_PCW_BODY_ONLY_TOO_LONG)) {
1091 pHcr->decInOut.errorLog |= TOO_MANY_PCW_BODY_BITS_DECODED;
1092 }
1093
1094 if (1 == errDetectPcwSegmentation(
1095 *pRemainingBitsInSegment - ERROR_PCW_BODY, pHcr, PCW_BODY,
1096 pQuantizedSpectralCoefficients +
1097 quantizedSpectralCoefficientsIdx - dimension,
1098 dimension)) {
1099 return;
1100 }
1101 pLeftStartOfSegment++; /* update pointer for decoding the next PCW */
1102 pRemainingBitsInSegment++; /* update pointer for decoding the next PCW
1103 */
1104 }
1105 } else if ((codebook < 11) && (pCbSign[codebook] ==
1106 1)) { /* possibly there follow 1,2,3 or 4
1107 sign bits after the codeword-body */
1108 /* PCW_Body and PCW_Sign */
1109 /*=======================*/
1110
1111 for (curExtSortCwInSec = pNumExtendedSortedCodewordInSection
1112 [numExtendedSortedCodewordInSectionIdx];
1113 curExtSortCwInSec != 0; curExtSortCwInSec--) {
1114 int err;
1115 numDecodedBits = 0;
1116
1117 pQuantVal = DecodePCW_Body(
1118 bs, pHcr->decInOut.bitstreamAnchor, pCurrentTree, pQuantValBase,
1119 pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits);
1120
1121 err = DecodePCW_Sign(
1122 bs, pHcr->decInOut.bitstreamAnchor, dimension, pQuantVal,
1123 pQuantizedSpectralCoefficients, &quantizedSpectralCoefficientsIdx,
1124 pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits);
1125 if (err != 0) {
1126 return;
1127 }
1128 /* one more PCW should be decoded */
1129
1130 if (maxAllowedCwLen < (numDecodedBits + ERROR_PCW_BODY_SIGN_TOO_LONG)) {
1131 pHcr->decInOut.errorLog |= TOO_MANY_PCW_BODY_SIGN_BITS_DECODED;
1132 }
1133
1134 if (1 == errDetectPcwSegmentation(
1135 *pRemainingBitsInSegment - ERROR_PCW_BODY_SIGN, pHcr,
1136 PCW_BODY_SIGN,
1137 pQuantizedSpectralCoefficients +
1138 quantizedSpectralCoefficientsIdx - dimension,
1139 dimension)) {
1140 return;
1141 }
1142 pLeftStartOfSegment++;
1143 pRemainingBitsInSegment++;
1144 }
1145 } else if ((pCbSign[codebook] == 1) &&
1146 (codebook >= 11)) { /* possibly there follow some sign bits and
1147 maybe one or two escape sequences after
1148 the cw-body */
1149 /* PCW_Body, PCW_Sign and maybe PCW_Escape */
1150 /*=========================================*/
1151
1152 for (curExtSortCwInSec = pNumExtendedSortedCodewordInSection
1153 [numExtendedSortedCodewordInSectionIdx];
1154 curExtSortCwInSec != 0; curExtSortCwInSec--) {
1155 int err;
1156 numDecodedBits = 0;
1157
1158 /* decode PCW_BODY */
1159 pQuantVal = DecodePCW_Body(
1160 bs, pHcr->decInOut.bitstreamAnchor, pCurrentTree, pQuantValBase,
1161 pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits);
1162
1163 err = DecodePCW_Sign(
1164 bs, pHcr->decInOut.bitstreamAnchor, dimension, pQuantVal,
1165 pQuantizedSpectralCoefficients, &quantizedSpectralCoefficientsIdx,
1166 pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits);
1167 if (err != 0) {
1168 return;
1169 }
1170
1171 /* decode PCW_ESCAPE if present */
1172 quantizedSpectralCoefficientsIdx -= DIMENSION_OF_ESCAPE_CODEBOOK;
1173
1174 if (fixp_abs(pQuantizedSpectralCoefficients
1175 [quantizedSpectralCoefficientsIdx]) ==
1176 (FIXP_DBL)ESCAPE_VALUE) {
1177 pQuantizedSpectralCoefficients[quantizedSpectralCoefficientsIdx] =
1178 (FIXP_DBL)DecodeEscapeSequence(
1179 bs, pHcr->decInOut.bitstreamAnchor,
1180 pQuantizedSpectralCoefficients
1181 [quantizedSpectralCoefficientsIdx],
1182 pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits,
1183 &pHcr->decInOut.errorLog);
1184 }
1185 quantizedSpectralCoefficientsIdx++;
1186 if (quantizedSpectralCoefficientsIdx >= 1024) {
1187 return;
1188 }
1189
1190 if (fixp_abs(pQuantizedSpectralCoefficients
1191 [quantizedSpectralCoefficientsIdx]) ==
1192 (FIXP_DBL)ESCAPE_VALUE) {
1193 pQuantizedSpectralCoefficients[quantizedSpectralCoefficientsIdx] =
1194 (FIXP_DBL)DecodeEscapeSequence(
1195 bs, pHcr->decInOut.bitstreamAnchor,
1196 pQuantizedSpectralCoefficients
1197 [quantizedSpectralCoefficientsIdx],
1198 pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits,
1199 &pHcr->decInOut.errorLog);
1200 }
1201 quantizedSpectralCoefficientsIdx++;
1202 if (quantizedSpectralCoefficientsIdx >= 1024) {
1203 return;
1204 }
1205
1206 /* one more PCW should be decoded */
1207
1208 if (maxAllowedCwLen <
1209 (numDecodedBits + ERROR_PCW_BODY_SIGN_ESC_TOO_LONG)) {
1210 pHcr->decInOut.errorLog |= TOO_MANY_PCW_BODY_SIGN_ESC_BITS_DECODED;
1211 }
1212
1213 if (1 == errDetectPcwSegmentation(
1214 *pRemainingBitsInSegment - ERROR_PCW_BODY_SIGN_ESC, pHcr,
1215 PCW_BODY_SIGN_ESC,
1216 pQuantizedSpectralCoefficients +
1217 quantizedSpectralCoefficientsIdx -
1218 DIMENSION_OF_ESCAPE_CODEBOOK,
1219 DIMENSION_OF_ESCAPE_CODEBOOK)) {
1220 return;
1221 }
1222 pLeftStartOfSegment++;
1223 pRemainingBitsInSegment++;
1224 }
1225 }
1226
1227 /* all PCWs belonging to this extended section should be decoded */
1228 numExtendedSortedCodewordInSectionIdx++;
1229 if (numExtendedSortedCodewordInSectionIdx >= MAX_SFB_HCR + MAX_HCR_SETS) {
1230 return;
1231 }
1232 }
1233 /* all PCWs should be decoded */
1234
1235 numExtendedSortedSectionsInSetsIdx++;
1236 if (numExtendedSortedSectionsInSetsIdx >= MAX_HCR_SETS) {
1237 return;
1238 }
1239
1240 /* Write back indexes into structure */
1241 pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx =
1242 numExtendedSortedCodewordInSectionIdx;
1243 pHcr->sectionInfo.extendedSortedCodebookIdx = extendedSortedCodebookIdx;
1244 pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx =
1245 numExtendedSortedSectionsInSetsIdx;
1246 pHcr->decInOut.quantizedSpectralCoefficientsIdx =
1247 quantizedSpectralCoefficientsIdx;
1248 pHcr->sectionInfo.maxLenOfCbInExtSrtSecIdx = maxLenOfCbInExtSrtSecIdx;
1249 }
1250
1251 /*---------------------------------------------------------------------------------------------
1252 description: This function checks immediately after every decoded PCW,
1253 whether out of the current segment too many bits have been read or not. If an
1254 error occurrs, probably the sideinfo or the HCR-bitstream block holding the
1255 huffman encoded quantized spectral coefficients is distorted. In this case the
1256 two or four quantized spectral coefficients belonging to the current codeword
1257 are marked (for being detected by concealment later).
1258 --------------------------------------------------------------------------------------------
1259 */
errDetectPcwSegmentation(SCHAR remainingBitsInSegment,H_HCR_INFO pHcr,PCW_TYPE kind,FIXP_DBL * qsc_base_of_cw,UCHAR dimension)1260 static UCHAR errDetectPcwSegmentation(SCHAR remainingBitsInSegment,
1261 H_HCR_INFO pHcr, PCW_TYPE kind,
1262 FIXP_DBL *qsc_base_of_cw,
1263 UCHAR dimension) {
1264 SCHAR i;
1265 if (remainingBitsInSegment < 0) {
1266 /* log the error */
1267 switch (kind) {
1268 case PCW_BODY:
1269 pHcr->decInOut.errorLog |= SEGMENT_OVERRIDE_ERR_PCW_BODY;
1270 break;
1271 case PCW_BODY_SIGN:
1272 pHcr->decInOut.errorLog |= SEGMENT_OVERRIDE_ERR_PCW_BODY_SIGN;
1273 break;
1274 case PCW_BODY_SIGN_ESC:
1275 pHcr->decInOut.errorLog |= SEGMENT_OVERRIDE_ERR_PCW_BODY_SIGN_ESC;
1276 break;
1277 }
1278 /* mark the erred lines */
1279 for (i = dimension; i != 0; i--) {
1280 *qsc_base_of_cw++ = (FIXP_DBL)Q_VALUE_INVALID;
1281 }
1282 return 1;
1283 }
1284 return 0;
1285 }
1286
1287 /*---------------------------------------------------------------------------------------------
1288 description: This function checks if all segments are empty after
1289 decoding. There are _no lines markded_ as invalid because it could not be traced
1290 back where from the remaining bits are.
1291 --------------------------------------------------------------------------------------------
1292 */
errDetectWithinSegmentationFinal(H_HCR_INFO pHcr)1293 static void errDetectWithinSegmentationFinal(H_HCR_INFO pHcr) {
1294 UCHAR segmentationErrorFlag = 0;
1295 USHORT i;
1296 SCHAR *pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
1297 UINT numSegment = pHcr->segmentInfo.numSegment;
1298
1299 for (i = numSegment; i != 0; i--) {
1300 if (*pRemainingBitsInSegment++ != 0) {
1301 segmentationErrorFlag = 1;
1302 }
1303 }
1304 if (segmentationErrorFlag == 1) {
1305 pHcr->decInOut.errorLog |= BIT_IN_SEGMENTATION_ERROR;
1306 }
1307 }
1308
1309 /*---------------------------------------------------------------------------------------------
1310 description: This function walks one step within the decoding tree. Which
1311 branch is taken depends on the decoded carryBit input parameter.
1312 --------------------------------------------------------------------------------------------
1313 */
CarryBitToBranchValue(UCHAR carryBit,UINT treeNode,UINT * branchValue,UINT * branchNode)1314 void CarryBitToBranchValue(UCHAR carryBit, UINT treeNode, UINT *branchValue,
1315 UINT *branchNode) {
1316 if (carryBit == 0) {
1317 *branchNode =
1318 (treeNode & MASK_LEFT) >> LEFT_OFFSET; /* MASK_LEFT: 00FFF000 */
1319 } else {
1320 *branchNode = treeNode & MASK_RIGHT; /* MASK_RIGHT: 00000FFF */
1321 }
1322
1323 *branchValue = *branchNode & CLR_BIT_10; /* clear bit 10 (if set) */
1324 }
1325
1326 /*---------------------------------------------------------------------------------------------
1327 description: Decodes the body of a priority codeword (PCW)
1328 -----------------------------------------------------------------------------------------------
1329 return: - return value is pointer to first of two or four quantized
1330 spectral coefficients
1331 --------------------------------------------------------------------------------------------
1332 */
DecodePCW_Body(HANDLE_FDK_BITSTREAM bs,const INT bsAnchor,const UINT * pCurrentTree,const SCHAR * pQuantValBase,INT * pLeftStartOfSegment,SCHAR * pRemainingBitsInSegment,int * pNumDecodedBits)1333 static const SCHAR *DecodePCW_Body(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
1334 const UINT *pCurrentTree,
1335 const SCHAR *pQuantValBase,
1336 INT *pLeftStartOfSegment,
1337 SCHAR *pRemainingBitsInSegment,
1338 int *pNumDecodedBits) {
1339 UCHAR carryBit;
1340 UINT branchNode;
1341 UINT treeNode;
1342 UINT branchValue;
1343 const SCHAR *pQuantVal;
1344
1345 /* decode PCW_BODY */
1346 treeNode = *pCurrentTree; /* get first node of current tree belonging to
1347 current codebook */
1348
1349 /* decode whole PCW-codeword-body */
1350 while (1) {
1351 carryBit = HcrGetABitFromBitstream(bs, bsAnchor, pLeftStartOfSegment,
1352 pLeftStartOfSegment, /* dummy */
1353 FROM_LEFT_TO_RIGHT);
1354 *pRemainingBitsInSegment -= 1;
1355 *pNumDecodedBits += 1;
1356
1357 CarryBitToBranchValue(carryBit, treeNode, &branchValue, &branchNode);
1358
1359 if ((branchNode & TEST_BIT_10) ==
1360 TEST_BIT_10) { /* test bit 10 ; if set --> codeword-body is complete */
1361 break; /* end of branch in tree reached i.e. a whole PCW-Body is decoded
1362 */
1363 } else {
1364 treeNode = *(
1365 pCurrentTree +
1366 branchValue); /* update treeNode for further step in decoding tree */
1367 }
1368 }
1369
1370 pQuantVal =
1371 pQuantValBase + branchValue; /* update pointer to valid first of 2 or 4
1372 quantized values */
1373
1374 return pQuantVal;
1375 }
1376
1377 /*---------------------------------------------------------------------------------------------
1378 description: This function decodes one escape sequence. In case of a
1379 escape codebook and in case of the absolute value of the quantized spectral
1380 value == 16, a escapeSequence is decoded in two steps:
1381 1. escape prefix
1382 2. escape word
1383 --------------------------------------------------------------------------------------------
1384 */
1385
DecodeEscapeSequence(HANDLE_FDK_BITSTREAM bs,const INT bsAnchor,INT quantSpecCoef,INT * pLeftStartOfSegment,SCHAR * pRemainingBitsInSegment,int * pNumDecodedBits,UINT * errorWord)1386 static INT DecodeEscapeSequence(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
1387 INT quantSpecCoef, INT *pLeftStartOfSegment,
1388 SCHAR *pRemainingBitsInSegment,
1389 int *pNumDecodedBits, UINT *errorWord) {
1390 UINT i;
1391 INT sign;
1392 UINT escapeOnesCounter = 0;
1393 UINT carryBit;
1394 INT escape_word = 0;
1395
1396 /* decode escape prefix */
1397 while (1) {
1398 carryBit = HcrGetABitFromBitstream(bs, bsAnchor, pLeftStartOfSegment,
1399 pLeftStartOfSegment, /* dummy */
1400 FROM_LEFT_TO_RIGHT);
1401 *pRemainingBitsInSegment -= 1;
1402 *pNumDecodedBits += 1;
1403 if (*pRemainingBitsInSegment < 0) {
1404 return Q_VALUE_INVALID;
1405 }
1406
1407 if (carryBit != 0) {
1408 escapeOnesCounter += 1;
1409 } else {
1410 escapeOnesCounter += 4;
1411 break;
1412 }
1413 }
1414
1415 /* decode escape word */
1416 for (i = escapeOnesCounter; i != 0; i--) {
1417 carryBit = HcrGetABitFromBitstream(bs, bsAnchor, pLeftStartOfSegment,
1418 pLeftStartOfSegment, /* dummy */
1419 FROM_LEFT_TO_RIGHT);
1420 *pRemainingBitsInSegment -= 1;
1421 *pNumDecodedBits += 1;
1422 if (*pRemainingBitsInSegment < 0) {
1423 return Q_VALUE_INVALID;
1424 }
1425
1426 escape_word <<= 1;
1427 escape_word = escape_word | carryBit;
1428 }
1429
1430 sign = (quantSpecCoef >= 0) ? 1 : -1;
1431
1432 if (escapeOnesCounter < 13) {
1433 quantSpecCoef = sign * (((INT)1 << escapeOnesCounter) + escape_word);
1434 } else {
1435 *errorWord |= TOO_MANY_PCW_BODY_SIGN_ESC_BITS_DECODED;
1436 quantSpecCoef = Q_VALUE_INVALID;
1437 }
1438 return quantSpecCoef;
1439 }
1440
1441 /*---------------------------------------------------------------------------------------------
1442 description: Decodes the Signbits of a priority codeword (PCW) and writes
1443 out the resulting quantized spectral values into unsorted sections
1444 -----------------------------------------------------------------------------------------------
1445 output: - two or four lines at position in corresponding section
1446 (which are not located at the desired position, i.e. they must be reordered in
1447 the last of eight function of HCR)
1448 -----------------------------------------------------------------------------------------------
1449 return: - updated pQuantSpecCoef pointer (to next empty storage for a
1450 line)
1451 --------------------------------------------------------------------------------------------
1452 */
DecodePCW_Sign(HANDLE_FDK_BITSTREAM bs,const INT bsAnchor,UINT codebookDim,const SCHAR * pQuantVal,FIXP_DBL * pQuantSpecCoef,int * quantSpecCoefIdx,INT * pLeftStartOfSegment,SCHAR * pRemainingBitsInSegment,int * pNumDecodedBits)1453 static int DecodePCW_Sign(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
1454 UINT codebookDim, const SCHAR *pQuantVal,
1455 FIXP_DBL *pQuantSpecCoef, int *quantSpecCoefIdx,
1456 INT *pLeftStartOfSegment,
1457 SCHAR *pRemainingBitsInSegment,
1458 int *pNumDecodedBits) {
1459 UINT i;
1460 UINT carryBit;
1461 INT quantSpecCoef;
1462
1463 for (i = codebookDim; i != 0; i--) {
1464 quantSpecCoef = *pQuantVal++;
1465 if (quantSpecCoef != 0) {
1466 carryBit = HcrGetABitFromBitstream(bs, bsAnchor, pLeftStartOfSegment,
1467 pLeftStartOfSegment, /* dummy */
1468 FROM_LEFT_TO_RIGHT);
1469 *pRemainingBitsInSegment -= 1;
1470 *pNumDecodedBits += 1;
1471 if (*pRemainingBitsInSegment < 0 || *pNumDecodedBits >= (1024 >> 1)) {
1472 return -1;
1473 }
1474
1475 /* adapt sign of values according to the decoded sign bit */
1476 if (carryBit != 0) {
1477 pQuantSpecCoef[*quantSpecCoefIdx] = -(FIXP_DBL)quantSpecCoef;
1478 } else {
1479 pQuantSpecCoef[*quantSpecCoefIdx] = (FIXP_DBL)quantSpecCoef;
1480 }
1481 } else {
1482 pQuantSpecCoef[*quantSpecCoefIdx] = FL2FXCONST_DBL(0.0f);
1483 }
1484 *quantSpecCoefIdx += 1;
1485 if (*quantSpecCoefIdx >= 1024) {
1486 return -1;
1487 }
1488 }
1489 return 0;
1490 }
1491
1492 /*---------------------------------------------------------------------------------------------
1493 description: Mutes spectral lines which have been marked as erroneous
1494 (Q_VALUE_INVALID)
1495 --------------------------------------------------------------------------------------------
1496 */
HcrMuteErroneousLines(H_HCR_INFO hHcr)1497 void HcrMuteErroneousLines(H_HCR_INFO hHcr) {
1498 int c;
1499 FIXP_DBL *RESTRICT pLong =
1500 SPEC_LONG(hHcr->decInOut.pQuantizedSpectralCoefficientsBase);
1501
1502 /* if there is a line with value Q_VALUE_INVALID mute it */
1503 for (c = 0; c < 1024; c++) {
1504 if (pLong[c] == (FIXP_DBL)Q_VALUE_INVALID) {
1505 pLong[c] = FL2FXCONST_DBL(0.0f); /* muting */
1506 }
1507 }
1508 }
1509