/* -----------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android

© Copyright  1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
Forschung e.V. All rights reserved.

 1.    INTRODUCTION
The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software
that implements the MPEG Advanced Audio Coding ("AAC") encoding and decoding
scheme for digital audio. This FDK AAC Codec software is intended to be used on
a wide variety of Android devices.

AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient
general perceptual audio codecs. AAC-ELD is considered the best-performing
full-bandwidth communications codec by independent studies and is widely
deployed. AAC has been standardized by ISO and IEC as part of the MPEG
specifications.

Patent licenses for necessary patent claims for the FDK AAC Codec (including
those of Fraunhofer) may be obtained through Via Licensing
(www.vialicensing.com) or through the respective patent owners individually for
the purpose of encoding or decoding bit streams in products that are compliant
with the ISO/IEC MPEG audio standards. Please note that most manufacturers of
Android devices already license these patent claims through Via Licensing or
directly from the patent owners, and therefore FDK AAC Codec software may
already be covered under those patent licenses when it is used for those
licensed purposes only.

Commercially-licensed AAC software libraries, including floating-point versions
with enhanced sound quality, are also available from Fraunhofer. Users are
encouraged to check the Fraunhofer website for additional applications
information and documentation.

2.    COPYRIGHT LICENSE

Redistribution and use in source and binary forms, with or without modification,
are permitted without payment of copyright license fees provided that you
satisfy the following conditions:

You must retain the complete text of this software license in redistributions of
the FDK AAC Codec or your modifications thereto in source code form.

You must retain the complete text of this software license in the documentation
and/or other materials provided with redistributions of the FDK AAC Codec or
your modifications thereto in binary form. You must make available free of
charge copies of the complete source code of the FDK AAC Codec and your
modifications thereto to recipients of copies in binary form.

The name of Fraunhofer may not be used to endorse or promote products derived
from this library without prior written permission.

You may not charge copyright license fees for anyone to use, copy or distribute
the FDK AAC Codec software or your modifications thereto.

Your modified versions of the FDK AAC Codec must carry prominent notices stating
that you changed the software and the date of any change. For modified versions
of the FDK AAC Codec, the term "Fraunhofer FDK AAC Codec Library for Android"
must be replaced by the term "Third-Party Modified Version of the Fraunhofer FDK
AAC Codec Library for Android."

3.    NO PATENT LICENSE

NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without
limitation the patents of Fraunhofer, ARE GRANTED BY THIS SOFTWARE LICENSE.
Fraunhofer provides no warranty of patent non-infringement with respect to this
software.

You may use this FDK AAC Codec software or modifications thereto only for
purposes that are authorized by appropriate patent licenses.

4.    DISCLAIMER

This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright
holders and contributors "AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES,
including but not limited to the implied warranties of merchantability and
fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary,
or consequential damages, including but not limited to procurement of substitute
goods or services; loss of use, data, or profits, or business interruption,
however caused and on any theory of liability, whether in contract, strict
liability, or tort (including negligence), arising in any way out of the use of
this software, even if advised of the possibility of such damage.

5.    CONTACT INFORMATION

Fraunhofer Institute for Integrated Circuits IIS
Attention: Audio and Multimedia Departments - FDK AAC LL
Am Wolfsmantel 33
91058 Erlangen, Germany

www.iis.fraunhofer.de/amm
amm-info@iis.fraunhofer.de
----------------------------------------------------------------------------- */

/*********************** MPEG surround decoder library *************************

   Author(s):

   Description: SAC Decoder Library Interface

*******************************************************************************/

#include "sac_dec_lib.h"
#include "sac_dec_interface.h"
#include "sac_dec.h"
#include "sac_bitdec.h"
#include "FDK_matrixCalloc.h"

#define MPS_DATA_BUFFER_SIZE (2048)

/**
 * \brief MPEG Surround data indication.
 **/
typedef enum {
  MPEGS_ANCTYPE_FRAME = 0, /*!< MPEG Surround frame, see ISO/IEC 23003-1 */
  MPEGS_ANCTYPE_HEADER_AND_FRAME = 1, /*!< MPEG Surround header and MPEG
                                         Surround frame, see ISO/IEC 23003-1 */
  MPEGS_ANCTYPE_RESERVED_1 = 2,       /*!< reserved, see ISO/IEC 23003-1 */
  MPEGS_ANCTYPE_RESERVED_2 = 3        /*!< reserved, see ISO/IEC 23003-1*/
} MPEGS_ANCTYPE;

/**
 * \brief MPEG Surround data segment indication.
 **/
typedef enum {
  MPEGS_CONTINUE = 0, /*!< Indicates if data segment continues a data block. */
  MPEGS_STOP = 1,     /*!< Indicates if data segment ends a data block. */
  MPEGS_START = 2,    /*!< Indicates if data segment begins a data block. */
  MPEGS_START_STOP =
      3 /*!< Indicates if data segment begins and ends a data block. */
} MPEGS_ANCSTARTSTOP;

/**
 * \brief MPEG Surround synchronizaiton state.
 *
 *  CAUTION: Changing the enumeration values can break the sync mechanism
 *because it is based on comparing the state values.
 **/
typedef enum {
  MPEGS_SYNC_LOST =
      0, /*!< Indicates lost sync because of current discontinuity. */
  MPEGS_SYNC_FOUND = 1,   /*!< Parsed a valid header and (re)intialization was
                             successfully completed. */
  MPEGS_SYNC_COMPLETE = 2 /*!< In sync and continuous. Found an independent
                             frame in addition to MPEGS_SYNC_FOUND.
                               Precondition: MPEGS_SYNC_FOUND. */
} MPEGS_SYNCSTATE;

/**
 * \brief MPEG Surround operation mode.
 **/
typedef enum {
  MPEGS_OPMODE_EMM = 0,           /*!< Mode: Enhanced Matrix Mode (Blind) */
  MPEGS_OPMODE_MPS_PAYLOAD = 1,   /*!< Mode: Normal, Stereo or Binaural */
  MPEGS_OPMODE_NO_MPS_PAYLOAD = 2 /*!< Mode: no MPEG Surround payload */
} MPEGS_OPMODE;

/**
 * \brief MPEG Surround init flags.
 **/
typedef enum {
  MPEGS_INIT_OK = 0x00000000, /*!< indicate correct initialization */
  MPEGS_INIT_ENFORCE_REINIT =
      0x00000001, /*!< indicate complete initialization */

  MPEGS_INIT_CHANGE_OUTPUT_MODE =
      0x00000010, /*!< indicate change of the output mode */
  MPEGS_INIT_CHANGE_PARTIALLY_COMPLEX =
      0x00000020, /*!< indicate change of low power/high quality */
  MPEGS_INIT_CHANGE_TIME_FREQ_INTERFACE =
      0x00000040, /*!< indicate change of qmf/time interface */
  MPEGS_INIT_CHANGE_HEADER = 0x00000080, /*!< indicate change of header */

  MPEGS_INIT_ERROR_PAYLOAD =
      0x00000100, /*!< indicate payload/ancType/ancStartStop error */

  MPEGS_INIT_BS_INTERRUPTION =
      0x00001000, /*!< indicate bitstream interruption  */
  MPEGS_INIT_CLEAR_HISTORY =
      0x00002000, /*!< indicate that all states shall be cleared */

  /* Re-initialization of submodules */

  MPEGS_INIT_CHANGE_CONCEAL_PARAMS = 0x00100000, /*!< indicate a change of at
                                                    least one error concealment
                                                    param */

  /* No re-initialization needed, currently not used */
  MPEGS_INIT_CHANGE_BYPASS_MODE =
      0x01000000, /*!< indicate change of bypass mode */

  /* Re-initialization needed, currently not used */
  MPEGS_INIT_ERROR_ANC_TYPE = 0x10000000, /*!< indicate ancType error*/
  MPEGS_INIT_ERROR_ANC_STARTSTOP =
      0x20000000 /*!< indicate ancStartStop error */
} MPEGS_INIT_FLAGS;

struct MpegSurroundDecoder {
  HANDLE_FDK_QMF_DOMAIN pQmfDomain;
  UCHAR mpsData[MPS_DATA_BUFFER_SIZE]; /* Buffer for MPS payload accross more
                                          than one segment */
  INT mpsDataBits;                     /* Amount of bits in mpsData */
  /* MPEG Surround decoder */
  SPATIAL_SPECIFIC_CONFIG spatialSpecificConfig[1]; /* SSC delay line which is
                                                       used during decoding */
  spatialDec *pSpatialDec;
  SPATIAL_SPECIFIC_CONFIG
  spatialSpecificConfigBackup; /* SSC used while parsing */

  /* Creation parameter */
  UCHAR mpegSurroundDecoderLevel;
  /* Run-time parameter */
  UCHAR mpegSurroundSscIsGlobalCfg; /* Flag telling that the SSC
                                       (::spatialSpecificConfig) is a
                                       out-of-band configuration. */
  UCHAR mpegSurroundUseTimeInterface;

  SPATIAL_BS_FRAME
  bsFrames[1];         /* Bitstream Structs that contain data read from the
                          SpatialFrame() bitstream element */
  BS_LL_STATE llState; /* Bit stream parser state memory */
  UCHAR bsFrameParse;  /* Current parse frame context index */
  UCHAR bsFrameDecode; /* Current decode/apply frame context index */
  UCHAR bsFrameDelay;  /* Amount of frames delay between parsing and processing.
                          Required i.e. for interpolation error concealment. */

  /* User prameters */
  SPATIALDEC_PARAM mpegSurroundUserParams;

  /* Internal flags */
  SPATIAL_DEC_UPMIX_TYPE upmixType;
  int initFlags[1];
  MPEGS_ANCSTARTSTOP ancStartStopPrev;
  MPEGS_SYNCSTATE fOnSync[1];

