/src/aac/libAACdec/src/aacdec_hcr.cpp
Line | Count | Source (jump to first uncovered line) |
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 | | */ |
173 | | static void errDetectorInHcrSideinfoShrt(SCHAR cb, SHORT numLine, |
174 | 126k | UINT *errorWord) { |
175 | 126k | if (cb < ZERO_HCB || cb >= MAX_CB_CHECK || cb == BOOKSCL) { |
176 | 0 | *errorWord |= CB_OUT_OF_RANGE_SHORT_BLOCK; |
177 | 0 | } |
178 | 126k | if (numLine < 0 || numLine > 1024) { |
179 | 0 | *errorWord |= LINE_IN_SECT_OUT_OF_RANGE_SHORT_BLOCK; |
180 | 0 | } |
181 | 126k | } |
182 | | |
183 | | /*--------------------------------------------------------------------------------------------- |
184 | | description: Check both HCR lengths |
185 | | -------------------------------------------------------------------------------------------- |
186 | | */ |
187 | | static void errDetectorInHcrLengths(SCHAR lengthOfLongestCodeword, |
188 | | SHORT lengthOfReorderedSpectralData, |
189 | 9.14k | UINT *errorWord) { |
190 | 9.14k | if (lengthOfReorderedSpectralData < lengthOfLongestCodeword) { |
191 | 6 | *errorWord |= HCR_SI_LENGTHS_FAILURE; |
192 | 6 | } |
193 | 9.14k | } |
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 | | |
201 | | void CHcr_Read(HANDLE_FDK_BITSTREAM bs, |
202 | | CAacDecoderChannelInfo *pAacDecoderChannelInfo, |
203 | 9.41k | const MP4_ELEMENT_ID globalHcrType) { |
204 | 9.41k | SHORT lengOfReorderedSpectralData; |
205 | 9.41k | SCHAR lengOfLongestCodeword; |
206 | | |
207 | 9.41k | pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfReorderedSpectralData = |
208 | 9.41k | 0; |
209 | 9.41k | pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfLongestCodeword = 0; |
210 | | |
211 | | /* ------- SI-Value No 1 ------- */ |
212 | 9.41k | lengOfReorderedSpectralData = FDKreadBits(bs, 14) + ERROR_LORSD; |
213 | 9.41k | if (globalHcrType == ID_CPE) { |
214 | 8.04k | if ((lengOfReorderedSpectralData >= 0) && |
215 | 8.04k | (lengOfReorderedSpectralData <= CPE_TOP_LENGTH)) { |
216 | 7.97k | pAacDecoderChannelInfo->pDynData->specificTo.aac |
217 | 7.97k | .lenOfReorderedSpectralData = |
218 | 7.97k | lengOfReorderedSpectralData; /* the decoded value is within range */ |
219 | 7.97k | } else { |
220 | 69 | if (lengOfReorderedSpectralData > CPE_TOP_LENGTH) { |
221 | 69 | pAacDecoderChannelInfo->pDynData->specificTo.aac |
222 | 69 | .lenOfReorderedSpectralData = |
223 | 69 | CPE_TOP_LENGTH; /* use valid maximum */ |
224 | 69 | } |
225 | 69 | } |
226 | 8.04k | } else if (globalHcrType == ID_SCE || globalHcrType == ID_LFE || |
227 | 1.37k | globalHcrType == ID_CCE) { |
228 | 1.37k | if ((lengOfReorderedSpectralData >= 0) && |
229 | 1.37k | (lengOfReorderedSpectralData <= SCE_TOP_LENGTH)) { |
230 | 1.32k | pAacDecoderChannelInfo->pDynData->specificTo.aac |
231 | 1.32k | .lenOfReorderedSpectralData = |
232 | 1.32k | lengOfReorderedSpectralData; /* the decoded value is within range */ |
233 | 1.32k | } else { |
234 | 48 | if (lengOfReorderedSpectralData > SCE_TOP_LENGTH) { |
235 | 48 | pAacDecoderChannelInfo->pDynData->specificTo.aac |
236 | 48 | .lenOfReorderedSpectralData = |
237 | 48 | SCE_TOP_LENGTH; /* use valid maximum */ |
238 | 48 | } |
239 | 48 | } |
240 | 1.37k | } |
241 | | |
242 | | /* ------- SI-Value No 2 ------- */ |
243 | 9.41k | lengOfLongestCodeword = FDKreadBits(bs, 6) + ERROR_LOLC; |
244 | 9.41k | if ((lengOfLongestCodeword >= 0) && |
245 | 9.41k | (lengOfLongestCodeword <= LEN_OF_LONGEST_CW_TOP_LENGTH)) { |
246 | 2.48k | pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfLongestCodeword = |
247 | 2.48k | lengOfLongestCodeword; /* the decoded value is within range */ |
248 | 6.92k | } else { |
249 | 6.92k | if (lengOfLongestCodeword > LEN_OF_LONGEST_CW_TOP_LENGTH) { |
250 | 6.92k | pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfLongestCodeword = |
251 | 6.92k | LEN_OF_LONGEST_CW_TOP_LENGTH; /* use valid maximum */ |
252 | 6.92k | } |
253 | 6.92k | } |
254 | 9.41k | } |
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 | | |
265 | | UINT HcrInit(H_HCR_INFO pHcr, CAacDecoderChannelInfo *pAacDecoderChannelInfo, |
266 | | const SamplingRateInfo *pSamplingRateInfo, |
267 | 9.14k | HANDLE_FDK_BITSTREAM bs) { |
268 | 9.14k | CIcsInfo *pIcsInfo = &pAacDecoderChannelInfo->icsInfo; |
269 | 9.14k | SHORT *pNumLinesInSec; |
270 | 9.14k | UCHAR *pCodeBk; |
271 | 9.14k | SHORT numSection; |
272 | 9.14k | SCHAR cb; |
273 | 9.14k | int numLine; |
274 | 9.14k | int i; |
275 | | |
276 | 9.14k | pHcr->decInOut.lengthOfReorderedSpectralData = |
277 | 9.14k | pAacDecoderChannelInfo->pDynData->specificTo.aac |
278 | 9.14k | .lenOfReorderedSpectralData; |
279 | 9.14k | pHcr->decInOut.lengthOfLongestCodeword = |
280 | 9.14k | pAacDecoderChannelInfo->pDynData->specificTo.aac.lenOfLongestCodeword; |
281 | 9.14k | pHcr->decInOut.pQuantizedSpectralCoefficientsBase = |
282 | 9.14k | pAacDecoderChannelInfo->pSpectralCoefficient; |
283 | 9.14k | pHcr->decInOut.quantizedSpectralCoefficientsIdx = 0; |
284 | 9.14k | pHcr->decInOut.pCodebook = |
285 | 9.14k | pAacDecoderChannelInfo->pDynData->specificTo.aac.aCodeBooks4Hcr; |
286 | 9.14k | pHcr->decInOut.pNumLineInSect = |
287 | 9.14k | pAacDecoderChannelInfo->pDynData->specificTo.aac.aNumLineInSec4Hcr; |
288 | 9.14k | pHcr->decInOut.numSection = |
289 | 9.14k | pAacDecoderChannelInfo->pDynData->specificTo.aac.numberSection; |
290 | 9.14k | pHcr->decInOut.errorLog = 0; |
291 | 9.14k | pHcr->nonPcwSideinfo.pResultBase = |
292 | 9.14k | SPEC_LONG(pAacDecoderChannelInfo->pSpectralCoefficient); |
293 | | |
294 | 9.14k | FDKsyncCache(bs); |
295 | 9.14k | pHcr->decInOut.bitstreamAnchor = (INT)FDKgetValidBits(bs); |
296 | | |
297 | 9.14k | if (!IsLongBlock(&pAacDecoderChannelInfo->icsInfo)) /* short block */ |
298 | 6.38k | { |
299 | 6.38k | SHORT band; |
300 | 6.38k | SHORT maxBand; |
301 | 6.38k | SCHAR group; |
302 | 6.38k | SCHAR winGroupLen; |
303 | 6.38k | SCHAR window; |
304 | 6.38k | SCHAR numUnitInBand; |
305 | 6.38k | SCHAR cntUnitInBand; |
306 | 6.38k | SCHAR groupWin; |
307 | 6.38k | SCHAR cb_prev; |
308 | | |
309 | 6.38k | UCHAR *pCodeBook; |
310 | 6.38k | const SHORT *BandOffsets; |
311 | 6.38k | SCHAR numOfGroups; |
312 | | |
313 | 6.38k | pCodeBook = pAacDecoderChannelInfo->pDynData->aCodeBook; /* in */ |
314 | 6.38k | pNumLinesInSec = pHcr->decInOut.pNumLineInSect; /* out */ |
315 | 6.38k | pCodeBk = pHcr->decInOut.pCodebook; /* out */ |
316 | 6.38k | BandOffsets = |
317 | 6.38k | GetScaleFactorBandOffsets(pIcsInfo, pSamplingRateInfo); /* aux */ |
318 | 6.38k | numOfGroups = GetWindowGroups(pIcsInfo); |
319 | | |
320 | 6.38k | numLine = 0; |
321 | 6.38k | numSection = 0; |
322 | 6.38k | cb = pCodeBook[0]; |
323 | 6.38k | cb_prev = pCodeBook[0]; |
324 | | |
325 | | /* convert HCR-sideinfo into a unitwise manner: When the cb changes, a new |
326 | | * section starts */ |
327 | | |
328 | 6.38k | *pCodeBk++ = cb_prev; |
329 | | |
330 | 6.38k | maxBand = GetScaleFactorBandsTransmitted(&pAacDecoderChannelInfo->icsInfo); |
331 | 38.2k | for (band = 0; band < maxBand; |
332 | 31.8k | band++) { /* from low to high sfbs i.e. from low to high frequencies */ |
333 | 31.8k | numUnitInBand = |
334 | 31.8k | ((BandOffsets[band + 1] - BandOffsets[band]) >> |
335 | 31.8k | FOUR_LOG_DIV_TWO_LOG); /* get the number of units in current sfb */ |
336 | 65.0k | for (cntUnitInBand = numUnitInBand; cntUnitInBand != 0; |
337 | 33.2k | cntUnitInBand--) { /* for every unit in the band */ |
338 | 161k | for (window = 0, group = 0; group < numOfGroups; group++) { |
339 | 128k | winGroupLen = (SCHAR)GetWindowGroupLength( |
340 | 128k | &pAacDecoderChannelInfo->icsInfo, group); |
341 | 394k | for (groupWin = winGroupLen; groupWin != 0; groupWin--, window++) { |
342 | 265k | cb = pCodeBook[group * 16 + band]; |
343 | 265k | if (cb != cb_prev) { |
344 | 119k | errDetectorInHcrSideinfoShrt(cb, numLine, |
345 | 119k | &pHcr->decInOut.errorLog); |
346 | 119k | if (pHcr->decInOut.errorLog != 0) { |
347 | 0 | return (pHcr->decInOut.errorLog); |
348 | 0 | } |
349 | 119k | *pCodeBk++ = cb; |
350 | 119k | *pNumLinesInSec++ = numLine; |
351 | 119k | numSection++; |
352 | | |
353 | 119k | cb_prev = cb; |
354 | 119k | numLine = LINES_PER_UNIT; |
355 | 146k | } else { |
356 | 146k | numLine += LINES_PER_UNIT; |
357 | 146k | } |
358 | 265k | } |
359 | 128k | } |
360 | 33.2k | } |
361 | 31.8k | } |
362 | | |
363 | 6.38k | numSection++; |
364 | | |
365 | 6.38k | errDetectorInHcrSideinfoShrt(cb, numLine, &pHcr->decInOut.errorLog); |
366 | 6.38k | if (numSection <= 0 || numSection > 1024 / 2) { |
367 | 0 | pHcr->decInOut.errorLog |= NUM_SECT_OUT_OF_RANGE_SHORT_BLOCK; |
368 | 0 | } |
369 | 6.38k | errDetectorInHcrLengths(pHcr->decInOut.lengthOfLongestCodeword, |
370 | 6.38k | pHcr->decInOut.lengthOfReorderedSpectralData, |
371 | 6.38k | &pHcr->decInOut.errorLog); |
372 | 6.38k | if (pHcr->decInOut.errorLog != 0) { |
373 | 4 | return (pHcr->decInOut.errorLog); |
374 | 4 | } |
375 | | |
376 | 6.38k | *pCodeBk = cb; |
377 | 6.38k | *pNumLinesInSec = numLine; |
378 | 6.38k | pHcr->decInOut.numSection = numSection; |
379 | | |
380 | 6.38k | } else /* end short block prepare SI */ |
381 | 2.76k | { /* long block */ |
382 | 2.76k | errDetectorInHcrLengths(pHcr->decInOut.lengthOfLongestCodeword, |
383 | 2.76k | pHcr->decInOut.lengthOfReorderedSpectralData, |
384 | 2.76k | &pHcr->decInOut.errorLog); |
385 | 2.76k | numSection = pHcr->decInOut.numSection; |
386 | 2.76k | pNumLinesInSec = pHcr->decInOut.pNumLineInSect; |
387 | 2.76k | pCodeBk = pHcr->decInOut.pCodebook; |
388 | 2.76k | if (numSection <= 0 || numSection > 64) { |
389 | 12 | pHcr->decInOut.errorLog |= NUM_SECT_OUT_OF_RANGE_LONG_BLOCK; |
390 | 12 | numSection = 0; |
391 | 12 | } |
392 | | |
393 | 5.79k | for (i = numSection; i != 0; i--) { |
394 | 3.03k | cb = *pCodeBk++; |
395 | | |
396 | 3.03k | if (cb < ZERO_HCB || cb >= MAX_CB_CHECK || cb == BOOKSCL) { |
397 | 0 | pHcr->decInOut.errorLog |= CB_OUT_OF_RANGE_LONG_BLOCK; |
398 | 0 | } |
399 | | |
400 | 3.03k | numLine = *pNumLinesInSec++; |
401 | | /* FDK_ASSERT(numLine > 0); */ |
402 | | |
403 | 3.03k | if ((numLine <= 0) || (numLine > 1024)) { |
404 | 71 | pHcr->decInOut.errorLog |= LINE_IN_SECT_OUT_OF_RANGE_LONG_BLOCK; |
405 | 71 | } |
406 | 3.03k | } |
407 | 2.76k | if (pHcr->decInOut.errorLog != 0) { |
408 | 21 | return (pHcr->decInOut.errorLog); |
409 | 21 | } |
410 | 2.76k | } |
411 | | |
412 | 9.12k | pCodeBk = pHcr->decInOut.pCodebook; |
413 | 138k | for (i = 0; i < numSection; i++) { |
414 | 129k | if ((*pCodeBk == NOISE_HCB) || (*pCodeBk == INTENSITY_HCB2) || |
415 | 129k | (*pCodeBk == INTENSITY_HCB)) { |
416 | 16.7k | *pCodeBk = 0; |
417 | 16.7k | } |
418 | 129k | pCodeBk++; |
419 | 129k | } |
420 | | |
421 | | /* HCR-sideinfo-input is complete and seems to be valid */ |
422 | | |
423 | 9.12k | return (pHcr->decInOut.errorLog); |
424 | 9.14k | } |
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 | | |
433 | | UINT HcrDecoder(H_HCR_INFO pHcr, CAacDecoderChannelInfo *pAacDecoderChannelInfo, |
434 | | const SamplingRateInfo *pSamplingRateInfo, |
435 | 9.12k | HANDLE_FDK_BITSTREAM bs) { |
436 | 9.12k | int pTmp1, pTmp2, pTmp3, pTmp4; |
437 | 9.12k | int pTmp5; |
438 | | |
439 | 9.12k | INT bitCntOffst; |
440 | 9.12k | INT saveBitCnt = (INT)FDKgetValidBits(bs); /* save bitstream position */ |
441 | | |
442 | 9.12k | HcrCalcNumCodeword(pHcr); |
443 | | |
444 | 9.12k | HcrSortCodebookAndNumCodewordInSection(pHcr); |
445 | | |
446 | 9.12k | HcrPrepareSegmentationGrid(pHcr); |
447 | | |
448 | 9.12k | HcrExtendedSectionInfo(pHcr); |
449 | | |
450 | 9.12k | if ((pHcr->decInOut.errorLog & HCR_FATAL_PCW_ERROR_MASK) != 0) { |
451 | 4 | return (pHcr->decInOut.errorLog); /* sideinfo is massively corrupt, return |
452 | | from HCR without having decoded |
453 | | anything */ |
454 | 4 | } |
455 | | |
456 | 9.12k | DeriveNumberOfExtendedSortedSectionsInSets( |
457 | 9.12k | pHcr->segmentInfo.numSegment, |
458 | 9.12k | pHcr->sectionInfo.pNumExtendedSortedCodewordInSection, |
459 | 9.12k | pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx, |
460 | 9.12k | pHcr->sectionInfo.pNumExtendedSortedSectionsInSets, |
461 | 9.12k | pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx); |
462 | | |
463 | | /* store */ |
464 | 9.12k | pTmp1 = pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx; |
465 | 9.12k | pTmp2 = pHcr->sectionInfo.extendedSortedCodebookIdx; |
466 | 9.12k | pTmp3 = pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx; |
467 | 9.12k | pTmp4 = pHcr->decInOut.quantizedSpectralCoefficientsIdx; |
468 | 9.12k | pTmp5 = pHcr->sectionInfo.maxLenOfCbInExtSrtSecIdx; |
469 | | |
470 | | /* ------- decode meaningful PCWs ------ */ |
471 | 9.12k | DecodePCWs(bs, pHcr); |
472 | | |
473 | 9.12k | if ((pHcr->decInOut.errorLog & HCR_FATAL_PCW_ERROR_MASK) == 0) { |
474 | | /* ------ decode the non-PCWs -------- */ |
475 | 6.12k | DecodeNonPCWs(bs, pHcr); |
476 | 6.12k | } |
477 | | |
478 | 9.12k | errDetectWithinSegmentationFinal(pHcr); |
479 | | |
480 | | /* restore */ |
481 | 9.12k | pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx = pTmp1; |
482 | 9.12k | pHcr->sectionInfo.extendedSortedCodebookIdx = pTmp2; |
483 | 9.12k | pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx = pTmp3; |
484 | 9.12k | pHcr->decInOut.quantizedSpectralCoefficientsIdx = pTmp4; |
485 | 9.12k | pHcr->sectionInfo.maxLenOfCbInExtSrtSecIdx = pTmp5; |
486 | | |
487 | 9.12k | HcrReorderQuantizedSpectralCoefficients(pHcr, pAacDecoderChannelInfo, |
488 | 9.12k | pSamplingRateInfo); |
489 | | |
490 | | /* restore bitstream position */ |
491 | 9.12k | bitCntOffst = (INT)FDKgetValidBits(bs) - saveBitCnt; |
492 | 9.12k | if (bitCntOffst) { |
493 | 8.92k | FDKpushBiDirectional(bs, bitCntOffst); |
494 | 8.92k | } |
495 | | |
496 | 9.12k | return (pHcr->decInOut.errorLog); |
497 | 9.12k | } |
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 | | |
510 | | static void HcrReorderQuantizedSpectralCoefficients( |
511 | | H_HCR_INFO pHcr, CAacDecoderChannelInfo *pAacDecoderChannelInfo, |
512 | 9.12k | const SamplingRateInfo *pSamplingRateInfo) { |
513 | 9.12k | INT qsc; |
514 | 9.12k | UINT abs_qsc; |
515 | 9.12k | UINT i, j; |
516 | 9.12k | USHORT numSpectralValuesInSection; |
517 | 9.12k | FIXP_DBL *pTeVa; |
518 | 9.12k | USHORT lavErrorCnt = 0; |
519 | | |
520 | 9.12k | UINT numSection = pHcr->decInOut.numSection; |
521 | 9.12k | SPECTRAL_PTR pQuantizedSpectralCoefficientsBase = |
522 | 9.12k | pHcr->decInOut.pQuantizedSpectralCoefficientsBase; |
523 | 9.12k | FIXP_DBL *pQuantizedSpectralCoefficients = |
524 | 9.12k | SPEC_LONG(pHcr->decInOut.pQuantizedSpectralCoefficientsBase); |
525 | 9.12k | const UCHAR *pCbDimShift = aDimCbShift; |
526 | 9.12k | const USHORT *pLargestAbsVal = aLargestAbsoluteValue; |
527 | 9.12k | UCHAR *pSortedCodebook = pHcr->sectionInfo.pSortedCodebook; |
528 | 9.12k | USHORT *pNumSortedCodewordInSection = |
529 | 9.12k | pHcr->sectionInfo.pNumSortedCodewordInSection; |
530 | 9.12k | USHORT *pReorderOffset = pHcr->sectionInfo.pReorderOffset; |
531 | 9.12k | FIXP_DBL pTempValues[1024]; |
532 | 9.12k | FIXP_DBL *pBak = pTempValues; |
533 | | |
534 | 9.12k | FDKmemclear(pTempValues, 1024 * sizeof(FIXP_DBL)); |
535 | | |
536 | | /* long and short: check if decoded huffman-values (quantized spectral |
537 | | * coefficients) are within range */ |
538 | 138k | for (i = numSection; i != 0; i--) { |
539 | 128k | numSpectralValuesInSection = *pNumSortedCodewordInSection++ |
540 | 128k | << pCbDimShift[*pSortedCodebook]; |
541 | 128k | pTeVa = &pTempValues[*pReorderOffset++]; |
542 | 1.97M | for (j = numSpectralValuesInSection; j != 0; j--) { |
543 | 1.84M | qsc = *pQuantizedSpectralCoefficients++; |
544 | 1.84M | abs_qsc = fAbs(qsc); |
545 | 1.84M | if (abs_qsc <= pLargestAbsVal[*pSortedCodebook]) { |
546 | 1.83M | *pTeVa++ = (FIXP_DBL)qsc; /* the qsc value is within range */ |
547 | 1.83M | } else { /* line is too high .. */ |
548 | 9.27k | if (abs_qsc == |
549 | 9.27k | Q_VALUE_INVALID) { /* .. because of previous marking --> dont set |
550 | | LAV flag (would be confusing), just copy out |
551 | | the already marked value */ |
552 | 6.13k | *pTeVa++ = (FIXP_DBL)qsc; |
553 | 6.13k | } else { /* .. because a too high value was decoded for this cb --> set |
554 | | LAV flag */ |
555 | 3.14k | *pTeVa++ = (FIXP_DBL)Q_VALUE_INVALID; |
556 | 3.14k | lavErrorCnt += 1; |
557 | 3.14k | } |
558 | 9.27k | } |
559 | 1.84M | } |
560 | 128k | pSortedCodebook++; |
561 | 128k | } |
562 | | |
563 | 9.12k | if (!IsLongBlock(&pAacDecoderChannelInfo->icsInfo)) { |
564 | 6.38k | FIXP_DBL *pOut; |
565 | 6.38k | FIXP_DBL locMax; |
566 | 6.38k | FIXP_DBL tmp; |
567 | 6.38k | SCHAR groupoffset; |
568 | 6.38k | SCHAR group; |
569 | 6.38k | SCHAR band; |
570 | 6.38k | SCHAR groupwin; |
571 | 6.38k | SCHAR window; |
572 | 6.38k | SCHAR numWinGroup; |
573 | 6.38k | SHORT interm; |
574 | 6.38k | SCHAR numSfbTransm; |
575 | 6.38k | SCHAR winGroupLen; |
576 | 6.38k | SHORT index; |
577 | 6.38k | INT msb; |
578 | 6.38k | INT lsb; |
579 | | |
580 | 6.38k | SHORT *pScaleFacHcr = pAacDecoderChannelInfo->pDynData->aScaleFactor; |
581 | 6.38k | SHORT *pSfbSclHcr = pAacDecoderChannelInfo->pDynData->aSfbScale; |
582 | 6.38k | const SHORT *BandOffsets = GetScaleFactorBandOffsets( |
583 | 6.38k | &pAacDecoderChannelInfo->icsInfo, pSamplingRateInfo); |
584 | | |
585 | 6.38k | pBak = pTempValues; |
586 | | /* deinterleave unitwise for short blocks */ |
587 | 57.4k | for (window = 0; window < (8); window++) { |
588 | 51.0k | pOut = SPEC(pQuantizedSpectralCoefficientsBase, window, |
589 | 51.0k | pAacDecoderChannelInfo->granuleLength); |
590 | 1.68M | for (i = 0; i < (LINES_PER_UNIT_GROUP); i++) { |
591 | 1.63M | pTeVa = pBak + (window << FOUR_LOG_DIV_TWO_LOG) + |
592 | 1.63M | i * 32; /* distance of lines between unit groups has to be |
593 | | constant for every framelength (32)! */ |
594 | 8.16M | for (j = (LINES_PER_UNIT); j != 0; j--) { |
595 | 6.53M | *pOut++ = *pTeVa++; |
596 | 6.53M | } |
597 | 1.63M | } |
598 | 51.0k | } |
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 | 6.38k | groupoffset = 0; |
604 | | |
605 | 6.38k | numWinGroup = GetWindowGroups(&pAacDecoderChannelInfo->icsInfo); |
606 | 6.38k | numSfbTransm = |
607 | 6.38k | GetScaleFactorBandsTransmitted(&pAacDecoderChannelInfo->icsInfo); |
608 | | |
609 | 31.9k | for (group = 0; group < numWinGroup; group++) { |
610 | 25.5k | winGroupLen = |
611 | 25.5k | GetWindowGroupLength(&pAacDecoderChannelInfo->icsInfo, group); |
612 | 150k | for (band = 0; band < numSfbTransm; band++) { |
613 | 125k | interm = group * 16 + band; |
614 | 125k | msb = pScaleFacHcr[interm] >> 2; |
615 | 125k | lsb = pScaleFacHcr[interm] & 3; |
616 | 379k | for (groupwin = 0; groupwin < winGroupLen; groupwin++) { |
617 | 254k | window = groupoffset + groupwin; |
618 | 254k | pBak = SPEC(pQuantizedSpectralCoefficientsBase, window, |
619 | 254k | pAacDecoderChannelInfo->granuleLength); |
620 | 254k | locMax = FL2FXCONST_DBL(0.0f); |
621 | 519k | for (index = BandOffsets[band]; index < BandOffsets[band + 1]; |
622 | 265k | index += LINES_PER_UNIT) { |
623 | 265k | pTeVa = &pBak[index]; |
624 | 1.32M | for (i = LINES_PER_UNIT; i != 0; i--) { |
625 | 1.06M | tmp = (*pTeVa < FL2FXCONST_DBL(0.0f)) ? -*pTeVa++ : *pTeVa++; |
626 | 1.06M | locMax = fixMax(tmp, locMax); |
627 | 1.06M | } |
628 | 265k | } |
629 | 254k | if (fixp_abs(locMax) > (FIXP_DBL)MAX_QUANTIZED_VALUE) { |
630 | 5.43k | locMax = (FIXP_DBL)MAX_QUANTIZED_VALUE; |
631 | 5.43k | } |
632 | 254k | pSfbSclHcr[window * 16 + band] = |
633 | 254k | msb - GetScaleFromValue( |
634 | 254k | locMax, lsb); /* save global scale maxima in this sfb */ |
635 | 254k | } |
636 | 125k | } |
637 | 25.5k | groupoffset += |
638 | 25.5k | GetWindowGroupLength(&pAacDecoderChannelInfo->icsInfo, group); |
639 | 25.5k | } |
640 | 6.38k | } else { |
641 | | /* copy straight for long-blocks */ |
642 | 2.73k | pQuantizedSpectralCoefficients = |
643 | 2.73k | SPEC_LONG(pQuantizedSpectralCoefficientsBase); |
644 | 2.80M | for (i = 1024; i != 0; i--) { |
645 | 2.80M | *pQuantizedSpectralCoefficients++ = *pBak++; |
646 | 2.80M | } |
647 | 2.73k | } |
648 | | |
649 | 9.12k | if (lavErrorCnt != 0) { |
650 | 2.37k | pHcr->decInOut.errorLog |= LAV_VIOLATION; |
651 | 2.37k | } |
652 | 9.12k | } |
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 | | |
669 | 9.12k | static void HcrCalcNumCodeword(H_HCR_INFO pHcr) { |
670 | 9.12k | int hcrSection; |
671 | 9.12k | UINT numCodeword; |
672 | | |
673 | 9.12k | UINT numSection = pHcr->decInOut.numSection; |
674 | 9.12k | UCHAR *pCodebook = pHcr->decInOut.pCodebook; |
675 | 9.12k | SHORT *pNumLineInSection = pHcr->decInOut.pNumLineInSect; |
676 | 9.12k | const UCHAR *pCbDimShift = aDimCbShift; |
677 | | |
678 | 9.12k | USHORT *pNumCodewordInSection = pHcr->sectionInfo.pNumCodewordInSection; |
679 | | |
680 | 9.12k | numCodeword = 0; |
681 | 138k | for (hcrSection = numSection; hcrSection != 0; hcrSection--) { |
682 | 129k | *pNumCodewordInSection = *pNumLineInSection++ >> pCbDimShift[*pCodebook]; |
683 | 129k | if (*pCodebook != 0) { |
684 | 93.9k | numCodeword += *pNumCodewordInSection; |
685 | 93.9k | } |
686 | 129k | pNumCodewordInSection++; |
687 | 129k | pCodebook++; |
688 | 129k | } |
689 | 9.12k | pHcr->sectionInfo.numCodeword = numCodeword; |
690 | 9.12k | } |
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 | | |
699 | 9.12k | static void HcrSortCodebookAndNumCodewordInSection(H_HCR_INFO pHcr) { |
700 | 9.12k | UINT i, j, k; |
701 | 9.12k | UCHAR temp; |
702 | 9.12k | UINT counter; |
703 | 9.12k | UINT startOffset; |
704 | 9.12k | UINT numZeroSection; |
705 | 9.12k | UCHAR *pDest; |
706 | 9.12k | UINT numSectionDec; |
707 | | |
708 | 9.12k | UINT numSection = pHcr->decInOut.numSection; |
709 | 9.12k | UCHAR *pCodebook = pHcr->decInOut.pCodebook; |
710 | 9.12k | UCHAR *pSortedCodebook = pHcr->sectionInfo.pSortedCodebook; |
711 | 9.12k | USHORT *pNumCodewordInSection = pHcr->sectionInfo.pNumCodewordInSection; |
712 | 9.12k | USHORT *pNumSortedCodewordInSection = |
713 | 9.12k | pHcr->sectionInfo.pNumSortedCodewordInSection; |
714 | 9.12k | UCHAR *pCodebookSwitch = pHcr->sectionInfo.pCodebookSwitch; |
715 | 9.12k | USHORT *pReorderOffset = pHcr->sectionInfo.pReorderOffset; |
716 | 9.12k | const UCHAR *pCbPriority = aCbPriority; |
717 | 9.12k | const UCHAR *pMinOfCbPair = aMinOfCbPair; |
718 | 9.12k | const UCHAR *pMaxOfCbPair = aMaxOfCbPair; |
719 | 9.12k | const UCHAR *pCbDimShift = aDimCbShift; |
720 | | |
721 | 9.12k | UINT searchStart = 0; |
722 | | |
723 | | /* calculate *pNumSortedSection and store the priorities in array |
724 | | * pSortedCdebook */ |
725 | 9.12k | pDest = pSortedCodebook; |
726 | 9.12k | numZeroSection = 0; |
727 | 138k | for (i = numSection; i != 0; i--) { |
728 | 129k | if (pCbPriority[*pCodebook] == 0) { |
729 | 35.1k | numZeroSection += 1; |
730 | 35.1k | } |
731 | 129k | *pDest++ = pCbPriority[*pCodebook++]; |
732 | 129k | } |
733 | 9.12k | pHcr->sectionInfo.numSortedSection = |
734 | 9.12k | numSection - numZeroSection; /* numSortedSection contains no zero or |
735 | | intensity section */ |
736 | 9.12k | pCodebook = pHcr->decInOut.pCodebook; |
737 | | |
738 | | /* sort priorities of the codebooks in array pSortedCdebook[] */ |
739 | 9.12k | numSectionDec = numSection - 1; |
740 | 9.12k | if (numSectionDec > 0) { |
741 | 6.33k | counter = numSectionDec; |
742 | 126k | for (j = numSectionDec; j != 0; j--) { |
743 | 1.43M | for (i = 0; i < counter; i++) { |
744 | | /* swap priorities */ |
745 | 1.31M | if (pSortedCodebook[i + 1] > pSortedCodebook[i]) { |
746 | 535k | temp = pSortedCodebook[i]; |
747 | 535k | pSortedCodebook[i] = pSortedCodebook[i + 1]; |
748 | 535k | pSortedCodebook[i + 1] = temp; |
749 | 535k | } |
750 | 1.31M | } |
751 | 119k | counter -= 1; |
752 | 119k | } |
753 | 6.33k | } |
754 | | |
755 | | /* clear codebookSwitch array */ |
756 | 138k | for (i = numSection; i != 0; i--) { |
757 | 129k | *pCodebookSwitch++ = 0; |
758 | 129k | } |
759 | 9.12k | pCodebookSwitch = pHcr->sectionInfo.pCodebookSwitch; |
760 | | |
761 | | /* sort sectionCodebooks and numCodwordsInSection and calculate |
762 | | * pReorderOffst[j] */ |
763 | 138k | for (j = 0; j < numSection; j++) { |
764 | 1.09M | for (i = searchStart; i < numSection; i++) { |
765 | 1.09M | if (pCodebookSwitch[i] == 0 && |
766 | 1.09M | (pMinOfCbPair[pSortedCodebook[j]] == pCodebook[i] || |
767 | 664k | pMaxOfCbPair[pSortedCodebook[j]] == pCodebook[i])) { |
768 | 129k | pCodebookSwitch[i] = 1; |
769 | 129k | pSortedCodebook[j] = pCodebook[i]; /* sort codebook */ |
770 | 129k | pNumSortedCodewordInSection[j] = |
771 | 129k | pNumCodewordInSection[i]; /* sort NumCodewordInSection */ |
772 | | |
773 | 129k | startOffset = 0; |
774 | 1.44M | for (k = 0; k < i; k++) { /* make entry in pReorderOffst */ |
775 | 1.31M | startOffset += pNumCodewordInSection[k] << pCbDimShift[pCodebook[k]]; |
776 | 1.31M | } |
777 | 129k | pReorderOffset[j] = |
778 | 129k | startOffset; /* offset for reordering the codewords */ |
779 | | |
780 | 129k | if (i == searchStart) { |
781 | 41.6k | k = i; |
782 | 171k | while (pCodebookSwitch[k++] == 1) searchStart++; |
783 | 41.6k | } |
784 | 129k | break; |
785 | 129k | } |
786 | 1.09M | } |
787 | 129k | } |
788 | 9.12k | } |
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 | | |
799 | 9.12k | static void HcrPrepareSegmentationGrid(H_HCR_INFO pHcr) { |
800 | 9.12k | USHORT i, j; |
801 | 9.12k | USHORT numSegment = 0; |
802 | 9.12k | INT segmentStart = 0; |
803 | 9.12k | UCHAR segmentWidth; |
804 | 9.12k | UCHAR lastSegmentWidth; |
805 | 9.12k | UCHAR sortedCodebook; |
806 | 9.12k | UCHAR endFlag = 0; |
807 | 9.12k | INT intermediateResult; |
808 | | |
809 | 9.12k | SCHAR lengthOfLongestCodeword = pHcr->decInOut.lengthOfLongestCodeword; |
810 | 9.12k | SHORT lengthOfReorderedSpectralData = |
811 | 9.12k | pHcr->decInOut.lengthOfReorderedSpectralData; |
812 | 9.12k | UINT numSortedSection = pHcr->sectionInfo.numSortedSection; |
813 | 9.12k | UCHAR *pSortedCodebook = pHcr->sectionInfo.pSortedCodebook; |
814 | 9.12k | USHORT *pNumSortedCodewordInSection = |
815 | 9.12k | pHcr->sectionInfo.pNumSortedCodewordInSection; |
816 | 9.12k | INT *pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment; |
817 | 9.12k | INT *pRightStartOfSegment = pHcr->segmentInfo.pRightStartOfSegment; |
818 | 9.12k | SCHAR *pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment; |
819 | 9.12k | const UCHAR *pMaxCwLength = aMaxCwLen; |
820 | | |
821 | 38.2k | for (i = numSortedSection; i != 0; i--) { |
822 | 37.1k | sortedCodebook = *pSortedCodebook++; |
823 | 37.1k | segmentWidth = |
824 | 37.1k | fMin((INT)pMaxCwLength[sortedCodebook], (INT)lengthOfLongestCodeword); |
825 | | |
826 | 320k | for (j = *pNumSortedCodewordInSection; j != 0; j--) { |
827 | | /* width allows a new segment */ |
828 | 291k | intermediateResult = segmentStart; |
829 | 291k | if ((segmentStart + segmentWidth) <= lengthOfReorderedSpectralData) { |
830 | | /* store segment start, segment length and increment the number of |
831 | | * segments */ |
832 | 283k | *pLeftStartOfSegment++ = intermediateResult; |
833 | 283k | *pRightStartOfSegment++ = intermediateResult + segmentWidth - 1; |
834 | 283k | *pRemainingBitsInSegment++ = segmentWidth; |
835 | 283k | segmentStart += segmentWidth; |
836 | 283k | numSegment += 1; |
837 | 283k | } |
838 | | /* width does not allow a new segment */ |
839 | 7.96k | else { |
840 | | /* correct the last segment length */ |
841 | 7.96k | pLeftStartOfSegment--; |
842 | 7.96k | pRightStartOfSegment--; |
843 | 7.96k | pRemainingBitsInSegment--; |
844 | 7.96k | segmentStart = *pLeftStartOfSegment; |
845 | | |
846 | 7.96k | lastSegmentWidth = lengthOfReorderedSpectralData - segmentStart; |
847 | 7.96k | *pRemainingBitsInSegment = lastSegmentWidth; |
848 | 7.96k | *pRightStartOfSegment = segmentStart + lastSegmentWidth - 1; |
849 | 7.96k | endFlag = 1; |
850 | 7.96k | break; |
851 | 7.96k | } |
852 | 291k | } |
853 | 37.1k | pNumSortedCodewordInSection++; |
854 | 37.1k | if (endFlag != 0) { |
855 | 7.96k | break; |
856 | 7.96k | } |
857 | 37.1k | } |
858 | 9.12k | pHcr->segmentInfo.numSegment = numSegment; |
859 | 9.12k | } |
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 | | |
872 | 9.12k | static void HcrExtendedSectionInfo(H_HCR_INFO pHcr) { |
873 | 9.12k | UINT srtSecCnt = 0; /* counter for sorted sections */ |
874 | 9.12k | UINT xSrtScCnt = 0; /* counter for extended sorted sections */ |
875 | 9.12k | UINT remainNumCwInSortSec; |
876 | 9.12k | UINT inSegmentRemainNumCW; |
877 | | |
878 | 9.12k | UINT numSortedSection = pHcr->sectionInfo.numSortedSection; |
879 | 9.12k | UCHAR *pSortedCodebook = pHcr->sectionInfo.pSortedCodebook; |
880 | 9.12k | USHORT *pNumSortedCodewordInSection = |
881 | 9.12k | pHcr->sectionInfo.pNumSortedCodewordInSection; |
882 | 9.12k | UCHAR *pExtendedSortedCoBo = pHcr->sectionInfo.pExtendedSortedCodebook; |
883 | 9.12k | USHORT *pNumExtSortCwInSect = |
884 | 9.12k | pHcr->sectionInfo.pNumExtendedSortedCodewordInSection; |
885 | 9.12k | UINT numSegment = pHcr->segmentInfo.numSegment; |
886 | 9.12k | UCHAR *pMaxLenOfCbInExtSrtSec = pHcr->sectionInfo.pMaxLenOfCbInExtSrtSec; |
887 | 9.12k | SCHAR lengthOfLongestCodeword = pHcr->decInOut.lengthOfLongestCodeword; |
888 | 9.12k | const UCHAR *pMaxCwLength = aMaxCwLen; |
889 | | |
890 | 9.12k | remainNumCwInSortSec = pNumSortedCodewordInSection[srtSecCnt]; |
891 | 9.12k | inSegmentRemainNumCW = numSegment; |
892 | | |
893 | 133k | while (srtSecCnt < numSortedSection) { |
894 | 124k | if (inSegmentRemainNumCW < remainNumCwInSortSec) { |
895 | 30.2k | pNumExtSortCwInSect[xSrtScCnt] = inSegmentRemainNumCW; |
896 | 30.2k | pExtendedSortedCoBo[xSrtScCnt] = pSortedCodebook[srtSecCnt]; |
897 | | |
898 | 30.2k | remainNumCwInSortSec -= inSegmentRemainNumCW; |
899 | 30.2k | inSegmentRemainNumCW = numSegment; |
900 | | /* data of a sorted section was not integrated in extended sorted section |
901 | | */ |
902 | 93.9k | } else if (inSegmentRemainNumCW == remainNumCwInSortSec) { |
903 | 7.43k | pNumExtSortCwInSect[xSrtScCnt] = inSegmentRemainNumCW; |
904 | 7.43k | pExtendedSortedCoBo[xSrtScCnt] = pSortedCodebook[srtSecCnt]; |
905 | | |
906 | 7.43k | srtSecCnt++; |
907 | 7.43k | remainNumCwInSortSec = pNumSortedCodewordInSection[srtSecCnt]; |
908 | 7.43k | inSegmentRemainNumCW = numSegment; |
909 | | /* data of a sorted section was integrated in extended sorted section */ |
910 | 86.5k | } else { /* inSegmentRemainNumCW > remainNumCwInSortSec */ |
911 | 86.5k | pNumExtSortCwInSect[xSrtScCnt] = remainNumCwInSortSec; |
912 | 86.5k | pExtendedSortedCoBo[xSrtScCnt] = pSortedCodebook[srtSecCnt]; |
913 | | |
914 | 86.5k | inSegmentRemainNumCW -= remainNumCwInSortSec; |
915 | 86.5k | srtSecCnt++; |
916 | 86.5k | remainNumCwInSortSec = pNumSortedCodewordInSection[srtSecCnt]; |
917 | | /* data of a sorted section was integrated in extended sorted section */ |
918 | 86.5k | } |
919 | 124k | pMaxLenOfCbInExtSrtSec[xSrtScCnt] = |
920 | 124k | fMin((INT)pMaxCwLength[pExtendedSortedCoBo[xSrtScCnt]], |
921 | 124k | (INT)lengthOfLongestCodeword); |
922 | | |
923 | 124k | xSrtScCnt += 1; |
924 | | |
925 | 124k | if (xSrtScCnt >= (MAX_SFB_HCR + MAX_HCR_SETS)) { |
926 | 4 | pHcr->decInOut.errorLog |= EXTENDED_SORTED_COUNTER_OVERFLOW; |
927 | 4 | return; |
928 | 4 | } |
929 | 124k | } |
930 | 9.12k | pNumExtSortCwInSect[xSrtScCnt] = 0; |
931 | 9.12k | } |
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 | | */ |
946 | | static void DeriveNumberOfExtendedSortedSectionsInSets( |
947 | | UINT numSegment, USHORT *pNumExtendedSortedCodewordInSection, |
948 | | int numExtendedSortedCodewordInSectionIdx, |
949 | | USHORT *pNumExtendedSortedSectionsInSets, |
950 | 9.12k | int numExtendedSortedSectionsInSetsIdx) { |
951 | 9.12k | USHORT counter = 0; |
952 | 9.12k | UINT cwSum = 0; |
953 | 9.12k | USHORT *pNumExSortCwInSec = pNumExtendedSortedCodewordInSection; |
954 | 9.12k | USHORT *pNumExSortSecInSets = pNumExtendedSortedSectionsInSets; |
955 | | |
956 | 128k | while (pNumExSortCwInSec[numExtendedSortedCodewordInSectionIdx] != 0) { |
957 | 119k | cwSum += pNumExSortCwInSec[numExtendedSortedCodewordInSectionIdx]; |
958 | 119k | numExtendedSortedCodewordInSectionIdx++; |
959 | 119k | if (numExtendedSortedCodewordInSectionIdx >= (MAX_SFB_HCR + MAX_HCR_SETS)) { |
960 | 0 | return; |
961 | 0 | } |
962 | 119k | if (cwSum > numSegment) { |
963 | 0 | return; |
964 | 0 | } |
965 | 119k | counter++; |
966 | 119k | if (counter > 1024 / 4) { |
967 | 0 | return; |
968 | 0 | } |
969 | 119k | if (cwSum == numSegment) { |
970 | 33.6k | pNumExSortSecInSets[numExtendedSortedSectionsInSetsIdx] = counter; |
971 | 33.6k | numExtendedSortedSectionsInSetsIdx++; |
972 | 33.6k | if (numExtendedSortedSectionsInSetsIdx >= MAX_HCR_SETS) { |
973 | 589 | return; |
974 | 589 | } |
975 | 33.0k | counter = 0; |
976 | 33.0k | cwSum = 0; |
977 | 33.0k | } |
978 | 119k | } |
979 | 8.53k | pNumExSortSecInSets[numExtendedSortedSectionsInSetsIdx] = |
980 | 8.53k | counter; /* save last entry for the last - probably shorter - set */ |
981 | 8.53k | } |
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 | | */ |
997 | 9.12k | static void DecodePCWs(HANDLE_FDK_BITSTREAM bs, H_HCR_INFO pHcr) { |
998 | 9.12k | UINT i; |
999 | 9.12k | USHORT extSortSec; |
1000 | 9.12k | USHORT curExtSortCwInSec; |
1001 | 9.12k | UCHAR codebook; |
1002 | 9.12k | UCHAR dimension; |
1003 | 9.12k | const UINT *pCurrentTree; |
1004 | 9.12k | const SCHAR *pQuantValBase; |
1005 | 9.12k | const SCHAR *pQuantVal; |
1006 | | |
1007 | 9.12k | USHORT *pNumExtendedSortedCodewordInSection = |
1008 | 9.12k | pHcr->sectionInfo.pNumExtendedSortedCodewordInSection; |
1009 | 9.12k | int numExtendedSortedCodewordInSectionIdx = |
1010 | 9.12k | pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx; |
1011 | 9.12k | UCHAR *pExtendedSortedCodebook = pHcr->sectionInfo.pExtendedSortedCodebook; |
1012 | 9.12k | int extendedSortedCodebookIdx = pHcr->sectionInfo.extendedSortedCodebookIdx; |
1013 | 9.12k | USHORT *pNumExtendedSortedSectionsInSets = |
1014 | 9.12k | pHcr->sectionInfo.pNumExtendedSortedSectionsInSets; |
1015 | 9.12k | int numExtendedSortedSectionsInSetsIdx = |
1016 | 9.12k | pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx; |
1017 | 9.12k | FIXP_DBL *pQuantizedSpectralCoefficients = |
1018 | 9.12k | SPEC_LONG(pHcr->decInOut.pQuantizedSpectralCoefficientsBase); |
1019 | 9.12k | int quantizedSpectralCoefficientsIdx = |
1020 | 9.12k | pHcr->decInOut.quantizedSpectralCoefficientsIdx; |
1021 | 9.12k | INT *pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment; |
1022 | 9.12k | SCHAR *pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment; |
1023 | 9.12k | UCHAR *pMaxLenOfCbInExtSrtSec = pHcr->sectionInfo.pMaxLenOfCbInExtSrtSec; |
1024 | 9.12k | int maxLenOfCbInExtSrtSecIdx = pHcr->sectionInfo.maxLenOfCbInExtSrtSecIdx; |
1025 | 9.12k | UCHAR maxAllowedCwLen; |
1026 | 9.12k | int numDecodedBits; |
1027 | 9.12k | const UCHAR *pCbDimension = aDimCb; |
1028 | 9.12k | const UCHAR *pCbSign = aSignCb; |
1029 | | |
1030 | | /* clear result array */ |
1031 | 9.12k | FDKmemclear(pQuantizedSpectralCoefficients + quantizedSpectralCoefficientsIdx, |
1032 | 9.12k | 1024 * sizeof(FIXP_DBL)); |
1033 | | |
1034 | | /* decode all PCWs in the extended sorted section(s) belonging to set 0 */ |
1035 | 9.12k | for (extSortSec = |
1036 | 9.12k | pNumExtendedSortedSectionsInSets[numExtendedSortedSectionsInSetsIdx]; |
1037 | 25.3k | extSortSec != 0; extSortSec--) { |
1038 | 20.3k | codebook = |
1039 | 20.3k | 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 | 20.3k | extendedSortedCodebookIdx++; |
1046 | 20.3k | if (extendedSortedCodebookIdx >= (MAX_SFB_HCR + MAX_HCR_SETS)) { |
1047 | 0 | return; |
1048 | 0 | } |
1049 | 20.3k | dimension = pCbDimension[codebook]; /* get dimension of codebook of this |
1050 | | extended sort. sec. */ |
1051 | 20.3k | pCurrentTree = |
1052 | 20.3k | aHuffTable[codebook]; /* convert codebook to pointer to QSCs */ |
1053 | 20.3k | pQuantValBase = |
1054 | 20.3k | aQuantTable[codebook]; /* convert codebook to index to table of QSCs */ |
1055 | 20.3k | maxAllowedCwLen = pMaxLenOfCbInExtSrtSec[maxLenOfCbInExtSrtSecIdx]; |
1056 | 20.3k | maxLenOfCbInExtSrtSecIdx++; |
1057 | 20.3k | if (maxLenOfCbInExtSrtSecIdx >= (MAX_SFB_HCR + MAX_HCR_SETS)) { |
1058 | 0 | return; |
1059 | 0 | } |
1060 | | |
1061 | | /* switch for decoding with different codebooks: */ |
1062 | 20.3k | if (pCbSign[codebook] == |
1063 | 20.3k | 0) { /* no sign bits follow after the codeword-body */ |
1064 | | /* PCW_BodyONLY */ |
1065 | | /*==============*/ |
1066 | | |
1067 | 672 | for (curExtSortCwInSec = pNumExtendedSortedCodewordInSection |
1068 | 672 | [numExtendedSortedCodewordInSectionIdx]; |
1069 | 7.19k | curExtSortCwInSec != 0; curExtSortCwInSec--) { |
1070 | 6.59k | numDecodedBits = 0; |
1071 | | |
1072 | | /* decode PCW_BODY */ |
1073 | 6.59k | pQuantVal = DecodePCW_Body( |
1074 | 6.59k | bs, pHcr->decInOut.bitstreamAnchor, pCurrentTree, pQuantValBase, |
1075 | 6.59k | pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits); |
1076 | | |
1077 | | /* result is written out here because NO sign bits follow the body */ |
1078 | 22.8k | for (i = dimension; i != 0; i--) { |
1079 | 16.2k | pQuantizedSpectralCoefficients[quantizedSpectralCoefficientsIdx] = |
1080 | 16.2k | (FIXP_DBL)*pQuantVal++; /* write quant. spec. coef. into |
1081 | | spectrum; sign is already valid */ |
1082 | 16.2k | quantizedSpectralCoefficientsIdx++; |
1083 | 16.2k | if (quantizedSpectralCoefficientsIdx >= 1024) { |
1084 | 5 | return; |
1085 | 5 | } |
1086 | 16.2k | } |
1087 | | |
1088 | | /* one more PCW should be decoded */ |
1089 | | |
1090 | 6.59k | if (maxAllowedCwLen < (numDecodedBits + ERROR_PCW_BODY_ONLY_TOO_LONG)) { |
1091 | 66 | pHcr->decInOut.errorLog |= TOO_MANY_PCW_BODY_BITS_DECODED; |
1092 | 66 | } |
1093 | | |
1094 | 6.59k | if (1 == errDetectPcwSegmentation( |
1095 | 6.59k | *pRemainingBitsInSegment - ERROR_PCW_BODY, pHcr, PCW_BODY, |
1096 | 6.59k | pQuantizedSpectralCoefficients + |
1097 | 6.59k | quantizedSpectralCoefficientsIdx - dimension, |
1098 | 6.59k | dimension)) { |
1099 | 66 | return; |
1100 | 66 | } |
1101 | 6.52k | pLeftStartOfSegment++; /* update pointer for decoding the next PCW */ |
1102 | 6.52k | pRemainingBitsInSegment++; /* update pointer for decoding the next PCW |
1103 | | */ |
1104 | 6.52k | } |
1105 | 19.6k | } else if ((codebook < 11) && (pCbSign[codebook] == |
1106 | 3.90k | 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 | 3.90k | for (curExtSortCwInSec = pNumExtendedSortedCodewordInSection |
1112 | 3.90k | [numExtendedSortedCodewordInSectionIdx]; |
1113 | 70.0k | curExtSortCwInSec != 0; curExtSortCwInSec--) { |
1114 | 66.3k | int err; |
1115 | 66.3k | numDecodedBits = 0; |
1116 | | |
1117 | 66.3k | pQuantVal = DecodePCW_Body( |
1118 | 66.3k | bs, pHcr->decInOut.bitstreamAnchor, pCurrentTree, pQuantValBase, |
1119 | 66.3k | pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits); |
1120 | | |
1121 | 66.3k | err = DecodePCW_Sign( |
1122 | 66.3k | bs, pHcr->decInOut.bitstreamAnchor, dimension, pQuantVal, |
1123 | 66.3k | pQuantizedSpectralCoefficients, &quantizedSpectralCoefficientsIdx, |
1124 | 66.3k | pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits); |
1125 | 66.3k | if (err != 0) { |
1126 | 148 | return; |
1127 | 148 | } |
1128 | | /* one more PCW should be decoded */ |
1129 | | |
1130 | 66.1k | if (maxAllowedCwLen < (numDecodedBits + ERROR_PCW_BODY_SIGN_TOO_LONG)) { |
1131 | 20 | pHcr->decInOut.errorLog |= TOO_MANY_PCW_BODY_SIGN_BITS_DECODED; |
1132 | 20 | } |
1133 | | |
1134 | 66.1k | if (1 == errDetectPcwSegmentation( |
1135 | 66.1k | *pRemainingBitsInSegment - ERROR_PCW_BODY_SIGN, pHcr, |
1136 | 66.1k | PCW_BODY_SIGN, |
1137 | 66.1k | pQuantizedSpectralCoefficients + |
1138 | 66.1k | quantizedSpectralCoefficientsIdx - dimension, |
1139 | 66.1k | dimension)) { |
1140 | 20 | return; |
1141 | 20 | } |
1142 | 66.1k | pLeftStartOfSegment++; |
1143 | 66.1k | pRemainingBitsInSegment++; |
1144 | 66.1k | } |
1145 | 15.7k | } else if ((pCbSign[codebook] == 1) && |
1146 | 15.7k | (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 | 15.7k | for (curExtSortCwInSec = pNumExtendedSortedCodewordInSection |
1153 | 15.7k | [numExtendedSortedCodewordInSectionIdx]; |
1154 | 78.1k | curExtSortCwInSec != 0; curExtSortCwInSec--) { |
1155 | 66.2k | int err; |
1156 | 66.2k | numDecodedBits = 0; |
1157 | | |
1158 | | /* decode PCW_BODY */ |
1159 | 66.2k | pQuantVal = DecodePCW_Body( |
1160 | 66.2k | bs, pHcr->decInOut.bitstreamAnchor, pCurrentTree, pQuantValBase, |
1161 | 66.2k | pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits); |
1162 | | |
1163 | 66.2k | err = DecodePCW_Sign( |
1164 | 66.2k | bs, pHcr->decInOut.bitstreamAnchor, dimension, pQuantVal, |
1165 | 66.2k | pQuantizedSpectralCoefficients, &quantizedSpectralCoefficientsIdx, |
1166 | 66.2k | pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits); |
1167 | 66.2k | if (err != 0) { |
1168 | 983 | return; |
1169 | 983 | } |
1170 | | |
1171 | | /* decode PCW_ESCAPE if present */ |
1172 | 65.3k | quantizedSpectralCoefficientsIdx -= DIMENSION_OF_ESCAPE_CODEBOOK; |
1173 | | |
1174 | 65.3k | if (fixp_abs(pQuantizedSpectralCoefficients |
1175 | 65.3k | [quantizedSpectralCoefficientsIdx]) == |
1176 | 65.3k | (FIXP_DBL)ESCAPE_VALUE) { |
1177 | 960 | pQuantizedSpectralCoefficients[quantizedSpectralCoefficientsIdx] = |
1178 | 960 | (FIXP_DBL)DecodeEscapeSequence( |
1179 | 960 | bs, pHcr->decInOut.bitstreamAnchor, |
1180 | 960 | pQuantizedSpectralCoefficients |
1181 | 960 | [quantizedSpectralCoefficientsIdx], |
1182 | 960 | pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits, |
1183 | 960 | &pHcr->decInOut.errorLog); |
1184 | 960 | } |
1185 | 65.3k | quantizedSpectralCoefficientsIdx++; |
1186 | 65.3k | if (quantizedSpectralCoefficientsIdx >= 1024) { |
1187 | 0 | return; |
1188 | 0 | } |
1189 | | |
1190 | 65.3k | if (fixp_abs(pQuantizedSpectralCoefficients |
1191 | 65.3k | [quantizedSpectralCoefficientsIdx]) == |
1192 | 65.3k | (FIXP_DBL)ESCAPE_VALUE) { |
1193 | 3.53k | pQuantizedSpectralCoefficients[quantizedSpectralCoefficientsIdx] = |
1194 | 3.53k | (FIXP_DBL)DecodeEscapeSequence( |
1195 | 3.53k | bs, pHcr->decInOut.bitstreamAnchor, |
1196 | 3.53k | pQuantizedSpectralCoefficients |
1197 | 3.53k | [quantizedSpectralCoefficientsIdx], |
1198 | 3.53k | pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits, |
1199 | 3.53k | &pHcr->decInOut.errorLog); |
1200 | 3.53k | } |
1201 | 65.3k | quantizedSpectralCoefficientsIdx++; |
1202 | 65.3k | if (quantizedSpectralCoefficientsIdx >= 1024) { |
1203 | 0 | return; |
1204 | 0 | } |
1205 | | |
1206 | | /* one more PCW should be decoded */ |
1207 | | |
1208 | 65.3k | if (maxAllowedCwLen < |
1209 | 65.3k | (numDecodedBits + ERROR_PCW_BODY_SIGN_ESC_TOO_LONG)) { |
1210 | 2.90k | pHcr->decInOut.errorLog |= TOO_MANY_PCW_BODY_SIGN_ESC_BITS_DECODED; |
1211 | 2.90k | } |
1212 | | |
1213 | 65.3k | if (1 == errDetectPcwSegmentation( |
1214 | 65.3k | *pRemainingBitsInSegment - ERROR_PCW_BODY_SIGN_ESC, pHcr, |
1215 | 65.3k | PCW_BODY_SIGN_ESC, |
1216 | 65.3k | pQuantizedSpectralCoefficients + |
1217 | 65.3k | quantizedSpectralCoefficientsIdx - |
1218 | 65.3k | DIMENSION_OF_ESCAPE_CODEBOOK, |
1219 | 65.3k | DIMENSION_OF_ESCAPE_CODEBOOK)) { |
1220 | 2.90k | return; |
1221 | 2.90k | } |
1222 | 62.4k | pLeftStartOfSegment++; |
1223 | 62.4k | pRemainingBitsInSegment++; |
1224 | 62.4k | } |
1225 | 15.7k | } |
1226 | | |
1227 | | /* all PCWs belonging to this extended section should be decoded */ |
1228 | 16.1k | numExtendedSortedCodewordInSectionIdx++; |
1229 | 16.1k | if (numExtendedSortedCodewordInSectionIdx >= MAX_SFB_HCR + MAX_HCR_SETS) { |
1230 | 0 | return; |
1231 | 0 | } |
1232 | 16.1k | } |
1233 | | /* all PCWs should be decoded */ |
1234 | | |
1235 | 4.99k | numExtendedSortedSectionsInSetsIdx++; |
1236 | 4.99k | if (numExtendedSortedSectionsInSetsIdx >= MAX_HCR_SETS) { |
1237 | 0 | return; |
1238 | 0 | } |
1239 | | |
1240 | | /* Write back indexes into structure */ |
1241 | 4.99k | pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx = |
1242 | 4.99k | numExtendedSortedCodewordInSectionIdx; |
1243 | 4.99k | pHcr->sectionInfo.extendedSortedCodebookIdx = extendedSortedCodebookIdx; |
1244 | 4.99k | pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx = |
1245 | 4.99k | numExtendedSortedSectionsInSetsIdx; |
1246 | 4.99k | pHcr->decInOut.quantizedSpectralCoefficientsIdx = |
1247 | 4.99k | quantizedSpectralCoefficientsIdx; |
1248 | 4.99k | pHcr->sectionInfo.maxLenOfCbInExtSrtSecIdx = maxLenOfCbInExtSrtSecIdx; |
1249 | 4.99k | } |
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 | | */ |
1260 | | static UCHAR errDetectPcwSegmentation(SCHAR remainingBitsInSegment, |
1261 | | H_HCR_INFO pHcr, PCW_TYPE kind, |
1262 | | FIXP_DBL *qsc_base_of_cw, |
1263 | 138k | UCHAR dimension) { |
1264 | 138k | SCHAR i; |
1265 | 138k | if (remainingBitsInSegment < 0) { |
1266 | | /* log the error */ |
1267 | 2.98k | switch (kind) { |
1268 | 66 | case PCW_BODY: |
1269 | 66 | pHcr->decInOut.errorLog |= SEGMENT_OVERRIDE_ERR_PCW_BODY; |
1270 | 66 | break; |
1271 | 20 | case PCW_BODY_SIGN: |
1272 | 20 | pHcr->decInOut.errorLog |= SEGMENT_OVERRIDE_ERR_PCW_BODY_SIGN; |
1273 | 20 | break; |
1274 | 2.90k | case PCW_BODY_SIGN_ESC: |
1275 | 2.90k | pHcr->decInOut.errorLog |= SEGMENT_OVERRIDE_ERR_PCW_BODY_SIGN_ESC; |
1276 | 2.90k | break; |
1277 | 2.98k | } |
1278 | | /* mark the erred lines */ |
1279 | 9.08k | for (i = dimension; i != 0; i--) { |
1280 | 6.09k | *qsc_base_of_cw++ = (FIXP_DBL)Q_VALUE_INVALID; |
1281 | 6.09k | } |
1282 | 2.98k | return 1; |
1283 | 2.98k | } |
1284 | 135k | return 0; |
1285 | 138k | } |
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 | | */ |
1293 | 9.12k | static void errDetectWithinSegmentationFinal(H_HCR_INFO pHcr) { |
1294 | 9.12k | UCHAR segmentationErrorFlag = 0; |
1295 | 9.12k | USHORT i; |
1296 | 9.12k | SCHAR *pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment; |
1297 | 9.12k | UINT numSegment = pHcr->segmentInfo.numSegment; |
1298 | | |
1299 | 292k | for (i = numSegment; i != 0; i--) { |
1300 | 283k | if (*pRemainingBitsInSegment++ != 0) { |
1301 | 191k | segmentationErrorFlag = 1; |
1302 | 191k | } |
1303 | 283k | } |
1304 | 9.12k | if (segmentationErrorFlag == 1) { |
1305 | 7.63k | pHcr->decInOut.errorLog |= BIT_IN_SEGMENTATION_ERROR; |
1306 | 7.63k | } |
1307 | 9.12k | } |
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 | | */ |
1314 | | void CarryBitToBranchValue(UCHAR carryBit, UINT treeNode, UINT *branchValue, |
1315 | 5.76M | UINT *branchNode) { |
1316 | 5.76M | if (carryBit == 0) { |
1317 | 4.05M | *branchNode = |
1318 | 4.05M | (treeNode & MASK_LEFT) >> LEFT_OFFSET; /* MASK_LEFT: 00FFF000 */ |
1319 | 4.05M | } else { |
1320 | 1.71M | *branchNode = treeNode & MASK_RIGHT; /* MASK_RIGHT: 00000FFF */ |
1321 | 1.71M | } |
1322 | | |
1323 | 5.76M | *branchValue = *branchNode & CLR_BIT_10; /* clear bit 10 (if set) */ |
1324 | 5.76M | } |
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 | | */ |
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 | 139k | int *pNumDecodedBits) { |
1339 | 139k | UCHAR carryBit; |
1340 | 139k | UINT branchNode; |
1341 | 139k | UINT treeNode; |
1342 | 139k | UINT branchValue; |
1343 | 139k | const SCHAR *pQuantVal; |
1344 | | |
1345 | | /* decode PCW_BODY */ |
1346 | 139k | treeNode = *pCurrentTree; /* get first node of current tree belonging to |
1347 | | current codebook */ |
1348 | | |
1349 | | /* decode whole PCW-codeword-body */ |
1350 | 652k | while (1) { |
1351 | 652k | carryBit = HcrGetABitFromBitstream(bs, bsAnchor, pLeftStartOfSegment, |
1352 | 652k | pLeftStartOfSegment, /* dummy */ |
1353 | 652k | FROM_LEFT_TO_RIGHT); |
1354 | 652k | *pRemainingBitsInSegment -= 1; |
1355 | 652k | *pNumDecodedBits += 1; |
1356 | | |
1357 | 652k | CarryBitToBranchValue(carryBit, treeNode, &branchValue, &branchNode); |
1358 | | |
1359 | 652k | if ((branchNode & TEST_BIT_10) == |
1360 | 652k | TEST_BIT_10) { /* test bit 10 ; if set --> codeword-body is complete */ |
1361 | 139k | break; /* end of branch in tree reached i.e. a whole PCW-Body is decoded |
1362 | | */ |
1363 | 513k | } else { |
1364 | 513k | treeNode = *( |
1365 | 513k | pCurrentTree + |
1366 | 513k | branchValue); /* update treeNode for further step in decoding tree */ |
1367 | 513k | } |
1368 | 652k | } |
1369 | | |
1370 | 139k | pQuantVal = |
1371 | 139k | pQuantValBase + branchValue; /* update pointer to valid first of 2 or 4 |
1372 | | quantized values */ |
1373 | | |
1374 | 139k | return pQuantVal; |
1375 | 139k | } |
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 | | |
1386 | | static INT DecodeEscapeSequence(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor, |
1387 | | INT quantSpecCoef, INT *pLeftStartOfSegment, |
1388 | | SCHAR *pRemainingBitsInSegment, |
1389 | 4.49k | int *pNumDecodedBits, UINT *errorWord) { |
1390 | 4.49k | UINT i; |
1391 | 4.49k | INT sign; |
1392 | 4.49k | UINT escapeOnesCounter = 0; |
1393 | 4.49k | UINT carryBit; |
1394 | 4.49k | INT escape_word = 0; |
1395 | | |
1396 | | /* decode escape prefix */ |
1397 | 6.83k | while (1) { |
1398 | 6.83k | carryBit = HcrGetABitFromBitstream(bs, bsAnchor, pLeftStartOfSegment, |
1399 | 6.83k | pLeftStartOfSegment, /* dummy */ |
1400 | 6.83k | FROM_LEFT_TO_RIGHT); |
1401 | 6.83k | *pRemainingBitsInSegment -= 1; |
1402 | 6.83k | *pNumDecodedBits += 1; |
1403 | 6.83k | if (*pRemainingBitsInSegment < 0) { |
1404 | 103 | return Q_VALUE_INVALID; |
1405 | 103 | } |
1406 | | |
1407 | 6.73k | if (carryBit != 0) { |
1408 | 2.34k | escapeOnesCounter += 1; |
1409 | 4.39k | } else { |
1410 | 4.39k | escapeOnesCounter += 4; |
1411 | 4.39k | break; |
1412 | 4.39k | } |
1413 | 6.73k | } |
1414 | | |
1415 | | /* decode escape word */ |
1416 | 21.0k | for (i = escapeOnesCounter; i != 0; i--) { |
1417 | 19.4k | carryBit = HcrGetABitFromBitstream(bs, bsAnchor, pLeftStartOfSegment, |
1418 | 19.4k | pLeftStartOfSegment, /* dummy */ |
1419 | 19.4k | FROM_LEFT_TO_RIGHT); |
1420 | 19.4k | *pRemainingBitsInSegment -= 1; |
1421 | 19.4k | *pNumDecodedBits += 1; |
1422 | 19.4k | if (*pRemainingBitsInSegment < 0) { |
1423 | 2.78k | return Q_VALUE_INVALID; |
1424 | 2.78k | } |
1425 | | |
1426 | 16.6k | escape_word <<= 1; |
1427 | 16.6k | escape_word = escape_word | carryBit; |
1428 | 16.6k | } |
1429 | | |
1430 | 1.61k | sign = (quantSpecCoef >= 0) ? 1 : -1; |
1431 | | |
1432 | 1.61k | if (escapeOnesCounter < 13) { |
1433 | 1.57k | quantSpecCoef = sign * (((INT)1 << escapeOnesCounter) + escape_word); |
1434 | 1.57k | } else { |
1435 | 35 | *errorWord |= TOO_MANY_PCW_BODY_SIGN_ESC_BITS_DECODED; |
1436 | 35 | quantSpecCoef = Q_VALUE_INVALID; |
1437 | 35 | } |
1438 | 1.61k | return quantSpecCoef; |
1439 | 4.39k | } |
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 | | */ |
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 | 132k | int *pNumDecodedBits) { |
1459 | 132k | UINT i; |
1460 | 132k | UINT carryBit; |
1461 | 132k | INT quantSpecCoef; |
1462 | | |
1463 | 399k | for (i = codebookDim; i != 0; i--) { |
1464 | 267k | quantSpecCoef = *pQuantVal++; |
1465 | 267k | if (quantSpecCoef != 0) { |
1466 | 185k | carryBit = HcrGetABitFromBitstream(bs, bsAnchor, pLeftStartOfSegment, |
1467 | 185k | pLeftStartOfSegment, /* dummy */ |
1468 | 185k | FROM_LEFT_TO_RIGHT); |
1469 | 185k | *pRemainingBitsInSegment -= 1; |
1470 | 185k | *pNumDecodedBits += 1; |
1471 | 185k | if (*pRemainingBitsInSegment < 0 || *pNumDecodedBits >= (1024 >> 1)) { |
1472 | 1.11k | return -1; |
1473 | 1.11k | } |
1474 | | |
1475 | | /* adapt sign of values according to the decoded sign bit */ |
1476 | 184k | if (carryBit != 0) { |
1477 | 46.5k | pQuantSpecCoef[*quantSpecCoefIdx] = -(FIXP_DBL)quantSpecCoef; |
1478 | 137k | } else { |
1479 | 137k | pQuantSpecCoef[*quantSpecCoefIdx] = (FIXP_DBL)quantSpecCoef; |
1480 | 137k | } |
1481 | 184k | } else { |
1482 | 82.4k | pQuantSpecCoef[*quantSpecCoefIdx] = FL2FXCONST_DBL(0.0f); |
1483 | 82.4k | } |
1484 | 266k | *quantSpecCoefIdx += 1; |
1485 | 266k | if (*quantSpecCoefIdx >= 1024) { |
1486 | 14 | return -1; |
1487 | 14 | } |
1488 | 266k | } |
1489 | 131k | return 0; |
1490 | 132k | } |
1491 | | |
1492 | | /*--------------------------------------------------------------------------------------------- |
1493 | | description: Mutes spectral lines which have been marked as erroneous |
1494 | | (Q_VALUE_INVALID) |
1495 | | -------------------------------------------------------------------------------------------- |
1496 | | */ |
1497 | 7.64k | void HcrMuteErroneousLines(H_HCR_INFO hHcr) { |
1498 | 7.64k | int c; |
1499 | 7.64k | FIXP_DBL *RESTRICT pLong = |
1500 | 7.64k | SPEC_LONG(hHcr->decInOut.pQuantizedSpectralCoefficientsBase); |
1501 | | |
1502 | | /* if there is a line with value Q_VALUE_INVALID mute it */ |
1503 | 7.83M | for (c = 0; c < 1024; c++) { |
1504 | 7.83M | if (pLong[c] == (FIXP_DBL)Q_VALUE_INVALID) { |
1505 | 9.27k | pLong[c] = FL2FXCONST_DBL(0.0f); /* muting */ |
1506 | 9.27k | } |
1507 | 7.83M | } |
1508 | 7.64k | } |