1*e5436536SAndroid Build Coastguard Worker /* -----------------------------------------------------------------------------
2*e5436536SAndroid Build Coastguard Worker Software License for The Fraunhofer FDK AAC Codec Library for Android
3*e5436536SAndroid Build Coastguard Worker
4*e5436536SAndroid Build Coastguard Worker © Copyright 1995 - 2021 Fraunhofer-Gesellschaft zur Förderung der angewandten
5*e5436536SAndroid Build Coastguard Worker Forschung e.V. All rights reserved.
6*e5436536SAndroid Build Coastguard Worker
7*e5436536SAndroid Build Coastguard Worker 1. INTRODUCTION
8*e5436536SAndroid Build Coastguard Worker The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software
9*e5436536SAndroid Build Coastguard Worker that implements the MPEG Advanced Audio Coding ("AAC") encoding and decoding
10*e5436536SAndroid Build Coastguard Worker scheme for digital audio. This FDK AAC Codec software is intended to be used on
11*e5436536SAndroid Build Coastguard Worker a wide variety of Android devices.
12*e5436536SAndroid Build Coastguard Worker
13*e5436536SAndroid Build Coastguard Worker AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient
14*e5436536SAndroid Build Coastguard Worker general perceptual audio codecs. AAC-ELD is considered the best-performing
15*e5436536SAndroid Build Coastguard Worker full-bandwidth communications codec by independent studies and is widely
16*e5436536SAndroid Build Coastguard Worker deployed. AAC has been standardized by ISO and IEC as part of the MPEG
17*e5436536SAndroid Build Coastguard Worker specifications.
18*e5436536SAndroid Build Coastguard Worker
19*e5436536SAndroid Build Coastguard Worker Patent licenses for necessary patent claims for the FDK AAC Codec (including
20*e5436536SAndroid Build Coastguard Worker those of Fraunhofer) may be obtained through Via Licensing
21*e5436536SAndroid Build Coastguard Worker (www.vialicensing.com) or through the respective patent owners individually for
22*e5436536SAndroid Build Coastguard Worker the purpose of encoding or decoding bit streams in products that are compliant
23*e5436536SAndroid Build Coastguard Worker with the ISO/IEC MPEG audio standards. Please note that most manufacturers of
24*e5436536SAndroid Build Coastguard Worker Android devices already license these patent claims through Via Licensing or
25*e5436536SAndroid Build Coastguard Worker directly from the patent owners, and therefore FDK AAC Codec software may
26*e5436536SAndroid Build Coastguard Worker already be covered under those patent licenses when it is used for those
27*e5436536SAndroid Build Coastguard Worker licensed purposes only.
28*e5436536SAndroid Build Coastguard Worker
29*e5436536SAndroid Build Coastguard Worker Commercially-licensed AAC software libraries, including floating-point versions
30*e5436536SAndroid Build Coastguard Worker with enhanced sound quality, are also available from Fraunhofer. Users are
31*e5436536SAndroid Build Coastguard Worker encouraged to check the Fraunhofer website for additional applications
32*e5436536SAndroid Build Coastguard Worker information and documentation.
33*e5436536SAndroid Build Coastguard Worker
34*e5436536SAndroid Build Coastguard Worker 2. COPYRIGHT LICENSE
35*e5436536SAndroid Build Coastguard Worker
36*e5436536SAndroid Build Coastguard Worker Redistribution and use in source and binary forms, with or without modification,
37*e5436536SAndroid Build Coastguard Worker are permitted without payment of copyright license fees provided that you
38*e5436536SAndroid Build Coastguard Worker satisfy the following conditions:
39*e5436536SAndroid Build Coastguard Worker
40*e5436536SAndroid Build Coastguard Worker You must retain the complete text of this software license in redistributions of
41*e5436536SAndroid Build Coastguard Worker the FDK AAC Codec or your modifications thereto in source code form.
42*e5436536SAndroid Build Coastguard Worker
43*e5436536SAndroid Build Coastguard Worker You must retain the complete text of this software license in the documentation
44*e5436536SAndroid Build Coastguard Worker and/or other materials provided with redistributions of the FDK AAC Codec or
45*e5436536SAndroid Build Coastguard Worker your modifications thereto in binary form. You must make available free of
46*e5436536SAndroid Build Coastguard Worker charge copies of the complete source code of the FDK AAC Codec and your
47*e5436536SAndroid Build Coastguard Worker modifications thereto to recipients of copies in binary form.
48*e5436536SAndroid Build Coastguard Worker
49*e5436536SAndroid Build Coastguard Worker The name of Fraunhofer may not be used to endorse or promote products derived
50*e5436536SAndroid Build Coastguard Worker from this library without prior written permission.
51*e5436536SAndroid Build Coastguard Worker
52*e5436536SAndroid Build Coastguard Worker You may not charge copyright license fees for anyone to use, copy or distribute
53*e5436536SAndroid Build Coastguard Worker the FDK AAC Codec software or your modifications thereto.
54*e5436536SAndroid Build Coastguard Worker
55*e5436536SAndroid Build Coastguard Worker Your modified versions of the FDK AAC Codec must carry prominent notices stating
56*e5436536SAndroid Build Coastguard Worker that you changed the software and the date of any change. For modified versions
57*e5436536SAndroid Build Coastguard Worker of the FDK AAC Codec, the term "Fraunhofer FDK AAC Codec Library for Android"
58*e5436536SAndroid Build Coastguard Worker must be replaced by the term "Third-Party Modified Version of the Fraunhofer FDK
59*e5436536SAndroid Build Coastguard Worker AAC Codec Library for Android."
60*e5436536SAndroid Build Coastguard Worker
61*e5436536SAndroid Build Coastguard Worker 3. NO PATENT LICENSE
62*e5436536SAndroid Build Coastguard Worker
63*e5436536SAndroid Build Coastguard Worker NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without
64*e5436536SAndroid Build Coastguard Worker limitation the patents of Fraunhofer, ARE GRANTED BY THIS SOFTWARE LICENSE.
65*e5436536SAndroid Build Coastguard Worker Fraunhofer provides no warranty of patent non-infringement with respect to this
66*e5436536SAndroid Build Coastguard Worker software.
67*e5436536SAndroid Build Coastguard Worker
68*e5436536SAndroid Build Coastguard Worker You may use this FDK AAC Codec software or modifications thereto only for
69*e5436536SAndroid Build Coastguard Worker purposes that are authorized by appropriate patent licenses.
70*e5436536SAndroid Build Coastguard Worker
71*e5436536SAndroid Build Coastguard Worker 4. DISCLAIMER
72*e5436536SAndroid Build Coastguard Worker
73*e5436536SAndroid Build Coastguard Worker This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright
74*e5436536SAndroid Build Coastguard Worker holders and contributors "AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES,
75*e5436536SAndroid Build Coastguard Worker including but not limited to the implied warranties of merchantability and
76*e5436536SAndroid Build Coastguard Worker fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
77*e5436536SAndroid Build Coastguard Worker CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary,
78*e5436536SAndroid Build Coastguard Worker or consequential damages, including but not limited to procurement of substitute
79*e5436536SAndroid Build Coastguard Worker goods or services; loss of use, data, or profits, or business interruption,
80*e5436536SAndroid Build Coastguard Worker however caused and on any theory of liability, whether in contract, strict
81*e5436536SAndroid Build Coastguard Worker liability, or tort (including negligence), arising in any way out of the use of
82*e5436536SAndroid Build Coastguard Worker this software, even if advised of the possibility of such damage.
83*e5436536SAndroid Build Coastguard Worker
84*e5436536SAndroid Build Coastguard Worker 5. CONTACT INFORMATION
85*e5436536SAndroid Build Coastguard Worker
86*e5436536SAndroid Build Coastguard Worker Fraunhofer Institute for Integrated Circuits IIS
87*e5436536SAndroid Build Coastguard Worker Attention: Audio and Multimedia Departments - FDK AAC LL
88*e5436536SAndroid Build Coastguard Worker Am Wolfsmantel 33
89*e5436536SAndroid Build Coastguard Worker 91058 Erlangen, Germany
90*e5436536SAndroid Build Coastguard Worker
91*e5436536SAndroid Build Coastguard Worker www.iis.fraunhofer.de/amm
92*e5436536SAndroid Build Coastguard Worker [email protected]
93*e5436536SAndroid Build Coastguard Worker ----------------------------------------------------------------------------- */
94*e5436536SAndroid Build Coastguard Worker
95*e5436536SAndroid Build Coastguard Worker /******************* MPEG transport format decoder library *********************
96*e5436536SAndroid Build Coastguard Worker
97*e5436536SAndroid Build Coastguard Worker Author(s): Daniel Homm
98*e5436536SAndroid Build Coastguard Worker
99*e5436536SAndroid Build Coastguard Worker Description:
100*e5436536SAndroid Build Coastguard Worker
101*e5436536SAndroid Build Coastguard Worker *******************************************************************************/
102*e5436536SAndroid Build Coastguard Worker
103*e5436536SAndroid Build Coastguard Worker #include "tpdec_latm.h"
104*e5436536SAndroid Build Coastguard Worker
105*e5436536SAndroid Build Coastguard Worker #include "FDK_bitstream.h"
106*e5436536SAndroid Build Coastguard Worker
107*e5436536SAndroid Build Coastguard Worker #define TPDEC_TRACKINDEX(p, l) (1 * (p) + (l))
108*e5436536SAndroid Build Coastguard Worker
CLatmDemux_GetValue(HANDLE_FDK_BITSTREAM bs)109*e5436536SAndroid Build Coastguard Worker static UINT CLatmDemux_GetValue(HANDLE_FDK_BITSTREAM bs) {
110*e5436536SAndroid Build Coastguard Worker UCHAR bytesForValue = 0, tmp = 0;
111*e5436536SAndroid Build Coastguard Worker int value = 0;
112*e5436536SAndroid Build Coastguard Worker
113*e5436536SAndroid Build Coastguard Worker bytesForValue = (UCHAR)FDKreadBits(bs, 2);
114*e5436536SAndroid Build Coastguard Worker
115*e5436536SAndroid Build Coastguard Worker for (UINT i = 0; i <= bytesForValue; i++) {
116*e5436536SAndroid Build Coastguard Worker value <<= 8;
117*e5436536SAndroid Build Coastguard Worker tmp = (UCHAR)FDKreadBits(bs, 8);
118*e5436536SAndroid Build Coastguard Worker value += tmp;
119*e5436536SAndroid Build Coastguard Worker }
120*e5436536SAndroid Build Coastguard Worker
121*e5436536SAndroid Build Coastguard Worker return value;
122*e5436536SAndroid Build Coastguard Worker }
123*e5436536SAndroid Build Coastguard Worker
CLatmDemux_ReadAudioMuxElement(HANDLE_FDK_BITSTREAM bs,CLatmDemux * pLatmDemux,int m_muxConfigPresent,CSTpCallBacks * pTpDecCallbacks,CSAudioSpecificConfig * pAsc,int * pfConfigFound)124*e5436536SAndroid Build Coastguard Worker static TRANSPORTDEC_ERROR CLatmDemux_ReadAudioMuxElement(
125*e5436536SAndroid Build Coastguard Worker HANDLE_FDK_BITSTREAM bs, CLatmDemux *pLatmDemux, int m_muxConfigPresent,
126*e5436536SAndroid Build Coastguard Worker CSTpCallBacks *pTpDecCallbacks, CSAudioSpecificConfig *pAsc,
127*e5436536SAndroid Build Coastguard Worker int *pfConfigFound) {
128*e5436536SAndroid Build Coastguard Worker TRANSPORTDEC_ERROR ErrorStatus = TRANSPORTDEC_OK;
129*e5436536SAndroid Build Coastguard Worker
130*e5436536SAndroid Build Coastguard Worker if (m_muxConfigPresent) {
131*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_useSameStreamMux = FDKreadBits(bs, 1);
132*e5436536SAndroid Build Coastguard Worker
133*e5436536SAndroid Build Coastguard Worker if (!pLatmDemux->m_useSameStreamMux) {
134*e5436536SAndroid Build Coastguard Worker int i;
135*e5436536SAndroid Build Coastguard Worker UCHAR configChanged = 0;
136*e5436536SAndroid Build Coastguard Worker UCHAR configMode = 0;
137*e5436536SAndroid Build Coastguard Worker
138*e5436536SAndroid Build Coastguard Worker FDK_BITSTREAM bsAnchor;
139*e5436536SAndroid Build Coastguard Worker
140*e5436536SAndroid Build Coastguard Worker FDK_BITSTREAM bsAnchorDummyParse;
141*e5436536SAndroid Build Coastguard Worker
142*e5436536SAndroid Build Coastguard Worker if (!pLatmDemux->applyAsc) {
143*e5436536SAndroid Build Coastguard Worker bsAnchorDummyParse = *bs;
144*e5436536SAndroid Build Coastguard Worker pLatmDemux->newCfgHasAudioPreRoll = 0;
145*e5436536SAndroid Build Coastguard Worker /* do dummy-parsing of ASC to determine if there is an audioPreRoll */
146*e5436536SAndroid Build Coastguard Worker configMode |= AC_CM_DET_CFG_CHANGE;
147*e5436536SAndroid Build Coastguard Worker if (TRANSPORTDEC_OK !=
148*e5436536SAndroid Build Coastguard Worker (ErrorStatus = CLatmDemux_ReadStreamMuxConfig(
149*e5436536SAndroid Build Coastguard Worker bs, pLatmDemux, pTpDecCallbacks, pAsc, pfConfigFound,
150*e5436536SAndroid Build Coastguard Worker configMode, configChanged))) {
151*e5436536SAndroid Build Coastguard Worker goto bail;
152*e5436536SAndroid Build Coastguard Worker }
153*e5436536SAndroid Build Coastguard Worker
154*e5436536SAndroid Build Coastguard Worker /* Allow flushing only when audioPreroll functionality is enabled in
155*e5436536SAndroid Build Coastguard Worker * current and new config otherwise the new config can be applied
156*e5436536SAndroid Build Coastguard Worker * immediately. */
157*e5436536SAndroid Build Coastguard Worker if (pAsc->m_sc.m_usacConfig.element[0]
158*e5436536SAndroid Build Coastguard Worker .extElement.usacExtElementHasAudioPreRoll &&
159*e5436536SAndroid Build Coastguard Worker pLatmDemux->newCfgHasAudioPreRoll) {
160*e5436536SAndroid Build Coastguard Worker pLatmDemux->newCfgHasAudioPreRoll = 0;
161*e5436536SAndroid Build Coastguard Worker /* with audioPreRoll we must flush before applying new cfg */
162*e5436536SAndroid Build Coastguard Worker pLatmDemux->applyAsc = 0;
163*e5436536SAndroid Build Coastguard Worker } else {
164*e5436536SAndroid Build Coastguard Worker *bs = bsAnchorDummyParse;
165*e5436536SAndroid Build Coastguard Worker pLatmDemux->applyAsc = 1; /* apply new config immediate */
166*e5436536SAndroid Build Coastguard Worker }
167*e5436536SAndroid Build Coastguard Worker }
168*e5436536SAndroid Build Coastguard Worker
169*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->applyAsc) {
170*e5436536SAndroid Build Coastguard Worker for (i = 0; i < 2; i++) {
171*e5436536SAndroid Build Coastguard Worker configMode = 0;
172*e5436536SAndroid Build Coastguard Worker
173*e5436536SAndroid Build Coastguard Worker if (i == 0) {
174*e5436536SAndroid Build Coastguard Worker configMode |= AC_CM_DET_CFG_CHANGE;
175*e5436536SAndroid Build Coastguard Worker bsAnchor = *bs;
176*e5436536SAndroid Build Coastguard Worker } else {
177*e5436536SAndroid Build Coastguard Worker configMode |= AC_CM_ALLOC_MEM;
178*e5436536SAndroid Build Coastguard Worker *bs = bsAnchor;
179*e5436536SAndroid Build Coastguard Worker }
180*e5436536SAndroid Build Coastguard Worker
181*e5436536SAndroid Build Coastguard Worker if (TRANSPORTDEC_OK !=
182*e5436536SAndroid Build Coastguard Worker (ErrorStatus = CLatmDemux_ReadStreamMuxConfig(
183*e5436536SAndroid Build Coastguard Worker bs, pLatmDemux, pTpDecCallbacks, pAsc, pfConfigFound,
184*e5436536SAndroid Build Coastguard Worker configMode, configChanged))) {
185*e5436536SAndroid Build Coastguard Worker goto bail;
186*e5436536SAndroid Build Coastguard Worker }
187*e5436536SAndroid Build Coastguard Worker
188*e5436536SAndroid Build Coastguard Worker if (ErrorStatus == TRANSPORTDEC_OK) {
189*e5436536SAndroid Build Coastguard Worker if ((i == 0) && (pAsc->AacConfigChanged || pAsc->SbrConfigChanged ||
190*e5436536SAndroid Build Coastguard Worker pAsc->SacConfigChanged)) {
191*e5436536SAndroid Build Coastguard Worker int errC;
192*e5436536SAndroid Build Coastguard Worker
193*e5436536SAndroid Build Coastguard Worker configChanged = 1;
194*e5436536SAndroid Build Coastguard Worker errC = pTpDecCallbacks->cbFreeMem(pTpDecCallbacks->cbFreeMemData,
195*e5436536SAndroid Build Coastguard Worker pAsc);
196*e5436536SAndroid Build Coastguard Worker if (errC != 0) {
197*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
198*e5436536SAndroid Build Coastguard Worker goto bail;
199*e5436536SAndroid Build Coastguard Worker }
200*e5436536SAndroid Build Coastguard Worker }
201*e5436536SAndroid Build Coastguard Worker }
202*e5436536SAndroid Build Coastguard Worker }
203*e5436536SAndroid Build Coastguard Worker }
204*e5436536SAndroid Build Coastguard Worker }
205*e5436536SAndroid Build Coastguard Worker }
206*e5436536SAndroid Build Coastguard Worker
207*e5436536SAndroid Build Coastguard Worker /* If there was no configuration read, its not possible to parse
208*e5436536SAndroid Build Coastguard Worker * PayloadLengthInfo below. */
209*e5436536SAndroid Build Coastguard Worker if (!*pfConfigFound) {
210*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_SYNC_ERROR;
211*e5436536SAndroid Build Coastguard Worker goto bail;
212*e5436536SAndroid Build Coastguard Worker }
213*e5436536SAndroid Build Coastguard Worker
214*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_AudioMuxVersionA == 0) {
215*e5436536SAndroid Build Coastguard Worker /* Do only once per call, because parsing and decoding is done in-line. */
216*e5436536SAndroid Build Coastguard Worker if (TRANSPORTDEC_OK !=
217*e5436536SAndroid Build Coastguard Worker (ErrorStatus = CLatmDemux_ReadPayloadLengthInfo(bs, pLatmDemux))) {
218*e5436536SAndroid Build Coastguard Worker *pfConfigFound = 0;
219*e5436536SAndroid Build Coastguard Worker goto bail;
220*e5436536SAndroid Build Coastguard Worker }
221*e5436536SAndroid Build Coastguard Worker } else {
222*e5436536SAndroid Build Coastguard Worker /* audioMuxVersionA > 0 is reserved for future extensions */
223*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_UNSUPPORTED_FORMAT;
224*e5436536SAndroid Build Coastguard Worker *pfConfigFound = 0;
225*e5436536SAndroid Build Coastguard Worker goto bail;
226*e5436536SAndroid Build Coastguard Worker }
227*e5436536SAndroid Build Coastguard Worker
228*e5436536SAndroid Build Coastguard Worker bail:
229*e5436536SAndroid Build Coastguard Worker if (ErrorStatus != TRANSPORTDEC_OK) {
230*e5436536SAndroid Build Coastguard Worker pLatmDemux->applyAsc = 1;
231*e5436536SAndroid Build Coastguard Worker }
232*e5436536SAndroid Build Coastguard Worker
233*e5436536SAndroid Build Coastguard Worker return (ErrorStatus);
234*e5436536SAndroid Build Coastguard Worker }
235*e5436536SAndroid Build Coastguard Worker
CLatmDemux_Read(HANDLE_FDK_BITSTREAM bs,CLatmDemux * pLatmDemux,TRANSPORT_TYPE tt,CSTpCallBacks * pTpDecCallbacks,CSAudioSpecificConfig * pAsc,int * pfConfigFound,const INT ignoreBufferFullness)236*e5436536SAndroid Build Coastguard Worker TRANSPORTDEC_ERROR CLatmDemux_Read(HANDLE_FDK_BITSTREAM bs,
237*e5436536SAndroid Build Coastguard Worker CLatmDemux *pLatmDemux, TRANSPORT_TYPE tt,
238*e5436536SAndroid Build Coastguard Worker CSTpCallBacks *pTpDecCallbacks,
239*e5436536SAndroid Build Coastguard Worker CSAudioSpecificConfig *pAsc,
240*e5436536SAndroid Build Coastguard Worker int *pfConfigFound,
241*e5436536SAndroid Build Coastguard Worker const INT ignoreBufferFullness) {
242*e5436536SAndroid Build Coastguard Worker UINT cntBits;
243*e5436536SAndroid Build Coastguard Worker UINT cmpBufferFullness;
244*e5436536SAndroid Build Coastguard Worker UINT audioMuxLengthBytesLast = 0;
245*e5436536SAndroid Build Coastguard Worker TRANSPORTDEC_ERROR ErrorStatus = TRANSPORTDEC_OK;
246*e5436536SAndroid Build Coastguard Worker
247*e5436536SAndroid Build Coastguard Worker cntBits = FDKgetValidBits(bs);
248*e5436536SAndroid Build Coastguard Worker
249*e5436536SAndroid Build Coastguard Worker if ((INT)cntBits < MIN_LATM_HEADERLENGTH) {
250*e5436536SAndroid Build Coastguard Worker return TRANSPORTDEC_NOT_ENOUGH_BITS;
251*e5436536SAndroid Build Coastguard Worker }
252*e5436536SAndroid Build Coastguard Worker
253*e5436536SAndroid Build Coastguard Worker if (TRANSPORTDEC_OK != (ErrorStatus = CLatmDemux_ReadAudioMuxElement(
254*e5436536SAndroid Build Coastguard Worker bs, pLatmDemux, (tt != TT_MP4_LATM_MCP0),
255*e5436536SAndroid Build Coastguard Worker pTpDecCallbacks, pAsc, pfConfigFound)))
256*e5436536SAndroid Build Coastguard Worker return (ErrorStatus);
257*e5436536SAndroid Build Coastguard Worker
258*e5436536SAndroid Build Coastguard Worker if (!ignoreBufferFullness) {
259*e5436536SAndroid Build Coastguard Worker cmpBufferFullness =
260*e5436536SAndroid Build Coastguard Worker 24 + audioMuxLengthBytesLast * 8 +
261*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_linfo[0][0].m_bufferFullness *
262*e5436536SAndroid Build Coastguard Worker pAsc[TPDEC_TRACKINDEX(0, 0)].m_channelConfiguration * 32;
263*e5436536SAndroid Build Coastguard Worker
264*e5436536SAndroid Build Coastguard Worker /* evaluate buffer fullness */
265*e5436536SAndroid Build Coastguard Worker
266*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_linfo[0][0].m_bufferFullness != 0xFF) {
267*e5436536SAndroid Build Coastguard Worker if (!pLatmDemux->BufferFullnessAchieved) {
268*e5436536SAndroid Build Coastguard Worker if (cntBits < cmpBufferFullness) {
269*e5436536SAndroid Build Coastguard Worker /* condition for start of decoding is not fulfilled */
270*e5436536SAndroid Build Coastguard Worker
271*e5436536SAndroid Build Coastguard Worker /* the current frame will not be decoded */
272*e5436536SAndroid Build Coastguard Worker return TRANSPORTDEC_NOT_ENOUGH_BITS;
273*e5436536SAndroid Build Coastguard Worker } else {
274*e5436536SAndroid Build Coastguard Worker pLatmDemux->BufferFullnessAchieved = 1;
275*e5436536SAndroid Build Coastguard Worker }
276*e5436536SAndroid Build Coastguard Worker }
277*e5436536SAndroid Build Coastguard Worker }
278*e5436536SAndroid Build Coastguard Worker }
279*e5436536SAndroid Build Coastguard Worker
280*e5436536SAndroid Build Coastguard Worker return (ErrorStatus);
281*e5436536SAndroid Build Coastguard Worker }
282*e5436536SAndroid Build Coastguard Worker
CLatmDemux_ReadStreamMuxConfig(HANDLE_FDK_BITSTREAM bs,CLatmDemux * pLatmDemux,CSTpCallBacks * pTpDecCallbacks,CSAudioSpecificConfig * pAsc,int * pfConfigFound,UCHAR configMode,UCHAR configChanged)283*e5436536SAndroid Build Coastguard Worker TRANSPORTDEC_ERROR CLatmDemux_ReadStreamMuxConfig(
284*e5436536SAndroid Build Coastguard Worker HANDLE_FDK_BITSTREAM bs, CLatmDemux *pLatmDemux,
285*e5436536SAndroid Build Coastguard Worker CSTpCallBacks *pTpDecCallbacks, CSAudioSpecificConfig *pAsc,
286*e5436536SAndroid Build Coastguard Worker int *pfConfigFound, UCHAR configMode, UCHAR configChanged) {
287*e5436536SAndroid Build Coastguard Worker CSAudioSpecificConfig ascDummy; /* the actual config is needed for flushing,
288*e5436536SAndroid Build Coastguard Worker after that new config can be parsed */
289*e5436536SAndroid Build Coastguard Worker CSAudioSpecificConfig *pAscDummy;
290*e5436536SAndroid Build Coastguard Worker pAscDummy = &ascDummy;
291*e5436536SAndroid Build Coastguard Worker pLatmDemux->usacExplicitCfgChanged = 0;
292*e5436536SAndroid Build Coastguard Worker LATM_LAYER_INFO *p_linfo = NULL;
293*e5436536SAndroid Build Coastguard Worker TRANSPORTDEC_ERROR ErrorStatus = TRANSPORTDEC_OK;
294*e5436536SAndroid Build Coastguard Worker UCHAR updateConfig[1 * 1] = {0};
295*e5436536SAndroid Build Coastguard Worker
296*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_AudioMuxVersion = FDKreadBits(bs, 1);
297*e5436536SAndroid Build Coastguard Worker
298*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_AudioMuxVersion == 0) {
299*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_AudioMuxVersionA = 0;
300*e5436536SAndroid Build Coastguard Worker } else {
301*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_AudioMuxVersionA = FDKreadBits(bs, 1);
302*e5436536SAndroid Build Coastguard Worker }
303*e5436536SAndroid Build Coastguard Worker
304*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_AudioMuxVersionA == 0) {
305*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_AudioMuxVersion == 1) {
306*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_taraBufferFullness = CLatmDemux_GetValue(bs);
307*e5436536SAndroid Build Coastguard Worker }
308*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_allStreamsSameTimeFraming = FDKreadBits(bs, 1);
309*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_noSubFrames = FDKreadBits(bs, 6) + 1;
310*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_numProgram = FDKreadBits(bs, 4) + 1;
311*e5436536SAndroid Build Coastguard Worker
312*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_numProgram > LATM_MAX_PROG) {
313*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_UNSUPPORTED_FORMAT;
314*e5436536SAndroid Build Coastguard Worker goto bail;
315*e5436536SAndroid Build Coastguard Worker }
316*e5436536SAndroid Build Coastguard Worker
317*e5436536SAndroid Build Coastguard Worker int idCnt = 0;
318*e5436536SAndroid Build Coastguard Worker for (UINT prog = 0; prog < pLatmDemux->m_numProgram; prog++) {
319*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_numLayer[prog] = FDKreadBits(bs, 3) + 1;
320*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_numLayer[prog] > LATM_MAX_LAYER) {
321*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_UNSUPPORTED_FORMAT;
322*e5436536SAndroid Build Coastguard Worker goto bail;
323*e5436536SAndroid Build Coastguard Worker }
324*e5436536SAndroid Build Coastguard Worker
325*e5436536SAndroid Build Coastguard Worker for (UINT lay = 0; lay < pLatmDemux->m_numLayer[prog]; lay++) {
326*e5436536SAndroid Build Coastguard Worker int useSameConfig;
327*e5436536SAndroid Build Coastguard Worker p_linfo = &pLatmDemux->m_linfo[prog][lay];
328*e5436536SAndroid Build Coastguard Worker
329*e5436536SAndroid Build Coastguard Worker p_linfo->m_streamID = idCnt++;
330*e5436536SAndroid Build Coastguard Worker p_linfo->m_frameLengthInBits = 0;
331*e5436536SAndroid Build Coastguard Worker
332*e5436536SAndroid Build Coastguard Worker if ((prog == 0) && (lay == 0)) {
333*e5436536SAndroid Build Coastguard Worker useSameConfig = 0;
334*e5436536SAndroid Build Coastguard Worker } else {
335*e5436536SAndroid Build Coastguard Worker useSameConfig = FDKreadBits(bs, 1);
336*e5436536SAndroid Build Coastguard Worker }
337*e5436536SAndroid Build Coastguard Worker
338*e5436536SAndroid Build Coastguard Worker if (useSameConfig) {
339*e5436536SAndroid Build Coastguard Worker if (lay > 0) {
340*e5436536SAndroid Build Coastguard Worker FDKmemcpy(&pAsc[TPDEC_TRACKINDEX(prog, lay)],
341*e5436536SAndroid Build Coastguard Worker &pAsc[TPDEC_TRACKINDEX(prog, lay - 1)],
342*e5436536SAndroid Build Coastguard Worker sizeof(CSAudioSpecificConfig));
343*e5436536SAndroid Build Coastguard Worker } else {
344*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
345*e5436536SAndroid Build Coastguard Worker goto bail;
346*e5436536SAndroid Build Coastguard Worker }
347*e5436536SAndroid Build Coastguard Worker } else {
348*e5436536SAndroid Build Coastguard Worker UINT usacConfigLengthPrev = 0;
349*e5436536SAndroid Build Coastguard Worker UCHAR usacConfigPrev[TP_USAC_MAX_CONFIG_LEN];
350*e5436536SAndroid Build Coastguard Worker
351*e5436536SAndroid Build Coastguard Worker if (!(pLatmDemux->applyAsc) &&
352*e5436536SAndroid Build Coastguard Worker (pAsc[TPDEC_TRACKINDEX(prog, lay)].m_aot == AOT_USAC)) {
353*e5436536SAndroid Build Coastguard Worker usacConfigLengthPrev =
354*e5436536SAndroid Build Coastguard Worker (UINT)(pAsc[TPDEC_TRACKINDEX(prog, lay)]
355*e5436536SAndroid Build Coastguard Worker .m_sc.m_usacConfig.UsacConfigBits +
356*e5436536SAndroid Build Coastguard Worker 7) >>
357*e5436536SAndroid Build Coastguard Worker 3; /* store previous USAC config length */
358*e5436536SAndroid Build Coastguard Worker if (usacConfigLengthPrev > TP_USAC_MAX_CONFIG_LEN) {
359*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
360*e5436536SAndroid Build Coastguard Worker goto bail;
361*e5436536SAndroid Build Coastguard Worker }
362*e5436536SAndroid Build Coastguard Worker FDKmemclear(usacConfigPrev, TP_USAC_MAX_CONFIG_LEN);
363*e5436536SAndroid Build Coastguard Worker FDKmemcpy(
364*e5436536SAndroid Build Coastguard Worker usacConfigPrev,
365*e5436536SAndroid Build Coastguard Worker &pAsc[TPDEC_TRACKINDEX(prog, lay)].m_sc.m_usacConfig.UsacConfig,
366*e5436536SAndroid Build Coastguard Worker usacConfigLengthPrev); /* store previous USAC config */
367*e5436536SAndroid Build Coastguard Worker }
368*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_AudioMuxVersion == 1) {
369*e5436536SAndroid Build Coastguard Worker FDK_BITSTREAM tmpBs;
370*e5436536SAndroid Build Coastguard Worker INT ascLen = 0;
371*e5436536SAndroid Build Coastguard Worker ascLen = CLatmDemux_GetValue(bs);
372*e5436536SAndroid Build Coastguard Worker /* The ascLen could be wrong, so check if validBits<=bufBits*/
373*e5436536SAndroid Build Coastguard Worker if (ascLen < 0 || ascLen > (INT)FDKgetValidBits(bs)) {
374*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
375*e5436536SAndroid Build Coastguard Worker goto bail;
376*e5436536SAndroid Build Coastguard Worker }
377*e5436536SAndroid Build Coastguard Worker FDKsyncCache(bs);
378*e5436536SAndroid Build Coastguard Worker tmpBs = *bs;
379*e5436536SAndroid Build Coastguard Worker tmpBs.hBitBuf.ValidBits = ascLen;
380*e5436536SAndroid Build Coastguard Worker
381*e5436536SAndroid Build Coastguard Worker /* Read ASC */
382*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->applyAsc) {
383*e5436536SAndroid Build Coastguard Worker if (TRANSPORTDEC_OK !=
384*e5436536SAndroid Build Coastguard Worker (ErrorStatus = AudioSpecificConfig_Parse(
385*e5436536SAndroid Build Coastguard Worker &pAsc[TPDEC_TRACKINDEX(prog, lay)], &tmpBs, 1,
386*e5436536SAndroid Build Coastguard Worker pTpDecCallbacks, configMode, configChanged,
387*e5436536SAndroid Build Coastguard Worker AOT_NULL_OBJECT)))
388*e5436536SAndroid Build Coastguard Worker goto bail;
389*e5436536SAndroid Build Coastguard Worker } else {
390*e5436536SAndroid Build Coastguard Worker if (TRANSPORTDEC_OK !=
391*e5436536SAndroid Build Coastguard Worker (ErrorStatus = AudioSpecificConfig_Parse(
392*e5436536SAndroid Build Coastguard Worker pAscDummy, &tmpBs, 1, pTpDecCallbacks, configMode,
393*e5436536SAndroid Build Coastguard Worker configChanged, AOT_NULL_OBJECT)))
394*e5436536SAndroid Build Coastguard Worker goto bail;
395*e5436536SAndroid Build Coastguard Worker }
396*e5436536SAndroid Build Coastguard Worker
397*e5436536SAndroid Build Coastguard Worker /* The field p_linfo->m_ascLen could be wrong, so check if */
398*e5436536SAndroid Build Coastguard Worker if (0 > (INT)FDKgetValidBits(&tmpBs)) {
399*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
400*e5436536SAndroid Build Coastguard Worker goto bail;
401*e5436536SAndroid Build Coastguard Worker }
402*e5436536SAndroid Build Coastguard Worker FDKpushFor(bs, ascLen); /* position bitstream after ASC */
403*e5436536SAndroid Build Coastguard Worker } else {
404*e5436536SAndroid Build Coastguard Worker /* Read ASC */
405*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->applyAsc) {
406*e5436536SAndroid Build Coastguard Worker if (TRANSPORTDEC_OK != (ErrorStatus = AudioSpecificConfig_Parse(
407*e5436536SAndroid Build Coastguard Worker &pAsc[TPDEC_TRACKINDEX(prog, lay)],
408*e5436536SAndroid Build Coastguard Worker bs, 0, pTpDecCallbacks, configMode,
409*e5436536SAndroid Build Coastguard Worker configChanged, AOT_NULL_OBJECT)))
410*e5436536SAndroid Build Coastguard Worker goto bail;
411*e5436536SAndroid Build Coastguard Worker } else {
412*e5436536SAndroid Build Coastguard Worker if (TRANSPORTDEC_OK !=
413*e5436536SAndroid Build Coastguard Worker (ErrorStatus = AudioSpecificConfig_Parse(
414*e5436536SAndroid Build Coastguard Worker pAscDummy, bs, 0, pTpDecCallbacks, configMode,
415*e5436536SAndroid Build Coastguard Worker configChanged, AOT_NULL_OBJECT)))
416*e5436536SAndroid Build Coastguard Worker goto bail;
417*e5436536SAndroid Build Coastguard Worker }
418*e5436536SAndroid Build Coastguard Worker }
419*e5436536SAndroid Build Coastguard Worker if (!pLatmDemux->applyAsc) {
420*e5436536SAndroid Build Coastguard Worker updateConfig[TPDEC_TRACKINDEX(prog, lay)] = 0;
421*e5436536SAndroid Build Coastguard Worker } else {
422*e5436536SAndroid Build Coastguard Worker updateConfig[TPDEC_TRACKINDEX(prog, lay)] = 1;
423*e5436536SAndroid Build Coastguard Worker }
424*e5436536SAndroid Build Coastguard Worker
425*e5436536SAndroid Build Coastguard Worker if (!pLatmDemux->applyAsc) {
426*e5436536SAndroid Build Coastguard Worker if (pAscDummy[TPDEC_TRACKINDEX(prog, lay)].m_aot ==
427*e5436536SAndroid Build Coastguard Worker AOT_USAC) { /* flush in case SMC has changed */
428*e5436536SAndroid Build Coastguard Worker const UINT usacConfigLength =
429*e5436536SAndroid Build Coastguard Worker (UINT)(pAscDummy->m_sc.m_usacConfig.UsacConfigBits + 7) >> 3;
430*e5436536SAndroid Build Coastguard Worker if (usacConfigLength > TP_USAC_MAX_CONFIG_LEN) {
431*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
432*e5436536SAndroid Build Coastguard Worker goto bail;
433*e5436536SAndroid Build Coastguard Worker }
434*e5436536SAndroid Build Coastguard Worker if (usacConfigLength != usacConfigLengthPrev) {
435*e5436536SAndroid Build Coastguard Worker FDKmemclear(&pAsc[TPDEC_TRACKINDEX(prog, lay)]
436*e5436536SAndroid Build Coastguard Worker .m_sc.m_usacConfig.UsacConfig,
437*e5436536SAndroid Build Coastguard Worker TP_USAC_MAX_CONFIG_LEN);
438*e5436536SAndroid Build Coastguard Worker FDKmemcpy(&pAsc[TPDEC_TRACKINDEX(prog, lay)]
439*e5436536SAndroid Build Coastguard Worker .m_sc.m_usacConfig.UsacConfig,
440*e5436536SAndroid Build Coastguard Worker &pAscDummy->m_sc.m_usacConfig.UsacConfig,
441*e5436536SAndroid Build Coastguard Worker usacConfigLength); /* store new USAC config */
442*e5436536SAndroid Build Coastguard Worker pAsc[TPDEC_TRACKINDEX(prog, lay)]
443*e5436536SAndroid Build Coastguard Worker .m_sc.m_usacConfig.UsacConfigBits =
444*e5436536SAndroid Build Coastguard Worker pAscDummy->m_sc.m_usacConfig.UsacConfigBits;
445*e5436536SAndroid Build Coastguard Worker pLatmDemux->usacExplicitCfgChanged = 1;
446*e5436536SAndroid Build Coastguard Worker } else {
447*e5436536SAndroid Build Coastguard Worker if (FDKmemcmp(usacConfigPrev,
448*e5436536SAndroid Build Coastguard Worker pAscDummy->m_sc.m_usacConfig.UsacConfig,
449*e5436536SAndroid Build Coastguard Worker usacConfigLengthPrev)) {
450*e5436536SAndroid Build Coastguard Worker FDKmemclear(&pAsc[TPDEC_TRACKINDEX(prog, lay)]
451*e5436536SAndroid Build Coastguard Worker .m_sc.m_usacConfig.UsacConfig,
452*e5436536SAndroid Build Coastguard Worker TP_USAC_MAX_CONFIG_LEN);
453*e5436536SAndroid Build Coastguard Worker FDKmemcpy(&pAsc[TPDEC_TRACKINDEX(prog, lay)]
454*e5436536SAndroid Build Coastguard Worker .m_sc.m_usacConfig.UsacConfig,
455*e5436536SAndroid Build Coastguard Worker &pAscDummy->m_sc.m_usacConfig.UsacConfig,
456*e5436536SAndroid Build Coastguard Worker usacConfigLength); /* store new USAC config */
457*e5436536SAndroid Build Coastguard Worker pAsc[TPDEC_TRACKINDEX(prog, lay)]
458*e5436536SAndroid Build Coastguard Worker .m_sc.m_usacConfig.UsacConfigBits =
459*e5436536SAndroid Build Coastguard Worker pAscDummy->m_sc.m_usacConfig.UsacConfigBits;
460*e5436536SAndroid Build Coastguard Worker pLatmDemux->usacExplicitCfgChanged = 1;
461*e5436536SAndroid Build Coastguard Worker }
462*e5436536SAndroid Build Coastguard Worker }
463*e5436536SAndroid Build Coastguard Worker
464*e5436536SAndroid Build Coastguard Worker if (pAscDummy[TPDEC_TRACKINDEX(prog, lay)]
465*e5436536SAndroid Build Coastguard Worker .m_sc.m_usacConfig.m_usacNumElements) {
466*e5436536SAndroid Build Coastguard Worker if (pAscDummy[TPDEC_TRACKINDEX(prog, lay)]
467*e5436536SAndroid Build Coastguard Worker .m_sc.m_usacConfig.element[0]
468*e5436536SAndroid Build Coastguard Worker .extElement.usacExtElementHasAudioPreRoll) {
469*e5436536SAndroid Build Coastguard Worker pLatmDemux->newCfgHasAudioPreRoll =
470*e5436536SAndroid Build Coastguard Worker 1; /* if dummy parsed cfg has audioPreRoll we first flush
471*e5436536SAndroid Build Coastguard Worker before applying new cfg */
472*e5436536SAndroid Build Coastguard Worker }
473*e5436536SAndroid Build Coastguard Worker }
474*e5436536SAndroid Build Coastguard Worker }
475*e5436536SAndroid Build Coastguard Worker }
476*e5436536SAndroid Build Coastguard Worker }
477*e5436536SAndroid Build Coastguard Worker
478*e5436536SAndroid Build Coastguard Worker p_linfo->m_frameLengthType = FDKreadBits(bs, 3);
479*e5436536SAndroid Build Coastguard Worker switch (p_linfo->m_frameLengthType) {
480*e5436536SAndroid Build Coastguard Worker case 0:
481*e5436536SAndroid Build Coastguard Worker p_linfo->m_bufferFullness = FDKreadBits(bs, 8);
482*e5436536SAndroid Build Coastguard Worker
483*e5436536SAndroid Build Coastguard Worker if (!pLatmDemux->m_allStreamsSameTimeFraming) {
484*e5436536SAndroid Build Coastguard Worker if ((lay > 0) &&
485*e5436536SAndroid Build Coastguard Worker (pAsc[TPDEC_TRACKINDEX(prog, lay)].m_aot == AOT_AAC_SCAL ||
486*e5436536SAndroid Build Coastguard Worker pAsc[TPDEC_TRACKINDEX(prog, lay)].m_aot ==
487*e5436536SAndroid Build Coastguard Worker AOT_ER_AAC_SCAL) &&
488*e5436536SAndroid Build Coastguard Worker (pAsc[TPDEC_TRACKINDEX(prog, lay - 1)].m_aot == AOT_CELP ||
489*e5436536SAndroid Build Coastguard Worker pAsc[TPDEC_TRACKINDEX(prog, lay - 1)].m_aot ==
490*e5436536SAndroid Build Coastguard Worker AOT_ER_CELP)) { /* The layer maybe
491*e5436536SAndroid Build Coastguard Worker ignored later so
492*e5436536SAndroid Build Coastguard Worker read it anyway: */
493*e5436536SAndroid Build Coastguard Worker /* coreFrameOffset = */ FDKreadBits(bs, 6);
494*e5436536SAndroid Build Coastguard Worker }
495*e5436536SAndroid Build Coastguard Worker }
496*e5436536SAndroid Build Coastguard Worker break;
497*e5436536SAndroid Build Coastguard Worker case 1:
498*e5436536SAndroid Build Coastguard Worker p_linfo->m_frameLengthInBits = FDKreadBits(bs, 9);
499*e5436536SAndroid Build Coastguard Worker break;
500*e5436536SAndroid Build Coastguard Worker case 3:
501*e5436536SAndroid Build Coastguard Worker case 4:
502*e5436536SAndroid Build Coastguard Worker case 5:
503*e5436536SAndroid Build Coastguard Worker /* CELP */
504*e5436536SAndroid Build Coastguard Worker case 6:
505*e5436536SAndroid Build Coastguard Worker case 7:
506*e5436536SAndroid Build Coastguard Worker /* HVXC */
507*e5436536SAndroid Build Coastguard Worker default:
508*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
509*e5436536SAndroid Build Coastguard Worker goto bail;
510*e5436536SAndroid Build Coastguard Worker } /* switch framelengthtype*/
511*e5436536SAndroid Build Coastguard Worker
512*e5436536SAndroid Build Coastguard Worker } /* layer loop */
513*e5436536SAndroid Build Coastguard Worker } /* prog loop */
514*e5436536SAndroid Build Coastguard Worker
515*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_otherDataPresent = FDKreadBits(bs, 1);
516*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_otherDataLength = 0;
517*e5436536SAndroid Build Coastguard Worker
518*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_otherDataPresent) {
519*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_AudioMuxVersion == 1) {
520*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_otherDataLength = CLatmDemux_GetValue(bs);
521*e5436536SAndroid Build Coastguard Worker } else {
522*e5436536SAndroid Build Coastguard Worker int otherDataLenEsc = 0;
523*e5436536SAndroid Build Coastguard Worker do {
524*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_otherDataLength <<= 8; // *= 256
525*e5436536SAndroid Build Coastguard Worker otherDataLenEsc = FDKreadBits(bs, 1);
526*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_otherDataLength += FDKreadBits(bs, 8);
527*e5436536SAndroid Build Coastguard Worker } while (otherDataLenEsc);
528*e5436536SAndroid Build Coastguard Worker }
529*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_audioMuxLengthBytes <
530*e5436536SAndroid Build Coastguard Worker (pLatmDemux->m_otherDataLength >> 3)) {
531*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
532*e5436536SAndroid Build Coastguard Worker goto bail;
533*e5436536SAndroid Build Coastguard Worker }
534*e5436536SAndroid Build Coastguard Worker }
535*e5436536SAndroid Build Coastguard Worker
536*e5436536SAndroid Build Coastguard Worker pLatmDemux->m_crcCheckPresent = FDKreadBits(bs, 1);
537*e5436536SAndroid Build Coastguard Worker
538*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_crcCheckPresent) {
539*e5436536SAndroid Build Coastguard Worker FDKreadBits(bs, 8);
540*e5436536SAndroid Build Coastguard Worker }
541*e5436536SAndroid Build Coastguard Worker
542*e5436536SAndroid Build Coastguard Worker } else {
543*e5436536SAndroid Build Coastguard Worker /* audioMuxVersionA > 0 is reserved for future extensions */
544*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_UNSUPPORTED_FORMAT;
545*e5436536SAndroid Build Coastguard Worker }
546*e5436536SAndroid Build Coastguard Worker
547*e5436536SAndroid Build Coastguard Worker /* Configure source decoder: */
548*e5436536SAndroid Build Coastguard Worker if (ErrorStatus == TRANSPORTDEC_OK) {
549*e5436536SAndroid Build Coastguard Worker UINT prog;
550*e5436536SAndroid Build Coastguard Worker for (prog = 0; prog < pLatmDemux->m_numProgram; prog++) {
551*e5436536SAndroid Build Coastguard Worker UINT lay;
552*e5436536SAndroid Build Coastguard Worker for (lay = 0; lay < pLatmDemux->m_numLayer[prog]; lay++) {
553*e5436536SAndroid Build Coastguard Worker if (updateConfig[TPDEC_TRACKINDEX(prog, lay)] != 0) {
554*e5436536SAndroid Build Coastguard Worker int cbError;
555*e5436536SAndroid Build Coastguard Worker cbError = pTpDecCallbacks->cbUpdateConfig(
556*e5436536SAndroid Build Coastguard Worker pTpDecCallbacks->cbUpdateConfigData,
557*e5436536SAndroid Build Coastguard Worker &pAsc[TPDEC_TRACKINDEX(prog, lay)],
558*e5436536SAndroid Build Coastguard Worker pAsc[TPDEC_TRACKINDEX(prog, lay)].configMode,
559*e5436536SAndroid Build Coastguard Worker &pAsc[TPDEC_TRACKINDEX(prog, lay)].AacConfigChanged);
560*e5436536SAndroid Build Coastguard Worker if (cbError == TRANSPORTDEC_NEED_TO_RESTART) {
561*e5436536SAndroid Build Coastguard Worker *pfConfigFound = 0;
562*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_NEED_TO_RESTART;
563*e5436536SAndroid Build Coastguard Worker goto bail;
564*e5436536SAndroid Build Coastguard Worker }
565*e5436536SAndroid Build Coastguard Worker if (cbError != 0) {
566*e5436536SAndroid Build Coastguard Worker *pfConfigFound = 0;
567*e5436536SAndroid Build Coastguard Worker if (lay == 0) {
568*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_SYNC_ERROR;
569*e5436536SAndroid Build Coastguard Worker goto bail;
570*e5436536SAndroid Build Coastguard Worker }
571*e5436536SAndroid Build Coastguard Worker } else {
572*e5436536SAndroid Build Coastguard Worker *pfConfigFound = 1;
573*e5436536SAndroid Build Coastguard Worker }
574*e5436536SAndroid Build Coastguard Worker } else {
575*e5436536SAndroid Build Coastguard Worker *pfConfigFound = 1;
576*e5436536SAndroid Build Coastguard Worker }
577*e5436536SAndroid Build Coastguard Worker }
578*e5436536SAndroid Build Coastguard Worker }
579*e5436536SAndroid Build Coastguard Worker }
580*e5436536SAndroid Build Coastguard Worker
581*e5436536SAndroid Build Coastguard Worker bail:
582*e5436536SAndroid Build Coastguard Worker if (ErrorStatus != TRANSPORTDEC_OK) {
583*e5436536SAndroid Build Coastguard Worker UCHAR applyAsc = pLatmDemux->applyAsc;
584*e5436536SAndroid Build Coastguard Worker FDKmemclear(pLatmDemux, sizeof(CLatmDemux)); /* reset structure */
585*e5436536SAndroid Build Coastguard Worker pLatmDemux->applyAsc = applyAsc;
586*e5436536SAndroid Build Coastguard Worker } else {
587*e5436536SAndroid Build Coastguard Worker /* no error and config parsing is finished */
588*e5436536SAndroid Build Coastguard Worker if (configMode == AC_CM_ALLOC_MEM) pLatmDemux->applyAsc = 0;
589*e5436536SAndroid Build Coastguard Worker }
590*e5436536SAndroid Build Coastguard Worker
591*e5436536SAndroid Build Coastguard Worker return (ErrorStatus);
592*e5436536SAndroid Build Coastguard Worker }
593*e5436536SAndroid Build Coastguard Worker
CLatmDemux_ReadAuChunkLengthInfo(HANDLE_FDK_BITSTREAM bs)594*e5436536SAndroid Build Coastguard Worker static int CLatmDemux_ReadAuChunkLengthInfo(HANDLE_FDK_BITSTREAM bs) {
595*e5436536SAndroid Build Coastguard Worker int len = 0, tmp = 255;
596*e5436536SAndroid Build Coastguard Worker int validBytes = (int)FDKgetValidBits(bs) >> 3;
597*e5436536SAndroid Build Coastguard Worker
598*e5436536SAndroid Build Coastguard Worker while (tmp == 255 && validBytes-- > 0) {
599*e5436536SAndroid Build Coastguard Worker tmp = (int)FDKreadBits(bs, 8);
600*e5436536SAndroid Build Coastguard Worker len += tmp;
601*e5436536SAndroid Build Coastguard Worker }
602*e5436536SAndroid Build Coastguard Worker
603*e5436536SAndroid Build Coastguard Worker return ((tmp == 255) ? -1 : (len << 3));
604*e5436536SAndroid Build Coastguard Worker }
605*e5436536SAndroid Build Coastguard Worker
CLatmDemux_ReadPayloadLengthInfo(HANDLE_FDK_BITSTREAM bs,CLatmDemux * pLatmDemux)606*e5436536SAndroid Build Coastguard Worker TRANSPORTDEC_ERROR CLatmDemux_ReadPayloadLengthInfo(HANDLE_FDK_BITSTREAM bs,
607*e5436536SAndroid Build Coastguard Worker CLatmDemux *pLatmDemux) {
608*e5436536SAndroid Build Coastguard Worker TRANSPORTDEC_ERROR ErrorStatus = TRANSPORTDEC_OK;
609*e5436536SAndroid Build Coastguard Worker int totalPayloadBits = 0;
610*e5436536SAndroid Build Coastguard Worker
611*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_allStreamsSameTimeFraming == 1) {
612*e5436536SAndroid Build Coastguard Worker FDK_ASSERT(pLatmDemux->m_numProgram <= LATM_MAX_PROG);
613*e5436536SAndroid Build Coastguard Worker for (UINT prog = 0; prog < pLatmDemux->m_numProgram; prog++) {
614*e5436536SAndroid Build Coastguard Worker FDK_ASSERT(pLatmDemux->m_numLayer[prog] <= LATM_MAX_LAYER);
615*e5436536SAndroid Build Coastguard Worker for (UINT lay = 0; lay < pLatmDemux->m_numLayer[prog]; lay++) {
616*e5436536SAndroid Build Coastguard Worker LATM_LAYER_INFO *p_linfo = &pLatmDemux->m_linfo[prog][lay];
617*e5436536SAndroid Build Coastguard Worker int auChunkLengthInfo = 0;
618*e5436536SAndroid Build Coastguard Worker
619*e5436536SAndroid Build Coastguard Worker switch (p_linfo->m_frameLengthType) {
620*e5436536SAndroid Build Coastguard Worker case 0:
621*e5436536SAndroid Build Coastguard Worker auChunkLengthInfo = CLatmDemux_ReadAuChunkLengthInfo(bs);
622*e5436536SAndroid Build Coastguard Worker if (auChunkLengthInfo >= 0) {
623*e5436536SAndroid Build Coastguard Worker p_linfo->m_frameLengthInBits = (UINT)auChunkLengthInfo;
624*e5436536SAndroid Build Coastguard Worker totalPayloadBits += p_linfo->m_frameLengthInBits;
625*e5436536SAndroid Build Coastguard Worker } else {
626*e5436536SAndroid Build Coastguard Worker return TRANSPORTDEC_PARSE_ERROR;
627*e5436536SAndroid Build Coastguard Worker }
628*e5436536SAndroid Build Coastguard Worker break;
629*e5436536SAndroid Build Coastguard Worker case 3:
630*e5436536SAndroid Build Coastguard Worker case 5:
631*e5436536SAndroid Build Coastguard Worker case 7:
632*e5436536SAndroid Build Coastguard Worker default:
633*e5436536SAndroid Build Coastguard Worker return TRANSPORTDEC_PARSE_ERROR; // AAC_DEC_LATM_INVALIDFRAMELENGTHTYPE;
634*e5436536SAndroid Build Coastguard Worker }
635*e5436536SAndroid Build Coastguard Worker }
636*e5436536SAndroid Build Coastguard Worker }
637*e5436536SAndroid Build Coastguard Worker } else {
638*e5436536SAndroid Build Coastguard Worker ErrorStatus = TRANSPORTDEC_PARSE_ERROR; // AAC_DEC_LATM_TIMEFRAMING;
639*e5436536SAndroid Build Coastguard Worker }
640*e5436536SAndroid Build Coastguard Worker if (pLatmDemux->m_audioMuxLengthBytes > (UINT)0 &&
641*e5436536SAndroid Build Coastguard Worker totalPayloadBits > (int)pLatmDemux->m_audioMuxLengthBytes * 8) {
642*e5436536SAndroid Build Coastguard Worker return TRANSPORTDEC_PARSE_ERROR;
643*e5436536SAndroid Build Coastguard Worker }
644*e5436536SAndroid Build Coastguard Worker
645*e5436536SAndroid Build Coastguard Worker return (ErrorStatus);
646*e5436536SAndroid Build Coastguard Worker }
647*e5436536SAndroid Build Coastguard Worker
CLatmDemux_GetFrameLengthInBits(CLatmDemux * pLatmDemux,const UINT prog,const UINT layer)648*e5436536SAndroid Build Coastguard Worker UINT CLatmDemux_GetFrameLengthInBits(CLatmDemux *pLatmDemux, const UINT prog,
649*e5436536SAndroid Build Coastguard Worker const UINT layer) {
650*e5436536SAndroid Build Coastguard Worker UINT nFrameLenBits = 0;
651*e5436536SAndroid Build Coastguard Worker if (prog < pLatmDemux->m_numProgram) {
652*e5436536SAndroid Build Coastguard Worker if (layer < pLatmDemux->m_numLayer[prog]) {
653*e5436536SAndroid Build Coastguard Worker nFrameLenBits = pLatmDemux->m_linfo[prog][layer].m_frameLengthInBits;
654*e5436536SAndroid Build Coastguard Worker }
655*e5436536SAndroid Build Coastguard Worker }
656*e5436536SAndroid Build Coastguard Worker return nFrameLenBits;
657*e5436536SAndroid Build Coastguard Worker }
658*e5436536SAndroid Build Coastguard Worker
CLatmDemux_GetOtherDataPresentFlag(CLatmDemux * pLatmDemux)659*e5436536SAndroid Build Coastguard Worker UINT CLatmDemux_GetOtherDataPresentFlag(CLatmDemux *pLatmDemux) {
660*e5436536SAndroid Build Coastguard Worker return pLatmDemux->m_otherDataPresent ? 1 : 0;
661*e5436536SAndroid Build Coastguard Worker }
662*e5436536SAndroid Build Coastguard Worker
CLatmDemux_GetOtherDataLength(CLatmDemux * pLatmDemux)663*e5436536SAndroid Build Coastguard Worker UINT CLatmDemux_GetOtherDataLength(CLatmDemux *pLatmDemux) {
664*e5436536SAndroid Build Coastguard Worker return pLatmDemux->m_otherDataLength;
665*e5436536SAndroid Build Coastguard Worker }
666*e5436536SAndroid Build Coastguard Worker
CLatmDemux_GetNrOfSubFrames(CLatmDemux * pLatmDemux)667*e5436536SAndroid Build Coastguard Worker UINT CLatmDemux_GetNrOfSubFrames(CLatmDemux *pLatmDemux) {
668*e5436536SAndroid Build Coastguard Worker return pLatmDemux->m_noSubFrames;
669*e5436536SAndroid Build Coastguard Worker }
670*e5436536SAndroid Build Coastguard Worker
CLatmDemux_GetNrOfLayers(CLatmDemux * pLatmDemux,const UINT prog)671*e5436536SAndroid Build Coastguard Worker UINT CLatmDemux_GetNrOfLayers(CLatmDemux *pLatmDemux, const UINT prog) {
672*e5436536SAndroid Build Coastguard Worker UINT numLayer = 0;
673*e5436536SAndroid Build Coastguard Worker if (prog < pLatmDemux->m_numProgram) {
674*e5436536SAndroid Build Coastguard Worker numLayer = pLatmDemux->m_numLayer[prog];
675*e5436536SAndroid Build Coastguard Worker }
676*e5436536SAndroid Build Coastguard Worker return numLayer;
677*e5436536SAndroid Build Coastguard Worker }
678