  /* Inital decoder configuration */
  SPATIAL_DEC_CONFIG decConfig;
};

static SACDEC_ERROR sscParseCheck(const SPATIAL_SPECIFIC_CONFIG *pSsc);

/**
 * \brief Get the number of QMF bands from the sampling frequency (in Hz)
 **/
static int mpegSurroundDecoder_GetNrOfQmfBands(
    const SPATIAL_SPECIFIC_CONFIG *pSsc, UINT sampleRate) {
  UINT samplingFrequency = sampleRate;
  int qmfBands = 64;

  if (pSsc != NULL) {
    switch (pSsc->coreCodec) {
      case AOT_USAC:
        if ((pSsc->stereoConfigIndex == 3)) {
          static const UCHAR mapIdx2QmfBands[3] = {24, 32, 16};
          FDK_ASSERT((pSsc->coreSbrFrameLengthIndex >= 2) &&
                     (pSsc->coreSbrFrameLengthIndex <= 4));
          qmfBands = mapIdx2QmfBands[pSsc->coreSbrFrameLengthIndex - 2];
        }
        return qmfBands;
      default:
        samplingFrequency = pSsc->samplingFreq;
        break;
    }
  }

  /* number of QMF bands depend on sampling frequency, see FDIS 23003-1:2006
   * Chapter 6.3.3 */
  if (samplingFrequency < 27713) {
    qmfBands = 32;
  }
  if (samplingFrequency > 55426) {
    qmfBands = 128;
  }

  return qmfBands;
}

/**
 * \brief Analyse init flags
 **/
static int mpegSurroundDecoder_CalcInitFlags(SPATIAL_SPECIFIC_CONFIG *pSsc1,
                                             SPATIAL_SPECIFIC_CONFIG *pSsc2,
                                             int upmixTypeFlag,
                                             int binauralQualityFlag,
                                             int partiallyComplexFlag,
                                             int *ctrlFlags) {
  /* Analyse core coder */
  if (pSsc1->coreCodec != pSsc2->coreCodec) {
    *ctrlFlags |= MASK_MPEGS_INIT_ALL_STATES;
    *ctrlFlags |= MASK_MPEGS_INIT_ALL_PARAMS;
  } else {
    /* Analyse elements for initialization of space analysis qmf filterbank */
    if ((partiallyComplexFlag) || (pSsc1->treeConfig != pSsc2->treeConfig) ||
        (pSsc1->samplingFreq != pSsc2->samplingFreq)) {
      *ctrlFlags |= MPEGS_INIT_STATES_ANA_QMF_FILTER;
      *ctrlFlags |= MPEGS_INIT_STATES_ANA_HYB_FILTER;
    }

    /* Analyse elements for initialization of space synthesis qmf filterbank */
    if ((upmixTypeFlag) || (partiallyComplexFlag) ||
        (pSsc1->treeConfig != pSsc2->treeConfig) ||
        (pSsc1->samplingFreq != pSsc2->samplingFreq) ||
        (pSsc1->bsFixedGainDMX != pSsc2->bsFixedGainDMX)) {
      *ctrlFlags |= MPEGS_INIT_STATES_SYN_QMF_FILTER;
    }

    /* Analyse elements for initialization of decorrelator */
    if ((upmixTypeFlag) || (partiallyComplexFlag) ||
        (pSsc1->treeConfig != pSsc2->treeConfig) ||
        (pSsc1->samplingFreq != pSsc2->samplingFreq) ||
        (pSsc1->decorrConfig != pSsc2->decorrConfig)) {
      *ctrlFlags |= MPEGS_INIT_STATES_DECORRELATOR;
    }

    /* Analyse elements for initialization of m1 and m2 calculation */
    if ((upmixTypeFlag) || (binauralQualityFlag) ||
        (pSsc1->treeConfig != pSsc2->treeConfig) ||
        (pSsc1->samplingFreq != pSsc2->samplingFreq))

    {
      *ctrlFlags |= MPEGS_INIT_STATES_M1M2;
    }

    /* Analyse elements for initialization of GES */
    if ((upmixTypeFlag) || (pSsc1->treeConfig != pSsc2->treeConfig) ||
        (pSsc1->tempShapeConfig != pSsc2->tempShapeConfig)) {
      *ctrlFlags |= MPEGS_INIT_STATES_GES;
    }

    /* Analyse elements for initialization of FDreverb */
    if ((upmixTypeFlag) || (binauralQualityFlag) || (partiallyComplexFlag) ||
        (pSsc1->samplingFreq != pSsc2->samplingFreq) ||
        (pSsc1->nTimeSlots != pSsc2->nTimeSlots)) {
      *ctrlFlags |= MPEGS_INIT_STATES_REVERB;
    }

    /* Reset previous frame data whenever the config changes */
    if (*ctrlFlags & MPEGS_INIT_CONFIG) {
      *ctrlFlags |= MPEGS_INIT_STATES_PARAM;
    }
  }

  return MPS_OK;
}

/**
 * \brief Reset MPEG Surround status info
 **/
static void updateMpegSurroundDecoderStatus(
    CMpegSurroundDecoder *pMpegSurroundDecoder, int initFlags,
    MPEGS_SYNCSTATE fOnSync, MPEGS_ANCSTARTSTOP ancStartStopPrev) {
  pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode] |=
      initFlags;
  if ((pMpegSurroundDecoder->mpegSurroundSscIsGlobalCfg != 0) &&
      (pMpegSurroundDecoder->fOnSync[pMpegSurroundDecoder->bsFrameDecode] >=
       MPEGS_SYNC_FOUND) &&
      (fOnSync < MPEGS_SYNC_FOUND)) {
    pMpegSurroundDecoder->fOnSync[pMpegSurroundDecoder->bsFrameDecode] =
        MPEGS_SYNC_FOUND;
  } else {
    pMpegSurroundDecoder->fOnSync[pMpegSurroundDecoder->bsFrameDecode] =
        fOnSync;
  }
  pMpegSurroundDecoder->ancStartStopPrev = ancStartStopPrev;
}

static SACDEC_ERROR mpegSurroundDecoder_Create(
    CMpegSurroundDecoder **pMpegSurroundDecoder, int stereoConfigIndex,
    HANDLE_FDK_QMF_DOMAIN pQmfDomain);

SAC_INSTANCE_AVAIL
mpegSurroundDecoder_IsFullMpegSurroundDecoderInstanceAvailable(
    CMpegSurroundDecoder *pMpegSurroundDecoder) {
  SAC_INSTANCE_AVAIL instanceAvailable = SAC_INSTANCE_NOT_FULL_AVAILABLE;

  if (pMpegSurroundDecoder->pSpatialDec != NULL) {
    instanceAvailable = SAC_INSTANCE_FULL_AVAILABLE;
  }

  return instanceAvailable;
}

SACDEC_ERROR mpegSurroundDecoder_Open(
    CMpegSurroundDecoder **pMpegSurroundDecoder, int stereoConfigIndex,
    HANDLE_FDK_QMF_DOMAIN pQmfDomain) {
  SACDEC_ERROR error;

  error = mpegSurroundDecoder_Create(pMpegSurroundDecoder, stereoConfigIndex,
                                     pQmfDomain);

  return error;
}

/**
 * \brief  Renamed function from getUpmixType to check_UParam_Build_DecConfig.
 *         This function checks if user params, decoder config and SSC are valid
 *         and if the decoder build can handle all this settings.
 *         The upmix type may be modified by this function.
 *         It is called in initMpegSurroundDecoder() after the ssc parse check,
 *         to have all checks in one place and to ensure these checks are always
 *         performed if config changes (inband and out-of-band).
 *
 * \param pUserParams  User data handle.
 * \param pDecConfig   decoder config handle.
 * \param pSsc         spatial specific config handle.
 * \param pUpmixType   upmix type which is set by this function
 *
 * \return  MPS_OK on sucess, and else on failure.
 */
static SACDEC_ERROR check_UParam_Build_DecConfig(
    SPATIALDEC_PARAM const *pUserParams, SPATIAL_DEC_CONFIG const *pDecConfig,
    const SPATIAL_SPECIFIC_CONFIG *pSsc, SPATIAL_DEC_UPMIX_TYPE *pUpmixType) {
  int dmxChannels, outChannels, maxNumOutChannels;

  FDK_ASSERT(pUserParams != NULL);
  FDK_ASSERT(pUpmixType != NULL);

  /* checks if implementation can handle the Ssc */

  switch (pSsc->treeConfig) {
    case SPATIALDEC_MODE_RSVD7: /* 212 */
      dmxChannels = 1;
      outChannels = 2;
      break;
    default:
      return MPS_UNSUPPORTED_CONFIG;
  }

  /* ------------------------------------------- */

  /* Analyse pDecConfig params */
  switch (pDecConfig->binauralMode) {
    case BINAURAL_NONE:
      break;
    default:
      return MPS_UNSUPPORTED_CONFIG;
  }

  switch (pDecConfig->decoderMode) {
    case EXT_HQ_ONLY:
      break;
    default:
      return MPS_UNSUPPORTED_CONFIG;
  }

  switch (pDecConfig->maxNumOutputChannels) {
    case OUTPUT_CHANNELS_DEFAULT:
      /* No special restrictions -> Get the level restriction: */
      switch (pDecConfig->decoderLevel) {
        case DECODER_LEVEL_0:
          maxNumOutChannels = 2;
          break;
        default:
          return MPS_UNSUPPORTED_CONFIG;
      }
      break;
    case OUTPUT_CHANNELS_2_0:
      maxNumOutChannels = 2;
      break;
    default:
      return MPS_UNSUPPORTED_CONFIG;
  }
  /* ------------------------- */

  /* check if we can handle user params */
  if (pUserParams->blindEnable == 1) {
    return MPS_UNSUPPORTED_CONFIG;
  }
  {
    switch ((SAC_DEC_OUTPUT_MODE)pUserParams->outputMode) {
      case SACDEC_OUT_MODE_NORMAL:
        if (maxNumOutChannels >= outChannels) {
          *pUpmixType = UPMIX_TYPE_NORMAL;
        } else {
          { *pUpmixType = UPMIX_TYPE_BYPASS; }
        }
        break;
      case SACDEC_OUT_MODE_STEREO:
        if (dmxChannels == 1) {
          if (outChannels == 2) {
            *pUpmixType = UPMIX_TYPE_NORMAL;
          }
        } else {
          *pUpmixType = UPMIX_TYPE_BYPASS;
        }
        break;
      case SACDEC_OUT_MODE_6CHANNEL:
        if (outChannels > 6) {
          { *pUpmixType = UPMIX_TYPE_BYPASS; }
        } else {
          *pUpmixType = UPMIX_TYPE_NORMAL;
        }
        break;
      default:
        return MPS_UNSUPPORTED_CONFIG;
    }
  }

  return MPS_OK;
}

