Coverage Report

Created: 2025-12-31 06:47

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/aac/libMpegTPDec/src/tpdec_lib.cpp
Line
Count
Source
1
/* -----------------------------------------------------------------------------
2
Software License for The Fraunhofer FDK AAC Codec Library for Android
3
4
© Copyright  1995 - 2022 Fraunhofer-Gesellschaft zur Förderung der angewandten
5
Forschung e.V. All rights reserved.
6
7
 1.    INTRODUCTION
8
The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software
9
that implements the MPEG Advanced Audio Coding ("AAC") encoding and decoding
10
scheme for digital audio. This FDK AAC Codec software is intended to be used on
11
a wide variety of Android devices.
12
13
AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient
14
general perceptual audio codecs. AAC-ELD is considered the best-performing
15
full-bandwidth communications codec by independent studies and is widely
16
deployed. AAC has been standardized by ISO and IEC as part of the MPEG
17
specifications.
18
19
Patent licenses for necessary patent claims for the FDK AAC Codec (including
20
those of Fraunhofer) may be obtained through Via Licensing
21
(www.vialicensing.com) or through the respective patent owners individually for
22
the purpose of encoding or decoding bit streams in products that are compliant
23
with the ISO/IEC MPEG audio standards. Please note that most manufacturers of
24
Android devices already license these patent claims through Via Licensing or
25
directly from the patent owners, and therefore FDK AAC Codec software may
26
already be covered under those patent licenses when it is used for those
27
licensed purposes only.
28
29
Commercially-licensed AAC software libraries, including floating-point versions
30
with enhanced sound quality, are also available from Fraunhofer. Users are
31
encouraged to check the Fraunhofer website for additional applications
32
information and documentation.
33
34
2.    COPYRIGHT LICENSE
35
36
Redistribution and use in source and binary forms, with or without modification,
37
are permitted without payment of copyright license fees provided that you
38
satisfy the following conditions:
39
40
You must retain the complete text of this software license in redistributions of
41
the FDK AAC Codec or your modifications thereto in source code form.
42
43
You must retain the complete text of this software license in the documentation
44
and/or other materials provided with redistributions of the FDK AAC Codec or
45
your modifications thereto in binary form. You must make available free of
46
charge copies of the complete source code of the FDK AAC Codec and your
47
modifications thereto to recipients of copies in binary form.
48
49
The name of Fraunhofer may not be used to endorse or promote products derived
50
from this library without prior written permission.
51
52
You may not charge copyright license fees for anyone to use, copy or distribute
53
the FDK AAC Codec software or your modifications thereto.
54
55
Your modified versions of the FDK AAC Codec must carry prominent notices stating
56
that you changed the software and the date of any change. For modified versions
57
of the FDK AAC Codec, the term "Fraunhofer FDK AAC Codec Library for Android"
58
must be replaced by the term "Third-Party Modified Version of the Fraunhofer FDK
59
AAC Codec Library for Android."
60
61
3.    NO PATENT LICENSE
62
63
NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without
64
limitation the patents of Fraunhofer, ARE GRANTED BY THIS SOFTWARE LICENSE.
65
Fraunhofer provides no warranty of patent non-infringement with respect to this
66
software.
67
68
You may use this FDK AAC Codec software or modifications thereto only for
69
purposes that are authorized by appropriate patent licenses.
70
71
4.    DISCLAIMER
72
73
This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright
74
holders and contributors "AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES,
75
including but not limited to the implied warranties of merchantability and
76
fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
77
CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary,
78
or consequential damages, including but not limited to procurement of substitute
79
goods or services; loss of use, data, or profits, or business interruption,
80
however caused and on any theory of liability, whether in contract, strict
81
liability, or tort (including negligence), arising in any way out of the use of
82
this software, even if advised of the possibility of such damage.
83
84
5.    CONTACT INFORMATION
85
86
Fraunhofer Institute for Integrated Circuits IIS
87
Attention: Audio and Multimedia Departments - FDK AAC LL
88
Am Wolfsmantel 33
89
91058 Erlangen, Germany
90
91
www.iis.fraunhofer.de/amm
92
amm-info@iis.fraunhofer.de
93
----------------------------------------------------------------------------- */
94
95
/******************* MPEG transport format decoder library *********************
96
97
   Author(s):   Manuel Jander
98
99
   Description: MPEG Transport decoder
100
101
*******************************************************************************/
102
103
#include "tpdec_lib.h"
104
105
/* library version */
106
#include "tp_version.h"
107
108
#include "tp_data.h"
109
110
#include "tpdec_adts.h"
111
112
#include "tpdec_adif.h"
113
114
#include "tpdec_latm.h"
115
116
#include "tpdec_drm.h"
117
118
#include "FDK_crc.h"
119
120
#define MODULE_NAME "transportDec"
121
122
typedef union {
123
  STRUCT_ADTS adts;
124
125
  CAdifHeader adif;
126
127
  CLatmDemux latm;
128
129
  STRUCT_DRM drm;
130
131
} transportdec_parser_t;
132
133
#define MHAS_CONFIG_PRESENT 0x001
134
#define MHAS_UI_PRESENT 0x002
135
136
struct TRANSPORTDEC {
137
  TRANSPORT_TYPE transportFmt; /*!< MPEG4 transportDec type. */
138
139
  CSTpCallBacks callbacks; /*!< Struct holding callback and its data */
140
141
  FDK_BITSTREAM bitStream[1]; /* Bitstream reader */
142
  UCHAR *bsBuffer;            /* Internal bitstreamd data buffer */
143
144
  transportdec_parser_t parser; /* Format specific parser structs. */
145
146
  CSAudioSpecificConfig asc[(1 * 1) + 1]; /* Audio specific config from the last
147
                                             config found. One additional
148
                                             CSAudioSpecificConfig is used
149
                                             temporarily for parsing. */
150
  CCtrlCFGChange ctrlCFGChange[(1 * 1)];  /* Controls config change */
151
152
  UINT globalFramePos;      /* Global transport frame reference bit position. */
153
  UINT accessUnitAnchor[1]; /* Current access unit start bit position. */
154
  INT auLength[1];          /* Length of current access unit. */
155
  INT numberOfRawDataBlocks; /* Current number of raw data blocks contained
156
                                remaining from the current transport frame. */
157
  UINT avgBitRate; /* Average bit rate used for frame loss estimation. */
158
  UINT lastValidBufferFullness; /* Last valid buffer fullness value for frame
159
                                   loss estimation */
160
  INT remainder; /* Reminder in division during lost access unit estimation. */
161
  INT missingAccessUnits; /* Estimated missing access units. */
162
  UINT burstPeriod;       /* Data burst period in mili seconds. */
163
  UINT holdOffFrames;     /* Amount of frames that were already hold off due to
164
                             buffer fullness condition not being met. */
165
  UINT flags;             /* Flags. */
166
  INT targetLayout;       /* CICP target layout. */
167
  UINT *pLoudnessInfoSetPosition; /* Reference and start position (bits) and
168
                                     length (bytes) of loudnessInfoSet within
169
                                     rsv603daConfig.  */
170
};
171
172
/* Flag bitmasks for "flags" member of struct TRANSPORTDEC */
173
2.19M
#define TPDEC_SYNCOK 1
174
507k
#define TPDEC_MINIMIZE_DELAY 2
175
1.01M
#define TPDEC_IGNORE_BUFFERFULLNESS 4
176
507k
#define TPDEC_EARLY_CONFIG 8
177
1.51M
#define TPDEC_LOST_FRAMES_PENDING 16
178
1.00M
#define TPDEC_CONFIG_FOUND 32
179
0
#define TPDEC_USE_ELEM_SKIPPING 64
180
181
/* force config/content change */
182
0
#define TPDEC_FORCE_CONFIG_CHANGE 1
183
#define TPDEC_FORCE_CONTENT_CHANGE 2
184
185
/* skip packet */
186
#define TPDEC_SKIP_PACKET 1
187
188
66.2k
C_ALLOC_MEM(Ram_TransportDecoder, struct TRANSPORTDEC, 1)
GetRam_TransportDecoder(int)
Line
Count
Source
188
C_ALLOC_MEM(Ram_TransportDecoder, struct TRANSPORTDEC, 1)
FreeRam_TransportDecoder(TRANSPORTDEC**)
Line
Count
Source
188
C_ALLOC_MEM(Ram_TransportDecoder, struct TRANSPORTDEC, 1)
189
66.2k
C_ALLOC_MEM(Ram_TransportDecoderBuffer, UCHAR, (8192 * 4))
GetRam_TransportDecoderBuffer(int)
Line
Count
Source
189
C_ALLOC_MEM(Ram_TransportDecoderBuffer, UCHAR, (8192 * 4))
FreeRam_TransportDecoderBuffer(unsigned char**)
Line
Count
Source
189
C_ALLOC_MEM(Ram_TransportDecoderBuffer, UCHAR, (8192 * 4))
190
191
HANDLE_TRANSPORTDEC transportDec_Open(const TRANSPORT_TYPE transportFmt,
192
33.1k
                                      const UINT flags, const UINT nrOfLayers) {
193
33.1k
  HANDLE_TRANSPORTDEC hInput;
194
195
33.1k
  hInput = GetRam_TransportDecoder(0);
196
33.1k
  if (hInput == NULL) {
197
0
    return NULL;
198
0
  }
199
200
  /* Init transportDec struct. */
201
33.1k
  hInput->transportFmt = transportFmt;
202
203
33.1k
  switch (transportFmt) {
204
0
    case TT_MP4_ADIF:
205
0
      break;
206
207
0
    case TT_MP4_ADTS:
208
0
      if (flags & TP_FLAG_MPEG4)
209
0
        hInput->parser.adts.decoderCanDoMpeg4 = 1;
210
0
      else
211
0
        hInput->parser.adts.decoderCanDoMpeg4 = 0;
212
0
      adtsRead_CrcInit(&hInput->parser.adts);
213
0
      hInput->parser.adts.BufferFullnesStartFlag = 1;
214
0
      hInput->numberOfRawDataBlocks = 0;
215
0
      break;
216
217
0
    case TT_DRM:
218
0
      drmRead_CrcInit(&hInput->parser.drm);
219
0
      break;
220
221
0
    case TT_MP4_LATM_MCP0:
222
0
    case TT_MP4_LATM_MCP1:
223
0
      hInput->parser.latm.usacExplicitCfgChanged = 0;
224
0
      hInput->parser.latm.applyAsc = 1;
225
0
      break;
226
33.1k
    case TT_MP4_LOAS:
227
33.1k
      hInput->parser.latm.usacExplicitCfgChanged = 0;
228
33.1k
      hInput->parser.latm.applyAsc = 1;
229
33.1k
      break;
230
0
    case TT_MP4_RAW:
231
0
      break;
232
233
0
    default:
234
0
      FreeRam_TransportDecoder(&hInput);
235
0
      hInput = NULL;
236
0
      break;
237
33.1k
  }
238
239
33.1k
  if (hInput != NULL) {
240
    /* Create bitstream */
241
33.1k
    {
242
33.1k
      hInput->bsBuffer = GetRam_TransportDecoderBuffer(0);
243
33.1k
      if (hInput->bsBuffer == NULL) {
244
0
        transportDec_Close(&hInput);
245
0
        return NULL;
246
0
      }
247
33.1k
      if (nrOfLayers > 1) {
248
0
        transportDec_Close(&hInput);
249
0
        return NULL;
250
0
      }
251
66.2k
      for (UINT i = 0; i < nrOfLayers; i++) {
252
33.1k
        FDKinitBitStream(&hInput->bitStream[i], hInput->bsBuffer, (8192 * 4), 0,
253
33.1k
                         BS_READER);
254
33.1k
      }
255
33.1k
    }
256
0
    hInput->burstPeriod = 0;
257
33.1k
  }
258
259
33.1k
  return hInput;
260
33.1k
}
261
262
TRANSPORTDEC_ERROR transportDec_OutOfBandConfig(HANDLE_TRANSPORTDEC hTp,
263
                                                UCHAR *conf, const UINT length,
264
0
                                                UINT layer) {
265
0
  int i;
266
267
0
  TRANSPORTDEC_ERROR err = TRANSPORTDEC_OK;
268
269
0
  FDK_BITSTREAM bs;
270
0
  HANDLE_FDK_BITSTREAM hBs = &bs;
271
272
0
  int fConfigFound = 0;
273
274
0
  UCHAR configChanged = 0;
275
0
  UCHAR configMode = AC_CM_DET_CFG_CHANGE;
276
277
0
  UCHAR tmpConf[1024] = {0};
278
0
  if (length > 1024) {
279
0
    return TRANSPORTDEC_UNSUPPORTED_FORMAT;
280
0
  }
281
0
  FDKmemcpy(tmpConf, conf, length);
282
0
  FDKinitBitStream(hBs, tmpConf, 1024, length << 3, BS_READER);
283
284
0
  for (i = 0; i < 2; i++) {
285
0
    if (i > 0) {
286
0
      FDKpushBack(hBs, (INT)length * 8 - (INT)FDKgetValidBits(hBs));
287
0
      configMode = AC_CM_ALLOC_MEM;
288
0
    }
289
290
    /* config transport decoder */
291
0
    switch (hTp->transportFmt) {
292
0
      case TT_MP4_LATM_MCP0:
293
0
      case TT_MP4_LATM_MCP1:
294
0
      case TT_MP4_LOAS: {
295
0
        if (layer != 0) {
296
0
          return TRANSPORTDEC_INVALID_PARAMETER;
297
0
        }
298
0
        CLatmDemux *pLatmDemux = &hTp->parser.latm;
299
0
        err = CLatmDemux_ReadStreamMuxConfig(hBs, pLatmDemux, &hTp->callbacks,
300
0
                                             hTp->asc, &fConfigFound,
301
0
                                             configMode, configChanged);
302
0
        if (err != TRANSPORTDEC_OK) {
303
0
          return err;
304
0
        }
305
0
      } break;
306
0
      default:
307
0
        fConfigFound = 1;
308
0
        err = AudioSpecificConfig_Parse(&hTp->asc[(1 * 1)], hBs, 1,
309
0
                                        &hTp->callbacks, configMode,
310
0
                                        configChanged, AOT_NULL_OBJECT);
311
0
        if (err == TRANSPORTDEC_OK) {
312
0
          int errC;
313
314
0
          hTp->asc[layer] = hTp->asc[(1 * 1)];
315
0
          errC = hTp->callbacks.cbUpdateConfig(
316
0
              hTp->callbacks.cbUpdateConfigData, &hTp->asc[layer],
317
0
              hTp->asc[layer].configMode, &hTp->asc[layer].AacConfigChanged);
318
0
          if (errC != 0) {
319
0
            err = TRANSPORTDEC_PARSE_ERROR;
320
0
          }
321
0
        }
322
0
        break;
323
0
      case TT_DRM:
324
0
        fConfigFound = 1;
325
0
        err = DrmRawSdcAudioConfig_Parse(&hTp->asc[layer], hBs, &hTp->callbacks,
326
0
                                         configMode, configChanged);
327
0
        if (err == TRANSPORTDEC_OK) {
328
0
          int errC;
329
330
0
          errC = hTp->callbacks.cbUpdateConfig(
331
0
              hTp->callbacks.cbUpdateConfigData, &hTp->asc[layer],
332
0
              hTp->asc[layer].configMode, &hTp->asc[layer].AacConfigChanged);
333
0
          if (errC != 0) {
334
0
            err = TRANSPORTDEC_PARSE_ERROR;
335
0
          }
336
0
        }
337
0
        break;
338
0
    }
339
340
0
    if (err == TRANSPORTDEC_OK) {
341
0
      if ((i == 0) && (hTp->asc[layer].AacConfigChanged ||
342
0
                       hTp->asc[layer].SbrConfigChanged ||
343
0
                       hTp->asc[layer].SacConfigChanged)) {
344
0
        int errC;
345
346
0
        configChanged = 1;
347
0
        errC = hTp->callbacks.cbFreeMem(hTp->callbacks.cbFreeMemData,
348
0
                                        &hTp->asc[layer]);
349
0
        if (errC != 0) {
350
0
          err = TRANSPORTDEC_PARSE_ERROR;
351
0
        }
352
0
      }
353
0
    }
354
355
    /* if an error is detected terminate config parsing to avoid that an invalid
356
     * config is accepted in the second pass */
357
0
    if (err != TRANSPORTDEC_OK) {
358
0
      break;
359
0
    }
360
0
  }
361
362
0
  if (err == TRANSPORTDEC_OK && fConfigFound) {
363
0
    hTp->flags |= TPDEC_CONFIG_FOUND;
364
0
  }
365
366
0
  return err;
367
0
}
368
369
TRANSPORTDEC_ERROR transportDec_InBandConfig(HANDLE_TRANSPORTDEC hTp,
370
                                             UCHAR *newConfig,
371
                                             const UINT newConfigLength,
372
                                             const UCHAR buildUpStatus,
373
                                             UCHAR *configChanged, UINT layer,
374
109
                                             UCHAR *implicitExplicitCfgDiff) {
375
109
  int errC;
376
109
  FDK_BITSTREAM bs;
377
109
  HANDLE_FDK_BITSTREAM hBs = &bs;
378
109
  TRANSPORTDEC_ERROR err = TRANSPORTDEC_OK;
379
109
  int fConfigFound = 0;
380
109
  UCHAR configMode = AC_CM_ALLOC_MEM;
381
109
  *implicitExplicitCfgDiff = 0;
382
383
109
  FDK_ASSERT(hTp->asc->m_aot == AOT_USAC);
384
385
109
  FDKinitBitStream(hBs, newConfig, TP_USAC_MAX_CONFIG_LEN, newConfigLength << 3,
386
109
                   BS_READER);
387
388
109
  if ((hTp->ctrlCFGChange[layer].flushStatus == TPDEC_FLUSH_OFF) &&
389
83
      (hTp->ctrlCFGChange[layer].buildUpStatus !=
390
83
       TPDEC_RSV60_BUILD_UP_IDLE_IN_BAND)) {
391
83
    if (hTp->asc->m_aot == AOT_USAC) {
392
83
      if ((UINT)(hTp->asc->m_sc.m_usacConfig.UsacConfigBits + 7) >> 3 ==
393
83
          newConfigLength) {
394
63
        if (0 == FDKmemcmp(newConfig, hTp->asc->m_sc.m_usacConfig.UsacConfig,
395
63
                           newConfigLength)) {
396
47
          if (hTp->parser.latm.usacExplicitCfgChanged) { /* configChange from
397
                                                            LOAS/LATM parser */
398
26
            hTp->parser.latm.usacExplicitCfgChanged = 0;
399
26
            hTp->ctrlCFGChange[layer].flushCnt = 0;
400
26
            hTp->ctrlCFGChange[layer].flushStatus =
401
26
                TPDEC_USAC_DASH_IPF_FLUSH_ON;
402
26
            hTp->ctrlCFGChange[layer].buildUpCnt = 0;
403
26
            hTp->ctrlCFGChange[layer].buildUpStatus = TPDEC_BUILD_UP_OFF;
404
26
          } else {
405
21
            *configChanged = 0;
406
21
            return err;
407
21
          }
408
47
        } else {
409
16
          *implicitExplicitCfgDiff = 1;
410
16
        }
411
63
      } else {
412
20
        *implicitExplicitCfgDiff = 1;
413
20
      }
414
      /* ISO/IEC 23003-3:2012/FDAM 3:2016(E) Annex F.2: explicit and implicit
415
       * config shall be identical. */
416
62
      if (*implicitExplicitCfgDiff) {
417
36
        switch (hTp->transportFmt) {
418
0
          case TT_MP4_LATM_MCP0:
419
0
          case TT_MP4_LATM_MCP1:
420
36
          case TT_MP4_LOAS:
421
            /* reset decoder to initial state to achieve definite behavior after
422
             * error in config */
423
36
            hTp->callbacks.cbFreeMem(hTp->callbacks.cbFreeMemData,
424
36
                                     &hTp->asc[layer]);
425
36
            hTp->parser.latm.usacExplicitCfgChanged = 0;
426
36
            hTp->parser.latm.applyAsc = 1;
427
36
            err = TRANSPORTDEC_PARSE_ERROR;
428
36
            goto bail;
429
0
          default:
430
0
            break;
431
36
        }
432
36
      }
433
62
    }
434
83
  }
435
436
52
  {
437
52
    if ((hTp->ctrlCFGChange[layer].flushStatus == TPDEC_FLUSH_OFF) &&
438
0
        (hTp->ctrlCFGChange[layer].buildUpStatus !=
439
0
         TPDEC_RSV60_BUILD_UP_IDLE_IN_BAND)) {
440
0
      hTp->ctrlCFGChange[layer].flushCnt = 0;
441
0
      hTp->ctrlCFGChange[layer].buildUpCnt = 0;
442
0
      hTp->ctrlCFGChange[layer].buildUpStatus = TPDEC_BUILD_UP_OFF;
443
0
      if (hTp->asc->m_aot == AOT_USAC) {
444
0
        hTp->ctrlCFGChange[layer].flushStatus = TPDEC_USAC_DASH_IPF_FLUSH_ON;
445
0
      }
446
0
    }
447
448
52
    if ((hTp->ctrlCFGChange[layer].flushStatus ==
449
52
         TPDEC_RSV60_DASH_IPF_ATSC_FLUSH_ON) ||
450
52
        (hTp->ctrlCFGChange[layer].flushStatus ==
451
52
         TPDEC_USAC_DASH_IPF_FLUSH_ON)) {
452
52
      SCHAR counter = 0;
453
52
      if (hTp->asc->m_aot == AOT_USAC) {
454
52
        counter = TPDEC_USAC_NUM_CONFIG_CHANGE_FRAMES;
455
52
      }
456
52
      if (hTp->ctrlCFGChange[layer].flushCnt >= counter) {
457
26
        hTp->ctrlCFGChange[layer].flushCnt = 0;
458
26
        hTp->ctrlCFGChange[layer].flushStatus = TPDEC_FLUSH_OFF;
459
26
        hTp->ctrlCFGChange[layer].forceCfgChange = 0;
460
26
        if (hTp->asc->m_aot == AOT_USAC) {
461
26
          hTp->ctrlCFGChange[layer].buildUpCnt =
462
26
              TPDEC_USAC_NUM_CONFIG_CHANGE_FRAMES - 1;
463
26
          hTp->ctrlCFGChange[layer].buildUpStatus = TPDEC_USAC_BUILD_UP_ON;
464
26
        }
465
26
      }
466
467
      /* Activate flush mode. After that continue with build up mode in core */
468
52
      if (hTp->callbacks.cbCtrlCFGChange(hTp->callbacks.cbCtrlCFGChangeData,
469
52
                                         &hTp->ctrlCFGChange[layer]) != 0) {
470
0
        err = TRANSPORTDEC_PARSE_ERROR;
471
0
      }
472
473
52
      if ((hTp->ctrlCFGChange[layer].flushStatus ==
474
52
           TPDEC_RSV60_DASH_IPF_ATSC_FLUSH_ON) ||
475
52
          (hTp->ctrlCFGChange[layer].flushStatus ==
476
52
           TPDEC_USAC_DASH_IPF_FLUSH_ON)) {
477
26
        hTp->ctrlCFGChange[layer].flushCnt++;
478
26
        return err;
479
26
      }
480
52
    }
481
482
26
    if (hTp->asc->m_aot == AOT_USAC) {
483
26
      fConfigFound = 1;
484
485
26
      if (err == TRANSPORTDEC_OK) {
486
26
        *configChanged = 0;
487
26
        configMode = AC_CM_DET_CFG_CHANGE;
488
489
78
        for (int i = 0; i < 2; i++) {
490
52
          if (i > 0) {
491
26
            FDKpushBack(hBs,
492
26
                        (INT)newConfigLength * 8 - (INT)FDKgetValidBits(hBs));
493
26
            configMode = AC_CM_ALLOC_MEM;
494
26
          }
495
          /* config transport decoder */
496
52
          err = AudioSpecificConfig_Parse(
497
52
              &hTp->asc[(1 * 1)], hBs, 0, &hTp->callbacks, configMode,
498
52
              *configChanged, hTp->asc[layer].m_aot);
499
52
          if (err == TRANSPORTDEC_OK) {
500
52
            hTp->asc[layer] = hTp->asc[(1 * 1)];
501
52
            errC = hTp->callbacks.cbUpdateConfig(
502
52
                hTp->callbacks.cbUpdateConfigData, &hTp->asc[layer],
503
52
                hTp->asc[layer].configMode, &hTp->asc[layer].AacConfigChanged);
504
52
            if (errC != 0) {
505
0
              err = TRANSPORTDEC_PARSE_ERROR;
506
0
            }
507
52
          }
508
509
52
          if (err == TRANSPORTDEC_OK) {
510
52
            if ((i == 0) && (hTp->asc[layer].AacConfigChanged ||
511
25
                             hTp->asc[layer].SbrConfigChanged ||
512
24
                             hTp->asc[layer].SacConfigChanged)) {
513
2
              *configChanged = 1;
514
2
              errC = hTp->callbacks.cbFreeMem(hTp->callbacks.cbFreeMemData,
515
2
                                              &hTp->asc[layer]);
516
2
              if (errC != 0) {
517
0
                err = TRANSPORTDEC_PARSE_ERROR;
518
0
              }
519
2
            }
520
52
          }
521
522
          /* if an error is detected terminate config parsing to avoid that an
523
           * invalid config is accepted in the second pass */
524
52
          if (err != TRANSPORTDEC_OK) {
525
0
            break;
526
0
          }
527
52
        }
528
26
      }
529
26
    }
530
531
62
  bail:
532
    /* save new config */
533
62
    if (err == TRANSPORTDEC_OK) {
534
26
      if (hTp->asc->m_aot == AOT_USAC) {
535
26
        hTp->asc->m_sc.m_usacConfig.UsacConfigBits = newConfigLength << 3;
536
26
        FDKmemcpy(hTp->asc->m_sc.m_usacConfig.UsacConfig, newConfig,
537
26
                  newConfigLength);
538
        /* in case of USAC reset transportDecoder variables here because
539
         * otherwise without IPF they are not reset */
540
26
        hTp->ctrlCFGChange[layer].flushCnt = 0;
541
26
        hTp->ctrlCFGChange[layer].flushStatus = TPDEC_FLUSH_OFF;
542
26
        hTp->ctrlCFGChange[layer].buildUpCnt = 0;
543
26
        hTp->ctrlCFGChange[layer].buildUpStatus = TPDEC_BUILD_UP_OFF;
544
26
      }
545
36
    } else {
546
36
      hTp->numberOfRawDataBlocks = 0;
547
548
      /* If parsing error while config found, clear ctrlCFGChange-struct */
549
36
      hTp->ctrlCFGChange[layer].flushCnt = 0;
550
36
      hTp->ctrlCFGChange[layer].flushStatus = TPDEC_FLUSH_OFF;
551
36
      hTp->ctrlCFGChange[layer].buildUpCnt = 0;
552
36
      hTp->ctrlCFGChange[layer].buildUpStatus = TPDEC_BUILD_UP_OFF;
553
36
      hTp->ctrlCFGChange[layer].cfgChanged = 0;
554
36
      hTp->ctrlCFGChange[layer].contentChanged = 0;
555
36
      hTp->ctrlCFGChange[layer].forceCfgChange = 0;
556
557
36
      hTp->callbacks.cbCtrlCFGChange(hTp->callbacks.cbCtrlCFGChangeData,
558
36
                                     &hTp->ctrlCFGChange[layer]);
559
36
    }
560
62
  }
561
562
62
  if (err == TRANSPORTDEC_OK && fConfigFound) {
563
26
    hTp->flags |= TPDEC_CONFIG_FOUND;
564
26
  }
565
566
62
  return err;
567
26
}
568
569
int transportDec_RegisterAscCallback(HANDLE_TRANSPORTDEC hTpDec,
570
                                     const cbUpdateConfig_t cbUpdateConfig,
571
33.1k
                                     void *user_data) {
572
33.1k
  if (hTpDec == NULL) {
573
0
    return -1;
574
0
  }
575
33.1k
  hTpDec->callbacks.cbUpdateConfig = cbUpdateConfig;
576
33.1k
  hTpDec->callbacks.cbUpdateConfigData = user_data;
577
33.1k
  return 0;
578
33.1k
}
579
580
int transportDec_RegisterFreeMemCallback(HANDLE_TRANSPORTDEC hTpDec,
581
                                         const cbFreeMem_t cbFreeMem,
582
33.1k
                                         void *user_data) {
583
33.1k
  if (hTpDec == NULL) {
584
0
    return -1;
585
0
  }
586
33.1k
  hTpDec->callbacks.cbFreeMem = cbFreeMem;
587
33.1k
  hTpDec->callbacks.cbFreeMemData = user_data;
588
33.1k
  return 0;
589
33.1k
}
590
591
int transportDec_RegisterCtrlCFGChangeCallback(
592
    HANDLE_TRANSPORTDEC hTpDec, const cbCtrlCFGChange_t cbCtrlCFGChange,
593
33.1k
    void *user_data) {
594
33.1k
  if (hTpDec == NULL) {
595
0
    return -1;
596
0
  }
597
33.1k
  hTpDec->callbacks.cbCtrlCFGChange = cbCtrlCFGChange;
598
33.1k
  hTpDec->callbacks.cbCtrlCFGChangeData = user_data;
599
33.1k
  return 0;
600
33.1k
}
601
602
int transportDec_RegisterSscCallback(HANDLE_TRANSPORTDEC hTpDec,
603
33.1k
                                     const cbSsc_t cbSsc, void *user_data) {
604
33.1k
  if (hTpDec == NULL) {
605
0
    return -1;
606
0
  }
607
33.1k
  hTpDec->callbacks.cbSsc = cbSsc;
608
33.1k
  hTpDec->callbacks.cbSscData = user_data;
609
33.1k
  return 0;
610
33.1k
}
611
612
int transportDec_RegisterSbrCallback(HANDLE_TRANSPORTDEC hTpDec,
613
33.1k
                                     const cbSbr_t cbSbr, void *user_data) {
614
33.1k
  if (hTpDec == NULL) {
615
0
    return -1;
616
0
  }
617
33.1k
  hTpDec->callbacks.cbSbr = cbSbr;
618
33.1k
  hTpDec->callbacks.cbSbrData = user_data;
619
33.1k
  return 0;
620
33.1k
}
621
622
int transportDec_RegisterUsacCallback(HANDLE_TRANSPORTDEC hTpDec,
623
0
                                      const cbUsac_t cbUsac, void *user_data) {
624
0
  if (hTpDec == NULL) {
625
0
    return -1;
626
0
  }
627
0
  hTpDec->callbacks.cbUsac = cbUsac;
628
0
  hTpDec->callbacks.cbUsacData = user_data;
629
0
  return 0;
630
0
}
631
632
int transportDec_RegisterUniDrcConfigCallback(HANDLE_TRANSPORTDEC hTpDec,
633
                                              const cbUniDrc_t cbUniDrc,
634
                                              void *user_data,
635
33.1k
                                              UINT *pLoudnessInfoSetPosition) {
636
33.1k
  if (hTpDec == NULL) {
637
0
    return -1;
638
0
  }
639
640
33.1k
  hTpDec->callbacks.cbUniDrc = cbUniDrc;
641
33.1k
  hTpDec->callbacks.cbUniDrcData = user_data;
642
643
33.1k
  hTpDec->pLoudnessInfoSetPosition = pLoudnessInfoSetPosition;
644
33.1k
  return 0;
645
33.1k
}
646
647
TRANSPORTDEC_ERROR transportDec_FillData(const HANDLE_TRANSPORTDEC hTp,
648
                                         UCHAR *pBuffer, const UINT bufferSize,
649
33.8k
                                         UINT *pBytesValid, const INT layer) {
650
33.8k
  HANDLE_FDK_BITSTREAM hBs;
651
652
33.8k
  if ((hTp == NULL) || (layer >= 1)) {
653
0
    return TRANSPORTDEC_INVALID_PARAMETER;
654
0
  }
655
656
  /* set bitbuffer shortcut */
657
33.8k
  hBs = &hTp->bitStream[layer];
658
659
33.8k
  if (TT_IS_PACKET(hTp->transportFmt)) {
660
0
    if (hTp->numberOfRawDataBlocks == 0) {
661
0
      FDKresetBitbuffer(hBs);
662
0
      FDKfeedBuffer(hBs, pBuffer, bufferSize, pBytesValid);
663
0
      if (*pBytesValid != 0) {
664
0
        return TRANSPORTDEC_TOO_MANY_BITS;
665
0
      }
666
0
    }
667
33.8k
  } else {
668
    /* ... else feed bitbuffer with new stream data (append). */
669
670
33.8k
    if (*pBytesValid == 0) {
671
      /* nothing to do */
672
0
      return TRANSPORTDEC_OK;
673
33.8k
    } else {
674
33.8k
      const int bytesValid = *pBytesValid;
675
33.8k
      FDKfeedBuffer(hBs, pBuffer, bufferSize, pBytesValid);
676
677
33.8k
      if (hTp->numberOfRawDataBlocks > 0) {
678
0
        hTp->globalFramePos += (bytesValid - *pBytesValid) * 8;
679
0
        hTp->accessUnitAnchor[layer] = FDKgetValidBits(hBs);
680
0
      }
681
33.8k
    }
682
33.8k
  }
683
684
33.8k
  return TRANSPORTDEC_OK;
685
33.8k
}
686
687
HANDLE_FDK_BITSTREAM transportDec_GetBitstream(const HANDLE_TRANSPORTDEC hTp,
688
1.50M
                                               const UINT layer) {
689
1.50M
  return &hTp->bitStream[layer];
690
1.50M
}
691
692
176
TRANSPORT_TYPE transportDec_GetFormat(const HANDLE_TRANSPORTDEC hTp) {
693
176
  return hTp->transportFmt;
694
176
}
695
696
24.5k
INT transportDec_GetBufferFullness(const HANDLE_TRANSPORTDEC hTp) {
697
24.5k
  INT bufferFullness = -1;
698
699
24.5k
  switch (hTp->transportFmt) {
700
0
    case TT_MP4_ADTS:
701
0
      if (hTp->parser.adts.bs.adts_fullness != 0x7ff) {
702
0
        bufferFullness = hTp->parser.adts.bs.frame_length * 8 +
703
0
                         hTp->parser.adts.bs.adts_fullness * 32 *
704
0
                             getNumberOfEffectiveChannels(
705
0
                                 hTp->parser.adts.bs.channel_config);
706
0
      }
707
0
      break;
708
24.5k
    case TT_MP4_LOAS:
709
24.5k
    case TT_MP4_LATM_MCP0:
710
24.5k
    case TT_MP4_LATM_MCP1:
711
24.5k
      if (hTp->parser.latm.m_linfo[0][0].m_bufferFullness != 0xff) {
712
23.9k
        bufferFullness = hTp->parser.latm.m_linfo[0][0].m_bufferFullness;
713
23.9k
      }
714
24.5k
      break;
715
0
    default:
716
0
      break;
717
24.5k
  }
718
719
24.5k
  return bufferFullness;
720
24.5k
}
721
722
/**
723
 * \brief adjust bit stream position and the end of an access unit.
724
 * \param hTp transport decoder handle.
725
 * \return error code.
726
 */
