• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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):   Christian Griebel
98 
99    Description: Dynamic range control (DRC) decoder tool for AAC
100 
101 *******************************************************************************/
102 
103 #include "aacdec_drc.h"
104 
105 #include "channelinfo.h"
106 #include "aac_rom.h"
107 
108 #include "sbrdecoder.h"
109 
110 /*
111  * Dynamic Range Control
112  */
113 
114 /* For parameter conversion */
115 #define DRC_PARAMETER_BITS (7)
116 #define DRC_MAX_QUANT_STEPS (1 << DRC_PARAMETER_BITS)
117 #define DRC_MAX_QUANT_FACTOR (DRC_MAX_QUANT_STEPS - 1)
118 #define DRC_PARAM_QUANT_STEP \
119   (FL2FXCONST_DBL(1.0f / (float)DRC_MAX_QUANT_FACTOR))
120 #define DRC_PARAM_SCALE (1)
121 #define DRC_SCALING_MAX \
122   ((FIXP_DBL)((INT)(DRC_PARAM_QUANT_STEP >> DRC_PARAM_SCALE) * (INT)127))
123 
124 #define DRC_BLOCK_LEN (1024)
125 #define DRC_BAND_MULT (4)
126 #define DRC_BLOCK_LEN_DIV_BAND_MULT (DRC_BLOCK_LEN / DRC_BAND_MULT)
127 
128 #define MAX_REFERENCE_LEVEL (127)
129 
130 #define DRC_HEAVY_THRESHOLD_DB (10)
131 
132 #define DVB_ANC_DATA_SYNC_BYTE (0xBC) /* DVB ancillary data sync byte. */
133 
134 #define OFF 0
135 #define ON 1
136 
convert_drcParam(FIXP_DBL param_dbl)137 static INT convert_drcParam(FIXP_DBL param_dbl) {
138   /* converts an internal DRC boost/cut scaling factor in FIXP_DBL
139      (which is downscaled by DRC_PARAM_SCALE)
140      back to an integer value between 0 and 127. */
141   LONG param_long;
142 
143   param_long = (LONG)param_dbl >> 7;
144   param_long = param_long * (INT)DRC_MAX_QUANT_FACTOR;
145   param_long >>= 31 - 7 - DRC_PARAM_SCALE - 1;
146   param_long += 1; /* for rounding */
147   param_long >>= 1;
148 
149   return (INT)param_long;
150 }
151 
152 /*!
153   \brief Initialize DRC information
154 
155   \self Handle of DRC info
156 
157   \return none
158 */
aacDecoder_drcInit(HANDLE_AAC_DRC self)159 void aacDecoder_drcInit(HANDLE_AAC_DRC self) {
160   CDrcParams *pParams;
161 
162   if (self == NULL) {
163     return;
164   }
165 
166   /* init control fields */
167   self->enable = OFF;
168   self->numThreads = 0;
169 
170   /* init params */
171   pParams = &self->params;
172   pParams->bsDelayEnable = 0;
173   pParams->cut = FL2FXCONST_DBL(0.0f);
174   pParams->usrCut = FL2FXCONST_DBL(0.0f);
175   pParams->boost = FL2FXCONST_DBL(0.0f);
176   pParams->usrBoost = FL2FXCONST_DBL(0.0f);
177   pParams->targetRefLevel = 96;
178   pParams->expiryFrame = AACDEC_DRC_DFLT_EXPIRY_FRAMES;
179   pParams->applyDigitalNorm = ON;
180   pParams->applyHeavyCompression = OFF;
181   pParams->usrApplyHeavyCompression = OFF;
182 
183   pParams->defaultPresentationMode = DISABLED_PARAMETER_HANDLING;
184   pParams->encoderTargetLevel = MAX_REFERENCE_LEVEL; /* worst case assumption */
185 
186   self->update = 1;
187   self->numOutChannels = 0;
188   self->prevAacNumChannels = 0;
189 
190   /* initial program ref level = target ref level */
191   self->progRefLevel = pParams->targetRefLevel;
192   self->progRefLevelPresent = 0;
193   self->presMode = -1;
194   self->uniDrcPrecedence = 0;
195 }
196 
197 /*!
198   \brief Initialize DRC control data for one channel
199 
200   \self Handle of DRC info
201 
202   \return none
203 */
aacDecoder_drcInitChannelData(CDrcChannelData * pDrcChData)204 void aacDecoder_drcInitChannelData(CDrcChannelData *pDrcChData) {
205   if (pDrcChData != NULL) {
206     pDrcChData->expiryCount = 0;
207     pDrcChData->numBands = 1;
208     pDrcChData->bandTop[0] = DRC_BLOCK_LEN_DIV_BAND_MULT - 1;
209     pDrcChData->drcValue[0] = 0;
210     pDrcChData->drcInterpolationScheme = 0;
211     pDrcChData->drcDataType = UNKNOWN_PAYLOAD;
212   }
213 }
214 
215 /*!
216   \brief  Set one single DRC parameter
217 
218   \self   Handle of DRC info.
219   \param  Parameter to be set.
220   \value  Value to be set.
221 
222   \return an error code.
223 */
aacDecoder_drcSetParam(HANDLE_AAC_DRC self,AACDEC_DRC_PARAM param,INT value)224 AAC_DECODER_ERROR aacDecoder_drcSetParam(HANDLE_AAC_DRC self,
225                                          AACDEC_DRC_PARAM param, INT value) {
226   AAC_DECODER_ERROR ErrorStatus = AAC_DEC_OK;
227 
228   switch (param) {
229     case DRC_CUT_SCALE:
230       /* set attenuation scale factor */
231       if ((value < 0) || (value > DRC_MAX_QUANT_FACTOR)) {
232         return AAC_DEC_SET_PARAM_FAIL;
233       }
234       if (self == NULL) {
235         return AAC_DEC_INVALID_HANDLE;
236       }
237       self->params.usrCut = (FIXP_DBL)(
238           (INT)(DRC_PARAM_QUANT_STEP >> DRC_PARAM_SCALE) * (INT)value);
239       self->update = 1;
240       break;
241     case DRC_BOOST_SCALE:
242       /* set boost factor */
243       if ((value < 0) || (value > DRC_MAX_QUANT_FACTOR)) {
244         return AAC_DEC_SET_PARAM_FAIL;
245       }
246       if (self == NULL) {
247         return AAC_DEC_INVALID_HANDLE;
248       }
249       self->params.usrBoost = (FIXP_DBL)(
250           (INT)(DRC_PARAM_QUANT_STEP >> DRC_PARAM_SCALE) * (INT)value);
251       self->update = 1;
252       break;
253     case TARGET_REF_LEVEL:
254       if (value > MAX_REFERENCE_LEVEL || value < -MAX_REFERENCE_LEVEL) {
255         return AAC_DEC_SET_PARAM_FAIL;
256       }
257       if (self == NULL) {
258         return AAC_DEC_INVALID_HANDLE;
259       }
260       if (value < 0) {
261         self->params.applyDigitalNorm = OFF;
262         self->params.targetRefLevel = -1;
263       } else {
264         /* ref_level must be between 0 and MAX_REFERENCE_LEVEL, inclusive */
265         self->params.applyDigitalNorm = ON;
266         if (self->params.targetRefLevel != (SCHAR)value) {
267           self->params.targetRefLevel = (SCHAR)value;
268           self->progRefLevel = (SCHAR)value; /* Always set the program reference
269                                                 level equal to the target level
270                                                 according to 4.5.2.7.3 of
271                                                 ISO/IEC 14496-3. */
272         }
273         self->update = 1;
274       }
275       break;
276     case APPLY_NORMALIZATION:
277       if ((value != OFF) && (value != ON)) {
278         return AAC_DEC_SET_PARAM_FAIL;
279       }
280       if (self == NULL) {
281         return AAC_DEC_INVALID_HANDLE;
282       }
283       /* Store new parameter value */
284       self->params.applyDigitalNorm = (UCHAR)value;
285       break;
286     case APPLY_HEAVY_COMPRESSION:
287       if ((value != OFF) && (value != ON)) {
288         return AAC_DEC_SET_PARAM_FAIL;
289       }
290       if (self == NULL) {
291         return AAC_DEC_INVALID_HANDLE;
292       }
293       /* Store new parameter value */
294       self->params.usrApplyHeavyCompression = (UCHAR)value;
295       self->update = 1;
296       break;
297     case DEFAULT_PRESENTATION_MODE:
298       if (value < AAC_DRC_PARAMETER_HANDLING_DISABLED ||
299           value > AAC_DRC_PRESENTATION_MODE_2_DEFAULT) {
300         return AAC_DEC_SET_PARAM_FAIL;
301       }
302       if (self == NULL) {
303         return AAC_DEC_INVALID_HANDLE;
304       }
305       self->params.defaultPresentationMode =
306           (AACDEC_DRC_PARAMETER_HANDLING)value;
307       self->update = 1;
308       break;
309     case ENCODER_TARGET_LEVEL:
310       if (value > MAX_REFERENCE_LEVEL || value < 0) {
311         return AAC_DEC_SET_PARAM_FAIL;
312       }
313       if (self == NULL) {
314         return AAC_DEC_INVALID_HANDLE;
315       }
316       self->params.encoderTargetLevel = (UCHAR)value;
317       self->update = 1;
318       break;
319     case DRC_BS_DELAY:
320       if (value < 0 || value > 1) {
321         return AAC_DEC_SET_PARAM_FAIL;
322       }
323       if (self == NULL) {
324         return AAC_DEC_INVALID_HANDLE;
325       }
326       self->params.bsDelayEnable = value;
327       break;
328     case DRC_DATA_EXPIRY_FRAME:
329       if (self == NULL) {
330         return AAC_DEC_INVALID_HANDLE;
331       }
332       self->params.expiryFrame = (value > 0) ? (UINT)value : 0;
333       break;
334     case MAX_OUTPUT_CHANNELS:
335       if (self == NULL) {
336         return AAC_DEC_INVALID_HANDLE;
337       }
338       self->numOutChannels = (INT)value;
339       self->update = 1;
340       break;
341     case UNIDRC_PRECEDENCE:
342       if (self == NULL) {
343         return AAC_DEC_INVALID_HANDLE;
344       }
345       self->uniDrcPrecedence = (UCHAR)value;
346       break;
347     default:
348       return AAC_DEC_SET_PARAM_FAIL;
349   } /* switch(param) */
350 
351   return ErrorStatus;
352 }
353 
parseExcludedChannels(UINT * excludedChnsMask,HANDLE_FDK_BITSTREAM bs)354 static int parseExcludedChannels(UINT *excludedChnsMask,
355                                  HANDLE_FDK_BITSTREAM bs) {
356   UINT excludeMask = 0;
357   UINT i, j;
358   int bitCnt = 9;
359 
360   for (i = 0, j = 1; i < 7; i++, j <<= 1) {
361     if (FDKreadBits(bs, 1)) {
362       excludeMask |= j;
363     }
364   }
365 
366   /* additional_excluded_chns */
367   while (FDKreadBits(bs, 1)) {
368     for (i = 0; i < 7; i++, j <<= 1) {
369       if (FDKreadBits(bs, 1)) {
370         excludeMask |= j;
371       }
372     }
373     bitCnt += 9;
374     FDK_ASSERT(j < (UINT)-1);
375   }
376 
377   *excludedChnsMask = excludeMask;
378 
379   return (bitCnt);
380 }
381 
382 /*!
383   \brief Save DRC payload bitstream position
384 
385   \self Handle of DRC info
386   \bs Handle of FDK bitstream
387 
388   \return The number of DRC payload bits
389 */
aacDecoder_drcMarkPayload(HANDLE_AAC_DRC self,HANDLE_FDK_BITSTREAM bs,AACDEC_DRC_PAYLOAD_TYPE type)390 int aacDecoder_drcMarkPayload(HANDLE_AAC_DRC self, HANDLE_FDK_BITSTREAM bs,
391                               AACDEC_DRC_PAYLOAD_TYPE type) {
392   UINT bsStartPos;
393   int i, numBands = 1, bitCnt = 0;
394 
395   if (self == NULL) {
396     return 0;
397   }
398 
399   bsStartPos = FDKgetValidBits(bs);
400 
401   switch (type) {
402     case MPEG_DRC_EXT_DATA: {
403       bitCnt = 4;
404 
405       if (FDKreadBits(bs, 1)) { /* pce_tag_present */
406         FDKreadBits(bs, 8);     /* pce_instance_tag + drc_tag_reserved_bits */
407         bitCnt += 8;
408       }
409 
410       if (FDKreadBits(bs, 1)) { /* excluded_chns_present */
411         FDKreadBits(bs, 7);     /* exclude mask [0..7] */
412         bitCnt += 8;
413         while (FDKreadBits(bs, 1)) { /* additional_excluded_chns */
414           FDKreadBits(bs, 7);        /* exclude mask [x..y] */
415           bitCnt += 8;
416         }
417       }
418 
419       if (FDKreadBits(bs, 1)) {         /* drc_bands_present */
420         numBands += FDKreadBits(bs, 4); /* drc_band_incr */
421         FDKreadBits(bs, 4);             /* reserved */
422         bitCnt += 8;
423         for (i = 0; i < numBands; i++) {
424           FDKreadBits(bs, 8); /* drc_band_top[i] */
425           bitCnt += 8;
426         }
427       }
428 
429       if (FDKreadBits(bs, 1)) { /* prog_ref_level_present */
430         FDKreadBits(bs, 8); /* prog_ref_level + prog_ref_level_reserved_bits */
431         bitCnt += 8;
432       }
433 
434       for (i = 0; i < numBands; i++) {
435         FDKreadBits(bs, 8); /* dyn_rng_sgn[i] + dyn_rng_ctl[i] */
436         bitCnt += 8;
437       }
438 
439       if ((self->numPayloads < MAX_DRC_THREADS) &&
440           ((INT)FDKgetValidBits(bs) >= 0)) {
441         self->drcPayloadPosition[self->numPayloads++] = bsStartPos;
442       }
443     } break;
444 
445     case DVB_DRC_ANC_DATA:
446       bitCnt += 8;
447       /* check sync word */
448       if (FDKreadBits(bs, 8) == DVB_ANC_DATA_SYNC_BYTE) {
449         int dmxLevelsPresent, compressionPresent;
450         int coarseGrainTcPresent, fineGrainTcPresent;
451 
452         /* bs_info field */
453         FDKreadBits(
454             bs,
455             8); /* mpeg_audio_type, dolby_surround_mode, presentation_mode */
456         bitCnt += 8;
457 
458         /* Evaluate ancillary_data_status */
459         FDKreadBits(bs, 3); /* reserved, set to 0 */
460         dmxLevelsPresent =
461             FDKreadBits(bs, 1); /* downmixing_levels_MPEG4_status */
462         FDKreadBits(bs, 1);     /* reserved, set to 0 */
463         compressionPresent =
464             FDKreadBits(bs, 1); /* audio_coding_mode_and_compression status */
465         coarseGrainTcPresent =
466             FDKreadBits(bs, 1); /* coarse_grain_timecode_status */
467         fineGrainTcPresent =
468             FDKreadBits(bs, 1); /* fine_grain_timecode_status */
469         bitCnt += 8;
470 
471         /* MPEG4 downmixing levels */
472         if (dmxLevelsPresent) {
473           FDKreadBits(bs, 8); /* downmixing_levels_MPEG4 */
474           bitCnt += 8;
475         }
476         /* audio coding mode and compression status */
477         if (compressionPresent) {
478           FDKreadBits(bs, 16); /* audio_coding_mode, Compression_value */
479           bitCnt += 16;
480         }
481         /* coarse grain timecode */
482         if (coarseGrainTcPresent) {
483           FDKreadBits(bs, 16); /* coarse_grain_timecode */
484           bitCnt += 16;
485         }
486         /* fine grain timecode */
487         if (fineGrainTcPresent) {
488           FDKreadBits(bs, 16); /* fine_grain_timecode */
489           bitCnt += 16;
490         }
491         if (!self->dvbAncDataAvailable && ((INT)FDKgetValidBits(bs) >= 0)) {
492           self->dvbAncDataPosition = bsStartPos;
493           self->dvbAncDataAvailable = 1;
494         }
495       }
496       break;
497 
498     default:
499       break;
500   }
501 
502   return (bitCnt);
503 }
504 
505 /*!
506   \brief Parse DRC parameters from bitstream
507 
508   \bs Handle of FDK bitstream (in)
509   \pDrcBs Pointer to DRC payload data container (out)
510   \payloadPosition Bitstream position of MPEG DRC data chunk (in)
511 
512   \return Flag telling whether new DRC data has been found or not.
513 */
aacDecoder_drcParse(HANDLE_FDK_BITSTREAM bs,CDrcPayload * pDrcBs,UINT payloadPosition)514 static int aacDecoder_drcParse(HANDLE_FDK_BITSTREAM bs, CDrcPayload *pDrcBs,
515                                UINT payloadPosition) {
516   int i, numBands;
517 
518   /* Move to the beginning of the DRC payload field */
519   FDKpushBiDirectional(bs, (INT)FDKgetValidBits(bs) - (INT)payloadPosition);
520 
521   /* pce_tag_present */
522   if (FDKreadBits(bs, 1)) {
523     pDrcBs->pceInstanceTag = FDKreadBits(bs, 4); /* pce_instance_tag */
524     /* only one program supported */
525     FDKreadBits(bs, 4); /* drc_tag_reserved_bits */
526   } else {
527     pDrcBs->pceInstanceTag = -1; /* not present */
528   }
529 
530   if (FDKreadBits(bs, 1)) { /* excluded_chns_present */
531     /* get excluded_chn_mask */
532     parseExcludedChannels(&pDrcBs->excludedChnsMask, bs);
533   } else {
534     pDrcBs->excludedChnsMask = 0;
535   }
536 
537   numBands = 1;
538   if (FDKreadBits(bs, 1)) /* drc_bands_present */
539   {
540     /* get band_incr */
541     numBands += FDKreadBits(bs, 4); /* drc_band_incr */
542     pDrcBs->channelData.drcInterpolationScheme =
543         FDKreadBits(bs, 4); /* drc_interpolation_scheme */
544     /* band_top */
545     for (i = 0; i < numBands; i++) {
546       pDrcBs->channelData.bandTop[i] = FDKreadBits(bs, 8); /* drc_band_top[i] */
547     }
548   } else {
549     pDrcBs->channelData.bandTop[0] = DRC_BLOCK_LEN_DIV_BAND_MULT -
550                                      1; /* ... comprising the whole spectrum. */
551     ;
552   }
553 
554   pDrcBs->channelData.numBands = numBands;
555 
556   if (FDKreadBits(bs, 1)) /* prog_ref_level_present */
557   {
558     pDrcBs->progRefLevel = FDKreadBits(bs, 7); /* prog_ref_level */
559     FDKreadBits(bs, 1); /* prog_ref_level_reserved_bits */
560   } else {
561     pDrcBs->progRefLevel = -1;
562   }
563 
564   for (i = 0; i < numBands; i++) {
565     pDrcBs->channelData.drcValue[i] = FDKreadBits(bs, 1)
566                                       << 7; /* dyn_rng_sgn[i] */
567     pDrcBs->channelData.drcValue[i] |=
568         FDKreadBits(bs, 7) & 0x7F; /* dyn_rng_ctl[i] */
569   }
570 
571   /* Set DRC payload type */
572   pDrcBs->channelData.drcDataType = MPEG_DRC_EXT_DATA;
573 
574   return (1);
575 }
576 
577 /*!
578   \brief Parse heavy compression value transported in DSEs of DVB streams with
579   MPEG-4 content.
580 
581   \bs Handle of FDK bitstream (in)
582   \pDrcBs Pointer to DRC payload data container (out)
583   \payloadPosition Bitstream position of DVB ancillary data chunk
584 
585   \return Flag telling whether new DRC data has been found or not.
586 */
587 #define DVB_COMPRESSION_SCALE (8) /* 48,164 dB */
588 
aacDecoder_drcReadCompression(HANDLE_FDK_BITSTREAM bs,CDrcPayload * pDrcBs,UINT payloadPosition)589 static int aacDecoder_drcReadCompression(HANDLE_FDK_BITSTREAM bs,
590                                          CDrcPayload *pDrcBs,
591                                          UINT payloadPosition) {
592   int foundDrcData = 0;
593   int dmxLevelsPresent, compressionPresent;
594 
595   /* Move to the beginning of the DRC payload field */
596   FDKpushBiDirectional(bs, (INT)FDKgetValidBits(bs) - (INT)payloadPosition);
597 
598   /* Sanity checks */
599   if (FDKgetValidBits(bs) < 24) {
600     return 0;
601   }
602 
603   /* Check sync word */
604   if (FDKreadBits(bs, 8) != DVB_ANC_DATA_SYNC_BYTE) {
605     return 0;
606   }
607 
608   /* Evaluate bs_info field */
609   if (FDKreadBits(bs, 2) != 3) { /* mpeg_audio_type */
610     /* No MPEG-4 audio data */
611     return 0;
612   }
613   FDKreadBits(bs, 2);                    /* dolby_surround_mode */
614   pDrcBs->presMode = FDKreadBits(bs, 2); /* presentation_mode */
615   FDKreadBits(bs, 1);                    /* stereo_downmix_mode */
616   if (FDKreadBits(bs, 1) != 0) {         /* reserved, set to 0 */
617     return 0;
618   }
619 
620   /* Evaluate ancillary_data_status */
621   if (FDKreadBits(bs, 3) != 0) { /* reserved, set to 0 */
622     return 0;
623   }
624   dmxLevelsPresent = FDKreadBits(bs, 1); /* downmixing_levels_MPEG4_status */
625   /*extensionPresent =*/FDKreadBits(bs,
626                                     1); /* ancillary_data_extension_status; */
627   compressionPresent =
628       FDKreadBits(bs, 1); /* audio_coding_mode_and_compression status */
629   /*coarseGrainTcPresent =*/FDKreadBits(bs,
630                                         1); /* coarse_grain_timecode_status */
631   /*fineGrainTcPresent   =*/FDKreadBits(bs, 1); /* fine_grain_timecode_status */
632 
633   if (dmxLevelsPresent) {
634     FDKreadBits(bs, 8); /* downmixing_levels_MPEG4 */
635   }
636 
637   /* audio_coding_mode_and_compression_status */
638   if (compressionPresent) {
639     UCHAR compressionOn, compressionValue;
640 
641     /* audio_coding_mode */
642     if (FDKreadBits(bs, 7) != 0) { /* The reserved bits shall be set to "0". */
643       return 0;
644     }
645     compressionOn = (UCHAR)FDKreadBits(bs, 1);    /* compression_on */
646     compressionValue = (UCHAR)FDKreadBits(bs, 8); /* Compression_value */
647 
648     if (compressionOn) {
649       /* A compression value is available so store the data just like MPEG DRC
650        * data */
651       pDrcBs->channelData.numBands = 1; /* One band ... */
652       pDrcBs->channelData.drcValue[0] =
653           compressionValue; /* ... with one value ... */
654       pDrcBs->channelData.bandTop[0] =
655           DRC_BLOCK_LEN_DIV_BAND_MULT -
656           1; /* ... comprising the whole spectrum. */
657       ;
658       pDrcBs->pceInstanceTag = -1; /* Not present */
659       pDrcBs->progRefLevel = -1;   /* Not present */
660       pDrcBs->channelData.drcDataType =
661           DVB_DRC_ANC_DATA; /* Set DRC payload type to DVB. */
662       foundDrcData = 1;
663     }
664   }
665 
666   return (foundDrcData);
667 }
668 
669 /*
670  * Extract DRC payload from bitstream and map it to channels.
671  *   Valid return values are:
672  *     -1 : An unexpected error occured.
673  *      0 : No error and no valid DRC data available.
674  *      1 : No error and valid DRC data has been mapped.
675  */
aacDecoder_drcExtractAndMap(HANDLE_AAC_DRC self,HANDLE_FDK_BITSTREAM hBs,CAacDecoderStaticChannelInfo * pAacDecoderStaticChannelInfo[],UCHAR pceInstanceTag,UCHAR channelMapping[],int validChannels)676 static int aacDecoder_drcExtractAndMap(
677     HANDLE_AAC_DRC self, HANDLE_FDK_BITSTREAM hBs,
678     CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo[],
679     UCHAR pceInstanceTag,
680     UCHAR channelMapping[], /* Channel mapping translating drcChannel index to
681                                canonical channel index */
682     int validChannels) {
683   CDrcPayload threadBs[MAX_DRC_THREADS];
684   CDrcPayload *validThreadBs[MAX_DRC_THREADS];
685   CDrcParams *pParams;
686   UINT backupBsPosition;
687   int result = 0;
688   int i, thread, validThreads = 0;
689 
690   FDK_ASSERT(self != NULL);
691   FDK_ASSERT(hBs != NULL);
692   FDK_ASSERT(pAacDecoderStaticChannelInfo != NULL);
693 
694   pParams = &self->params;
695 
696   self->numThreads = 0;
697   backupBsPosition = FDKgetValidBits(hBs);
698 
699   for (i = 0; i < self->numPayloads && self->numThreads < MAX_DRC_THREADS;
700        i++) {
701     /* Init payload data chunk. The memclear is very important because it
702        initializes the most values. Without it the module wouldn't work properly
703        or crash. */
704     FDKmemclear(&threadBs[self->numThreads], sizeof(CDrcPayload));
705     threadBs[self->numThreads].channelData.bandTop[0] =
706         DRC_BLOCK_LEN_DIV_BAND_MULT - 1;
707 
708     /* Extract payload */
709     self->numThreads += aacDecoder_drcParse(hBs, &threadBs[self->numThreads],
710                                             self->drcPayloadPosition[i]);
711   }
712   self->numPayloads = 0;
713 
714   if (self->dvbAncDataAvailable &&
715       self->numThreads < MAX_DRC_THREADS) { /* Append a DVB heavy compression
716                                                payload thread if available. */
717 
718     /* Init payload data chunk. The memclear is very important because it
719        initializes the most values. Without it the module wouldn't work properly
720        or crash. */
721     FDKmemclear(&threadBs[self->numThreads], sizeof(CDrcPayload));
722     threadBs[self->numThreads].channelData.bandTop[0] =
723         DRC_BLOCK_LEN_DIV_BAND_MULT - 1;
724 
725     /* Extract payload */
726     self->numThreads += aacDecoder_drcReadCompression(
727         hBs, &threadBs[self->numThreads], self->dvbAncDataPosition);
728   }
729   self->dvbAncDataAvailable = 0;
730 
731   /* Reset the bitbufffer */
732   FDKpushBiDirectional(hBs, (INT)FDKgetValidBits(hBs) - (INT)backupBsPosition);
733 
734   /* calculate number of valid bits in excl_chn_mask */
735 
736   /* coupling channels not supported */
737 
738   /* check for valid threads */
739   for (thread = 0; thread < self->numThreads; thread++) {
740     CDrcPayload *pThreadBs = &threadBs[thread];
741     int numExclChns = 0;
742 
743     switch ((AACDEC_DRC_PAYLOAD_TYPE)pThreadBs->channelData.drcDataType) {
744       default:
745         continue;
746       case MPEG_DRC_EXT_DATA:
747       case DVB_DRC_ANC_DATA:
748         break;
749     }
750 
751     if (pThreadBs->pceInstanceTag >= 0) { /* if PCE tag present */
752       if (pThreadBs->pceInstanceTag != pceInstanceTag) {
753         continue; /* don't accept */
754       }
755     }
756 
757     /* calculate number of excluded channels */
758     if (pThreadBs->excludedChnsMask > 0) {
759       INT exclMask = pThreadBs->excludedChnsMask;
760       int ch;
761       for (ch = 0; ch < validChannels; ch++) {
762         numExclChns += exclMask & 0x1;
763         exclMask >>= 1;
764       }
765     }
766     if (numExclChns < validChannels) {
767       validThreadBs[validThreads] = pThreadBs;
768       validThreads++;
769     }
770   }
771 
772   /* map DRC bitstream information onto DRC channel information */
773   for (thread = 0; thread < validThreads; thread++) {
774     CDrcPayload *pThreadBs = validThreadBs[thread];
775     INT exclMask = pThreadBs->excludedChnsMask;
776     AACDEC_DRC_PAYLOAD_TYPE drcPayloadType =
777         (AACDEC_DRC_PAYLOAD_TYPE)pThreadBs->channelData.drcDataType;
778     int ch;
779 
780     /* last progRefLevel transmitted is the one that is used
781      * (but it should really only be transmitted once per block!)
782      */
783     if (pThreadBs->progRefLevel >= 0) {
784       self->progRefLevel = pThreadBs->progRefLevel;
785       self->progRefLevelPresent = 1;
786       self->prlExpiryCount = 0; /* Got a new value -> Reset counter */
787     }
788 
789     if (drcPayloadType == DVB_DRC_ANC_DATA) {
790       /* Announce the presentation mode of this valid thread. */
791       self->presMode = pThreadBs->presMode;
792     }
793 
794     /* SCE, CPE and LFE */
795     for (ch = 0; ch < validChannels; ch++) {
796       AACDEC_DRC_PAYLOAD_TYPE prvPayloadType = UNKNOWN_PAYLOAD;
797       int mapedChannel = channelMapping[ch];
798 
799       if ((mapedChannel >= validChannels) ||
800           ((exclMask & (1 << mapedChannel)) != 0))
801         continue;
802 
803       if ((pParams->expiryFrame <= 0) ||
804           (pAacDecoderStaticChannelInfo[ch]->drcData.expiryCount <
805            pParams->expiryFrame)) {
806         prvPayloadType =
807             (AACDEC_DRC_PAYLOAD_TYPE)pAacDecoderStaticChannelInfo[ch]
808                 ->drcData.drcDataType;
809       }
810       if (((drcPayloadType == MPEG_DRC_EXT_DATA) &&
811            (prvPayloadType != DVB_DRC_ANC_DATA)) ||
812           ((drcPayloadType == DVB_DRC_ANC_DATA) &&
813            (pParams->applyHeavyCompression ==
814             ON))) { /* copy thread to channel */
815         pAacDecoderStaticChannelInfo[ch]->drcData = pThreadBs->channelData;
816         result = 1;
817       }
818     }
819     /* CCEs not supported by now */
820   }
821 
822   /* Increment and check expiry counter for the program reference level: */
823   if ((pParams->expiryFrame > 0) &&
824       (self->prlExpiryCount++ >
825        pParams->expiryFrame)) { /* The program reference level is too old, so
826                                    set it back to the target level. */
827     self->progRefLevelPresent = 0;
828     self->progRefLevel = pParams->targetRefLevel;
829     self->prlExpiryCount = 0;
830   }
831 
832   return result;
833 }
834 
aacDecoder_drcApply(HANDLE_AAC_DRC self,void * pSbrDec,CAacDecoderChannelInfo * pAacDecoderChannelInfo,CDrcChannelData * pDrcChData,FIXP_DBL * extGain,int ch,int aacFrameSize,int bSbrPresent)835 void aacDecoder_drcApply(HANDLE_AAC_DRC self, void *pSbrDec,
836                          CAacDecoderChannelInfo *pAacDecoderChannelInfo,
837                          CDrcChannelData *pDrcChData, FIXP_DBL *extGain,
838                          int ch, /* needed only for SBR */
839                          int aacFrameSize, int bSbrPresent) {
840   int band, bin, numBands;
841   int bottom = 0;
842   int modifyBins = 0;
843 
844   FIXP_DBL max_mantissa;
845   INT max_exponent;
846 
847   FIXP_DBL norm_mantissa = FL2FXCONST_DBL(0.5f);
848   INT norm_exponent = 1;
849 
850   FIXP_DBL fact_mantissa[MAX_DRC_BANDS];
851   INT fact_exponent[MAX_DRC_BANDS];
852 
853   CDrcParams *pParams = &self->params;
854 
855   FIXP_DBL *pSpectralCoefficient =
856       SPEC_LONG(pAacDecoderChannelInfo->pSpectralCoefficient);
857   CIcsInfo *pIcsInfo = &pAacDecoderChannelInfo->icsInfo;
858   SHORT *pSpecScale = pAacDecoderChannelInfo->specScale;
859 
860   int winSeq = pIcsInfo->WindowSequence;
861 
862   /* Increment and check expiry counter */
863   if ((pParams->expiryFrame > 0) &&
864       (++pDrcChData->expiryCount >
865        pParams->expiryFrame)) { /* The DRC data is too old, so delete it. */
866     aacDecoder_drcInitChannelData(pDrcChData);
867   }
868 
869   if (self->enable != ON) {
870     sbrDecoder_drcDisable((HANDLE_SBRDECODER)pSbrDec, ch);
871     if (extGain != NULL) {
872       INT gainScale = (INT)*extGain;
873       /* The gain scaling must be passed to the function in the buffer pointed
874        * on by extGain. */
875       if (gainScale >= 0 && gainScale <= DFRACT_BITS) {
876         *extGain = scaleValue(norm_mantissa, norm_exponent - gainScale);
877       } else {
878         FDK_ASSERT(0);
879       }
880     }
881     return;
882   }
883 
884   numBands = pDrcChData->numBands;
885 
886   /* If program reference normalization is done in the digital domain,
887   modify factor to perform normalization.  prog_ref_level can
888   alternatively be passed to the system for modification of the level in
889   the analog domain.  Analog level modification avoids problems with
890   reduced DAC SNR (if signal is attenuated) or clipping (if signal is
891   boosted) */
892 
893   if (pParams->targetRefLevel >= 0) {
894     /* 0.5^((targetRefLevel - progRefLevel)/24) */
895     norm_mantissa =
896         fLdPow(FL2FXCONST_DBL(-1.0), /* log2(0.5) */
897                0,
898                (FIXP_DBL)((INT)(FL2FXCONST_DBL(1.0f / 24.0) >> 3) *
899                           (INT)(pParams->targetRefLevel - self->progRefLevel)),
900                3, &norm_exponent);
901   }
902   /* Always export the normalization gain (if possible). */
903   if (extGain != NULL) {
904     INT gainScale = (INT)*extGain;
905     /* The gain scaling must be passed to the function in the buffer pointed on
906      * by extGain. */
907     if (gainScale >= 0 && gainScale <= DFRACT_BITS) {
908       *extGain = scaleValue(norm_mantissa, norm_exponent - gainScale);
909     } else {
910       FDK_ASSERT(0);
911     }
912   }
913   if (self->params.applyDigitalNorm == OFF) {
914     /* Reset normalization gain since this module must not apply it */
915     norm_mantissa = FL2FXCONST_DBL(0.5f);
916     norm_exponent = 1;
917   }
918 
919   /* calc scale factors */
920   for (band = 0; band < numBands; band++) {
921     UCHAR drcVal = pDrcChData->drcValue[band];
922 
923     fact_mantissa[band] = FL2FXCONST_DBL(0.5f);
924     fact_exponent[band] = 1;
925 
926     if ((pParams->applyHeavyCompression == ON) &&
927         ((AACDEC_DRC_PAYLOAD_TYPE)pDrcChData->drcDataType ==
928          DVB_DRC_ANC_DATA)) {
929       INT compressionFactorVal_e;
930       int valX, valY;
931 
932       valX = drcVal >> 4;
933       valY = drcVal & 0x0F;
934 
935       /* calculate the unscaled heavy compression factor.
936          compressionFactor = 48.164 - 6.0206*valX - 0.4014*valY dB
937          range: -48.166 dB to 48.164 dB */
938       if (drcVal != 0x7F) {
939         fact_mantissa[band] = fPowInt(
940             FL2FXCONST_DBL(0.95483867181), /* -0.4014dB = 0.95483867181 */
941             0, valY, &compressionFactorVal_e);
942 
943         /* -0.0008dB (48.164 - 6.0206*8 = -0.0008) */
944         fact_mantissa[band] =
945             fMult(FL2FXCONST_DBL(0.99990790084), fact_mantissa[band]);
946 
947         fact_exponent[band] =
948             DVB_COMPRESSION_SCALE - valX + compressionFactorVal_e;
949       }
950     } else if ((AACDEC_DRC_PAYLOAD_TYPE)pDrcChData->drcDataType ==
951                MPEG_DRC_EXT_DATA) {
952       /* apply the scaled dynamic range control words to factor.
953        * if scaling drc_cut (or drc_boost), or control word drc_mantissa is 0
954        * then there is no dynamic range compression
955        *
956        * if pDrcChData->drcSgn[band] is
957        *  1 then gain is < 1 :  factor = 2^(-self->cut   *
958        * pDrcChData->drcMag[band] / 24) 0 then gain is > 1 :  factor = 2^(
959        * self->boost * pDrcChData->drcMag[band] / 24)
960        */
961 
962       if ((drcVal & 0x7F) > 0) {
963         FIXP_DBL tParamVal = (drcVal & 0x80) ? -pParams->cut : pParams->boost;
964 
965         fact_mantissa[band] = f2Pow(
966             (FIXP_DBL)((INT)fMult(FL2FXCONST_DBL(1.0f / 192.0f), tParamVal) *
967                        (drcVal & 0x7F)),
968             3 + DRC_PARAM_SCALE, &fact_exponent[band]);
969       }
970     }
971 
972     fact_mantissa[band] = fMult(fact_mantissa[band], norm_mantissa);
973     fact_exponent[band] += norm_exponent;
974 
975   } /* end loop over bands */
976 
977   /* normalizations */
978   {
979     int res;
980 
981     max_mantissa = FL2FXCONST_DBL(0.0f);
982     max_exponent = 0;
983     for (band = 0; band < numBands; band++) {
984       max_mantissa = fixMax(max_mantissa, fact_mantissa[band]);
985       max_exponent = fixMax(max_exponent, fact_exponent[band]);
986     }
987 
988     /* left shift factors to gain accurancy */
989     res = CntLeadingZeros(max_mantissa) - 1;
990 
991     /* above topmost DRC band gain factor is 1 */
992     if (((pDrcChData->bandTop[fMax(0, numBands - 1)] + 1) << 2) < aacFrameSize)
993       res = 0;
994 
995     if (res > 0) {
996       res = fixMin(res, max_exponent);
997       max_exponent -= res;
998 
999       for (band = 0; band < numBands; band++) {
1000         fact_mantissa[band] <<= res;
1001         fact_exponent[band] -= res;
1002       }
1003     }
1004 
1005     /* normalize magnitudes to one scale factor */
1006     for (band = 0; band < numBands; band++) {
1007       if (fact_exponent[band] < max_exponent) {
1008         fact_mantissa[band] >>= max_exponent - fact_exponent[band];
1009       }
1010       if (fact_mantissa[band] != FL2FXCONST_DBL(0.5f)) {
1011         modifyBins = 1;
1012       }
1013     }
1014     if (max_exponent != 1) {
1015       modifyBins = 1;
1016     }
1017   }
1018 
1019   /*  apply factor to spectral lines
1020    *  short blocks must take care that bands fall on
1021    *  block boundaries!
1022    */
1023   if (!bSbrPresent) {
1024     bottom = 0;
1025 
1026     if (!modifyBins) {
1027       /* We don't have to modify the spectral bins because the fractional part
1028          of all factors is 0.5. In order to keep accurancy we don't apply the
1029          factor but decrease the exponent instead. */
1030       max_exponent -= 1;
1031     } else {
1032       for (band = 0; band < numBands; band++) {
1033         int top = fixMin((int)((pDrcChData->bandTop[band] + 1) << 2),
1034                          aacFrameSize); /* ... * DRC_BAND_MULT; */
1035 
1036         for (bin = bottom; bin < top; bin++) {
1037           pSpectralCoefficient[bin] =
1038               fMult(pSpectralCoefficient[bin], fact_mantissa[band]);
1039         }
1040 
1041         bottom = top;
1042       }
1043     }
1044 
1045     /* above topmost DRC band gain factor is 1 */
1046     if (max_exponent > 0) {
1047       for (bin = bottom; bin < aacFrameSize; bin += 1) {
1048         pSpectralCoefficient[bin] >>= max_exponent;
1049       }
1050     }
1051 
1052     /* adjust scaling */
1053     pSpecScale[0] += max_exponent;
1054 
1055     if (winSeq == BLOCK_SHORT) {
1056       int win;
1057       for (win = 1; win < 8; win++) {
1058         pSpecScale[win] += max_exponent;
1059       }
1060     }
1061   } else {
1062     HANDLE_SBRDECODER hSbrDecoder = (HANDLE_SBRDECODER)pSbrDec;
1063     numBands = pDrcChData->numBands;
1064 
1065     /* feed factors into SBR decoder for application in QMF domain. */
1066     sbrDecoder_drcFeedChannel(hSbrDecoder, ch, numBands, fact_mantissa,
1067                               max_exponent, pDrcChData->drcInterpolationScheme,
1068                               winSeq, pDrcChData->bandTop);
1069   }
1070 
1071   return;
1072 }
1073 
1074 /*
1075  * DRC parameter and presentation mode handling
1076  */
aacDecoder_drcParameterHandling(HANDLE_AAC_DRC self,INT aacNumChannels,SCHAR prevDrcProgRefLevel,SCHAR prevDrcPresMode)1077 static void aacDecoder_drcParameterHandling(HANDLE_AAC_DRC self,
1078                                             INT aacNumChannels,
1079                                             SCHAR prevDrcProgRefLevel,
1080                                             SCHAR prevDrcPresMode) {
1081   int isDownmix, isMonoDownmix, isStereoDownmix;
1082   int dDmx, dHr;
1083   AACDEC_DRC_PARAMETER_HANDLING drcParameterHandling;
1084   CDrcParams *p;
1085 
1086   FDK_ASSERT(self != NULL);
1087 
1088   p = &self->params;
1089 
1090   if (self->progRefLevel != prevDrcProgRefLevel) self->update = 1;
1091 
1092   if (self->presMode != prevDrcPresMode) self->update = 1;
1093 
1094   if (self->prevAacNumChannels != aacNumChannels) self->update = 1;
1095 
1096   /* return if no relevant parameter has changed */
1097   if (!self->update) {
1098     return;
1099   }
1100 
1101   /* derive downmix property. aacNumChannels: number of channels in aac stream,
1102    * numOutChannels: number of output channels */
1103   isDownmix = (aacNumChannels > self->numOutChannels);
1104   isDownmix = (isDownmix && (self->numOutChannels > 0));
1105   isMonoDownmix = (isDownmix && (self->numOutChannels == 1));
1106   isStereoDownmix = (isDownmix && (self->numOutChannels == 2));
1107 
1108   if ((self->presMode == 1) || (self->presMode == 2)) {
1109     drcParameterHandling = (AACDEC_DRC_PARAMETER_HANDLING)self->presMode;
1110   } else { /* no presentation mode -> use parameter handling specified by
1111               AAC_DRC_DEFAULT_PRESENTATION_MODE */
1112     drcParameterHandling = p->defaultPresentationMode;
1113   }
1114 
1115   /* by default, do as desired */
1116   p->cut = p->usrCut;
1117   p->boost = p->usrBoost;
1118   p->applyHeavyCompression = p->usrApplyHeavyCompression;
1119 
1120   switch (drcParameterHandling) {
1121     case DISABLED_PARAMETER_HANDLING:
1122     default:
1123       /* use drc parameters as requested */
1124       break;
1125 
1126     case ENABLED_PARAMETER_HANDLING:
1127       /* dDmx: estimated headroom reduction due to downmix, format: -1/4*dB
1128          dDmx = floor(-4*20*log10(aacNumChannels/numOutChannels)) */
1129       if (isDownmix) {
1130         FIXP_DBL dmxTmp;
1131         int e_log, e_mult;
1132         dmxTmp = fDivNorm(self->numOutChannels,
1133                           aacNumChannels); /* inverse division ->
1134                                               negative sign after
1135                                               logarithm */
1136         dmxTmp = fLog2(dmxTmp, 0, &e_log);
1137         dmxTmp = fMultNorm(
1138             dmxTmp, FL2FXCONST_DBL(4.0f * 20.0f * 0.30103f / (float)(1 << 5)),
1139             &e_mult); /* e = e_log + e_mult + 5 */
1140         dDmx = (int)scaleValue(dmxTmp, e_log + e_mult + 5 - (DFRACT_BITS - 1));
1141       } else {
1142         dDmx = 0;
1143       }
1144 
1145       /* dHr: Full estimated (decoder) headroom reduction due to loudness
1146        * normalisation (DTL - PRL) and downmix. Format: -1/4*dB */
1147       if (p->targetRefLevel >= 0) { /* if target level is provided */
1148         dHr = p->targetRefLevel + dDmx - self->progRefLevel;
1149       } else {
1150         dHr = dDmx;
1151       }
1152 
1153       if (dHr < 0) { /* if headroom is reduced */
1154         /* Use compression, but as little as possible. */
1155         /* eHr: Headroom provided by encoder, format: -1/4 dB */
1156         int eHr = fixMin(p->encoderTargetLevel - self->progRefLevel, 0);
1157         if (eHr <
1158             dHr) { /* if encoder provides more headroom than decoder needs */
1159           /* derive scaling of light DRC */
1160           FIXP_DBL calcFactor_norm;
1161           INT calcFactor; /* fraction of DRC gains that is minimally needed for
1162                              clipping prevention */
1163           calcFactor_norm =
1164               fDivNorm(-dHr, -eHr); /* 0.0 < calcFactor_norm < 1.0 */
1165           calcFactor_norm = calcFactor_norm >> DRC_PARAM_SCALE;
1166           /* quantize to 128 steps */
1167           calcFactor = convert_drcParam(
1168               calcFactor_norm); /* convert to integer value between 0 and 127 */
1169           calcFactor_norm = (FIXP_DBL)(
1170               (INT)(DRC_PARAM_QUANT_STEP >> DRC_PARAM_SCALE) * calcFactor);
1171           p->cut = (calcFactor_norm > p->cut)
1172                        ? calcFactor_norm
1173                        : p->cut; /* use calcFactor_norm as lower limit */
1174         } else {
1175           /* encoder provides equal or less headroom than decoder needs */
1176           /* the time domain limiter must always be active in this case. It is
1177            * assumed that the framework activates it by default */
1178           p->cut = DRC_SCALING_MAX;
1179           if ((dHr - eHr) <=
1180               -4 * DRC_HEAVY_THRESHOLD_DB) { /* use heavy compression if
1181                                                 headroom deficit is equal or
1182                                                 higher than
1183                                                 DRC_HEAVY_THRESHOLD_DB */
1184             p->applyHeavyCompression = ON;
1185           }
1186         }
1187       } else { /* dHr >= 0 */
1188         /* no restrictions required, as headroom is not reduced. */
1189         /* p->cut = p->usrCut; */
1190       }
1191       break;
1192 
1193       /* presentation mode 1 and 2 according to ETSI TS 101 154:
1194          Digital Video Broadcasting (DVB); Specification for the use of Video
1195          and Audio Coding in Broadcasting Applications based on the MPEG-2
1196          Transport Stream, section C.5.4., "Decoding", and Table C.33. Also
1197          according to amendment 4 to ISO/IEC 14496-3, section 4.5.2.14.2.4, and
1198          Table AMD4.11. ISO DRC            -> applyHeavyCompression = OFF (Use
1199          light compression, MPEG-style) Compression_value  ->
1200          applyHeavyCompression = ON  (Use heavy compression, DVB-style) scaling
1201          restricted -> p->cut = DRC_SCALING_MAX */
1202 
1203     case DRC_PRESENTATION_MODE_1: /* presentation mode 1, Light:-31/Heavy:-23 */
1204       if ((p->targetRefLevel >= 0) &&
1205           (p->targetRefLevel <
1206            124)) { /* if target level is provided and > -31 dB */
1207         /* playback up to -23 dB */
1208         p->applyHeavyCompression = ON;
1209       } else { /* target level <= -31 dB or not provided */
1210         /* playback -31 dB */
1211         if (isMonoDownmix || isStereoDownmix) { /* stereo or mono downmixing */
1212           p->cut = DRC_SCALING_MAX;
1213         }
1214       }
1215       break;
1216 
1217     case DRC_PRESENTATION_MODE_2: /* presentation mode 2, Light:-23/Heavy:-23 */
1218       if ((p->targetRefLevel >= 0) &&
1219           (p->targetRefLevel <
1220            124)) { /* if target level is provided and > -31 dB */
1221         /* playback up to -23 dB */
1222         if (isMonoDownmix) { /* if mono downmix */
1223           p->applyHeavyCompression = ON;
1224         } else {
1225           p->applyHeavyCompression = OFF;
1226           p->cut = DRC_SCALING_MAX;
1227         }
1228       } else { /* target level <= -31 dB or not provided */
1229         /* playback -31 dB */
1230         p->applyHeavyCompression = OFF;
1231         if (isMonoDownmix || isStereoDownmix) { /* stereo or mono downmixing */
1232           p->cut = DRC_SCALING_MAX;
1233         }
1234       }
1235       break;
1236   } /*  switch (drcParameterHandling) */
1237 
1238   /* With heavy compression, there is no scaling.
1239      Scaling factors are set for notification only. */
1240   if (p->applyHeavyCompression == ON) {
1241     p->boost = DRC_SCALING_MAX;
1242     p->cut = DRC_SCALING_MAX;
1243   }
1244 
1245   /* switch on/off processing */
1246   self->enable = ((p->boost > (FIXP_DBL)0) || (p->cut > (FIXP_DBL)0) ||
1247                   (p->applyHeavyCompression == ON) || (p->targetRefLevel >= 0));
1248   self->enable = (self->enable && !self->uniDrcPrecedence);
1249 
1250   self->prevAacNumChannels = aacNumChannels;
1251   self->update = 0;
1252 }
1253 
1254 /*
1255  * Prepare DRC processing
1256  *   Valid return values are:
1257  *     -1 : An unexpected error occured.
1258  *      0 : No error and no valid DRC data available.
1259  *      1 : No error and valid DRC data has been mapped.
1260  */
aacDecoder_drcProlog(HANDLE_AAC_DRC self,HANDLE_FDK_BITSTREAM hBs,CAacDecoderStaticChannelInfo * pAacDecoderStaticChannelInfo[],UCHAR pceInstanceTag,UCHAR channelMapping[],int validChannels)1261 int aacDecoder_drcProlog(
1262     HANDLE_AAC_DRC self, HANDLE_FDK_BITSTREAM hBs,
1263     CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo[],
1264     UCHAR pceInstanceTag,
1265     UCHAR channelMapping[], /* Channel mapping translating drcChannel index to
1266                                canonical channel index */
1267     int validChannels) {
1268   int result = 0;
1269 
1270   if (self == NULL) {
1271     return -1;
1272   }
1273 
1274   if (!self->params.bsDelayEnable) {
1275     /* keep previous progRefLevel and presMode for update flag in
1276      * drcParameterHandling */
1277     INT prevPRL, prevPM = 0;
1278     prevPRL = self->progRefLevel;
1279     prevPM = self->presMode;
1280 
1281     result = aacDecoder_drcExtractAndMap(
1282         self, hBs, pAacDecoderStaticChannelInfo, pceInstanceTag, channelMapping,
1283         validChannels);
1284 
1285     if (result < 0) {
1286       return result;
1287     }
1288 
1289     /* Drc parameter handling */
1290     aacDecoder_drcParameterHandling(self, validChannels, prevPRL, prevPM);
1291   }
1292 
1293   return result;
1294 }
1295 
1296 /*
1297  * Finalize DRC processing
1298  *   Valid return values are:
1299  *     -1 : An unexpected error occured.
1300  *      0 : No error and no valid DRC data available.
1301  *      1 : No error and valid DRC data has been mapped.
1302  */
aacDecoder_drcEpilog(HANDLE_AAC_DRC self,HANDLE_FDK_BITSTREAM hBs,CAacDecoderStaticChannelInfo * pAacDecoderStaticChannelInfo[],UCHAR pceInstanceTag,UCHAR channelMapping[],int validChannels)1303 int aacDecoder_drcEpilog(
1304     HANDLE_AAC_DRC self, HANDLE_FDK_BITSTREAM hBs,
1305     CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo[],
1306     UCHAR pceInstanceTag,
1307     UCHAR channelMapping[], /* Channel mapping translating drcChannel index to
1308                                canonical channel index */
1309     int validChannels) {
1310   int result = 0;
1311 
1312   if (self == NULL) {
1313     return -1;
1314   }
1315 
1316   if (self->params.bsDelayEnable) {
1317     /* keep previous progRefLevel and presMode for update flag in
1318      * drcParameterHandling */
1319     INT prevPRL, prevPM = 0;
1320     prevPRL = self->progRefLevel;
1321     prevPM = self->presMode;
1322 
1323     result = aacDecoder_drcExtractAndMap(
1324         self, hBs, pAacDecoderStaticChannelInfo, pceInstanceTag, channelMapping,
1325         validChannels);
1326 
1327     if (result < 0) {
1328       return result;
1329     }
1330 
1331     /* Drc parameter handling */
1332     aacDecoder_drcParameterHandling(self, validChannels, prevPRL, prevPM);
1333   }
1334 
1335   return result;
1336 }
1337 
1338 /*
1339  * Export relevant metadata info from bitstream payload.
1340  */
aacDecoder_drcGetInfo(HANDLE_AAC_DRC self,SCHAR * pPresMode,SCHAR * pProgRefLevel)1341 void aacDecoder_drcGetInfo(HANDLE_AAC_DRC self, SCHAR *pPresMode,
1342                            SCHAR *pProgRefLevel) {
1343   if (self != NULL) {
1344     if (pPresMode != NULL) {
1345       *pPresMode = self->presMode;
1346     }
1347     if (pProgRefLevel != NULL) {
1348       if (self->progRefLevelPresent) {
1349         *pProgRefLevel = self->progRefLevel;
1350       } else {
1351         *pProgRefLevel = -1;
1352       }
1353     }
1354   }
1355 }
1356