/**
 * \brief Init MPEG Surround decoder.
 **/
static SACDEC_ERROR initMpegSurroundDecoder(
    CMpegSurroundDecoder *pMpegSurroundDecoder) {
  SACDEC_ERROR err;
  int initFlags = MPEGS_INIT_NONE, initFlagsDec;
  int upmixTypeCurr = pMpegSurroundDecoder->upmixType;

  FDK_ASSERT(pMpegSurroundDecoder != NULL);

  SPATIAL_SPECIFIC_CONFIG *const pSSCinput =
      &pMpegSurroundDecoder->spatialSpecificConfigBackup;
  SPATIAL_SPECIFIC_CONFIG *const pSSCtarget =
      &pMpegSurroundDecoder
           ->spatialSpecificConfig[pMpegSurroundDecoder->bsFrameDecode];
  initFlagsDec =
      pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode];

  if (pSSCinput->coreCodec != AOT_USAC) {
    /* here we check if we have a valid Ssc */
    err = sscParseCheck(pSSCinput);
    if (err != MPS_OK) goto bail;
  }

  /* here we check if Ssc matches build; also check UParams and DecConfig */
  /* if desired upmixType is changes                                      */
  err = check_UParam_Build_DecConfig(
      &pMpegSurroundDecoder->mpegSurroundUserParams,
      &pMpegSurroundDecoder->decConfig, pSSCinput,
      &pMpegSurroundDecoder->upmixType);
  if (err != MPS_OK) goto bail;

  /* init config */
  if (initFlagsDec & MPEGS_INIT_CHANGE_HEADER) {
    initFlags |= MPEGS_INIT_CONFIG;
  }
  /* init all states */
  if (initFlagsDec & MPEGS_INIT_CLEAR_HISTORY) {
    initFlags |= MASK_MPEGS_INIT_ALL_STATES;
  }
  if (initFlagsDec & MPEGS_INIT_CHANGE_CONCEAL_PARAMS) {
    initFlags |= MPEGS_INIT_PARAMS_ERROR_CONCEALMENT;
  }

  if (initFlagsDec & MPEGS_INIT_ENFORCE_REINIT) {
    /* init all states */
    initFlags |= MASK_MPEGS_INIT_ALL_STATES;
    initFlags |= MASK_MPEGS_INIT_ALL_PARAMS;
  } else {
    /* analyse states which have to be initialized */
    mpegSurroundDecoder_CalcInitFlags(
        pSSCtarget, pSSCinput,
        (upmixTypeCurr !=
         pMpegSurroundDecoder->upmixType), /* upmixType changed */
        0, (initFlagsDec & MPEGS_INIT_CHANGE_PARTIALLY_COMPLEX) ? 1 : 0,
        &initFlags);
  }

  {
    int nrOfQmfBands;
    FDKmemcpy(pSSCtarget, pSSCinput, sizeof(SPATIAL_SPECIFIC_CONFIG));

    nrOfQmfBands = mpegSurroundDecoder_GetNrOfQmfBands(
        pSSCtarget, pSSCtarget->samplingFreq);
    err = FDK_SpatialDecInit(
        pMpegSurroundDecoder->pSpatialDec,
        &pMpegSurroundDecoder->bsFrames[pMpegSurroundDecoder->bsFrameDecode],
        pSSCtarget, nrOfQmfBands, pMpegSurroundDecoder->upmixType,
        &pMpegSurroundDecoder->mpegSurroundUserParams, initFlags);

    if (err != MPS_OK) goto bail;

    /* Signal that we got a header and can go on decoding */
    if (err == MPS_OK) {
      initFlagsDec = MPEGS_INIT_OK;
      {
        pMpegSurroundDecoder->fOnSync[pMpegSurroundDecoder->bsFrameDecode] =
            MPEGS_SYNC_FOUND;
      }
    }
  }

bail:
  pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode] =
      initFlagsDec;
  return err;
}

/**
 * \brief Init MPEG Surround decoder.
 **/
SACDEC_ERROR mpegSurroundDecoder_Init(
    CMpegSurroundDecoder *pMpegSurroundDecoder) {
  SACDEC_ERROR err = MPS_OK;

  if (pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode]) {
    err = initMpegSurroundDecoder(pMpegSurroundDecoder);
  }
  return err;
}

/**
 * \brief Open MPEG Surround decoder.
 **/
static SACDEC_ERROR mpegSurroundDecoder_Create(
    CMpegSurroundDecoder **pMpegSurroundDecoder, int stereoConfigIndex,
    HANDLE_FDK_QMF_DOMAIN pQmfDomain) {
  SACDEC_ERROR err = MPS_OK;
  CMpegSurroundDecoder *sacDec = NULL;
  spatialDec *self = NULL;

  /* decoderLevel  decoderMode  maxNumOutputChannels  binauralMode */
  static const SPATIAL_DEC_CONFIG decConfig = {
      (CFG_LEVEL)(0), EXT_HQ_ONLY, OUTPUT_CHANNELS_DEFAULT, BINAURAL_NONE};

  if (*pMpegSurroundDecoder == NULL) {
    FDK_ALLOCATE_MEMORY_1D(*pMpegSurroundDecoder, 1, CMpegSurroundDecoder)

    for (int i = 0; i < 1; i++) {
      err = SpatialDecCreateBsFrame(&(*pMpegSurroundDecoder)->bsFrames[i],
                                    &(*pMpegSurroundDecoder)->llState);
      if (err != MPS_OK) {
        sacDec = *pMpegSurroundDecoder;
        goto bail;
      }
    }
    (*pMpegSurroundDecoder)->pQmfDomain = pQmfDomain;

    (*pMpegSurroundDecoder)->bsFrameDelay = 1;
    (*pMpegSurroundDecoder)->bsFrameParse = 0;
    (*pMpegSurroundDecoder)->bsFrameDecode = 0;

    return err;
  } else {
    sacDec = *pMpegSurroundDecoder;
  }

  if (sacDec->pSpatialDec == NULL) {
    if ((self = FDK_SpatialDecOpen(&decConfig, stereoConfigIndex)) == NULL) {
      err = MPS_OUTOFMEMORY;
      goto bail;
    }
  } else {
    self = sacDec->pSpatialDec;
  }

  self->pQmfDomain = sacDec->pQmfDomain;

  sacDec->pSpatialDec = self;

  /* default parameter set */
  sacDec->mpegSurroundUserParams.outputMode = SACDEC_OUT_MODE_NORMAL;
  sacDec->mpegSurroundUserParams.blindEnable = 0;
  sacDec->mpegSurroundUserParams.bypassMode = 0;
  sacDec->mpegSurroundUserParams.concealMethod = 1;
  sacDec->mpegSurroundUserParams.concealNumKeepFrames = 10;
  sacDec->mpegSurroundUserParams.concealFadeOutSlopeLength = 5;
  sacDec->mpegSurroundUserParams.concealFadeInSlopeLength = 5;
  sacDec->mpegSurroundUserParams.concealNumReleaseFrames = 3;
  sacDec->mpegSurroundSscIsGlobalCfg = 0;
  sacDec->mpegSurroundUseTimeInterface = 1;
  sacDec->mpegSurroundDecoderLevel = decConfig.decoderLevel;

  sacDec->upmixType = UPMIX_TYPE_NORMAL;

  /* signalize spatial decoder re-initalization */
  updateMpegSurroundDecoderStatus(sacDec, MPEGS_INIT_ENFORCE_REINIT,
                                  MPEGS_SYNC_LOST, MPEGS_STOP);

  /* return decoder instance */
  *pMpegSurroundDecoder = sacDec;
  sacDec->decConfig = decConfig;

  SpatialDecInitParserContext(sacDec->pSpatialDec);

  return err;

bail:
  if (sacDec != NULL) {
    mpegSurroundDecoder_Close(sacDec);
  }
  *pMpegSurroundDecoder = NULL;
  if (err == MPS_OK) {
    return MPS_OUTOFMEMORY;
  } else {
    return err;
  }
}

/**
 * \brief Config MPEG Surround decoder.
 **/