727
static TRANSPORTDEC_ERROR transportDec_AdjustEndOfAccessUnit(
728
487k
    HANDLE_TRANSPORTDEC hTp) {
729
487k
  HANDLE_FDK_BITSTREAM hBs = &hTp->bitStream[0];
730
487k
  TRANSPORTDEC_ERROR err = TRANSPORTDEC_OK;
731
732
487k
  switch (hTp->transportFmt) {
733
0
    case TT_MP4_ADIF:
734
      /* Do byte align at the end of raw_data_block() because UsacFrame() is not
735
       * byte aligned. */
736
0
      FDKbyteAlign(hBs, hTp->accessUnitAnchor[0]);
737
0
      break;
738
487k
    case TT_MP4_LOAS:
739
487k
    case TT_MP4_LATM_MCP0:
740
487k
    case TT_MP4_LATM_MCP1:
741
487k
      if (hTp->numberOfRawDataBlocks == 0) {
742
        /* Do byte align at the end of AudioMuxElement. */
743
122k
        FDKbyteAlign(hBs, hTp->globalFramePos);
744
745
        /* Check global frame length */
746
122k
        if (hTp->transportFmt == TT_MP4_LOAS &&
747
122k
            hTp->parser.latm.m_audioMuxLengthBytes > 0) {
748
122k
          int loasOffset;
749
750
122k
          loasOffset = ((INT)hTp->parser.latm.m_audioMuxLengthBytes * 8 +
751
122k
                        (INT)FDKgetValidBits(hBs)) -
752
122k
                       (INT)hTp->globalFramePos;
753
122k
          if (loasOffset != 0) {
754
120k
            FDKpushBiDirectional(hBs, loasOffset);
755
            /* For ELD and other payloads there is an unknown amount of padding,
756
               so ignore unread bits, but throw an error only if too many bits
757
               where read. */
758
120k
            if (loasOffset < 0) {
759
120k
              err = TRANSPORTDEC_PARSE_ERROR;
760
120k
            }
761
120k
          }
762
122k
        }
763
122k
      }
764
487k
      break;
765
766
0
    case TT_MP4_ADTS:
767
0
      if (hTp->parser.adts.bs.protection_absent == 0) {
768
0
        int offset;
769
770
        /* Calculate offset to end of AU */
771
0
        offset = hTp->parser.adts
772
0
                     .rawDataBlockDist[hTp->parser.adts.bs.num_raw_blocks -
773
0
                                       hTp->numberOfRawDataBlocks]
774
0
                 << 3;
775
        /* CAUTION: The PCE (if available) is declared to be a part of the
776
         * header! */
777
0
        offset -= (INT)hTp->accessUnitAnchor[0] - (INT)FDKgetValidBits(hBs) +
778
0
                  16 + hTp->parser.adts.bs.num_pce_bits;
779
0
        FDKpushBiDirectional(hBs, offset);
780
0
      }
781
0
      if (hTp->parser.adts.bs.num_raw_blocks > 0 &&
782
0
          hTp->parser.adts.bs.protection_absent == 0) {
783
        /* Note this CRC read currently happens twice because of
784
         * transportDec_CrcCheck() */
785
0
        hTp->parser.adts.crcReadValue = FDKreadBits(hBs, 16);
786
0
      }
787
0
      if (hTp->numberOfRawDataBlocks == 0) {
788
        /* Check global frame length */
789
0
        if (hTp->parser.adts.bs.protection_absent == 0) {
790
0
          int offset;
791
792
0
          offset = (hTp->parser.adts.bs.frame_length * 8 - ADTS_SYNCLENGTH +
793
0
                    (INT)FDKgetValidBits(hBs)) -
794
0
                   (INT)hTp->globalFramePos;
795
0
          if (offset != 0) {
796
0
            FDKpushBiDirectional(hBs, offset);
797
0
          }
798
0
        }
799
0
      }
800
0
      break;
801
802
0
    default:
803
0
      break;
804
487k
  }
805
806
487k
  return err;
807
487k
}
808
809
/**
810
 * \brief Determine additional buffer fullness contraint due to burst data
811
 * reception. The parameter TPDEC_PARAM_BURSTPERIOD must have been set as a
812
 * precondition.
813
 * \param hTp transport decoder handle.
814
 * \param bufferFullness the buffer fullness value of the first frame to be
815
 * decoded.
816
 * \param bitsAvail the amount of available bits at the end of the first frame
817
 * to be decoded.
818
 * \return error code
819
 */