SACDEC_ERROR mpegSurroundDecoder_Config(
    CMpegSurroundDecoder *pMpegSurroundDecoder, HANDLE_FDK_BITSTREAM hBs,
    AUDIO_OBJECT_TYPE coreCodec, INT samplingRate, INT stereoConfigIndex,
    INT coreSbrFrameLengthIndex, INT configBytes, const UCHAR configMode,
    UCHAR *configChanged) {
  SACDEC_ERROR err = MPS_OK;

  switch (coreCodec) {
    case AOT_DRM_USAC:
    case AOT_USAC:
      if (configMode == AC_CM_DET_CFG_CHANGE) {
        /* In config detection mode write spatial specific config parameters
         * into temporarily allocated structure */
        SPATIAL_SPECIFIC_CONFIG spatialSpecificConfig;
        err = SpatialDecParseMps212Config(
            hBs, &spatialSpecificConfig, samplingRate, coreCodec,
            stereoConfigIndex, coreSbrFrameLengthIndex);
      } else {
        err = SpatialDecParseMps212Config(
            hBs, &pMpegSurroundDecoder->spatialSpecificConfigBackup,
            samplingRate, coreCodec, stereoConfigIndex,
            coreSbrFrameLengthIndex);
      }
      break;
    case AOT_ER_AAC_ELD:
    case AOT_ER_AAC_LD:
      err = SpatialDecParseSpecificConfig(
          hBs, &pMpegSurroundDecoder->spatialSpecificConfigBackup, configBytes,
          coreCodec);
      break;
    default:
      err = MPS_UNSUPPORTED_FORMAT;
      break;
  }

  if (err != MPS_OK) {
    goto bail;
  }

  if (configMode & AC_CM_DET_CFG_CHANGE) {
    return err;
  }

  if (configMode & AC_CM_ALLOC_MEM) {
    if (*configChanged) {
      if ((err = mpegSurroundDecoder_Open(&pMpegSurroundDecoder,
                                          stereoConfigIndex, NULL))) {
        return err;
      }
    }
  }

  {
    SPATIAL_SPECIFIC_CONFIG *sscParse =
        &pMpegSurroundDecoder
             ->spatialSpecificConfig[pMpegSurroundDecoder->bsFrameParse];

    if (FDK_SpatialDecCompareSpatialSpecificConfigHeader(
            &pMpegSurroundDecoder->spatialSpecificConfigBackup, sscParse)) {
      pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameParse] |=
          MPEGS_INIT_CHANGE_HEADER;
      /* Error resilience code */
      if (pMpegSurroundDecoder->pSpatialDec == NULL) {
        err = MPS_NOTOK;
        goto bail;
      }
      SpatialDecInitParserContext(pMpegSurroundDecoder->pSpatialDec);
      pMpegSurroundDecoder->pSpatialDec->pConfigCurrent =
          &pMpegSurroundDecoder
               ->spatialSpecificConfig[pMpegSurroundDecoder->bsFrameDecode];
    }
  }

  if (err == MPS_OK) {
    /* We got a valid out-of-band configuration so label it accordingly. */
    pMpegSurroundDecoder->mpegSurroundSscIsGlobalCfg = 1;
  }

bail:
  return err;
}

/**
 * \brief Determine MPEG Surround operation mode.
 **/
static MPEGS_OPMODE mpegSurroundOperationMode(
    CMpegSurroundDecoder *pMpegSurroundDecoder, int mpsDataBits) {
  MPEGS_OPMODE mode;

  {
    if ((mpsDataBits > 0) &&
        (pMpegSurroundDecoder->mpegSurroundUserParams.blindEnable == 0)) {
      mode = MPEGS_OPMODE_MPS_PAYLOAD; /* Mode: Normal, Stereo or Binaural */
    } else {
      mode = MPEGS_OPMODE_NO_MPS_PAYLOAD; /* Mode: No MPEG Surround Payload */
      updateMpegSurroundDecoderStatus(pMpegSurroundDecoder,
                                      MPEGS_INIT_ERROR_PAYLOAD, MPEGS_SYNC_LOST,
                                      MPEGS_STOP);
    }
  }

  return (mode);
}

/**
 * \brief  Check ssc for parse errors.
 *         This one is called in initMpegSurroundDecoder()
 *         to ensure checking of inband and out-of-band mps configs.
 *         Only parse errors checked here! Check for valid config is done
 *         in check_UParam_Build_DecConfig()!
 *
 * \param pSsc         spatial specific config handle.
 *
 * \return  MPS_OK on sucess, and else on parse error.
 */
static SACDEC_ERROR sscParseCheck(const SPATIAL_SPECIFIC_CONFIG *pSsc) {
  SACDEC_ERROR err = MPS_OK;

  if (pSsc->samplingFreq > 96000) return MPS_PARSE_ERROR;
  if (pSsc->samplingFreq < 8000) return MPS_PARSE_ERROR;

  switch (pSsc->freqRes) {
    case SPATIALDEC_FREQ_RES_28:
    case SPATIALDEC_FREQ_RES_20:
    case SPATIALDEC_FREQ_RES_14:
    case SPATIALDEC_FREQ_RES_10:
    case SPATIALDEC_FREQ_RES_23:
    case SPATIALDEC_FREQ_RES_15:
    case SPATIALDEC_FREQ_RES_12:
    case SPATIALDEC_FREQ_RES_9:
    case SPATIALDEC_FREQ_RES_7:
    case SPATIALDEC_FREQ_RES_5:
    case SPATIALDEC_FREQ_RES_4:
      break;
    case SPATIALDEC_FREQ_RES_40: /* 40 doesn't exist in ISO/IEC 23003-1 */
    default:
      return MPS_PARSE_ERROR;
  }

  if ((pSsc->treeConfig < 0) || (pSsc->treeConfig > 7)) {
    return MPS_PARSE_ERROR;
  }

  if ((pSsc->quantMode < 0) || (pSsc->quantMode > 2)) {
    return MPS_PARSE_ERROR;
  }

  if (pSsc->tempShapeConfig == 3) {
    return MPS_PARSE_ERROR;
  }

  if (pSsc->decorrConfig == 3) {
    return MPS_PARSE_ERROR;
  }

  /* now we are sure there were no parsing errors */

  return err;
}

/**
 * \brief  Check number of time slots
 *
 * Basically the mps frame length must be a multiple of the core coder frame
 * length. The below table shows all valid configurations in detail. See ISO/IEC
 * 23003-1: "Table 4A - Allowed values for bsFrameLength in the Baseline MPEG
 * Surround Profile"
 *
 * Downmix Coder        Downmix Code      Allowed values for bsFrameLength
 * Allowed frame sizes for normal, downsampled and upsampled MPS Framelength
 *                      (QMF Samples)
 *
 * AAC 1024                  16           15, 31, 47, 63 1024  2048  3072  4096
 * downsampled MPS           32           31, 63 1024  2048 upsampled MPS
 * 8            7, 15, 23, 31, 39, 47, 55, 63, 71    1024  2048  3072  4096
 * 5120  6144  7168  8192  9216
 *
 * AAC 960                   15           14, 29, 44, 59 960  1920  2880  3840
 * downsampled MPS           30           29, 59 960  1920 upsampled MPS
 * 7,5           14, 29, 44, 59                        1920  3840  5760  7680
 *
 * HE-AAC 1024/2048          32           31, 63 2048  4096 downsampled MPS
 * 64           63                                    2048 upsampled MPS
 * 16           15, 31, 47, 63                        2048  4096  6144  8192
 *
 * HE-AAC 960/1920           30           29, 59 1920  3840 downsampled MPS
 * 60           59                                    1920 upsampled MPS
 * 15           14, 29, 44, 59                        1920  3840  5760  7680
 *
 * BSAC                      16           15, 31, 47, 63 1024  2048  3072  4096
 * downsampled MPS           32           31, 63 1024  2048 upsampled MPS
 * 8            7, 15, 23, 31, 39, 47, 55, 63, 71    1024  2048  3072  4096
 * 5120  6144  7168  8192  9216
 *
 * BSAC with SBR             32           31, 63 2048  4096 downsampled MPS
 * 64           63                                    2048 upsampled MPS
 * 16           15, 31, 47, 63                        2048  4096  6144  8192
 *
 * AAC LD 512                 8            7, 15, 23, 31, 39, 47, 55, 63, 71
 * 512  1024  1536  2048  2560  3072  3584  4096  4608 downsampled MPS
 * 16           15, 31, 47, 63                         512  1024  1536  2048
 *
 * AAC ELD 512                8            7, 15, 23, 31, 39, 47, 55, 63, 71
 * 512  1024  1536  2048  2560  3072  3584  4096  4608 downsampled MPS
 * 16           15, 31, 47, 63                         512  1024  1536  2048
 *
 * AAC ELD with SBR 512/1024 16           15, 31, 47, 63 1024  2048  3072  4096
 * downsampled MPS           32           31, 63 1024  2048 upsampled MPS
 * 8            7, 15, 23, 31, 39, 47, 55, 63, 71    1024  2048  3072  4096
 * 5120  6144  7168  8192  9216
 *
 * MPEG1/2 Layer II          18           17, 35, 53, 71 1152  2304  3456  4608
 * downsampled MPS           36           35, 71 1152  2304
 *
 * MPEG1/2 Layer III         18           17, 35, 53, 71 1152  2304  3456  4608
 * downsampled MPS           36           35, 71 1152  2304
 *
 * \param frameLength
 * \param qmfBands
 * \param timeSlots
 *
 * \return  error code
 */
SACDEC_ERROR checkTimeSlots(int frameLength, int qmfBands, int timeSlots) {
  int len;
  int maxFrameLength;

  if (qmfBands == 64) {
    /* normal MPEG Surround */
    switch (frameLength) {
      case 960:
      case 1920:
        maxFrameLength = 3840;
        break;
      case 1024:
      case 2048:
        maxFrameLength = 4096;
        break;
      case 512:
      case 1152:
        maxFrameLength = 4608;
        break;
      default:
        return MPS_PARSE_ERROR;
    }
  } else if (qmfBands == 32) {
    /* downsampled MPEG Surround */
    switch (frameLength) {
      case 960:
      case 1920:
        maxFrameLength = 1920;
        break;
      case 512:
      case 1024:
      case 2048:
        maxFrameLength = 2048;
        break;
      case 1152:
        maxFrameLength = 2304;
        break;
      default:
        return MPS_PARSE_ERROR;
    }
  } else if (qmfBands == 128) {
    /* upsampled MPEG Surround */
    switch (frameLength) {
      case 1920:
        maxFrameLength = 7680;
        break;
      case 1024:
        maxFrameLength = 9216;
        break;
      case 2048:
        maxFrameLength = 8192;
        break;
      case 512:
      case 960:
      case 1152:
      /* no break, no support for upsampled MPEG Surround */
      default:
        return MPS_PARSE_ERROR;
    }
  } else {
    return MPS_PARSE_ERROR;
  }

  len = frameLength;

  while (len <= maxFrameLength) {
    if (len == timeSlots * qmfBands) {
      return MPS_OK;
    }
    len += frameLength;
  }
  return MPS_PARSE_ERROR;
}

/**
 * \brief  Check ssc for consistency (e.g. bit errors could cause trouble)
 *         First of currently two ssc-checks.
 *         This (old) one is called in mpegSurroundDecoder_Apply()
 *         only if inband mps config is contained in stream.
 *
 *         New ssc check is split in two functions sscParseCheck() and
 * check_UParam_Build_DecConfig(). sscParseCheck() checks only for correct
 * parsing. check_UParam_Build_DecConfig() is used to check if we have a
 * valid config. Both are called in initMpegSurroundDecoder() to ensure
 * checking of inband and out-of-band mps configs.
 *
 *         If this function can be integrated into the new functions.
 *         We can remove this one.
 *
 * \param pSsc         spatial specific config handle.
 * \param frameLength
 * \param sampleRate
 *
 * \return  MPS_OK on sucess, and else on failure.
 */
static SACDEC_ERROR sscCheckInBand(SPATIAL_SPECIFIC_CONFIG *pSsc,
                                   int frameLength, int sampleRate) {
  SACDEC_ERROR err = MPS_OK;
  int qmfBands;

  FDK_ASSERT(pSsc != NULL);

  /* core fs and mps fs must match */
  if (pSsc->samplingFreq != sampleRate) {
    err = MPS_PARSE_ERROR /* MPEGSDEC_SSC_PARSE_ERROR */;
  }

  qmfBands = mpegSurroundDecoder_GetNrOfQmfBands(pSsc, pSsc->samplingFreq);

  if (checkTimeSlots(frameLength, qmfBands, pSsc->nTimeSlots) != MPS_OK) {
    err = MPS_PARSE_ERROR;
  }

  return err;
}

SACDEC_ERROR
mpegSurroundDecoder_ConfigureQmfDomain(
    CMpegSurroundDecoder *pMpegSurroundDecoder,
    SAC_INPUT_CONFIG sac_dec_interface, UINT coreSamplingRate,
    AUDIO_OBJECT_TYPE coreCodec) {
  SACDEC_ERROR err = MPS_OK;
  FDK_QMF_DOMAIN_GC *pGC = NULL;

  if (pMpegSurroundDecoder == NULL) {
    return MPS_INVALID_HANDLE;
  }

  FDK_ASSERT(pMpegSurroundDecoder->pSpatialDec);

  pGC = &pMpegSurroundDecoder->pQmfDomain->globalConf;
  if (pMpegSurroundDecoder->mpegSurroundSscIsGlobalCfg) {
    SPATIAL_SPECIFIC_CONFIG *pSSC =
        &pMpegSurroundDecoder->spatialSpecificConfigBackup;
    if (sac_dec_interface == SAC_INTERFACE_TIME) {
      /* For SAC_INTERFACE_QMF these parameters are set by SBR. */
      pGC->nBandsAnalysis_requested = mpegSurroundDecoder_GetNrOfQmfBands(
          pSSC, coreSamplingRate); /* coreSamplingRate == outputSamplingRate for
                                      SAC_INTERFACE_TIME */
      pGC->nBandsSynthesis_requested = pGC->nBandsAnalysis_requested;
      pGC->nInputChannels_requested =
          fMax((UINT)pSSC->nInputChannels, (UINT)pGC->nInputChannels_requested);
    }
    pGC->nOutputChannels_requested =
        fMax((UINT)pSSC->nOutputChannels, (UINT)pGC->nOutputChannels_requested);
  } else {
    if (sac_dec_interface == SAC_INTERFACE_TIME) {
      /* For SAC_INTERFACE_QMF these parameters are set by SBR. */
      pGC->nBandsAnalysis_requested = mpegSurroundDecoder_GetNrOfQmfBands(
          NULL, coreSamplingRate); /* coreSamplingRate == outputSamplingRate for
                                      SAC_INTERFACE_TIME */
      pGC->nBandsSynthesis_requested = pGC->nBandsAnalysis_requested;
      pGC->nInputChannels_requested =
          pMpegSurroundDecoder->pSpatialDec->createParams.maxNumInputChannels;
    }
    pGC->nOutputChannels_requested =
        pMpegSurroundDecoder->pSpatialDec->createParams.maxNumOutputChannels;
  }
  pGC->nQmfProcBands_requested = 64;
  pGC->nQmfProcChannels_requested =
      fMin((INT)pGC->nInputChannels_requested,
           pMpegSurroundDecoder->pSpatialDec->createParams.maxNumInputChannels);

  if (coreCodec == AOT_ER_AAC_ELD) {
    pGC->flags_requested |= QMF_FLAG_MPSLDFB;
  }

  return err;
}

/**
 * \brief Decode MPEG Surround frame.
 **/
int mpegSurroundDecoder_ParseNoHeader(
    CMpegSurroundDecoder *pMpegSurroundDecoder, HANDLE_FDK_BITSTREAM hBs,
    int *pMpsDataBits, int fGlobalIndependencyFlag) {
  SACDEC_ERROR err = MPS_OK;
  SPATIAL_SPECIFIC_CONFIG *sscParse;
  int bitsAvail, numSacBits;

  if (pMpegSurroundDecoder == NULL || hBs == NULL) {
    return MPS_INVALID_HANDLE;
  }

  sscParse = &pMpegSurroundDecoder
                  ->spatialSpecificConfig[pMpegSurroundDecoder->bsFrameParse];

  bitsAvail = FDKgetValidBits(hBs);

  /* First spatial specific config is parsed into spatialSpecificConfigBackup,
   * second spatialSpecificConfigBackup is copied into
   * spatialSpecificConfig[bsFrameDecode] */
  if (pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameParse]) {
    FDKmemcpy(sscParse, &pMpegSurroundDecoder->spatialSpecificConfigBackup,
              sizeof(SPATIAL_SPECIFIC_CONFIG));
    pMpegSurroundDecoder->fOnSync[pMpegSurroundDecoder->bsFrameParse] =
        MPEGS_SYNC_FOUND;
  }

  if (bitsAvail <= 0) {
    err = MPS_PARSE_ERROR;
  } else {
    err = SpatialDecParseFrameData(
        pMpegSurroundDecoder->pSpatialDec,
        &pMpegSurroundDecoder->bsFrames[pMpegSurroundDecoder->bsFrameParse],
        hBs, sscParse, (UPMIXTYPE)pMpegSurroundDecoder->upmixType,
        fGlobalIndependencyFlag);
    if (err == MPS_OK) {
      pMpegSurroundDecoder->bsFrames[pMpegSurroundDecoder->bsFrameParse]
          .newBsData = 1;
    }
  }

  numSacBits = bitsAvail - (INT)FDKgetValidBits(hBs);

  if (numSacBits > bitsAvail) {
    pMpegSurroundDecoder->bsFrames[pMpegSurroundDecoder->bsFrameParse]
        .newBsData = 0;
    err = MPS_PARSE_ERROR;
  }

  *pMpsDataBits -= numSacBits;

  return err;
}

/**
 * \brief Check, if ancType is valid.
 **/
static int isValidAncType(CMpegSurroundDecoder *pMpegSurroundDecoder,
                          int ancType) {
  int ret = 1;

  if ((ancType != MPEGS_ANCTYPE_HEADER_AND_FRAME) &&
      (ancType != MPEGS_ANCTYPE_FRAME)) {
    ret = 0;
  }

  if (ret == 0) {
    updateMpegSurroundDecoderStatus(pMpegSurroundDecoder,
                                    MPEGS_INIT_ERROR_PAYLOAD, MPEGS_SYNC_LOST,
                                    MPEGS_STOP);
  }

  return (ret);
}

/**
 * \brief Check, if ancStartStop is valid.
 **/
static int isValidAncStartStop(CMpegSurroundDecoder *pMpegSurroundDecoder,
                               int ancStartStop) {
  int ret = 1;

  switch (ancStartStop) {
    case MPEGS_START:
      /* Sequence start - start and continue - start not allowed */
      if ((pMpegSurroundDecoder->ancStartStopPrev == MPEGS_START) ||
          (pMpegSurroundDecoder->ancStartStopPrev == MPEGS_CONTINUE)) {
        ret = 0;
      }
      break;

    case MPEGS_STOP:
      /* MPS payload of the previous frame must be valid if current type is stop
         Sequence startstop - stop and stop - stop not allowed
         Sequence startstop - continue and stop - continue are allowed */
      if ((pMpegSurroundDecoder->ancStartStopPrev == MPEGS_STOP) ||
          (pMpegSurroundDecoder->ancStartStopPrev == MPEGS_START_STOP)) {
        ret = 0;
      }
      break;

    case MPEGS_CONTINUE:
    case MPEGS_START_STOP:
      /* No error detection possible for this states */
      break;
  }

  if (ret == 0) {
    updateMpegSurroundDecoderStatus(pMpegSurroundDecoder,
                                    MPEGS_INIT_ERROR_PAYLOAD, MPEGS_SYNC_LOST,
                                    MPEGS_STOP);
  } else {
    pMpegSurroundDecoder->ancStartStopPrev = (MPEGS_ANCSTARTSTOP)ancStartStop;
  }

  return (ret);
}