820
static TRANSPORTDEC_ERROR additionalHoldOffNeeded(HANDLE_TRANSPORTDEC hTp,
821
                                                  INT bufferFullness,
822
24.5k
                                                  INT bitsAvail) {
823
24.5k
  INT checkLengthBits, avgBitsPerFrame;
824
24.5k
  INT maxAU; /* maximum number of frames per Master Frame */
825
24.5k
  INT samplesPerFrame = hTp->asc->m_samplesPerFrame;
826
24.5k
  INT samplingFrequency = (INT)hTp->asc->m_samplingFrequency;
827
828
24.5k
  if ((hTp->avgBitRate == 0) || (hTp->burstPeriod == 0)) {
829
24.5k
    return TRANSPORTDEC_OK;
830
24.5k
  }
831
0
  if ((samplesPerFrame == 0) || (samplingFrequency == 0)) {
832
0
    return TRANSPORTDEC_NOT_ENOUGH_BITS;
833
0
  }
834
835
  /* One Master Frame is sent every hTp->burstPeriod ms */
836
0
  maxAU = hTp->burstPeriod * samplingFrequency + (samplesPerFrame * 1000 - 1);
837
0
  maxAU = maxAU / (samplesPerFrame * 1000);
838
  /* Subtract number of frames which were already held off. */
839
0
  maxAU -= hTp->holdOffFrames;
840
841
0
  avgBitsPerFrame = hTp->avgBitRate * samplesPerFrame + (samplingFrequency - 1);
842
0
  avgBitsPerFrame = avgBitsPerFrame / samplingFrequency;
843
844
  /* Consider worst case of bufferFullness quantization. */
845
0
  switch (hTp->transportFmt) {
846
0
    case TT_MP4_ADIF:
847
0
    case TT_MP4_ADTS:
848
0
    case TT_MP4_LOAS:
849
0
    case TT_MP4_LATM_MCP0:
850
0
    case TT_MP4_LATM_MCP1:
851
0
      bufferFullness += 31;
852
0
      break;
853
0
    default: /* added to avoid compiler warning */
854
0
      break; /* added to avoid compiler warning */
855
0
  }
856
857
0
  checkLengthBits = bufferFullness + (maxAU - 1) * avgBitsPerFrame;
858
859
  /* Check if buffer is big enough to fullfill buffer fullness condition */
860
0
  if ((checkLengthBits /*+headerBits*/) > (((8192 * 4) << 3) - 7)) {
861
0
    return TRANSPORTDEC_SYNC_ERROR;
862
0
  }
863
864
0
  if (bitsAvail < checkLengthBits) {
865
0
    return TRANSPORTDEC_NOT_ENOUGH_BITS;
866
0
  } else {
867
0
    return TRANSPORTDEC_OK;
868
0
  }
869
0
}
870
871
static TRANSPORTDEC_ERROR transportDec_readHeader(
872
    HANDLE_TRANSPORTDEC hTp, HANDLE_FDK_BITSTREAM hBs, int syncLength,
873
    int ignoreBufferFullness, int *pRawDataBlockLength,
874
    int *pfTraverseMoreFrames, int *pSyncLayerFrameBits, int *pfConfigFound,
875
759k
    int *pHeaderBits) {
876
759k
  TRANSPORTDEC_ERROR err = TRANSPORTDEC_OK;
877
759k
  int rawDataBlockLength = *pRawDataBlockLength;
878
759k
  int fTraverseMoreFrames =
879
759k
      (pfTraverseMoreFrames != NULL) ? *pfTraverseMoreFrames : 0;
880
759k
  int syncLayerFrameBits =
881
759k
      (pSyncLayerFrameBits != NULL) ? *pSyncLayerFrameBits : 0;
882
759k
  int fConfigFound = (pfConfigFound != NULL) ? *pfConfigFound : 0;
883
759k
  int startPos;
884
885
759k
  startPos = (INT)FDKgetValidBits(hBs);
886
887
759k
  switch (hTp->transportFmt) {
888
0
    case TT_MP4_ADTS:
889
0
      if (hTp->numberOfRawDataBlocks <= 0) {
890
0
        int i, errC;
891
892
0
        hTp->globalFramePos = FDKgetValidBits(hBs);
893
894
0
        UCHAR configChanged = 0;
895
0
        UCHAR configMode = AC_CM_DET_CFG_CHANGE;
896
897
0
        for (i = 0; i < 2; i++) {
898
0
          if (i > 0) {
899
0
            FDKpushBack(hBs,
900
0
                        (INT)hTp->globalFramePos - (INT)FDKgetValidBits(hBs));
901
0
            configMode = AC_CM_ALLOC_MEM;
902
0
          }
903
904
          /* Parse ADTS header */
905
0
          err = adtsRead_DecodeHeader(&hTp->parser.adts, &hTp->asc[0], hBs,
906
0
                                      ignoreBufferFullness);
907
0
          if (err != TRANSPORTDEC_OK) {
908
0
            if (err != TRANSPORTDEC_NOT_ENOUGH_BITS) {
909
0
              err = TRANSPORTDEC_SYNC_ERROR;
910
0
            }
911
0
          } else {
912
0
            errC = hTp->callbacks.cbUpdateConfig(
913
0
                hTp->callbacks.cbUpdateConfigData, &hTp->asc[0], configMode,
914
0
                &configChanged);
915
0
            if (errC != 0) {
916
0
              if (errC == TRANSPORTDEC_NEED_TO_RESTART) {
917
0
                err = TRANSPORTDEC_NEED_TO_RESTART;
918
0
                goto bail;
919
0
              } else {
920
0
                err = TRANSPORTDEC_SYNC_ERROR;
921
0
              }
922
0
            } else {
923
0
              fConfigFound = 1;
924
0
              hTp->numberOfRawDataBlocks =
925
0
                  hTp->parser.adts.bs.num_raw_blocks + 1;
926
0
            }
927
0
          }
928
929
0
          if (err == TRANSPORTDEC_OK) {
930
0
            if ((i == 0) && configChanged) {
931
0
              errC = hTp->callbacks.cbFreeMem(hTp->callbacks.cbFreeMemData,
932
0
                                              &hTp->asc[0]);
933
0
              if (errC != 0) {
934
0
                err = TRANSPORTDEC_PARSE_ERROR;
935
0
              }
936
0
            }
937
0
          }
938
          /* if an error is detected terminate config parsing to avoid that an
939
           * invalid config is accepted in the second pass */
940
0
          if (err != TRANSPORTDEC_OK) {
941
0
            break;
942
0
          }
943
0
        }
944
0
      } else {
945
        /* Reset CRC because the next bits are the beginning of a
946
         * raw_data_block() */
947
0
        FDKcrcReset(&hTp->parser.adts.crcInfo);
948
0
        hTp->parser.adts.bs.num_pce_bits = 0;
949
0
      }
950
0
      if (err == TRANSPORTDEC_OK) {
951
0
        hTp->numberOfRawDataBlocks--;
952
0
        rawDataBlockLength = adtsRead_GetRawDataBlockLength(
953
0
            &hTp->parser.adts,
954
0
            (hTp->parser.adts.bs.num_raw_blocks - hTp->numberOfRawDataBlocks));
955
0
        if (rawDataBlockLength <= 0) {
956
          /* No further frame traversal possible. */
957
0
          fTraverseMoreFrames = 0;
958
0
        }
959
0
        syncLayerFrameBits = (hTp->parser.adts.bs.frame_length << 3) -
960
0
                             (startPos - (INT)FDKgetValidBits(hBs)) -
961
0
                             syncLength;
962
0
        if (syncLayerFrameBits <= 0) {
963
0
          err = TRANSPORTDEC_SYNC_ERROR;
964
0
        }
965
0
      } else {
966
0
        hTp->numberOfRawDataBlocks = 0;
967
0
      }
968
0
      break;
969
759k
    case TT_MP4_LOAS:
970
759k
      if (hTp->numberOfRawDataBlocks <= 0) {
971
397k
        syncLayerFrameBits = (INT)FDKreadBits(hBs, 13);
972
397k
        hTp->parser.latm.m_audioMuxLengthBytes = syncLayerFrameBits;
973
397k
        syncLayerFrameBits <<= 3;
974
397k
      }
975
759k
      FDK_FALLTHROUGH;
976
759k
    case TT_MP4_LATM_MCP1:
977
759k
    case TT_MP4_LATM_MCP0:
978
759k
      if (hTp->numberOfRawDataBlocks <= 0) {
979
397k
        hTp->globalFramePos = FDKgetValidBits(hBs);
980
981
397k
        err = CLatmDemux_Read(hBs, &hTp->parser.latm, hTp->transportFmt,
982
397k
                              &hTp->callbacks, hTp->asc, &fConfigFound,
983
397k
                              ignoreBufferFullness);
984
985
397k
        if (err != TRANSPORTDEC_OK) {
986
248k
          if ((err != TRANSPORTDEC_NOT_ENOUGH_BITS) &&
987
248k
              !TPDEC_IS_FATAL_ERROR(err)) {
988
248k
            err = TRANSPORTDEC_SYNC_ERROR;
989
248k
          }
990
248k
        } else {
991
148k
          hTp->numberOfRawDataBlocks =
992
148k
              CLatmDemux_GetNrOfSubFrames(&hTp->parser.latm);
993
148k
          if (hTp->transportFmt == TT_MP4_LOAS) {
994
148k
            syncLayerFrameBits -= startPos - (INT)FDKgetValidBits(hBs) - (13);
995
148k
            if (syncLayerFrameBits <= 0) {
996
18.4k
              err = TRANSPORTDEC_SYNC_ERROR;
997
18.4k
            }
998
148k
          }
999
148k
        }
1000
397k
      } else {
1001
362k
        err = CLatmDemux_ReadPayloadLengthInfo(hBs, &hTp->parser.latm);
1002
362k
        if (err != TRANSPORTDEC_OK) {
1003
4.74k
          err = TRANSPORTDEC_SYNC_ERROR;
1004
4.74k
        }
1005
362k
      }
1006
759k
      if (err == TRANSPORTDEC_OK) {
1007
487k
        int layer;
1008
487k
        rawDataBlockLength = 0;
1009
487k
        for (layer = 0;
1010
975k
             layer < (int)CLatmDemux_GetNrOfLayers(&hTp->parser.latm, 0);
1011
487k
             layer += 1) {
1012
487k
          rawDataBlockLength +=
1013
487k
              CLatmDemux_GetFrameLengthInBits(&hTp->parser.latm, 0, layer);
1014
487k
        }
1015
487k
        hTp->numberOfRawDataBlocks--;
1016
487k
      } else {
1017
271k
        hTp->numberOfRawDataBlocks = 0;
1018
271k
      }
1019
759k
      break;
1020
0
    default: { syncLayerFrameBits = 0; } break;
1021
759k
  }
1022
1023
759k
bail:
1024
1025
759k
  *pRawDataBlockLength = rawDataBlockLength;
1026
1027
759k
  if (pHeaderBits != NULL) {
1028
759k
    *pHeaderBits += startPos - (INT)FDKgetValidBits(hBs);
1029
759k
  }
1030
1031
1.51M
  for (int i = 0; i < (1 * 1); i++) {
1032
    /* If parsing error while config found, clear ctrlCFGChange-struct */
1033
759k
    if (hTp->ctrlCFGChange[i].cfgChanged && err != TRANSPORTDEC_OK) {
1034
0
      hTp->numberOfRawDataBlocks = 0;
1035
0
      hTp->ctrlCFGChange[i].flushCnt = 0;
1036
0
      hTp->ctrlCFGChange[i].flushStatus = TPDEC_FLUSH_OFF;
1037
0
      hTp->ctrlCFGChange[i].buildUpCnt = 0;
1038
0
      hTp->ctrlCFGChange[i].buildUpStatus = TPDEC_BUILD_UP_OFF;
1039
0
      hTp->ctrlCFGChange[i].cfgChanged = 0;
1040
0
      hTp->ctrlCFGChange[i].contentChanged = 0;
1041
0
      hTp->ctrlCFGChange[i].forceCfgChange = 0;
1042
1043
0
      hTp->callbacks.cbCtrlCFGChange(hTp->callbacks.cbCtrlCFGChangeData,
1044
0
                                     &hTp->ctrlCFGChange[i]);
1045
0
    }
1046
759k
  }
1047
1048
759k
  if (pfConfigFound != NULL) {
1049
759k
    *pfConfigFound = fConfigFound;
1050
759k
  }
1051
1052
759k
  if (pfTraverseMoreFrames != NULL) {
1053
759k
    *pfTraverseMoreFrames = fTraverseMoreFrames;
1054
759k
  }
1055
759k
  if (pSyncLayerFrameBits != NULL) {
1056
759k
    *pSyncLayerFrameBits = syncLayerFrameBits;
1057
759k
  }
1058
1059
759k
  return err;
1060
759k
}
1061
1062
/* How many bits to advance for synchronization search. */
1063
45.0M
#define TPDEC_SYNCSKIP 8
1064
1065
static TRANSPORTDEC_ERROR synchronization(HANDLE_TRANSPORTDEC hTp,
1066
508k
                                          INT *pHeaderBits) {
1067
508k
  TRANSPORTDEC_ERROR err = TRANSPORTDEC_OK, errFirstFrame = TRANSPORTDEC_OK;
1068
508k
  HANDLE_FDK_BITSTREAM hBs = &hTp->bitStream[0];
1069
1070
508k
  INT syncLayerFrameBits = 0; /* Length of sync layer frame (i.e. LOAS) */
1071
508k
  INT rawDataBlockLength = 0, rawDataBlockLengthPrevious;
1072
508k
  INT totalBits;
1073
508k
  INT headerBits = 0, headerBitsFirstFrame = 0, headerBitsPrevious;
1074
508k
  INT numFramesTraversed = 0, fTraverseMoreFrames,
1075
508k
      fConfigFound = (hTp->flags & TPDEC_CONFIG_FOUND), startPosFirstFrame = -1;
1076
508k
  INT numRawDataBlocksFirstFrame = 0, numRawDataBlocksPrevious,
1077
508k
      globalFramePosFirstFrame = 0, rawDataBlockLengthFirstFrame = 0;
1078
508k
  INT ignoreBufferFullness =
1079
508k
      hTp->flags &
1080
508k
      (TPDEC_LOST_FRAMES_PENDING | TPDEC_IGNORE_BUFFERFULLNESS | TPDEC_SYNCOK);
1081
508k
  UINT endTpFrameBitsPrevious = 0;
1082
1083
  /* Synch parameters */
1084
508k
  INT syncLength; /* Length of sync word in bits */
1085
508k
  UINT syncWord;  /* Sync word to be found */
1086
508k
  UINT syncMask;  /* Mask for sync word (for adding one bit, so comprising one
1087
                     bit less) */
1088
508k
  C_ALLOC_SCRATCH_START(contextFirstFrame, transportdec_parser_t, 1);
1089
1090
508k
  totalBits = (INT)FDKgetValidBits(hBs);
1091
1092
508k
  if (totalBits <= 0) {
1093
537
    err = TRANSPORTDEC_NOT_ENOUGH_BITS;
1094
537
    goto bail;
1095
537
  }
1096
1097
507k
  fTraverseMoreFrames =
1098
507k
      (hTp->flags & (TPDEC_MINIMIZE_DELAY | TPDEC_EARLY_CONFIG)) &&
1099
0
      !(hTp->flags & TPDEC_SYNCOK);
1100
1101
  /* Set transport specific sync parameters */
1102
507k
  switch (hTp->transportFmt) {
1103
0
    case TT_MP4_ADTS:
1104
0
      syncWord = ADTS_SYNCWORD;
1105
0
      syncLength = ADTS_SYNCLENGTH;
1106
0
      break;
1107
507k
    case TT_MP4_LOAS:
1108
507k
      syncWord = 0x2B7;
1109
507k
      syncLength = 11;
1110
507k
      break;
1111
0
    default:
1112
0
      syncWord = 0;
1113
0
      syncLength = 0;
1114
0
      break;
1115
507k
  }
1116
1117
507k
  syncMask = (1 << syncLength) - 1;
1118
1119
772k
  do {
1120
772k
    INT bitsAvail = 0;   /* Bits available in bitstream buffer    */
1121
772k
    INT checkLengthBits; /* Helper to check remaining bits and buffer boundaries
1122
                          */
1123
772k
    UINT synch;          /* Current sync word read from bitstream */
1124
1125
772k
    headerBitsPrevious = headerBits;
1126
1127
772k
    bitsAvail = (INT)FDKgetValidBits(hBs);
1128
1129
772k
    if (hTp->numberOfRawDataBlocks == 0) {
1130
      /* search synchword */
1131
1132
410k
      FDK_ASSERT((bitsAvail % TPDEC_SYNCSKIP) == 0);
1133
1134
410k
      if ((bitsAvail - syncLength) < TPDEC_SYNCSKIP) {
1135
4.46k
        err = TRANSPORTDEC_NOT_ENOUGH_BITS;
1136
4.46k
        headerBits = 0;
1137
405k
      } else {
1138
405k
        synch = FDKreadBits(hBs, syncLength);
1139
1140
405k
        if (!(hTp->flags & TPDEC_SYNCOK)) {
1141
11.2M
          for (; (bitsAvail - syncLength) >= TPDEC_SYNCSKIP;
1142
11.2M
               bitsAvail -= TPDEC_SYNCSKIP) {
1143
11.2M
            if (synch == syncWord) {
1144
290k
              break;
1145
290k
            }
1146
10.9M
            synch = ((synch << TPDEC_SYNCSKIP) & syncMask) |
1147
10.9M
                    FDKreadBits(hBs, TPDEC_SYNCSKIP);
1148
10.9M
          }
1149
294k
        }
1150
405k
        if (synch != syncWord) {
1151
          /* No correct syncword found. */
1152
8.30k
          err = TRANSPORTDEC_SYNC_ERROR;
1153
397k
        } else {
1154
397k
          err = TRANSPORTDEC_OK;
1155
397k
        }
1156
405k
        headerBits = syncLength;
1157
405k
      }
1158
410k
    } else {
1159
362k
      headerBits = 0;
1160
362k
    }
1161
1162
    /* Save previous raw data block data */
1163
772k
    rawDataBlockLengthPrevious = rawDataBlockLength;
1164
772k
    numRawDataBlocksPrevious = hTp->numberOfRawDataBlocks;
1165
1166
    /* Parse transport header (raw data block granularity) */
1167
1168
772k
    if (err == TRANSPORTDEC_OK) {
1169
759k
      err = transportDec_readHeader(hTp, hBs, syncLength, ignoreBufferFullness,
1170
759k
                                    &rawDataBlockLength, &fTraverseMoreFrames,
1171
759k
                                    &syncLayerFrameBits, &fConfigFound,
1172
759k
                                    &headerBits);
1173
759k
      if (headerBits > bitsAvail) {
1174
14.4k
        err = (headerBits < (INT)hBs->hBitBuf.bufBits)
1175
14.4k
                  ? TRANSPORTDEC_NOT_ENOUGH_BITS
1176
14.4k
                  : TRANSPORTDEC_SYNC_ERROR;
1177
14.4k
      }
1178
759k
      if (TPDEC_IS_FATAL_ERROR(err)) {
1179
        /* Rewind - TPDEC_SYNCSKIP, in order to look for a synch one bit ahead
1180
         * next time. Ensure that the bit amount lands at a multiple of
1181
         * TPDEC_SYNCSKIP. */
1182
0
        FDKpushBiDirectional(
1183
0
            hBs, -headerBits + TPDEC_SYNCSKIP + (bitsAvail % TPDEC_SYNCSKIP));
1184
1185
0
        goto bail;
1186
0
      }
1187
759k
    }
1188
1189
772k
    bitsAvail -= headerBits;
1190
1191
772k
    checkLengthBits = syncLayerFrameBits;
1192
1193
    /* Check if the whole frame would fit the bitstream buffer */
1194
772k
    if (err == TRANSPORTDEC_OK) {
1195
487k
      if ((checkLengthBits + headerBits) > (((8192 * 4) << 3) - 7)) {
1196
        /* We assume that the size of the transport bit buffer has been
1197
           chosen to meet all system requirements, thus this condition
1198
           is considered a synchronisation error. */
1199
0
        err = TRANSPORTDEC_SYNC_ERROR;
1200
487k
      } else {
1201
487k
        if (bitsAvail < checkLengthBits) {
1202
323
          err = TRANSPORTDEC_NOT_ENOUGH_BITS;
1203
323
        }
1204
487k
      }
1205
487k
    }
1206
1207
772k
    if (err == TRANSPORTDEC_NOT_ENOUGH_BITS) {
1208
10.1k
      break;
1209
10.1k
    }
1210
1211
762k
    if (err == TRANSPORTDEC_SYNC_ERROR) {
1212
274k
      int bits;
1213
1214
      /* Enforce re-sync of transport headers. */
1215
274k
      hTp->numberOfRawDataBlocks = 0;
1216
1217
      /* Ensure that the bit amount lands at a multiple of TPDEC_SYNCSKIP */
1218
274k
      bits = (bitsAvail + headerBits) % TPDEC_SYNCSKIP;
1219
      /* Rewind - TPDEC_SYNCSKIP, in order to look for a synch one bit ahead
1220
       * next time. */
1221
274k
      FDKpushBiDirectional(hBs, -(headerBits - TPDEC_SYNCSKIP) + bits);
1222
274k
      headerBits = 0;
1223
274k
    }
1224
1225
    /* Frame traversal */
1226
762k
    if (fTraverseMoreFrames) {
1227
      /* Save parser context for early config discovery "rewind all frames" */
1228
0
      if ((hTp->flags & TPDEC_EARLY_CONFIG) &&
1229
0
          !(hTp->flags & TPDEC_MINIMIZE_DELAY)) {
1230
        /* ignore buffer fullness if just traversing additional frames for ECD
1231
         */
1232
0
        ignoreBufferFullness = 1;
1233
1234
        /* Save context in order to return later */
1235
0
        if (err == TRANSPORTDEC_OK && startPosFirstFrame == -1) {
1236
0
          startPosFirstFrame = FDKgetValidBits(hBs);
1237
0
          numRawDataBlocksFirstFrame = hTp->numberOfRawDataBlocks;
1238
0
          globalFramePosFirstFrame = hTp->globalFramePos;
1239
0
          rawDataBlockLengthFirstFrame = rawDataBlockLength;
1240
0
          headerBitsFirstFrame = headerBits;
1241
0
          errFirstFrame = err;
1242
0
          FDKmemcpy(contextFirstFrame, &hTp->parser,
1243
0
                    sizeof(transportdec_parser_t));
1244
0
        }
1245
1246
        /* Break when config was found or it is not possible anymore to find a
1247
         * config */
1248
0
        if (startPosFirstFrame != -1 &&
1249
0
            (fConfigFound || err != TRANSPORTDEC_OK)) {
1250
          /* In case of ECD and sync error, do not rewind anywhere. */
1251
0
          if (err == TRANSPORTDEC_SYNC_ERROR) {
1252
0
            startPosFirstFrame = -1;
1253
0
            fConfigFound = 0;
1254
0
            numFramesTraversed = 0;
1255
0
          }
1256
0
          break;
1257
0
        }
1258
0
      }
1259
1260
0
      if (err == TRANSPORTDEC_OK) {
1261
0
        FDKpushFor(hBs, rawDataBlockLength);
1262
0
        numFramesTraversed++;
1263
0
        endTpFrameBitsPrevious = (INT)FDKgetValidBits(hBs);
1264
        /* Ignore error here itentionally. */
1265
0
        transportDec_AdjustEndOfAccessUnit(hTp);
1266
0
        endTpFrameBitsPrevious -= FDKgetValidBits(hBs);
1267
0
      }
1268
0
    }
1269
762k
  } while (fTraverseMoreFrames ||
1270
762k
           (err == TRANSPORTDEC_SYNC_ERROR && !(hTp->flags & TPDEC_SYNCOK)));
1271
1272
  /* Restore context in case of ECD frame traversal */
1273
507k
  if (startPosFirstFrame != -1 && (fConfigFound || err != TRANSPORTDEC_OK)) {
1274
0
    FDKpushBiDirectional(hBs, FDKgetValidBits(hBs) - startPosFirstFrame);
1275
0
    FDKmemcpy(&hTp->parser, contextFirstFrame, sizeof(transportdec_parser_t));
1276
0
    hTp->numberOfRawDataBlocks = numRawDataBlocksFirstFrame;
1277
0
    hTp->globalFramePos = globalFramePosFirstFrame;
1278
0
    rawDataBlockLength = rawDataBlockLengthFirstFrame;
1279
0
    headerBits = headerBitsFirstFrame;
1280
0
    err = errFirstFrame;
1281
0
    numFramesTraversed = 0;
1282
0
  }
1283
1284
  /* Additional burst data mode buffer fullness check. */
1285
507k
  if (!(hTp->flags & (TPDEC_LOST_FRAMES_PENDING | TPDEC_IGNORE_BUFFERFULLNESS |
1286
507k
                      TPDEC_SYNCOK)) &&
1287
33.8k
      err == TRANSPORTDEC_OK) {
1288
24.5k
    err =
1289
24.5k
        additionalHoldOffNeeded(hTp, transportDec_GetBufferFullness(hTp),
1290
24.5k
                                (INT)FDKgetValidBits(hBs) - syncLayerFrameBits);
1291
24.5k
    if (err == TRANSPORTDEC_NOT_ENOUGH_BITS) {
1292
0
      hTp->holdOffFrames++;
1293
0
    }
1294
24.5k
  }
1295
1296
  /* Rewind for retry because of not enough bits */
1297
507k
  if (err == TRANSPORTDEC_NOT_ENOUGH_BITS) {
1298
10.1k
    FDKpushBack(hBs, headerBits);
1299
10.1k
    hTp->numberOfRawDataBlocks = numRawDataBlocksPrevious;
1300
10.1k
    headerBits = 0;
1301
10.1k
    rawDataBlockLength = rawDataBlockLengthPrevious;
1302
497k
  } else {
1303
    /* reset hold off frame counter */
1304
497k
    hTp->holdOffFrames = 0;
1305
497k
  }
1306
1307
  /* Return to last good frame in case of frame traversal but not ECD. */
1308
507k
  if (numFramesTraversed > 0) {
1309
0
    FDKpushBack(hBs, rawDataBlockLengthPrevious + endTpFrameBitsPrevious);
1310
0
    if (err != TRANSPORTDEC_OK) {
1311
0
      hTp->numberOfRawDataBlocks = numRawDataBlocksPrevious;
1312
0
      headerBits = headerBitsPrevious;
1313
0
      rawDataBlockLength = rawDataBlockLengthPrevious;
1314
0
    }
1315
0
    err = TRANSPORTDEC_OK;
1316
0
  }
1317
1318
508k
bail:
1319
508k
  hTp->auLength[0] = rawDataBlockLength;
1320
1321
  /* Detect pointless TRANSPORTDEC_NOT_ENOUGH_BITS error case, where the bit
1322
     buffer is already full, or no new burst packet fits. Recover by advancing
1323
     the bit buffer. */
1324
508k
  if ((totalBits > 0) && (TRANSPORTDEC_NOT_ENOUGH_BITS == err) &&
1325
10.1k
      (FDKgetValidBits(hBs) >=
1326
10.1k
       (((8192 * 4) * 8 - ((hTp->avgBitRate * hTp->burstPeriod) / 1000)) -
1327
10.1k
        7))) {
1328
0
    FDKpushFor(hBs, TPDEC_SYNCSKIP);
1329
0
    err = TRANSPORTDEC_SYNC_ERROR;
1330
0
  }
1331
1332
508k
  if (err == TRANSPORTDEC_OK) {
1333
487k
    hTp->flags |= TPDEC_SYNCOK;
1334
487k
  }
1335
1336
508k
  if (fConfigFound) {
1337
499k
    hTp->flags |= TPDEC_CONFIG_FOUND;
1338
499k
  }
1339
1340
508k
  if (pHeaderBits != NULL) {
1341
508k
    *pHeaderBits = headerBits;
1342
508k
  }
1343
1344
508k
  if (err == TRANSPORTDEC_SYNC_ERROR) {
1345
10.0k
    hTp->flags &= ~TPDEC_SYNCOK;
1346
10.0k
  }
1347
1348
508k
  C_ALLOC_SCRATCH_END(contextFirstFrame, transportdec_parser_t, 1);
1349
1350
508k
  return err;
1351
507k
}
1352
1353
/**
1354
 * \brief Synchronize to stream and estimate the amount of missing access units
1355
 * due to a current synchronization error in case of constant average bit rate.
1356
 */