int mpegSurroundDecoder_Parse(CMpegSurroundDecoder *pMpegSurroundDecoder,
                              HANDLE_FDK_BITSTREAM hBs, int *pMpsDataBits,
                              AUDIO_OBJECT_TYPE coreCodec, int sampleRate,
                              int frameSize, int fGlobalIndependencyFlag) {
  SACDEC_ERROR err = MPS_OK;
  SPATIAL_SPECIFIC_CONFIG *sscParse;
  SPATIAL_BS_FRAME *bsFrame;
  HANDLE_FDK_BITSTREAM hMpsBsData = NULL;
  FDK_BITSTREAM mpsBsData;
  int mpsDataBits = *pMpsDataBits;
  int mpsBsBits;
  MPEGS_ANCTYPE ancType;
  MPEGS_ANCSTARTSTOP ancStartStop;

  if (pMpegSurroundDecoder == NULL) {
    return MPS_INVALID_HANDLE;
  }

  FDK_ASSERT(pMpegSurroundDecoder->pSpatialDec);

  mpsBsBits = FDKgetValidBits(hBs);

  sscParse = &pMpegSurroundDecoder
                  ->spatialSpecificConfig[pMpegSurroundDecoder->bsFrameParse];
  bsFrame = &pMpegSurroundDecoder->bsFrames[pMpegSurroundDecoder->bsFrameParse];

  /*
     Find operation mode of mpeg surround decoder:
     - MPEGS_OPMODE_EMM:            Mode: Enhanced Matrix Mode (Blind)
     - MPEGS_OPMODE_MPS_PAYLOAD:    Mode: Normal, Stereo or Binaural
     - MPEGS_OPMODE_NO_MPS_PAYLOAD: Mode: No MpegSurround Payload
  */
  {
    /* Parse ancType and ancStartStop */
    ancType = (MPEGS_ANCTYPE)FDKreadBits(hBs, 2);
    ancStartStop = (MPEGS_ANCSTARTSTOP)FDKreadBits(hBs, 2);
    mpsDataBits -= 4;

    /* Set valid anc type flag, if ancType signals a payload with either header
     * and frame or frame */
    if (isValidAncType(pMpegSurroundDecoder, ancType)) {
      /* Set valid anc startstop flag, if transmitted sequence is not illegal */
      if (isValidAncStartStop(pMpegSurroundDecoder, ancStartStop)) {
        switch (ancStartStop) {
          case MPEGS_START:
            /* Assuming that core coder frame size (AAC) is smaller than MPS
               coder frame size. Save audio data for next frame. */
            if (mpsDataBits > MPS_DATA_BUFFER_SIZE * 8) {
              err = MPS_NOTOK;
              goto bail;
            }
            for (int i = 0; i < mpsDataBits / 8; i++) {
              pMpegSurroundDecoder->mpsData[i] = FDKreadBits(hBs, 8);
            }
            pMpegSurroundDecoder->mpsDataBits = mpsDataBits;
            break;

          case MPEGS_CONTINUE:
          case MPEGS_STOP:
            /* Assuming that core coder frame size (AAC) is smaller than MPS
               coder frame size. Save audio data for next frame. */
            if ((pMpegSurroundDecoder->mpsDataBits + mpsDataBits) >
                MPS_DATA_BUFFER_SIZE * 8) {
              err = MPS_NOTOK;
              goto bail;
            }
            for (int i = 0; i < mpsDataBits / 8; i++) {
              pMpegSurroundDecoder
                  ->mpsData[(pMpegSurroundDecoder->mpsDataBits / 8) + i] =
                  FDKreadBits(hBs, 8);
            }
            pMpegSurroundDecoder->mpsDataBits += mpsDataBits;
            FDKinitBitStream(&mpsBsData, pMpegSurroundDecoder->mpsData,
                             MAX_BUFSIZE_BYTES,
                             pMpegSurroundDecoder->mpsDataBits, BS_READER);
            hMpsBsData = &mpsBsData;
            break;

          case MPEGS_START_STOP:
            pMpegSurroundDecoder->mpsDataBits = mpsDataBits;
            hMpsBsData = hBs;
            break;

          default:
            FDK_ASSERT(0);
        }

        if ((ancStartStop == MPEGS_STOP) ||
            (ancStartStop == MPEGS_START_STOP)) {
          switch (ancType) {
            case MPEGS_ANCTYPE_HEADER_AND_FRAME: {
              int parseResult, bitsRead;
              SPATIAL_SPECIFIC_CONFIG spatialSpecificConfigTmp =
                  pMpegSurroundDecoder->spatialSpecificConfigBackup;

              /* Parse spatial specific config */
              bitsRead = FDKgetValidBits(hMpsBsData);

              err = SpatialDecParseSpecificConfigHeader(
                  hMpsBsData,
                  &pMpegSurroundDecoder->spatialSpecificConfigBackup, coreCodec,
                  pMpegSurroundDecoder->upmixType);

              bitsRead = (bitsRead - FDKgetValidBits(hMpsBsData));
              parseResult = ((err == MPS_OK) ? bitsRead : -bitsRead);

              if (parseResult < 0) {
                parseResult = -parseResult;
                err = MPS_PARSE_ERROR;
              } else if (err == MPS_OK) {
                /* Check SSC for consistency (e.g. bit errors could cause
                 * trouble) */
                err = sscCheckInBand(
                    &pMpegSurroundDecoder->spatialSpecificConfigBackup,
                    frameSize, sampleRate);
              }
              if (err != MPS_OK) {
                pMpegSurroundDecoder->spatialSpecificConfigBackup =
                    spatialSpecificConfigTmp;
                break;
              }

              pMpegSurroundDecoder->mpsDataBits -= parseResult;

              /* Initiate re-initialization, if header has changed */
              if (FDK_SpatialDecCompareSpatialSpecificConfigHeader(
                      &pMpegSurroundDecoder->spatialSpecificConfigBackup,
                      sscParse) == MPS_UNEQUAL_SSC) {
                pMpegSurroundDecoder
                    ->initFlags[pMpegSurroundDecoder->bsFrameParse] |=
                    MPEGS_INIT_CHANGE_HEADER;
                SpatialDecInitParserContext(pMpegSurroundDecoder->pSpatialDec);
                /* We found a valid in-band configuration. Therefore any
                 * previous config is invalid now. */
                pMpegSurroundDecoder->mpegSurroundSscIsGlobalCfg = 0;
              }
            }
            case MPEGS_ANCTYPE_FRAME:

              if (pMpegSurroundDecoder
                      ->initFlags[pMpegSurroundDecoder->bsFrameParse] &
                  MPEGS_INIT_ERROR_PAYLOAD) {
                err = MPS_PARSE_ERROR;
                break;
              }

              /* First spatial specific config is parsed into
               * spatialSpecificConfigBackup, second spatialSpecificConfigBackup
               * is copied into spatialSpecificConfig[bsFrameDecode] */
              if (pMpegSurroundDecoder
                      ->initFlags[pMpegSurroundDecoder->bsFrameParse]) {
                FDKmemcpy(sscParse,
                          &pMpegSurroundDecoder->spatialSpecificConfigBackup,
                          sizeof(SPATIAL_SPECIFIC_CONFIG));
                pMpegSurroundDecoder
                    ->fOnSync[pMpegSurroundDecoder->bsFrameParse] =
                    MPEGS_SYNC_FOUND;
              }

              if (pMpegSurroundDecoder
                      ->fOnSync[pMpegSurroundDecoder->bsFrameParse] >=
                  MPEGS_SYNC_FOUND) {
                int nbits = 0, bitsAvail;

                if (err != MPS_OK) {
                  break;
                }

                bitsAvail = FDKgetValidBits(hMpsBsData);

                if (bitsAvail <= 0) {
                  err = MPS_PARSE_ERROR;
                } else {
                  err = SpatialDecParseFrameData(
                      pMpegSurroundDecoder->pSpatialDec, bsFrame, hMpsBsData,
                      sscParse, (UPMIXTYPE)pMpegSurroundDecoder->upmixType,
                      fGlobalIndependencyFlag);
                  if (err == MPS_OK) {
                    bsFrame->newBsData = 1;
                  }
                }

                nbits = bitsAvail - (INT)FDKgetValidBits(hMpsBsData);

                if ((nbits > bitsAvail) ||
                    (nbits > pMpegSurroundDecoder->mpsDataBits) ||
                    (pMpegSurroundDecoder->mpsDataBits > nbits + 7 &&
                     !IS_LOWDELAY(coreCodec))) {
                  bsFrame->newBsData = 0;
                  err = MPS_PARSE_ERROR;
                  break;
                }
                pMpegSurroundDecoder->mpsDataBits -= nbits;
              }
              break;

            default: /* added to avoid compiler warning */
              err = MPS_NOTOK;
              break; /* added to avoid compiler warning */
          }          /* switch (ancType) */

          if (err == MPS_OK) {
            pMpegSurroundDecoder->ancStartStopPrev = ancStartStop;
          } else {
            updateMpegSurroundDecoderStatus(pMpegSurroundDecoder,
                                            MPEGS_INIT_ERROR_PAYLOAD,
                                            MPEGS_SYNC_LOST, MPEGS_STOP);
            pMpegSurroundDecoder->mpsDataBits = 0;
          }
        } /* (ancStartStop == MPEGS_STOP) || (ancStartStop == MPEGS_START_STOP)
           */
      }   /* validAncStartStop */
    }     /* validAncType */
  }

bail:

  *pMpsDataBits -= (mpsBsBits - FDKgetValidBits(hBs));

  return err;
}

int mpegSurroundDecoder_Apply(CMpegSurroundDecoder *pMpegSurroundDecoder,
                              INT_PCM *input, PCM_MPS *pTimeData,
                              const int timeDataSize, int timeDataFrameSize,
                              int *nChannels, int *frameSize, int sampleRate,
                              AUDIO_OBJECT_TYPE coreCodec,
                              AUDIO_CHANNEL_TYPE channelType[],
                              UCHAR channelIndices[],
                              const FDK_channelMapDescr *const mapDescr) {
  SACDEC_ERROR err = MPS_OK;
  PCM_MPS *pTimeOut = pTimeData;
  UINT initControlFlags = 0, controlFlags = 0;
  int timeDataRequiredSize = 0;
  int newData;

  if (pMpegSurroundDecoder == NULL) {
    return MPS_INVALID_HANDLE;
  }

  FDK_ASSERT(pMpegSurroundDecoder->pSpatialDec);

  if (!FDK_chMapDescr_isValid(mapDescr)) {
    return MPS_INVALID_HANDLE;
  }

  if ((*nChannels <= 0) || (*nChannels > 2)) {
    return MPS_NOTOK;
  }

  pMpegSurroundDecoder->pSpatialDec->pConfigCurrent =
      &pMpegSurroundDecoder
           ->spatialSpecificConfig[pMpegSurroundDecoder->bsFrameDecode];
  newData = pMpegSurroundDecoder->bsFrames[pMpegSurroundDecoder->bsFrameParse]
                .newBsData;

  switch (mpegSurroundOperationMode(pMpegSurroundDecoder, 1000)) {
    case MPEGS_OPMODE_MPS_PAYLOAD:
      if (pMpegSurroundDecoder
              ->initFlags[pMpegSurroundDecoder->bsFrameDecode]) {
        err = initMpegSurroundDecoder(pMpegSurroundDecoder);
      }

      if (err == MPS_OK) {
        if ((pMpegSurroundDecoder
                 ->fOnSync[pMpegSurroundDecoder->bsFrameDecode] !=
             MPEGS_SYNC_COMPLETE) &&
            (pMpegSurroundDecoder->bsFrames[pMpegSurroundDecoder->bsFrameDecode]
                 .bsIndependencyFlag == 1)) {
          /* We got a valid header and independently decodeable frame data.
              -> Go to the next sync level and start processing. */
          pMpegSurroundDecoder->fOnSync[pMpegSurroundDecoder->bsFrameDecode] =
              MPEGS_SYNC_COMPLETE;
        }
      } else {
        /* We got a valid config header but found an error while parsing the
           bitstream. Wait for the next independent frame and apply error
           conealment in the meantime. */
        pMpegSurroundDecoder->fOnSync[pMpegSurroundDecoder->bsFrameDecode] =
            MPEGS_SYNC_FOUND;
        controlFlags |= MPEGS_CONCEAL;
        err = MPS_OK;
      }
      /*
         Concealment:
         - Bitstream is available, no sync found during bitstream processing
         - Bitstream is available, sync lost due to corrupted bitstream
         - Bitstream is available, sync found but no independent frame
      */
      if (pMpegSurroundDecoder->fOnSync[pMpegSurroundDecoder->bsFrameDecode] !=
          MPEGS_SYNC_COMPLETE) {
        controlFlags |= MPEGS_CONCEAL;
      }
      break;

    case MPEGS_OPMODE_NO_MPS_PAYLOAD:
      /* Concealment: No bitstream is available */
      controlFlags |= MPEGS_CONCEAL;
      break;

    default:
      err = MPS_NOTOK;
  }

  if (err != MPS_OK) {
    goto bail;
  }

  /*
   * Force BypassMode if choosen by user
   */
  if (pMpegSurroundDecoder->mpegSurroundUserParams.bypassMode) {
    controlFlags |= MPEGS_BYPASSMODE;
  }

  if (pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode]) {
    int startWithDfltCfg = 0;
    /*
     * Init with a default configuration if we came here and are still not
     * initialized.
     */
    if (pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode] &
        MPEGS_INIT_ENFORCE_REINIT) {
      /* Get default spatial specific config */
      if (FDK_SpatialDecInitDefaultSpatialSpecificConfig(
              &pMpegSurroundDecoder->spatialSpecificConfigBackup, coreCodec,
              *nChannels, sampleRate,
              *frameSize /
                  mpegSurroundDecoder_GetNrOfQmfBands(NULL, sampleRate),
              pMpegSurroundDecoder->mpegSurroundDecoderLevel,
              pMpegSurroundDecoder->mpegSurroundUserParams.blindEnable)) {
        err = MPS_NOTOK;
        goto bail;
      }

      /* Initiate re-initialization, if header has changed */
      if (FDK_SpatialDecCompareSpatialSpecificConfigHeader(
              &pMpegSurroundDecoder->spatialSpecificConfigBackup,
              &pMpegSurroundDecoder->spatialSpecificConfig
                   [pMpegSurroundDecoder->bsFrameDecode]) == MPS_UNEQUAL_SSC) {
        pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode] |=
            MPEGS_INIT_CHANGE_HEADER;
        SpatialDecInitParserContext(pMpegSurroundDecoder->pSpatialDec);
      }

      startWithDfltCfg = 1;
    }

    /* First spatial specific config is parsed into spatialSpecificConfigBackup,
     * second spatialSpecificConfigBackup is copied into spatialSpecificConfig
     */
    err = initMpegSurroundDecoder(pMpegSurroundDecoder);

    if (startWithDfltCfg) {
      /* initialized with default config, but no sync found */
      /* maybe use updateMpegSurroundDecoderStatus later on */
      pMpegSurroundDecoder->fOnSync[pMpegSurroundDecoder->bsFrameDecode] =
          MPEGS_SYNC_LOST;
    }

    /* Since we do not have state MPEGS_SYNC_COMPLETE apply concealment */
    controlFlags |= MPEGS_CONCEAL;

    if (err != MPS_OK) {
      goto bail;
    }
  }

  /*
   * Process MPEG Surround Audio
   */
  initControlFlags = controlFlags;

  /* Check that provided output buffer is large enough. */
  timeDataRequiredSize =
      (timeDataFrameSize *
       pMpegSurroundDecoder->pSpatialDec->numOutputChannelsAT *
       pMpegSurroundDecoder->pQmfDomain->globalConf.nBandsSynthesis) /
      pMpegSurroundDecoder->pQmfDomain->globalConf.nBandsAnalysis;
  if (timeDataSize < timeDataRequiredSize) {
    err = MPS_OUTPUT_BUFFER_TOO_SMALL;
    goto bail;
  }

  if ((pMpegSurroundDecoder->pSpatialDec->pConfigCurrent->syntaxFlags &
       SACDEC_SYNTAX_USAC) &&
      (pMpegSurroundDecoder->pSpatialDec->stereoConfigIndex > 1)) {
    FDK_ASSERT(timeDataRequiredSize >= timeDataFrameSize * *nChannels);
    /* Place samples comprising QMF time slots spaced at QMF output Band raster
     * to allow slot wise processing */
    int timeDataFrameSizeOut =
        (timeDataFrameSize *
         pMpegSurroundDecoder->pQmfDomain->globalConf.nBandsSynthesis) /
        pMpegSurroundDecoder->pQmfDomain->globalConf.nBandsAnalysis;
    pMpegSurroundDecoder->pQmfDomain->globalConf.TDinput =
        pTimeData + timeDataFrameSizeOut - timeDataFrameSize;
    for (int i = *nChannels - 1; i >= 0; i--) {
      FDKmemmove(pTimeData + (i + 1) * timeDataFrameSizeOut - timeDataFrameSize,
                 pTimeData + timeDataFrameSize * i,
                 sizeof(PCM_MPS) * timeDataFrameSize);
      FDKmemclear(pTimeData + i * timeDataFrameSizeOut,
                  sizeof(PCM_MPS) * (timeDataFrameSizeOut - timeDataFrameSize));
    }
  } else {
    if (pMpegSurroundDecoder->mpegSurroundUseTimeInterface) {
      FDKmemcpy(input, pTimeData,
                sizeof(INT_PCM) * (*nChannels) * (*frameSize));
      pMpegSurroundDecoder->pQmfDomain->globalConf.TDinput = input;
    }
  }

  /*
   * Process MPEG Surround Audio
   */
  err = SpatialDecApplyFrame(
      pMpegSurroundDecoder->pSpatialDec,
      &pMpegSurroundDecoder->bsFrames[pMpegSurroundDecoder->bsFrameDecode],
      pMpegSurroundDecoder->mpegSurroundUseTimeInterface ? INPUTMODE_TIME
                                                         : INPUTMODE_QMF_SBR,
      pMpegSurroundDecoder->pQmfDomain->globalConf.TDinput, NULL, NULL,
      pTimeOut, *frameSize, &controlFlags, *nChannels, mapDescr);
  *nChannels = pMpegSurroundDecoder->pSpatialDec->numOutputChannelsAT;

  if (err !=
      MPS_OK) { /* A fatal error occured. Go back to start and try again: */
    updateMpegSurroundDecoderStatus(pMpegSurroundDecoder,
                                    MPEGS_INIT_ENFORCE_REINIT, MPEGS_SYNC_LOST,
                                    MPEGS_STOP);
    *frameSize =
        0; /* Declare that framework can not use the data in pTimeOut. */
  } else {
    if (((controlFlags & MPEGS_CONCEAL) &&
         !(initControlFlags & MPEGS_CONCEAL)) ||
        (pMpegSurroundDecoder->pSpatialDec->errInt !=
         MPS_OK)) { /* Account for errors that occured in
                       SpatialDecApplyFrame(): */
      updateMpegSurroundDecoderStatus(pMpegSurroundDecoder,
                                      MPEGS_INIT_ERROR_PAYLOAD, MPEGS_SYNC_LOST,
                                      MPEGS_STOP);
    }
  }

  if ((err == MPS_OK) && !(controlFlags & MPEGS_BYPASSMODE) &&
      !(pMpegSurroundDecoder->upmixType == UPMIX_TYPE_BYPASS)) {
    SpatialDecChannelProperties(pMpegSurroundDecoder->pSpatialDec, channelType,
                                channelIndices, mapDescr);
  }