1357
static TRANSPORTDEC_ERROR transportDec_readStream(HANDLE_TRANSPORTDEC hTp,
1358
508k
                                                  const UINT layer) {
1359
508k
  TRANSPORTDEC_ERROR error = TRANSPORTDEC_OK;
1360
508k
  HANDLE_FDK_BITSTREAM hBs = &hTp->bitStream[layer];
1361
1362
508k
  INT headerBits;
1363
508k
  INT bitDistance, bfDelta;
1364
1365
  /* Obtain distance to next synch word */
1366
508k
  bitDistance = (INT)FDKgetValidBits(hBs);
1367
508k
  error = synchronization(hTp, &headerBits);
1368
508k
  bitDistance -= (INT)FDKgetValidBits(hBs);
1369
1370
508k
  FDK_ASSERT(bitDistance >= 0);
1371
1372
508k
  INT nAU = -1;
1373
1374
508k
  if (error == TRANSPORTDEC_SYNC_ERROR ||
1375
498k
      (hTp->flags & TPDEC_LOST_FRAMES_PENDING)) {
1376
    /* Check if estimating lost access units is feasible. */
1377
10.0k
    if (hTp->avgBitRate > 0 && hTp->asc[0].m_samplesPerFrame > 0 &&
1378
0
        hTp->asc[0].m_samplingFrequency > 0) {
1379
0
      if (error == TRANSPORTDEC_OK) {
1380
0
        int aj;
1381
1382
0
        aj = transportDec_GetBufferFullness(hTp);
1383
0
        if (aj > 0) {
1384
0
          bfDelta = aj;
1385
0
        } else {
1386
0
          bfDelta = 0;
1387
0
        }
1388
        /* sync was ok: last of a series of bad access units. */
1389
0
        hTp->flags &= ~TPDEC_LOST_FRAMES_PENDING;
1390
        /* Add up bitDistance until end of the current frame. Later we substract
1391
           this frame from the grand total, since this current successfully
1392
           synchronized frame should not be skipped of course; but it must be
1393
           accounted into the bufferfulness math. */
1394
0
        bitDistance += hTp->auLength[0];
1395
0
      } else {
1396
0
        if (!(hTp->flags & TPDEC_LOST_FRAMES_PENDING)) {
1397
          /* sync not ok: one of many bad access units. */
1398
0
          hTp->flags |= TPDEC_LOST_FRAMES_PENDING;
1399
0
          bfDelta = -(INT)hTp->lastValidBufferFullness;
1400
0
        } else {
1401
0
          bfDelta = 0;
1402
0
        }
1403
0
      }
1404
1405
0
      {
1406
0
        int num, denom;
1407
1408
        /* Obtain estimate of number of lost frames */
1409
0
        num = (INT)hTp->asc[0].m_samplingFrequency * (bfDelta + bitDistance) +
1410
0
              hTp->remainder;
1411
0
        denom = hTp->avgBitRate * hTp->asc[0].m_samplesPerFrame;
1412
0
        if (num > 0) {
1413
0
          nAU = num / denom;
1414
0
          hTp->remainder = num % denom;
1415
0
        } else {
1416
0
          hTp->remainder = num;
1417
0
        }
1418
1419
0
        if (error == TRANSPORTDEC_OK) {
1420
          /* Final adjustment of remainder, taken -1 into account because
1421
             current frame should not be skipped, thus substract -1 or do
1422
             nothing instead of +1-1 accordingly. */
1423
0
          if ((denom - hTp->remainder) >= hTp->remainder) {
1424
0
            nAU--;
1425
0
          }
1426
1427
0
          if (nAU < 0) {
1428
            /* There was one frame too much concealed, so unfortunately we will
1429
             * have to skip one good frame. */
1430
0
            transportDec_EndAccessUnit(hTp);
1431
0
            error = synchronization(hTp, &headerBits);
1432
0
            nAU = -1;
1433
0
          }
1434
0
          hTp->remainder = 0;
1435
          /* Enforce last missed frames to be concealed. */
1436
0
          if (nAU > 0) {
1437
0
            FDKpushBack(hBs, headerBits);
1438
0
          }
1439
0
        }
1440
0
      }
1441
0
    }
1442
10.0k
  }
1443
1444
  /* Be sure that lost frames are handled correctly. This is necessary due to
1445
     some sync error sequences where later it turns out that there is not enough
1446
     data, but the bits upto the sync word are discarded, thus causing a value
1447
     of nAU > 0 */
1448
508k
  if (nAU > 0) {
1449
0
    error = TRANSPORTDEC_SYNC_ERROR;
1450
0
  }
1451
1452
508k
  hTp->missingAccessUnits = nAU;
1453
1454
508k
  return error;
1455
508k
}
1456
1457
/* returns error code */
1458
TRANSPORTDEC_ERROR transportDec_ReadAccessUnit(const HANDLE_TRANSPORTDEC hTp,
1459
508k
                                               const UINT layer) {
1460
508k
  TRANSPORTDEC_ERROR err = TRANSPORTDEC_OK;
1461
508k
  HANDLE_FDK_BITSTREAM hBs;
1462
1463
508k
  if (!hTp) {
1464
0
    return TRANSPORTDEC_INVALID_PARAMETER;
1465
0
  }
1466
1467
508k
  hBs = &hTp->bitStream[layer];
1468
1469
508k
  if ((INT)FDKgetValidBits(hBs) <= 0) {
1470
    /* This is only relevant for RAW and ADIF cases.
1471
     * For streaming formats err will get overwritten. */
1472
537
    err = TRANSPORTDEC_NOT_ENOUGH_BITS;
1473
537
    hTp->numberOfRawDataBlocks = 0;
1474
537
  }
1475
1476
508k
  switch (hTp->transportFmt) {
1477
0
    case TT_MP4_ADIF:
1478
      /* Read header if not already done */
1479
0
      if (!(hTp->flags & TPDEC_CONFIG_FOUND)) {
1480
0
        int i;
1481
0
        CProgramConfig *pce;
1482
0
        INT bsStart = FDKgetValidBits(hBs);
1483
0
        UCHAR configChanged = 0;
1484
0
        UCHAR configMode = AC_CM_DET_CFG_CHANGE;
1485
1486
0
        for (i = 0; i < 2; i++) {
1487
0
          if (i > 0) {
1488
0
            FDKpushBack(hBs, bsStart - (INT)FDKgetValidBits(hBs));
1489
0
            configMode = AC_CM_ALLOC_MEM;
1490
0
          }
1491
1492
0
          AudioSpecificConfig_Init(&hTp->asc[0]);
1493
0
          pce = &hTp->asc[0].m_progrConfigElement;
1494
0
          err = adifRead_DecodeHeader(&hTp->parser.adif, pce, hBs);
1495
0
          if (err) goto bail;
1496
1497
          /* Map adif header to ASC */
1498
0
          hTp->asc[0].m_aot = (AUDIO_OBJECT_TYPE)(pce->Profile + 1);
1499
0
          hTp->asc[0].m_samplingFrequencyIndex = pce->SamplingFrequencyIndex;
1500
0
          hTp->asc[0].m_samplingFrequency =
1501
0
              SamplingRateTable[pce->SamplingFrequencyIndex];
1502
0
          hTp->asc[0].m_channelConfiguration = 0;
1503
0
          hTp->asc[0].m_samplesPerFrame = 1024;
1504
0
          hTp->avgBitRate = hTp->parser.adif.BitRate;
1505
1506
          /* Call callback to decoder. */
1507
0
          {
1508
0
            int errC;
1509
1510
0
            errC = hTp->callbacks.cbUpdateConfig(
1511
0
                hTp->callbacks.cbUpdateConfigData, &hTp->asc[0], configMode,
1512
0
                &configChanged);
1513
0
            if (errC == 0) {
1514
0
              hTp->flags |= TPDEC_CONFIG_FOUND;
1515
0
            } else {
1516
0
              err = TRANSPORTDEC_PARSE_ERROR;
1517
0
              goto bail;
1518
0
            }
1519
0
          }
1520
1521
0
          if (err == TRANSPORTDEC_OK) {
1522
0
            if ((i == 0) && configChanged) {
1523
0
              int errC;
1524
0
              errC = hTp->callbacks.cbFreeMem(hTp->callbacks.cbFreeMemData,
1525
0
                                              &hTp->asc[0]);
1526
0
              if (errC != 0) {
1527
0
                err = TRANSPORTDEC_PARSE_ERROR;
1528
0
              }
1529
0
            }
1530
0
          }
1531
0
        }
1532
0
      }
1533
0
      hTp->auLength[layer] = -1; /* Access Unit data length is unknown. */
1534
0
      break;
1535
1536
0
    case TT_MP4_RAW:
1537
0
    case TT_DRM:
1538
      /* One Access Unit was filled into buffer.
1539
         So get the length out of the buffer. */
1540
0
      hTp->auLength[layer] = FDKgetValidBits(hBs);
1541
0
      hTp->flags |= TPDEC_SYNCOK;
1542
0
      break;
1543
1544
0
    case TT_MP4_LATM_MCP0:
1545
0
    case TT_MP4_LATM_MCP1:
1546
0
      if (err == TRANSPORTDEC_OK) {
1547
0
        int fConfigFound = hTp->flags & TPDEC_CONFIG_FOUND;
1548
0
        err = transportDec_readHeader(hTp, hBs, 0, 1, &hTp->auLength[layer],
1549
0
                                      NULL, NULL, &fConfigFound, NULL);
1550
0
        if (fConfigFound) {
1551
0
          hTp->flags |= TPDEC_CONFIG_FOUND;
1552
0
        }
1553
0
      }
1554
0
      break;
1555
1556
0
    case TT_MP4_ADTS:
1557
508k
    case TT_MP4_LOAS:
1558
508k
      err = transportDec_readStream(hTp, layer);
1559
508k
      break;
1560
1561
0
    default:
1562
0
      err = TRANSPORTDEC_UNSUPPORTED_FORMAT;
1563
0
      break;
1564
508k
  }
1565
1566
508k
  if (err == TRANSPORTDEC_OK) {
1567
487k
    hTp->accessUnitAnchor[layer] = FDKgetValidBits(hBs);
1568
487k
  } else {
1569
20.7k
    hTp->accessUnitAnchor[layer] = 0;
1570
20.7k
  }
1571
1572
508k
bail:
1573
508k
  return err;
1574
508k
}
1575
1576
TRANSPORTDEC_ERROR transportDec_GetAsc(const HANDLE_TRANSPORTDEC hTp,
1577
                                       const UINT layer,
1578
0
                                       CSAudioSpecificConfig *asc) {
1579
0
  TRANSPORTDEC_ERROR err = TRANSPORTDEC_OK;
1580
1581
0
  if (hTp != NULL) {
1582
0
    *asc = hTp->asc[layer];
1583
0
    err = TRANSPORTDEC_OK;
1584
0
  } else {
1585
0
    err = TRANSPORTDEC_INVALID_PARAMETER;
1586
0
  }
1587
0
  return err;
1588
0
}
1589
1590
INT transportDec_GetAuBitsRemaining(const HANDLE_TRANSPORTDEC hTp,
1591
1.07M
                                    const UINT layer) {
1592
1.07M
  INT bits;
1593
1594
1.07M
  if (hTp->accessUnitAnchor[layer] > 0 && hTp->auLength[layer] > 0) {
1595
331k
    bits = (INT)FDKgetValidBits(&hTp->bitStream[layer]);
1596
331k
    if (bits >= 0) {
1597
325k
      bits = hTp->auLength[layer] - ((INT)hTp->accessUnitAnchor[layer] - bits);
1598
325k
    }
1599
739k
  } else {
1600
739k
    bits = FDKgetValidBits(&hTp->bitStream[layer]);
1601
739k
  }
1602
1603
1.07M
  return bits;
1604
1.07M
}
1605
1606
INT transportDec_GetAuBitsTotal(const HANDLE_TRANSPORTDEC hTp,
1607
489k
                                const UINT layer) {
1608
489k
  return hTp->auLength[layer];
1609
489k
}
1610
1611
TRANSPORTDEC_ERROR transportDec_GetMissingAccessUnitCount(
1612
10.0k
    INT *pNAccessUnits, HANDLE_TRANSPORTDEC hTp) {
1613
10.0k
  *pNAccessUnits = hTp->missingAccessUnits;
1614
1615
10.0k
  return TRANSPORTDEC_OK;
1616
10.0k
}
1617
1618
/* Inform the transportDec layer that reading of access unit has finished. */
1619
487k
TRANSPORTDEC_ERROR transportDec_EndAccessUnit(HANDLE_TRANSPORTDEC hTp) {
1620
487k
  TRANSPORTDEC_ERROR err = TRANSPORTDEC_OK;
1621
1622
487k
  switch (hTp->transportFmt) {
1623
487k
    case TT_MP4_LOAS:
1624
487k
    case TT_MP4_LATM_MCP0:
1625
487k
    case TT_MP4_LATM_MCP1: {
1626
487k
      HANDLE_FDK_BITSTREAM hBs = &hTp->bitStream[0];
1627
487k
      if (hTp->numberOfRawDataBlocks == 0) {
1628
        /* Read other data if available. */
1629
11.2k
        if (CLatmDemux_GetOtherDataPresentFlag(&hTp->parser.latm)) {
1630
2.13k
          int otherDataLen = CLatmDemux_GetOtherDataLength(&hTp->parser.latm);
1631
1632
2.13k
          if ((INT)FDKgetValidBits(hBs) >= otherDataLen) {
1633
2.08k
            FDKpushFor(hBs, otherDataLen);
1634
2.08k
          } else {
1635
            /* Do byte align at the end of AudioMuxElement. */
1636
48
            if (hTp->numberOfRawDataBlocks == 0) {
1637
48
              FDKbyteAlign(hBs, hTp->globalFramePos);
1638
48
            }
1639
48
            return TRANSPORTDEC_NOT_ENOUGH_BITS;
1640
48
          }
1641
2.13k
        }
1642
476k
      } else {
1643
        /* If bit buffer has not more bits but hTp->numberOfRawDataBlocks > 0
1644
           then too many bits were read and obviously no more RawDataBlocks can
1645
           be read. Set numberOfRawDataBlocks to zero to attempt a new sync
1646
           attempt. */
1647
476k
        if ((INT)FDKgetValidBits(hBs) <= 0) {
1648
111k
          hTp->numberOfRawDataBlocks = 0;
1649
111k
        }
1650
476k
      }
1651
487k
    } break;
1652
487k
    default:
1653
0
      break;
1654
487k
  }
1655
1656
487k
  err = transportDec_AdjustEndOfAccessUnit(hTp);
1657
1658
487k
  switch (hTp->transportFmt) {
1659
487k
    default:
1660
487k
      break;
1661
487k
  }
1662
1663
487k
  return err;
1664
487k
}
1665
1666
TRANSPORTDEC_ERROR transportDec_SetParam(const HANDLE_TRANSPORTDEC hTp,
1667
                                         const TPDEC_PARAM param,
1668
0
                                         const INT value) {
1669
0
  TRANSPORTDEC_ERROR error = TRANSPORTDEC_OK;
1670
1671
0
  if (hTp == NULL) {
1672
0
    return TRANSPORTDEC_INVALID_PARAMETER;
1673
0
  }
1674
1675
0
  switch (param) {
1676
0
    case TPDEC_PARAM_MINIMIZE_DELAY:
1677
0
      if (value) {
1678
0
        hTp->flags |= TPDEC_MINIMIZE_DELAY;
1679
0
      } else {
1680
0
        hTp->flags &= ~TPDEC_MINIMIZE_DELAY;
1681
0
      }
1682
0
      break;
1683
0
    case TPDEC_PARAM_EARLY_CONFIG:
1684
0
      if (value) {
1685
0
        hTp->flags |= TPDEC_EARLY_CONFIG;
1686
0
      } else {
1687
0
        hTp->flags &= ~TPDEC_EARLY_CONFIG;
1688
0
      }
1689
0
      break;
1690
0
    case TPDEC_PARAM_IGNORE_BUFFERFULLNESS:
1691
0
      if (value) {
1692
0
        hTp->flags |= TPDEC_IGNORE_BUFFERFULLNESS;
1693
0
      } else {
1694
0
        hTp->flags &= ~TPDEC_IGNORE_BUFFERFULLNESS;
1695
0
      }
1696
0
      break;
1697
0
    case TPDEC_PARAM_SET_BITRATE:
1698
0
      hTp->avgBitRate = value;
1699
0
      break;
1700
0
    case TPDEC_PARAM_BURST_PERIOD:
1701
0
      hTp->burstPeriod = value;
1702
0
      break;
1703
0
    case TPDEC_PARAM_RESET: {
1704
0
      int i;
1705
1706
0
      for (i = 0; i < (1 * 1); i++) {
1707
0
        FDKresetBitbuffer(&hTp->bitStream[i]);
1708
0
        hTp->auLength[i] = 0;
1709
0
        hTp->accessUnitAnchor[i] = 0;
1710
0
      }
1711
0
      hTp->flags &= ~(TPDEC_SYNCOK | TPDEC_LOST_FRAMES_PENDING);
1712
0
      if (hTp->transportFmt != TT_MP4_ADIF) {
1713
0
        hTp->flags &= ~TPDEC_CONFIG_FOUND;
1714
0
      }
1715
0
      hTp->remainder = 0;
1716
0
      hTp->avgBitRate = 0;
1717
0
      hTp->missingAccessUnits = 0;
1718
0
      hTp->numberOfRawDataBlocks = 0;
1719
0
      hTp->globalFramePos = 0;
1720
0
      hTp->holdOffFrames = 0;
1721
0
    } break;
1722
0
    case TPDEC_PARAM_TARGETLAYOUT:
1723
0
      hTp->targetLayout = value;
1724
0
      break;
1725
0
    case TPDEC_PARAM_FORCE_CONFIG_CHANGE:
1726
0
      hTp->ctrlCFGChange[value].forceCfgChange = TPDEC_FORCE_CONFIG_CHANGE;
1727
0
      break;
1728
0
    case TPDEC_PARAM_USE_ELEM_SKIPPING:
1729
0
      if (value) {
1730
0
        hTp->flags |= TPDEC_USE_ELEM_SKIPPING;
1731
0
      } else {
1732
0
        hTp->flags &= ~TPDEC_USE_ELEM_SKIPPING;
1733
0
      }
1734
0
      break;
1735
0
  }
1736
1737
0
  return error;
1738
0
}
1739
1740
0
UINT transportDec_GetNrOfSubFrames(HANDLE_TRANSPORTDEC hTp) {
1741
0
  UINT nSubFrames = 0;
1742
1743
0
  if (hTp == NULL) return 0;
1744
1745
0
  if (hTp->transportFmt == TT_MP4_LATM_MCP1 ||
1746
0
      hTp->transportFmt == TT_MP4_LATM_MCP0 || hTp->transportFmt == TT_MP4_LOAS)
1747
0
    nSubFrames = CLatmDemux_GetNrOfSubFrames(&hTp->parser.latm);
1748
0
  else if (hTp->transportFmt == TT_MP4_ADTS)
1749
0
    nSubFrames = hTp->parser.adts.bs.num_raw_blocks;
1750
1751
0
  return nSubFrames;
1752
0
}
1753
1754
33.1k
void transportDec_Close(HANDLE_TRANSPORTDEC *phTp) {
1755
33.1k
  if (phTp != NULL) {
1756
33.1k
    if (*phTp != NULL) {
1757
33.1k
      FreeRam_TransportDecoderBuffer(&(*phTp)->bsBuffer);
1758
33.1k
      FreeRam_TransportDecoder(phTp);
1759
33.1k
    }
1760
33.1k
  }
1761
33.1k
}
1762
1763
0
TRANSPORTDEC_ERROR transportDec_GetLibInfo(LIB_INFO *info) {
1764
0
  int i;
1765
1766
0
  if (info == NULL) {
1767
0
    return TRANSPORTDEC_UNKOWN_ERROR;
1768
0
  }
1769
1770
  /* search for next free tab */
1771
0
  for (i = 0; i < FDK_MODULE_LAST; i++) {
1772
0
    if (info[i].module_id == FDK_NONE) break;
1773
0
  }
1774
0
  if (i == FDK_MODULE_LAST) return TRANSPORTDEC_UNKOWN_ERROR;
1775
0
  info += i;
1776
1777
0
  info->module_id = FDK_TPDEC;
1778
#ifdef SUPPRESS_BUILD_DATE_INFO
1779
  info->build_date = "";
1780
  info->build_time = "";
1781
#else
1782
0
  info->build_date = __DATE__;
1783
0
  info->build_time = __TIME__;
1784
0
#endif
1785
0
  info->title = TP_LIB_TITLE;
1786
0
  info->version = LIB_VERSION(TP_LIB_VL0, TP_LIB_VL1, TP_LIB_VL2);
1787
0
  LIB_VERSION_STRING(info);
1788
0
  info->flags = 0 | CAPF_ADIF | CAPF_ADTS | CAPF_LATM | CAPF_LOAS |
1789
0
                CAPF_RAWPACKETS | CAPF_DRM;
1790
1791
0
  return TRANSPORTDEC_OK; /* FDKERR_NOERROR; */
1792
0
}
1793
1794
42.5k
int transportDec_CrcStartReg(HANDLE_TRANSPORTDEC pTp, INT mBits) {
1795
42.5k
  switch (pTp->transportFmt) {
1796
0
    case TT_MP4_ADTS:
1797
0
      return adtsRead_CrcStartReg(&pTp->parser.adts, &pTp->bitStream[0], mBits);
1798
0
    case TT_DRM:
1799
0
      return drmRead_CrcStartReg(&pTp->parser.drm, &pTp->bitStream[0], mBits);
1800
42.5k
    default:
1801
42.5k
      return -1;
1802
42.5k
  }
1803
42.5k
}
1804
1805
41.9k
void transportDec_CrcEndReg(HANDLE_TRANSPORTDEC pTp, INT reg) {
1806
41.9k
  switch (pTp->transportFmt) {
1807
0
    case TT_MP4_ADTS:
1808
0
      adtsRead_CrcEndReg(&pTp->parser.adts, &pTp->bitStream[0], reg);
1809
0
      break;
1810
0
    case TT_DRM:
1811
0
      drmRead_CrcEndReg(&pTp->parser.drm, &pTp->bitStream[0], reg);
1812
0
      break;
1813
41.9k
    default:
1814
41.9k
      break;
1815
41.9k
  }
1816
41.9k
}
1817
1818
489k
TRANSPORTDEC_ERROR transportDec_CrcCheck(HANDLE_TRANSPORTDEC pTp) {
1819
489k
  switch (pTp->transportFmt) {
1820
0
    case TT_MP4_ADTS:
1821
0
      if ((pTp->parser.adts.bs.num_raw_blocks > 0) &&
1822
0
          (pTp->parser.adts.bs.protection_absent == 0)) {
1823
0
        transportDec_AdjustEndOfAccessUnit(pTp);
1824
0
      }
1825
0
      return adtsRead_CrcCheck(&pTp->parser.adts);
1826
0
    case TT_DRM:
1827
0
      return drmRead_CrcCheck(&pTp->parser.drm);
1828
489k
    default:
1829
489k
      return TRANSPORTDEC_OK;
1830
489k
  }
1831
489k
}
1832
1833
TRANSPORTDEC_ERROR transportDec_DrmRawSdcAudioConfig_Check(UCHAR *conf,
1834
0
                                                           const UINT length) {
1835
0
  CSAudioSpecificConfig asc;
1836
0
  FDK_BITSTREAM bs;
1837
0
  HANDLE_FDK_BITSTREAM hBs = &bs;
1838
1839
0
  FDKinitBitStream(hBs, conf, BUFSIZE_DUMMY_VALUE, length << 3, BS_READER);
1840
1841
0
  TRANSPORTDEC_ERROR err =
1842
0
      DrmRawSdcAudioConfig_Parse(&asc, hBs, NULL, (UCHAR)AC_CM_ALLOC_MEM, 0);
1843
1844
0
  return err;
1845
0
}