bail:

  if (newData) {
    /* numParameterSetsPrev shall only be read in the decode process, because of
       that we can update this state variable here */
    pMpegSurroundDecoder->pSpatialDec->numParameterSetsPrev =
        pMpegSurroundDecoder->bsFrames[pMpegSurroundDecoder->bsFrameDecode]
            .numParameterSets;
  }

  return (err);
}

/**
 * \brief Free config dependent MPEG Surround memory.
 **/
SACDEC_ERROR mpegSurroundDecoder_FreeMem(
    CMpegSurroundDecoder *pMpegSurroundDecoder) {
  SACDEC_ERROR err = MPS_OK;

  if (pMpegSurroundDecoder != NULL) {
    FDK_SpatialDecClose(pMpegSurroundDecoder->pSpatialDec);
    pMpegSurroundDecoder->pSpatialDec = NULL;
  }

  return err;
}

/**
 * \brief Close MPEG Surround decoder.
 **/
void mpegSurroundDecoder_Close(CMpegSurroundDecoder *pMpegSurroundDecoder) {
  if (pMpegSurroundDecoder != NULL) {
    FDK_SpatialDecClose(pMpegSurroundDecoder->pSpatialDec);
    pMpegSurroundDecoder->pSpatialDec = NULL;

    for (int i = 0; i < 1; i++) {
      SpatialDecCloseBsFrame(&pMpegSurroundDecoder->bsFrames[i]);
    }

    FDK_FREE_MEMORY_1D(pMpegSurroundDecoder);
  }
}

#define SACDEC_VL0 2
#define SACDEC_VL1 0
#define SACDEC_VL2 0

int mpegSurroundDecoder_GetLibInfo(LIB_INFO *info) {
  int i;

  if (info == NULL) {
    return -1;
  }

  /* search for next free tab */
  for (i = 0; i < FDK_MODULE_LAST; i++) {
    if (info[i].module_id == FDK_NONE) break;
  }
  if (i == FDK_MODULE_LAST) return -1;

  info += i;

  info->module_id = FDK_MPSDEC;
#ifdef __ANDROID__
  info->build_date = "";
  info->build_time = "";
#else
  info->build_date = __DATE__;
  info->build_time = __TIME__;
#endif
  info->title = "MPEG Surround Decoder";
  info->version = LIB_VERSION(SACDEC_VL0, SACDEC_VL1, SACDEC_VL2);
  LIB_VERSION_STRING(info);
  info->flags = 0 | CAPF_MPS_LD | CAPF_MPS_USAC | CAPF_MPS_HQ |
                CAPF_MPS_1CH_IN | CAPF_MPS_2CH_OUT; /* end flags */

  return 0;
}

SACDEC_ERROR mpegSurroundDecoder_SetParam(
    CMpegSurroundDecoder *pMpegSurroundDecoder, const SACDEC_PARAM param,
    const INT value) {
  SACDEC_ERROR err = MPS_OK;
  SPATIALDEC_PARAM *pUserParams = NULL;

  /* check decoder handle */
  if (pMpegSurroundDecoder != NULL) {
    /* init local shortcuts */
    pUserParams = &pMpegSurroundDecoder->mpegSurroundUserParams;
  } else {
    err = MPS_INVALID_HANDLE;
    /* check the parameter values before exiting. */
  }

  /* apply param value */
  switch (param) {
    case SACDEC_OUTPUT_MODE:
      switch ((SAC_DEC_OUTPUT_MODE)value) {
        case SACDEC_OUT_MODE_NORMAL:
        case SACDEC_OUT_MODE_STEREO:
          break;
        default:
          err = MPS_INVALID_PARAMETER;
      }
      if (err == MPS_OK) {
        if (0) {
          err = MPS_INVALID_PARAMETER;
        } else if (pUserParams->outputMode != (UCHAR)value) {
          pUserParams->outputMode = (UCHAR)value;
          pMpegSurroundDecoder
              ->initFlags[pMpegSurroundDecoder->bsFrameDecode] |=
              MPEGS_INIT_CHANGE_OUTPUT_MODE;
        }
      }
      break;

    case SACDEC_INTERFACE:
      if (value < 0 || value > 1) {
        err = MPS_INVALID_PARAMETER;
      }
      if (err != MPS_OK) {
        goto bail;
      }
      if (pMpegSurroundDecoder->mpegSurroundUseTimeInterface != (UCHAR)value) {
        pMpegSurroundDecoder->mpegSurroundUseTimeInterface = (UCHAR)value;
        pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode] |=
            MPEGS_INIT_CHANGE_TIME_FREQ_INTERFACE;
      }
      break;

    case SACDEC_BS_INTERRUPTION:
      if ((err == MPS_OK) && (value != 0)) {
        updateMpegSurroundDecoderStatus(pMpegSurroundDecoder,
                                        MPEGS_INIT_BS_INTERRUPTION,
                                        MPEGS_SYNC_LOST, MPEGS_STOP);
      }
      break;

    case SACDEC_CLEAR_HISTORY:
      if ((err == MPS_OK) && (value != 0)) {
        /* Just reset the states and go on. */
        updateMpegSurroundDecoderStatus(pMpegSurroundDecoder,
                                        MPEGS_INIT_CLEAR_HISTORY,
                                        MPEGS_SYNC_LOST, MPEGS_STOP);
      }
      break;

    case SACDEC_CONCEAL_NUM_KEEP_FRAMES:
      if (value < 0) { /* Check valid value range */
        err = MPS_INVALID_PARAMETER;
      }
      if (err != MPS_OK) {
        goto bail;
      }
      if (pUserParams->concealNumKeepFrames != (UINT)value) {
        pUserParams->concealNumKeepFrames = (UINT)value;
        pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode] |=
            MPEGS_INIT_CHANGE_CONCEAL_PARAMS;
      }
      break;

    case SACDEC_CONCEAL_FADE_OUT_SLOPE_LENGTH:
      if (value < 0) { /* Check valid value range */
        err = MPS_INVALID_PARAMETER;
      }
      if (err != MPS_OK) {
        goto bail;
      }
      if (pUserParams->concealFadeOutSlopeLength != (UINT)value) {
        pUserParams->concealFadeOutSlopeLength = (UINT)value;
        pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode] |=
            MPEGS_INIT_CHANGE_CONCEAL_PARAMS;
      }
      break;

    case SACDEC_CONCEAL_FADE_IN_SLOPE_LENGTH:
      if (value < 0) { /* Check valid value range */
        err = MPS_INVALID_PARAMETER;
      }
      if (err != MPS_OK) {
        goto bail;
      }
      if (pUserParams->concealFadeInSlopeLength != (UINT)value) {
        pUserParams->concealFadeInSlopeLength = (UINT)value;
        pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode] |=
            MPEGS_INIT_CHANGE_CONCEAL_PARAMS;
      }
      break;

    case SACDEC_CONCEAL_NUM_RELEASE_FRAMES:
      if (value < 0) { /* Check valid value range */
        err = MPS_INVALID_PARAMETER;
      }
      if (err != MPS_OK) {
        goto bail;
      }
      if (pUserParams->concealNumReleaseFrames != (UINT)value) {
        pUserParams->concealNumReleaseFrames = (UINT)value;
        pMpegSurroundDecoder->initFlags[pMpegSurroundDecoder->bsFrameDecode] |=
            MPEGS_INIT_CHANGE_CONCEAL_PARAMS;
      }
      break;

    default:
      err = MPS_INVALID_PARAMETER;
      break;
  } /* switch(param) */

bail:
  return err;
}

SACDEC_ERROR mpegSurroundDecoder_IsPseudoLR(
    CMpegSurroundDecoder *pMpegSurroundDecoder, int *bsPseudoLr) {
  if (pMpegSurroundDecoder != NULL) {
    const SPATIAL_SPECIFIC_CONFIG *sscDecode =
        &pMpegSurroundDecoder
             ->spatialSpecificConfig[pMpegSurroundDecoder->bsFrameDecode];
    *bsPseudoLr = (int)sscDecode->bsPseudoLr;
    return MPS_OK;
  } else
    return MPS_INVALID_HANDLE;
}

/**
 * \brief Get the signal delay caused by the MPEG Surround decoder module.
 **/
UINT mpegSurroundDecoder_GetDelay(const CMpegSurroundDecoder *self) {
  INT outputDelay = 0;

  if (self != NULL) {
    const SPATIAL_SPECIFIC_CONFIG *sscDecode =
        &self->spatialSpecificConfig[self->bsFrameDecode];
    AUDIO_OBJECT_TYPE coreCodec = sscDecode->coreCodec;

    /* See chapter 4.5 (delay and synchronization) of ISO/IEC FDIS 23003-1 and
       chapter 5.4.3 of ISO/IEC FDIS 23003-2 for details on the following
       figures. */

    if (coreCodec > AOT_NULL_OBJECT) {
      if (IS_LOWDELAY(coreCodec)) {
        /* All low delay variants (ER-AAC-(E)LD): */
        outputDelay += 256;
      } else if (!IS_USAC(coreCodec)) {
        /* By the method of elimination this is the GA (AAC-LC, HE-AAC, ...)
         * branch: */
        outputDelay += 320 + 257; /* cos to exp delay + QMF synthesis */
        if (self->mpegSurroundUseTimeInterface) {
          outputDelay += 320 + 384; /* QMF and hybrid analysis */
        }
      }
    }
  }

  return (outputDelay);
}
