/* -----------------------------------------------------------------------------
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
----------------------------------------------------------------------------- */

/**************************** SBR decoder library ******************************

   Author(s):

   Description:

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

/*!
  \file
  \brief  Envelope calculation

  The envelope adjustor compares the energies present in the transposed
  highband to the reference energies conveyed with the bitstream.
  The highband is amplified (sometimes) or attenuated (mostly) to the
  desired level.

  The spectral shape of the reference energies can be changed several times per
  frame if necessary. Each set of energy values corresponding to a certain range
  in time will be called an <em>envelope</em> here.
  The bitstream supports several frequency scales and two resolutions. Normally,
  one or more QMF-subbands are grouped to one SBR-band. An envelope contains
  reference energies for each SBR-band.
  In addition to the energy envelopes, noise envelopes are transmitted that
  define the ratio of energy which is generated by adding noise instead of
  transposing the lowband. The noise envelopes are given in a coarser time
  and frequency resolution.
  If a signal contains strong tonal components, synthetic sines can be
  generated in individual SBR bands.

  An overlap buffer of 6 QMF-timeslots is used to allow a more
  flexible alignment of the envelopes in time that is not restricted to the
  core codec's frame borders.
  Therefore the envelope adjustor has access to the spectral data of the
  current frame as well as the last 6 QMF-timeslots of the previous frame.
  However, in average only the data of 1 frame is being processed as
  the adjustor is called once per frame.

  Depending on the frequency range set in the bitstream, only QMF-subbands
  between <em>lowSubband</em> and <em>highSubband</em> are adjusted.

  Scaling of spectral data to maximize SNR (see #QMF_SCALE_FACTOR) as well as a
  special Mantissa-Exponent format ( see  calculateSbrEnvelope() ) are being
  used. The main entry point for this modules is calculateSbrEnvelope().

  \sa sbr_scale.h, #QMF_SCALE_FACTOR, calculateSbrEnvelope(), \ref
  documentationOverview
*/

#include "env_calc.h"

#include "sbrdec_freq_sca.h"
#include "env_extr.h"
#include "transcendent.h"
#include "sbr_ram.h"
#include "sbr_rom.h"

#include "genericStds.h" /* need FDKpow() for debug outputs */

typedef struct {
  FIXP_DBL nrgRef[MAX_FREQ_COEFFS];
  FIXP_DBL nrgEst[MAX_FREQ_COEFFS];
  FIXP_DBL nrgGain[MAX_FREQ_COEFFS];
  FIXP_DBL noiseLevel[MAX_FREQ_COEFFS];
  FIXP_DBL nrgSine[MAX_FREQ_COEFFS];

  SCHAR nrgRef_e[MAX_FREQ_COEFFS];
  SCHAR nrgEst_e[MAX_FREQ_COEFFS];
  SCHAR nrgGain_e[MAX_FREQ_COEFFS];
  SCHAR noiseLevel_e[MAX_FREQ_COEFFS];
  SCHAR nrgSine_e[MAX_FREQ_COEFFS];
  /* yet another exponent [0]: for ts < no_cols; [1]: for ts >= no_cols */
  SCHAR exponent[2];
} ENV_CALC_NRGS;

static void equalizeFiltBufferExp(FIXP_DBL *filtBuffer, SCHAR *filtBuffer_e,
                                  FIXP_DBL *NrgGain, SCHAR *NrgGain_e,
                                  int subbands);

static void calcNrgPerSubband(FIXP_DBL **analysBufferReal,
                              FIXP_DBL **analysBufferImag, int lowSubband,
                              int highSubband, int start_pos, int next_pos,
                              SCHAR frameExp, FIXP_DBL *nrgEst,
                              SCHAR *nrgEst_e);

static void calcNrgPerSfb(FIXP_DBL **analysBufferReal,
                          FIXP_DBL **analysBufferImag, int nSfb,
                          UCHAR *freqBandTable, int start_pos, int next_pos,
                          SCHAR input_e, FIXP_DBL *nrg_est, SCHAR *nrg_est_e);

static void calcSubbandGain(FIXP_DBL nrgRef, SCHAR nrgRef_e,
                            ENV_CALC_NRGS *nrgs, int c, FIXP_DBL tmpNoise,
                            SCHAR tmpNoise_e, UCHAR sinePresentFlag,
                            UCHAR sineMapped, int noNoiseFlag);

static void calcAvgGain(ENV_CALC_NRGS *nrgs, int lowSubband, int highSubband,
                        FIXP_DBL *sumRef_m, SCHAR *sumRef_e,
                        FIXP_DBL *ptrAvgGain_m, SCHAR *ptrAvgGain_e);

static void adjustTimeSlot_EldGrid(FIXP_DBL *ptrReal, ENV_CALC_NRGS *nrgs,
                                   UCHAR *ptrHarmIndex, int lowSubbands,
                                   int noSubbands, int scale_change,
                                   int noNoiseFlag, int *ptrPhaseIndex,
                                   int scale_diff_low);

static void adjustTimeSlotLC(FIXP_DBL *ptrReal, ENV_CALC_NRGS *nrgs,
                             UCHAR *ptrHarmIndex, int lowSubbands,
                             int noSubbands, int scale_change, int noNoiseFlag,
                             int *ptrPhaseIndex);

/**
 * \brief Variant of adjustTimeSlotHQ() which only regards gain and noise but no
 * additional harmonics
 */
static void adjustTimeSlotHQ_GainAndNoise(
    FIXP_DBL *ptrReal, FIXP_DBL *ptrImag,
    HANDLE_SBR_CALCULATE_ENVELOPE h_sbr_cal_env, ENV_CALC_NRGS *nrgs,
    int lowSubbands, int noSubbands, int scale_change, FIXP_SGL smooth_ratio,
    int noNoiseFlag, int filtBufferNoiseShift);
/**
 * \brief Variant of adjustTimeSlotHQ() which only adds the additional harmonics
 */
static void adjustTimeSlotHQ_AddHarmonics(
    FIXP_DBL *ptrReal, FIXP_DBL *ptrImag,
    HANDLE_SBR_CALCULATE_ENVELOPE h_sbr_cal_env, ENV_CALC_NRGS *nrgs,
    int lowSubbands, int noSubbands, int scale_change);

static void adjustTimeSlotHQ(FIXP_DBL *ptrReal, FIXP_DBL *ptrImag,
                             HANDLE_SBR_CALCULATE_ENVELOPE h_sbr_cal_env,
                             ENV_CALC_NRGS *nrgs, int lowSubbands,
                             int noSubbands, int scale_change,
                             FIXP_SGL smooth_ratio, int noNoiseFlag,
                             int filtBufferNoiseShift);

/*!
  \brief     Map sine flags from bitstream to QMF bands

  The bitstream carries only 1 sine flag per band (Sfb) and frame.
  This function maps every sine flag from the bitstream to a specific QMF
  subband and to a specific envelope where the sine shall start. The result is
  stored in the vector sineMapped which contains one entry per QMF subband. The
  value of an entry specifies the envelope where a sine shall start. A value of
  32 indicates that no sine is present in the subband. The missing harmonics
  flags from the previous frame (harmFlagsPrev) determine if a sine starts at
  the beginning of the frame or at the transient position. Additionally, the
  flags in harmFlagsPrev are being updated by this function for the next frame.
*/
static void mapSineFlags(
    UCHAR *freqBandTable, /*!< Band borders (there's only 1 flag per band) */
    int nSfb,             /*!< Number of bands in the table */
    ULONG *addHarmonics,  /*!< Packed addHarmonics of current frame (aligned to
                             the MSB) */
    ULONG *harmFlagsPrev, /*!< Packed addHarmonics of previous frame (aligned to
                             the LSB) */
    ULONG *harmFlagsPrevActive, /*!< Packed sineMapped of previous frame
                                   (aligned to the LSB) */
    int tranEnv,                /*!< Transient position */
    SCHAR *sineMapped) /*!< Resulting vector of sine start positions for each
                          QMF band */

{
  int i;
  int bitcount = 31;
  ULONG harmFlagsQmfBands[ADD_HARMONICS_FLAGS_SIZE] = {0};
  ULONG *curFlags = addHarmonics;

  /*
    Format of addHarmonics (aligned to MSB):

      Up to MAX_FREQ_COEFFS sfb bands can be flagged for a sign.
      first word  = flags for lowest 32 sfb bands in use
      second word = flags for higest 32 sfb bands (if present)

    Format of harmFlagsPrev (aligned to LSB):

      Index is absolute (not relative to lsb) so it is correct even if lsb
    changes first word  = flags for lowest 32 qmf bands (0...31) second word =
    flags for next higher 32 qmf bands (32...63)

  */

  /* Reset the output vector first */
  FDKmemset(sineMapped, 32,
            MAX_FREQ_COEFFS * sizeof(SCHAR)); /* 32 means 'no sine' */
  FDKmemclear(harmFlagsPrevActive, ADD_HARMONICS_FLAGS_SIZE * sizeof(ULONG));
  for (i = 0; i < nSfb; i++) {
    ULONG maskSfb =
        1 << bitcount; /* mask to extract addHarmonics flag of current Sfb */

    if (*curFlags & maskSfb) {          /* There is a sine in this band */
      const int lsb = freqBandTable[0]; /* start of sbr range */
      /* qmf band to which sine should be added */
      const int qmfBand = (freqBandTable[i] + freqBandTable[i + 1]) >> 1;
      const int qmfBandDiv32 = qmfBand >> 5;
      const int maskQmfBand =
          1 << (qmfBand &
                31); /* mask to extract harmonic flag from prevFlags */

      /* mapping of sfb with sine to a certain qmf band -> for harmFlagsPrev */
      harmFlagsQmfBands[qmfBandDiv32] |= maskQmfBand;

      /*
        If there was a sine in the last frame, let it continue from the first
        envelope on else start at the transient position. Indexing of sineMapped
        starts relative to lsb.
      */
      sineMapped[qmfBand - lsb] =
          (harmFlagsPrev[qmfBandDiv32] & maskQmfBand) ? 0 : tranEnv;
      if (sineMapped[qmfBand - lsb] < PVC_NTIMESLOT) {
        harmFlagsPrevActive[qmfBandDiv32] |= maskQmfBand;
      }
    }

    if (bitcount-- == 0) {
      bitcount = 31;
      curFlags++;
    }
  }
  FDKmemcpy(harmFlagsPrev, harmFlagsQmfBands,
            sizeof(ULONG) * ADD_HARMONICS_FLAGS_SIZE);
}

/*!
  \brief     Restore sineMapped of previous frame

  For PVC it might happen that the PVC framing (always 0) is out of sync with
  the SBR framing. The adding of additional harmonics is done based on the SBR
  framing. If the SBR framing is trailing the PVC framing the sine mapping of
  the previous SBR frame needs to be used for the overlapping time slots.
*/
/*static*/ void mapSineFlagsPvc(
    UCHAR *freqBandTable,       /*!< Band borders (there's only 1 flag per
                                   band) */
    int nSfb,                   /*!< Number of bands in the table */
    ULONG *harmFlagsPrev,       /*!< Packed addHarmonics of previous frame
                                   (aligned to the MSB) */
    ULONG *harmFlagsPrevActive, /*!< Packed sineMapped of previous
                                   frame (aligned to the LSB) */
    SCHAR *sineMapped,          /*!< Resulting vector of sine start positions
                                   for each QMF band */
    int sinusoidalPos,          /*!< sinusoidal position */
    SCHAR *sinusoidalPosPrev,   /*!< sinusoidal position of previous
                                   frame */
    int trailingSbrFrame)       /*!< indication if the SBR framing is
                                   trailing the PVC framing */
{
  /* Reset the output vector first */
  FDKmemset(sineMapped, 32, MAX_FREQ_COEFFS); /* 32 means 'no sine' */

  if (trailingSbrFrame) {
    /* restore sineMapped[] of previous frame */
    int i;
    const int lsb = freqBandTable[0];
    const int usb = freqBandTable[nSfb];
    for (i = lsb; i < usb; i++) {
      const int qmfBandDiv32 = i >> 5;
      const int maskQmfBand =
          1 << (i & 31); /* mask to extract harmonic flag from prevFlags */

      /* Two cases need to be distinguished ... */
      if (harmFlagsPrevActive[qmfBandDiv32] & maskQmfBand) {
        /* the sine mapping already started last PVC frame -> seamlessly
         * continue */
        sineMapped[i - lsb] = 0;
      } else if (harmFlagsPrev[qmfBandDiv32] & maskQmfBand) {
        /* sinusoidalPos of prev PVC frame was >= PVC_NTIMESLOT -> sine starts
         * in this frame */
        sineMapped[i - lsb] =
            *sinusoidalPosPrev - PVC_NTIMESLOT; /* we are 16 sbr time slots
                                                   ahead of last frame now */
      }
    }
  }
  *sinusoidalPosPrev = sinusoidalPos;
}

/*!
  \brief     Reduce gain-adjustment induced aliasing for real valued filterbank.
*/
/*static*/ void aliasingReduction(
    FIXP_DBL *degreeAlias, /*!< estimated aliasing for each QMF
                              channel */
    ENV_CALC_NRGS *nrgs,
    UCHAR *useAliasReduction, /*!< synthetic sine energy for each
                                 subband, used as flag */
    int noSubbands)           /*!< number of QMF channels to process */
{
  FIXP_DBL *nrgGain = nrgs->nrgGain; /*!< subband gains to be modified */
  SCHAR *nrgGain_e =
      nrgs->nrgGain_e; /*!< subband gains to be modified (exponents) */
  FIXP_DBL *nrgEst = nrgs->nrgEst; /*!< subband energy before amplification */
  SCHAR *nrgEst_e =
      nrgs->nrgEst_e; /*!< subband energy before amplification (exponents) */
  int grouping = 0, index = 0, noGroups, k;
  int groupVector[MAX_FREQ_COEFFS];

  /* Calculate grouping*/
  for (k = 0; k < noSubbands - 1; k++) {
    if ((degreeAlias[k + 1] != FL2FXCONST_DBL(0.0f)) && useAliasReduction[k]) {
      if (grouping == 0) {
        groupVector[index++] = k;
        grouping = 1;
      } else {
        if (groupVector[index - 1] + 3 == k) {
          groupVector[index++] = k + 1;
          grouping = 0;
        }
      }
    } else {
      if (grouping) {
        if (useAliasReduction[k])
          groupVector[index++] = k + 1;
        else
          groupVector[index++] = k;
        grouping = 0;
      }
    }
  }

  if (grouping) {
    groupVector[index++] = noSubbands;
  }
  noGroups = index >> 1;

  /*Calculate new gain*/
  for (int group = 0; group < noGroups; group++) {
    FIXP_DBL nrgOrig = FL2FXCONST_DBL(
        0.0f); /* Original signal energy in current group of bands */
    SCHAR nrgOrig_e = 0;
    FIXP_DBL nrgAmp = FL2FXCONST_DBL(
        0.0f); /* Amplified signal energy in group (using current gains) */
    SCHAR nrgAmp_e = 0;
    FIXP_DBL nrgMod = FL2FXCONST_DBL(
        0.0f); /* Signal energy in group when applying modified gains */
    SCHAR nrgMod_e = 0;
    FIXP_DBL groupGain; /* Total energy gain in group */
    SCHAR groupGain_e;
    FIXP_DBL compensation; /* Compensation factor for the energy change when
                              applying modified gains */
    SCHAR compensation_e;

    int startGroup = groupVector[2 * group];
    int stopGroup = groupVector[2 * group + 1];

    /* Calculate total energy in group before and after amplification with
     * current gains: */
    for (k = startGroup; k < stopGroup; k++) {
      /* Get original band energy */
      FIXP_DBL tmp = nrgEst[k];
      SCHAR tmp_e = nrgEst_e[k];

      FDK_add_MantExp(tmp, tmp_e, nrgOrig, nrgOrig_e, &nrgOrig, &nrgOrig_e);

      /* Multiply band energy with current gain */
      tmp = fMult(tmp, nrgGain[k]);
      tmp_e = tmp_e + nrgGain_e[k];

      FDK_add_MantExp(tmp, tmp_e, nrgAmp, nrgAmp_e, &nrgAmp, &nrgAmp_e);
    }

    /* Calculate total energy gain in group */
    FDK_divide_MantExp(nrgAmp, nrgAmp_e, nrgOrig, nrgOrig_e, &groupGain,
                       &groupGain_e);

    for (k = startGroup; k < stopGroup; k++) {
      FIXP_DBL tmp;
      SCHAR tmp_e;

      FIXP_DBL alpha = degreeAlias[k];
      if (k < noSubbands - 1) {
        if (degreeAlias[k + 1] > alpha) alpha = degreeAlias[k + 1];
      }

      /* Modify gain depending on the degree of aliasing */
      FDK_add_MantExp(
          fMult(alpha, groupGain), groupGain_e,
          fMult(/*FL2FXCONST_DBL(1.0f)*/ (FIXP_DBL)MAXVAL_DBL - alpha,
                nrgGain[k]),
          nrgGain_e[k], &nrgGain[k], &nrgGain_e[k]);

      /* Apply modified gain to original energy */
      tmp = fMult(nrgGain[k], nrgEst[k]);
      tmp_e = nrgGain_e[k] + nrgEst_e[k];

      /* Accumulate energy with modified gains applied */
      FDK_add_MantExp(tmp, tmp_e, nrgMod, nrgMod_e, &nrgMod, &nrgMod_e);
    }

    /* Calculate compensation factor to retain the energy of the amplified
     * signal */
    FDK_divide_MantExp(nrgAmp, nrgAmp_e, nrgMod, nrgMod_e, &compensation,
                       &compensation_e);

    /* Apply compensation factor to all gains of the group */
    for (k = startGroup; k < stopGroup; k++) {
      nrgGain[k] = fMult(nrgGain[k], compensation);
      nrgGain_e[k] = nrgGain_e[k] + compensation_e;
    }
  }
}

#define INTER_TES_SF_CHANGE 3

typedef struct {
  FIXP_DBL subsample_power_low[(((1024) / (32) * (4) / 2) + (3 * (4)))];
  FIXP_DBL subsample_power_high[(((1024) / (32) * (4) / 2) + (3 * (4)))];
  FIXP_DBL gain[(((1024) / (32) * (4) / 2) + (3 * (4)))];
  SCHAR subsample_power_low_sf[(((1024) / (32) * (4) / 2) + (3 * (4)))];
  SCHAR subsample_power_high_sf[(((1024) / (32) * (4) / 2) + (3 * (4)))];
} ITES_TEMP;

static void apply_inter_tes(FIXP_DBL **qmfReal, FIXP_DBL **qmfImag,
                            const QMF_SCALE_FACTOR *sbrScaleFactor,
                            const SCHAR exp[2], const int RATE,
                            const int startPos, const int stopPos,
                            const int lowSubband, const int nbSubband,
                            const UCHAR gamma_idx) {
  int highSubband = lowSubband + nbSubband;
  FIXP_DBL *subsample_power_high, *subsample_power_low;
  SCHAR *subsample_power_high_sf, *subsample_power_low_sf;
  FIXP_DBL total_power_high = (FIXP_DBL)0;
  FIXP_DBL total_power_low = (FIXP_DBL)0;
  FIXP_DBL *gain;
  int gain_sf[(((1024) / (32) * (4) / 2) + (3 * (4)))];

  /* gamma[gamma_idx] = {0.0f, 1.0f, 2.0f, 4.0f} */
  int gamma_sf =
      (int)gamma_idx - 1; /* perhaps +1 to save one bit? (0.99999f vs 1.f) */

  int nbSubsample = stopPos - startPos;
  int i, j;

  C_ALLOC_SCRATCH_START(pTmp, ITES_TEMP, 1);
  subsample_power_high = pTmp->subsample_power_high;
  subsample_power_low = pTmp->subsample_power_low;
  subsample_power_high_sf = pTmp->subsample_power_high_sf;
  subsample_power_low_sf = pTmp->subsample_power_low_sf;
  gain = pTmp->gain;

  if (gamma_idx > 0) {
    int preShift2 = 32 - fNormz((FIXP_DBL)nbSubsample);
    int total_power_low_sf = 1 - DFRACT_BITS;
    int total_power_high_sf = 1 - DFRACT_BITS;

    for (i = 0; i < nbSubsample; ++i) {
      FIXP_DBL bufferReal[(((1024) / (32) * (4) / 2) + (3 * (4)))];
      FIXP_DBL bufferImag[(((1024) / (32) * (4) / 2) + (3 * (4)))];
      FIXP_DBL maxVal = (FIXP_DBL)0;

      int ts = startPos + i;

      int low_sf = (ts < 3 * RATE) ? sbrScaleFactor->ov_lb_scale
                                   : sbrScaleFactor->lb_scale;
      low_sf = 15 - low_sf;

      for (j = 0; j < lowSubband; ++j) {
        bufferImag[j] = qmfImag[startPos + i][j];
        maxVal |= (FIXP_DBL)((LONG)(bufferImag[j]) ^
                             ((LONG)bufferImag[j] >> (DFRACT_BITS - 1)));
        bufferReal[j] = qmfReal[startPos + i][j];
        maxVal |= (FIXP_DBL)((LONG)(bufferReal[j]) ^
                             ((LONG)bufferReal[j] >> (DFRACT_BITS - 1)));
      }

      subsample_power_low[i] = (FIXP_DBL)0;
      subsample_power_low_sf[i] = 0;

      if (maxVal != FL2FXCONST_DBL(0.f)) {
        /* multiply first, then shift for safe summation */
        int preShift = 1 - CntLeadingZeros(maxVal);
        int postShift = 32 - fNormz((FIXP_DBL)lowSubband);

        /* reduce preShift because otherwise we risk to square -1.f */
        if (preShift != 0) preShift++;

        subsample_power_low_sf[i] += (low_sf + preShift) * 2 + postShift + 1;

        scaleValues(bufferReal, lowSubband, -preShift);
        scaleValues(bufferImag, lowSubband, -preShift);
        for (j = 0; j < lowSubband; ++j) {
          FIXP_DBL addme;
          addme = fPow2Div2(bufferReal[j]);
          subsample_power_low[i] += addme >> postShift;
          addme = fPow2Div2(bufferImag[j]);
          subsample_power_low[i] += addme >> postShift;
        }
      }

      /* now get high */

      maxVal = (FIXP_DBL)0;

      int high_sf = exp[(ts < 16 * RATE) ? 0 : 1];

      for (j = lowSubband; j < highSubband; ++j) {
        bufferImag[j] = qmfImag[startPos + i][j];
        maxVal |= (FIXP_DBL)((LONG)(bufferImag[j]) ^
                             ((LONG)bufferImag[j] >> (DFRACT_BITS - 1)));
        bufferReal[j] = qmfReal[startPos + i][j];
        maxVal |= (FIXP_DBL)((LONG)(bufferReal[j]) ^
                             ((LONG)bufferReal[j] >> (DFRACT_BITS - 1)));
      }

      subsample_power_high[i] = (FIXP_DBL)0;
      subsample_power_high_sf[i] = 0;

      if (maxVal != FL2FXCONST_DBL(0.f)) {
        int preShift = 1 - CntLeadingZeros(maxVal);
        /* reduce preShift because otherwise we risk to square -1.f */
        if (preShift != 0) preShift++;

        int postShift = 32 - fNormz((FIXP_DBL)(highSubband - lowSubband));
        subsample_power_high_sf[i] += (high_sf + preShift) * 2 + postShift + 1;

        scaleValues(&bufferReal[lowSubband], highSubband - lowSubband,
                    -preShift);
        scaleValues(&bufferImag[lowSubband], highSubband - lowSubband,
                    -preShift);
        for (j = lowSubband; j < highSubband; j++) {
          subsample_power_high[i] += fPow2Div2(bufferReal[j]) >> postShift;
          subsample_power_high[i] += fPow2Div2(bufferImag[j]) >> postShift;
        }
      }

      /* sum all together */
      FIXP_DBL new_summand = subsample_power_low[i];
      int new_summand_sf = subsample_power_low_sf[i];

      /* make sure the current sum, and the new summand have the same SF */
      if (new_summand_sf > total_power_low_sf) {
        int diff = fMin(DFRACT_BITS - 1, new_summand_sf - total_power_low_sf);
        total_power_low >>= diff;
        total_power_low_sf = new_summand_sf;
      } else if (new_summand_sf < total_power_low_sf) {
        new_summand >>= total_power_low_sf - new_summand_sf;
      }

      total_power_low += (new_summand >> preShift2);

      new_summand = subsample_power_high[i];
      new_summand_sf = subsample_power_high_sf[i];
      if (new_summand_sf > total_power_high_sf) {
        total_power_high >>=
            fMin(DFRACT_BITS - 1, new_summand_sf - total_power_high_sf);
        total_power_high_sf = new_summand_sf;
      } else if (new_summand_sf < total_power_high_sf) {
        new_summand >>= total_power_high_sf - new_summand_sf;
      }

      total_power_high += (new_summand >> preShift2);
    }

    total_power_low_sf += preShift2;
    total_power_high_sf += preShift2;

    /* gain[i] = e_LOW[i] */
    for (i = 0; i < nbSubsample; ++i) {
      int sf2;
      FIXP_DBL mult =
          fMultNorm(subsample_power_low[i], (FIXP_DBL)nbSubsample, &sf2);
      int mult_sf = subsample_power_low_sf[i] + DFRACT_BITS - 1 + sf2;

      if (total_power_low != FIXP_DBL(0)) {
        gain[i] = fDivNorm(mult, total_power_low, &sf2);
        gain_sf[i] = mult_sf - total_power_low_sf + sf2;
        gain[i] = sqrtFixp_lookup(gain[i], &gain_sf[i]);
        if (gain_sf[i] < 0) {
          gain[i] >>= -gain_sf[i];
          gain_sf[i] = 0;
        }
      } else {
        if (mult == FIXP_DBL(0)) {
          gain[i] = FIXP_DBL(0);
          gain_sf[i] = 0;
        } else {
          gain[i] = (FIXP_DBL)MAXVAL_DBL;
          gain_sf[i] = 0;
        }
      }
    }

    FIXP_DBL total_power_high_after = (FIXP_DBL)0;
    int total_power_high_after_sf = 1 - DFRACT_BITS;

    /* gain[i] = g_inter[i] */
    for (i = 0; i < nbSubsample; ++i) {
      if (gain_sf[i] < 0) {
        gain[i] >>= -gain_sf[i];
        gain_sf[i] = 0;
      }

      /* calculate: gain[i] = 1.0f + gamma * (gain[i] - 1.0f); */
      FIXP_DBL one = (FIXP_DBL)MAXVAL_DBL >>
                     gain_sf[i]; /* to substract this from gain[i] */

      /* gamma is actually always 1 according to the table, so skip the
       * fMultDiv2 */
      FIXP_DBL mult = (gain[i] - one) >> 1;
      int mult_sf = gain_sf[i] + gamma_sf;

      one = FL2FXCONST_DBL(0.5f) >> mult_sf;
      gain[i] = one + mult;
      gain_sf[i] += gamma_sf + 1; /* +1 because of fMultDiv2() */

      /* set gain to at least 0.2f */
      FIXP_DBL point_two = FL2FXCONST_DBL(0.8f); /* scaled up by 2 */
      int point_two_sf = -2;

      FIXP_DBL tmp = gain[i];
      if (point_two_sf < gain_sf[i]) {
        point_two >>= gain_sf[i] - point_two_sf;
      } else {
        tmp >>= point_two_sf - gain_sf[i];
      }

      /* limit and calculate gain[i]^2 too */
      FIXP_DBL gain_pow2;
      int gain_pow2_sf;
      if (tmp < point_two) {
        gain[i] = FL2FXCONST_DBL(0.8f);
        gain_sf[i] = -2;
        gain_pow2 = FL2FXCONST_DBL(0.64f);
        gain_pow2_sf = -4;
      } else {
        /* this upscaling seems quite important */
        int r = CountLeadingBits(gain[i]);
        gain[i] <<= r;
        gain_sf[i] -= r;

        gain_pow2 = fPow2(gain[i]);
        gain_pow2_sf = gain_sf[i] << 1;
      }

      int room;
      subsample_power_high[i] =
          fMultNorm(subsample_power_high[i], gain_pow2, &room);
      subsample_power_high_sf[i] =
          subsample_power_high_sf[i] + gain_pow2_sf + room;

      int new_summand_sf = subsample_power_high_sf[i]; /* + gain_pow2_sf; */
      if (new_summand_sf > total_power_high_after_sf) {
        total_power_high_after >>=
            fMin(DFRACT_BITS - 1, new_summand_sf - total_power_high_after_sf);
        total_power_high_after_sf = new_summand_sf;
      } else if (new_summand_sf < total_power_high_after_sf) {
        subsample_power_high[i] >>= total_power_high_after_sf - new_summand_sf;
      }
      total_power_high_after += subsample_power_high[i] >> preShift2;
    }

    total_power_high_after_sf += preShift2;

    int sf2 = 0;
    FIXP_DBL gain_adj_2 = FL2FX_DBL(0.5f);
    int gain_adj_2_sf = 1;

    if ((total_power_high != (FIXP_DBL)0) &&
        (total_power_high_after != (FIXP_DBL)0)) {
      gain_adj_2 = fDivNorm(total_power_high, total_power_high_after, &sf2);
      gain_adj_2_sf = total_power_high_sf - total_power_high_after_sf + sf2;
    }

    FIXP_DBL gain_adj = sqrtFixp_lookup(gain_adj_2, &gain_adj_2_sf);
    int gain_adj_sf = gain_adj_2_sf;

    for (i = 0; i < nbSubsample; ++i) {
      gain[i] = fMult(gain[i], gain_adj);
      gain_sf[i] += gain_adj_sf;

      /* limit gain */
      if (gain_sf[i] > INTER_TES_SF_CHANGE) {
        gain[i] = (FIXP_DBL)MAXVAL_DBL;
        gain_sf[i] = INTER_TES_SF_CHANGE;
      }
    }

    for (i = 0; i < nbSubsample; ++i) {
      /* equalize gain[]'s scale factors */
      gain[i] >>= INTER_TES_SF_CHANGE - gain_sf[i];

      for (j = lowSubband; j < highSubband; j++) {
        qmfReal[startPos + i][j] = fMult(qmfReal[startPos + i][j], gain[i]);
        qmfImag[startPos + i][j] = fMult(qmfImag[startPos + i][j], gain[i]);
      }
    }
  } else { /* gamma_idx == 0 */
    /* Inter-TES is not active. Still perform the scale change to have a
     * consistent scaling for all envelopes of this frame. */
    for (i = 0; i < nbSubsample; ++i) {
      for (j = lowSubband; j < highSubband; j++) {
        qmfReal[startPos + i][j] >>= INTER_TES_SF_CHANGE;
        qmfImag[startPos + i][j] >>= INTER_TES_SF_CHANGE;
      }
    }
  }
  C_ALLOC_SCRATCH_END(pTmp, ITES_TEMP, 1);
}

/*!
  \brief  Apply spectral envelope to subband samples

  This function is called from sbr_dec.cpp in each frame.

  To enhance accuracy and due to the usage of tables for squareroots and
  inverse, some calculations are performed with the operands being split
  into mantissa and exponent. The variable names in the source code carry
  the suffixes <em>_m</em> and  <em>_e</em> respectively. The control data
  in #hFrameData containts envelope data which is represented by this format but
  stored in single words. (See requantizeEnvelopeData() for details). This data
  is unpacked within calculateSbrEnvelope() to follow the described suffix
  convention.

  The actual value (comparable to the corresponding float-variable in the
  research-implementation) of a mantissa/exponent-pair can be calculated as

  \f$ value = value\_m * 2^{value\_e} \f$

  All energies and noise levels decoded from the bitstream suit for an
  original signal magnitude of \f$\pm 32768 \f$ rather than \f$ \pm 1\f$.
  Therefore, the scale factor <em>hb_scale</em> passed into this function will
  be converted to an 'input exponent' (#input_e), which fits the internal
  representation.

  Before the actual processing, an exponent #adj_e for resulting adjusted
  samples is derived from the maximum reference energy.

  Then, for each envelope, the following steps are performed:

  \li Calculate energy in the signal to be adjusted. Depending on the the value
  of #interpolFreq (interpolation mode), this is either done seperately for each
  QMF-subband or for each SBR-band. The resulting energies are stored in
  #nrgEst_m[#MAX_FREQ_COEFFS] (mantissas) and #nrgEst_e[#MAX_FREQ_COEFFS]
  (exponents). \li Calculate gain and noise level for each subband:<br> \f$ gain
  = \sqrt{ \frac{nrgRef}{nrgEst} \cdot (1 - noiseRatio) } \hspace{2cm} noise =
  \sqrt{ nrgRef \cdot noiseRatio } \f$<br> where <em>noiseRatio</em> and
  <em>nrgRef</em> are extracted from the bitstream and <em>nrgEst</em> is the
  subband energy before adjustment. The resulting gains are stored in
  #nrgGain_m[#MAX_FREQ_COEFFS] (mantissas) and #nrgGain_e[#MAX_FREQ_COEFFS]
  (exponents), the noise levels are stored in #noiseLevel_m[#MAX_FREQ_COEFFS]
  and #noiseLevel_e[#MAX_FREQ_COEFFS] (exponents). The sine levels are stored in
  #nrgSine_m[#MAX_FREQ_COEFFS] and #nrgSine_e[#MAX_FREQ_COEFFS]. \li Noise
  limiting: The gain for each subband is limited both absolutely and relatively
  compared to the total gain over all subbands. \li Boost gain: Calculate and
  apply boost factor for each limiter band in order to compensate for the energy
  loss imposed by the limiting. \li Apply gains and add noise: The gains and
  noise levels are applied to all timeslots of the current envelope. A short
  FIR-filter (length 4 QMF-timeslots) can be used to smooth the sudden change at
  the envelope borders. Each complex subband sample of the current timeslot is
  multiplied by the smoothed gain, then random noise with the calculated level
  is added.

  \note
  To reduce the stack size, some of the local arrays could be located within
  the time output buffer. Of the 512 samples temporarily available there,
  about half the size is already used by #SBR_FRAME_DATA. A pointer to the
  remaining free memory could be supplied by an additional argument to
  calculateSbrEnvelope() in sbr_dec:

  \par
  \code
    calculateSbrEnvelope (&hSbrDec->sbrScaleFactor,
                          &hSbrDec->SbrCalculateEnvelope,
                          hHeaderData,
                          hFrameData,
                          QmfBufferReal,
                          QmfBufferImag,
                          timeOutPtr + sizeof(SBR_FRAME_DATA)/sizeof(Float) +
  1); \endcode

  \par
  Within calculateSbrEnvelope(), some pointers could be defined instead of the
  arrays #nrgRef_m, #nrgRef_e, #nrgEst_m, #nrgEst_e, #noiseLevel_m:

  \par
  \code
    fract*        nrgRef_m = timeOutPtr;
    SCHAR*        nrgRef_e = nrgRef_m + MAX_FREQ_COEFFS;
    fract*        nrgEst_m = nrgRef_e + MAX_FREQ_COEFFS;
    SCHAR*        nrgEst_e = nrgEst_m + MAX_FREQ_COEFFS;
    fract*        noiseLevel_m = nrgEst_e + MAX_FREQ_COEFFS;
  \endcode

  <br>
*/
void calculateSbrEnvelope(
    QMF_SCALE_FACTOR *sbrScaleFactor, /*!< Scaling factors */
    HANDLE_SBR_CALCULATE_ENVELOPE
        h_sbr_cal_env, /*!< Handle to struct filled by the create-function */
    HANDLE_SBR_HEADER_DATA hHeaderData, /*!< Static control data */
    HANDLE_SBR_FRAME_DATA hFrameData,   /*!< Control data of current frame */
    PVC_DYNAMIC_DATA *pPvcDynamicData,
    FIXP_DBL *
        *analysBufferReal, /*!< Real part of subband samples to be processed */
    FIXP_DBL *
        *analysBufferImag, /*!< Imag part of subband samples to be processed */
    const int useLP,
    FIXP_DBL *degreeAlias, /*!< Estimated aliasing for each QMF channel */
    const UINT flags, const int frameErrorFlag) {
  int c, i, i_stop, j, envNoise = 0;
  UCHAR *borders = hFrameData->frameInfo.borders;
  UCHAR *bordersPvc = hFrameData->frameInfo.pvcBorders;
  int pvc_mode = pPvcDynamicData->pvc_mode;
  int first_start =
      ((pvc_mode > 0) ? bordersPvc[0] : borders[0]) * hHeaderData->timeStep;
  FIXP_SGL *noiseLevels = hFrameData->sbrNoiseFloorLevel;
  HANDLE_FREQ_BAND_DATA hFreq = &hHeaderData->freqBandData;
  UCHAR **pFreqBandTable = hFreq->freqBandTable;
  UCHAR *pFreqBandTableNoise = hFreq->freqBandTableNoise;

  int lowSubband = hFreq->lowSubband;
  int highSubband = hFreq->highSubband;
  int noSubbands = highSubband - lowSubband;

  /* old high subband before headerchange
     we asume no headerchange here        */
  int ov_highSubband = hFreq->highSubband;

  int noNoiseBands = hFreq->nNfb;
  UCHAR *noSubFrameBands = hFreq->nSfb;
  int no_cols = hHeaderData->numberTimeSlots * hHeaderData->timeStep;

  SCHAR sineMapped[MAX_FREQ_COEFFS];
  SCHAR ov_adj_e = SCALE2EXP(sbrScaleFactor->ov_hb_scale);
  SCHAR adj_e = 0;
  SCHAR output_e;
  SCHAR final_e = 0;
  /* inter-TES is active in one or more envelopes of the current SBR frame */
  const int iTES_enable = hFrameData->iTESactive;
  const int iTES_scale_change = (iTES_enable) ? INTER_TES_SF_CHANGE : 0;
  SCHAR maxGainLimit_e = (frameErrorFlag) ? MAX_GAIN_CONCEAL_EXP : MAX_GAIN_EXP;

  UCHAR smooth_length = 0;

  FIXP_SGL *pIenv = hFrameData->iEnvelope;

  C_ALLOC_SCRATCH_START(useAliasReduction, UCHAR, 64)

  /* if values differ we had a headerchange; if old highband is bigger then new
     one we need to patch overlap-highband-scaling for this frame (see use of
     ov_highSubband) as overlap contains higher frequency components which would
     get lost */
  if (hFreq->highSubband < hFreq->ov_highSubband) {
    ov_highSubband = hFreq->ov_highSubband;
  }

  if (pvc_mode > 0) {
    if (hFrameData->frameInfo.bordersNoise[0] > bordersPvc[0]) {
      /* noise envelope of previous frame is trailing into current PVC frame */
      envNoise = -1;
      noiseLevels = h_sbr_cal_env->prevSbrNoiseFloorLevel;
      noNoiseBands = h_sbr_cal_env->prevNNfb;
      noSubFrameBands = h_sbr_cal_env->prevNSfb;
      lowSubband = h_sbr_cal_env->prevLoSubband;
      highSubband = h_sbr_cal_env->prevHiSubband;

      noSubbands = highSubband - lowSubband;
      ov_highSubband = highSubband;
      if (highSubband < h_sbr_cal_env->prev_ov_highSubband) {
        ov_highSubband = h_sbr_cal_env->prev_ov_highSubband;
      }

      pFreqBandTable[0] = h_sbr_cal_env->prevFreqBandTableLo;
      pFreqBandTable[1] = h_sbr_cal_env->prevFreqBandTableHi;
      pFreqBandTableNoise = h_sbr_cal_env->prevFreqBandTableNoise;
    }

    mapSineFlagsPvc(pFreqBandTable[1], noSubFrameBands[1],
                    h_sbr_cal_env->harmFlagsPrev,
                    h_sbr_cal_env->harmFlagsPrevActive, sineMapped,
                    hFrameData->sinusoidal_position,
                    &h_sbr_cal_env->sinusoidal_positionPrev,
                    (borders[0] > bordersPvc[0]) ? 1 : 0);
  } else {
    /*
      Extract sine flags for all QMF bands
    */
    mapSineFlags(pFreqBandTable[1], noSubFrameBands[1],
                 hFrameData->addHarmonics, h_sbr_cal_env->harmFlagsPrev,
                 h_sbr_cal_env->harmFlagsPrevActive,
                 hFrameData->frameInfo.tranEnv, sineMapped);
  }

  /*
    Scan for maximum in bufferd noise levels.
    This is needed in case that we had strong noise in the previous frame
    which is smoothed into the current frame.
    The resulting exponent is used as start value for the maximum search
    in reference energies
  */
  if (!useLP)
    adj_e = h_sbr_cal_env->filtBufferNoise_e -
            getScalefactor(h_sbr_cal_env->filtBufferNoise, noSubbands);

  /*
    Scan for maximum reference energy to be able
    to select appropriate values for adj_e and final_e.
  */
  if (pvc_mode > 0) {
    INT maxSfbNrg_e = pPvcDynamicData->predEsg_expMax;

    /* Energy -> magnitude (sqrt halfens exponent) */
    maxSfbNrg_e =
        (maxSfbNrg_e + 1) >> 1; /* +1 to go safe (round to next higher int) */

    /* Some safety margin is needed for 2 reasons:
       - The signal energy is not equally spread over all subband samples in
         a specific sfb of an envelope (Nrg could be too high by a factor of
         envWidth * sfbWidth)
       - Smoothing can smear high gains of the previous envelope into the
       current
    */
    maxSfbNrg_e += 6;

    adj_e = maxSfbNrg_e;
    // final_e should not exist for PVC fixfix framing
  } else {
    for (i = 0; i < hFrameData->frameInfo.nEnvelopes; i++) {
      INT maxSfbNrg_e =
          -FRACT_BITS + NRG_EXP_OFFSET; /* start value for maximum search */

      /* Fetch frequency resolution for current envelope: */
      for (j = noSubFrameBands[hFrameData->frameInfo.freqRes[i]]; j != 0; j--) {
        maxSfbNrg_e = fixMax(maxSfbNrg_e, (INT)((LONG)(*pIenv++) & MASK_E));
      }
      maxSfbNrg_e -= NRG_EXP_OFFSET;

      /* Energy -> magnitude (sqrt halfens exponent) */
      maxSfbNrg_e =
          (maxSfbNrg_e + 1) >> 1; /* +1 to go safe (round to next higher int) */

      /* Some safety margin is needed for 2 reasons:
         - The signal energy is not equally spread over all subband samples in
           a specific sfb of an envelope (Nrg could be too high by a factor of
           envWidth * sfbWidth)
         - Smoothing can smear high gains of the previous envelope into the
         current
      */
      maxSfbNrg_e += 6;

      if (borders[i] < hHeaderData->numberTimeSlots)
        /* This envelope affects timeslots that belong to the output frame */
        adj_e = fMax(maxSfbNrg_e, adj_e);

      if (borders[i + 1] > hHeaderData->numberTimeSlots)
        /* This envelope affects timeslots after the output frame */
        final_e = fMax(maxSfbNrg_e, final_e);
    }
  }
  /*
    Calculate adjustment factors and apply them for every envelope.
  */
  pIenv = hFrameData->iEnvelope;

  if (pvc_mode > 0) {
    /* iterate over SBR time slots starting with bordersPvc[i] */
    i = bordersPvc[0]; /* usually 0; can be >0 if switching from legacy SBR to
                          PVC */
    i_stop = PVC_NTIMESLOT;
    FDK_ASSERT(bordersPvc[hFrameData->frameInfo.nEnvelopes] == PVC_NTIMESLOT);
  } else {
    /* iterate over SBR envelopes starting with 0 */
    i = 0;
    i_stop = hFrameData->frameInfo.nEnvelopes;
  }
  for (; i < i_stop; i++) {
    int k, noNoiseFlag;
    SCHAR noise_e, input_e = SCALE2EXP(sbrScaleFactor->hb_scale);
    C_ALLOC_SCRATCH_START(pNrgs, ENV_CALC_NRGS, 1);

    /*
      Helper variables.
    */
    int start_pos, stop_pos, freq_res;
    if (pvc_mode > 0) {
      start_pos =
          hHeaderData->timeStep *
          i; /* Start-position in time (subband sample) for current envelope. */
      stop_pos = hHeaderData->timeStep * (i + 1); /* Stop-position in time
                                                     (subband sample) for
                                                     current envelope. */
      freq_res =
          hFrameData->frameInfo
              .freqRes[0]; /* Frequency resolution for current envelope. */
      FDK_ASSERT(
          freq_res ==
          hFrameData->frameInfo.freqRes[hFrameData->frameInfo.nEnvelopes - 1]);
    } else {
      start_pos = hHeaderData->timeStep *
                  borders[i]; /* Start-position in time (subband sample) for
                                 current envelope. */
      stop_pos = hHeaderData->timeStep *
                 borders[i + 1]; /* Stop-position in time (subband sample) for
                                    current envelope. */
      freq_res =
          hFrameData->frameInfo
              .freqRes[i]; /* Frequency resolution for current envelope. */
    }

    /* Always fully initialize the temporary energy table. This prevents
       negative energies and extreme gain factors in cases where the number of
       limiter bands exceeds the number of subbands. The latter can be caused by
       undetected bit errors and is tested by some streams from the
       certification set. */
    FDKmemclear(pNrgs, sizeof(ENV_CALC_NRGS));

    if (pvc_mode > 0) {
      /* get predicted energy values from PVC module */
      expandPredEsg(pPvcDynamicData, i, (int)MAX_FREQ_COEFFS, pNrgs->nrgRef,
                    pNrgs->nrgRef_e);

      if (i == borders[0]) {
        mapSineFlags(pFreqBandTable[1], noSubFrameBands[1],
                     hFrameData->addHarmonics, h_sbr_cal_env->harmFlagsPrev,
                     h_sbr_cal_env->harmFlagsPrevActive,
                     hFrameData->sinusoidal_position, sineMapped);
      }

      if (i >= hFrameData->frameInfo.bordersNoise[envNoise + 1]) {
        if (envNoise >= 0) {
          noiseLevels += noNoiseBands; /* The noise floor data is stored in a
                                          row [noiseFloor1 noiseFloor2...].*/
        } else {
          /* leave trailing noise envelope of past frame */
          noNoiseBands = hFreq->nNfb;
          noSubFrameBands = hFreq->nSfb;
          noiseLevels = hFrameData->sbrNoiseFloorLevel;

          lowSubband = hFreq->lowSubband;
          highSubband = hFreq->highSubband;

          noSubbands = highSubband - lowSubband;
          ov_highSubband = highSubband;
          if (highSubband < hFreq->ov_highSubband) {
            ov_highSubband = hFreq->ov_highSubband;
          }

          pFreqBandTable[0] = hFreq->freqBandTableLo;
          pFreqBandTable[1] = hFreq->freqBandTableHi;
          pFreqBandTableNoise = hFreq->freqBandTableNoise;
        }
        envNoise++;
      }
    } else {
      /* If the start-pos of the current envelope equals the stop pos of the
         current noise envelope, increase the pointer (i.e. choose the next
         noise-floor).*/
      if (borders[i] == hFrameData->frameInfo.bordersNoise[envNoise + 1]) {
        noiseLevels += noNoiseBands; /* The noise floor data is stored in a row
                                        [noiseFloor1 noiseFloor2...].*/
        envNoise++;
      }
    }
    if (i == hFrameData->frameInfo.tranEnv ||
        i == h_sbr_cal_env->prevTranEnv) /* attack */
    {
      noNoiseFlag = 1;
      if (!useLP) smooth_length = 0; /* No smoothing on attacks! */
    } else {
      noNoiseFlag = 0;
      if (!useLP)
        smooth_length = (1 - hHeaderData->bs_data.smoothingLength)
                        << 2; /* can become either 0 or 4 */
    }

    /*
      Energy estimation in transposed highband.
    */
    if (hHeaderData->bs_data.interpolFreq)
      calcNrgPerSubband(analysBufferReal, (useLP) ? NULL : analysBufferImag,
                        lowSubband, highSubband, start_pos, stop_pos, input_e,
                        pNrgs->nrgEst, pNrgs->nrgEst_e);
    else
      calcNrgPerSfb(analysBufferReal, (useLP) ? NULL : analysBufferImag,
                    noSubFrameBands[freq_res], pFreqBandTable[freq_res],
                    start_pos, stop_pos, input_e, pNrgs->nrgEst,
                    pNrgs->nrgEst_e);

    /*
      Calculate subband gains
    */
    {
      UCHAR *table = pFreqBandTable[freq_res];
      UCHAR *pUiNoise =
          &pFreqBandTableNoise[1]; /*! Upper limit of the current noise floor
                                      band. */

      FIXP_SGL *pNoiseLevels = noiseLevels;

      FIXP_DBL tmpNoise =
          FX_SGL2FX_DBL((FIXP_SGL)((LONG)(*pNoiseLevels) & MASK_M));
      SCHAR tmpNoise_e =
          (UCHAR)((LONG)(*pNoiseLevels++) & MASK_E) - NOISE_EXP_OFFSET;

      int cc = 0;
      c = 0;
      if (pvc_mode > 0) {
        for (j = 0; j < noSubFrameBands[freq_res]; j++) {
          UCHAR sinePresentFlag = 0;
          int li = table[j];
          int ui = table[j + 1];

          for (k = li; k < ui; k++) {
            sinePresentFlag |= (i >= sineMapped[cc]);
            cc++;
          }

          for (k = li; k < ui; k++) {
            FIXP_DBL refNrg = pNrgs->nrgRef[k - lowSubband];
            SCHAR refNrg_e = pNrgs->nrgRef_e[k - lowSubband];

            if (k >= *pUiNoise) {
              tmpNoise =
                  FX_SGL2FX_DBL((FIXP_SGL)((LONG)(*pNoiseLevels) & MASK_M));
              tmpNoise_e =
                  (SCHAR)((LONG)(*pNoiseLevels++) & MASK_E) - NOISE_EXP_OFFSET;

              pUiNoise++;
            }

            FDK_ASSERT(k >= lowSubband);

            if (useLP) useAliasReduction[k - lowSubband] = !sinePresentFlag;

            pNrgs->nrgSine[c] = FL2FXCONST_DBL(0.0f);
            pNrgs->nrgSine_e[c] = 0;

            calcSubbandGain(refNrg, refNrg_e, pNrgs, c, tmpNoise, tmpNoise_e,
                            sinePresentFlag, i >= sineMapped[c], noNoiseFlag);

            c++;
          }
        }
      } else {
        for (j = 0; j < noSubFrameBands[freq_res]; j++) {
          FIXP_DBL refNrg = FX_SGL2FX_DBL((FIXP_SGL)((LONG)(*pIenv) & MASK_M));
          SCHAR refNrg_e = (SCHAR)((LONG)(*pIenv) & MASK_E) - NRG_EXP_OFFSET;

          UCHAR sinePresentFlag = 0;
          int li = table[j];
          int ui = table[j + 1];

          for (k = li; k < ui; k++) {
            sinePresentFlag |= (i >= sineMapped[cc]);
            cc++;
          }

          for (k = li; k < ui; k++) {
            if (k >= *pUiNoise) {
              tmpNoise =
                  FX_SGL2FX_DBL((FIXP_SGL)((LONG)(*pNoiseLevels) & MASK_M));
              tmpNoise_e =
                  (SCHAR)((LONG)(*pNoiseLevels++) & MASK_E) - NOISE_EXP_OFFSET;

              pUiNoise++;
            }

            FDK_ASSERT(k >= lowSubband);

            if (useLP) useAliasReduction[k - lowSubband] = !sinePresentFlag;

            pNrgs->nrgSine[c] = FL2FXCONST_DBL(0.0f);
            pNrgs->nrgSine_e[c] = 0;

            calcSubbandGain(refNrg, refNrg_e, pNrgs, c, tmpNoise, tmpNoise_e,
                            sinePresentFlag, i >= sineMapped[c], noNoiseFlag);

            pNrgs->nrgRef[c] = refNrg;
            pNrgs->nrgRef_e[c] = refNrg_e;

            c++;
          }
          pIenv++;
        }
      }
    }

    /*
      Noise limiting
    */

    for (c = 0; c < hFreq->noLimiterBands; c++) {
      FIXP_DBL sumRef, boostGain, maxGain;
      FIXP_DBL accu = FL2FXCONST_DBL(0.0f);
      SCHAR sumRef_e, boostGain_e, maxGain_e, accu_e = 0;
      int maxGainLimGainSum_e = 0;

      calcAvgGain(pNrgs, hFreq->limiterBandTable[c],
                  hFreq->limiterBandTable[c + 1], &sumRef, &sumRef_e, &maxGain,
                  &maxGain_e);

      /* Multiply maxGain with limiterGain: */
      maxGain = fMult(
          maxGain,
          FDK_sbrDecoder_sbr_limGains_m[hHeaderData->bs_data.limiterGains]);
      /* maxGain_e +=
       * FDK_sbrDecoder_sbr_limGains_e[hHeaderData->bs_data.limiterGains]; */
      /* The addition of maxGain_e and FDK_sbrDecoder_sbr_limGains_e[3] might
         yield values greater than 127 which doesn't fit into an SCHAR! In these
         rare situations limit maxGain_e to 127.
      */
      maxGainLimGainSum_e =
          maxGain_e +
          FDK_sbrDecoder_sbr_limGains_e[hHeaderData->bs_data.limiterGains];
      maxGain_e =
          (maxGainLimGainSum_e > 127) ? (SCHAR)127 : (SCHAR)maxGainLimGainSum_e;

      /* Scale mantissa of MaxGain into range between 0.5 and 1: */
      if (maxGain == FL2FXCONST_DBL(0.0f))
        maxGain_e = -FRACT_BITS;
      else {
        SCHAR charTemp = CountLeadingBits(maxGain);
        maxGain_e -= charTemp;
        maxGain <<= (int)charTemp;
      }

      if (maxGain_e >= maxGainLimit_e) { /* upper limit (e.g. 96 dB) */
        maxGain = FL2FXCONST_DBL(0.5f);
        maxGain_e = maxGainLimit_e;
      }

      /* Every subband gain is compared to the scaled "average gain"
         and limited if necessary: */
      for (k = hFreq->limiterBandTable[c]; k < hFreq->limiterBandTable[c + 1];
           k++) {
        if ((pNrgs->nrgGain_e[k] > maxGain_e) ||
            (pNrgs->nrgGain_e[k] == maxGain_e && pNrgs->nrgGain[k] > maxGain)) {
          FIXP_DBL noiseAmp;
          SCHAR noiseAmp_e;

          FDK_divide_MantExp(maxGain, maxGain_e, pNrgs->nrgGain[k],
                             pNrgs->nrgGain_e[k], &noiseAmp, &noiseAmp_e);
          pNrgs->noiseLevel[k] = fMult(pNrgs->noiseLevel[k], noiseAmp);
          pNrgs->noiseLevel_e[k] += noiseAmp_e;
          pNrgs->nrgGain[k] = maxGain;
          pNrgs->nrgGain_e[k] = maxGain_e;
        }
      }

      /* -- Boost gain
        Calculate and apply boost factor for each limiter band:
        1. Check how much energy would be present when using the limited gain
        2. Calculate boost factor by comparison with reference energy
        3. Apply boost factor to compensate for the energy loss due to limiting
      */
      for (k = hFreq->limiterBandTable[c]; k < hFreq->limiterBandTable[c + 1];
           k++) {
        /* 1.a  Add energy of adjusted signal (using preliminary gain) */
        FIXP_DBL tmp = fMult(pNrgs->nrgGain[k], pNrgs->nrgEst[k]);
        SCHAR tmp_e = pNrgs->nrgGain_e[k] + pNrgs->nrgEst_e[k];
        FDK_add_MantExp(tmp, tmp_e, accu, accu_e, &accu, &accu_e);

        /* 1.b  Add sine energy (if present) */
        if (pNrgs->nrgSine[k] != FL2FXCONST_DBL(0.0f)) {
          FDK_add_MantExp(pNrgs->nrgSine[k], pNrgs->nrgSine_e[k], accu, accu_e,
                          &accu, &accu_e);
        } else {
          /* 1.c  Add noise energy (if present) */
          if (noNoiseFlag == 0) {
            FDK_add_MantExp(pNrgs->noiseLevel[k], pNrgs->noiseLevel_e[k], accu,
                            accu_e, &accu, &accu_e);
          }
        }
      }

      /* 2.a  Calculate ratio of wanted energy and accumulated energy */
      if (accu == (FIXP_DBL)0) { /* If divisor is 0, limit quotient to +4 dB */
        boostGain = FL2FXCONST_DBL(0.6279716f);
        boostGain_e = 2;
      } else {
        INT div_e;
        boostGain = fDivNorm(sumRef, accu, &div_e);
        boostGain_e = sumRef_e - accu_e + div_e;
      }

      /* 2.b Result too high? --> Limit the boost factor to +4 dB */
      if ((boostGain_e > 3) ||
          (boostGain_e == 2 && boostGain > FL2FXCONST_DBL(0.6279716f)) ||
          (boostGain_e == 3 && boostGain > FL2FXCONST_DBL(0.3139858f))) {
        boostGain = FL2FXCONST_DBL(0.6279716f);
        boostGain_e = 2;
      }
      /* 3.  Multiply all signal components with the boost factor */
      for (k = hFreq->limiterBandTable[c]; k < hFreq->limiterBandTable[c + 1];
           k++) {
        pNrgs->nrgGain[k] = fMultDiv2(pNrgs->nrgGain[k], boostGain);
        pNrgs->nrgGain_e[k] = pNrgs->nrgGain_e[k] + boostGain_e + 1;

        pNrgs->nrgSine[k] = fMultDiv2(pNrgs->nrgSine[k], boostGain);
        pNrgs->nrgSine_e[k] = pNrgs->nrgSine_e[k] + boostGain_e + 1;

        pNrgs->noiseLevel[k] = fMultDiv2(pNrgs->noiseLevel[k], boostGain);
        pNrgs->noiseLevel_e[k] = pNrgs->noiseLevel_e[k] + boostGain_e + 1;
      }
    }
    /* End of noise limiting */

    if (useLP)
      aliasingReduction(degreeAlias + lowSubband, pNrgs, useAliasReduction,
                        noSubbands);

    /* For the timeslots within the range for the output frame,
       use the same scale for the noise levels.
       Drawback: If the envelope exceeds the frame border, the noise levels
                 will have to be rescaled later to fit final_e of
                 the gain-values.
    */
    noise_e = (start_pos < no_cols) ? adj_e : final_e;

    /*
      Convert energies to amplitude levels
    */
    for (k = 0; k < noSubbands; k++) {
      FDK_sqrt_MantExp(&pNrgs->nrgSine[k], &pNrgs->nrgSine_e[k], &noise_e);
      FDK_sqrt_MantExp(&pNrgs->nrgGain[k], &pNrgs->nrgGain_e[k],
                       &pNrgs->nrgGain_e[k]);
      FDK_sqrt_MantExp(&pNrgs->noiseLevel[k], &pNrgs->noiseLevel_e[k],
                       &noise_e);
    }

    /*
      Apply calculated gains and adaptive noise
    */

    /* assembleHfSignals() */
    {
      int scale_change, sc_change;
      FIXP_SGL smooth_ratio;
      int filtBufferNoiseShift = 0;

      /* Initialize smoothing buffers with the first valid values */
      if (h_sbr_cal_env->startUp) {
        if (!useLP) {
          h_sbr_cal_env->filtBufferNoise_e = noise_e;

          FDKmemcpy(h_sbr_cal_env->filtBuffer_e, pNrgs->nrgGain_e,
                    noSubbands * sizeof(SCHAR));
          FDKmemcpy(h_sbr_cal_env->filtBufferNoise, pNrgs->noiseLevel,
                    noSubbands * sizeof(FIXP_DBL));
          FDKmemcpy(h_sbr_cal_env->filtBuffer, pNrgs->nrgGain,
                    noSubbands * sizeof(FIXP_DBL));
        }
        h_sbr_cal_env->startUp = 0;
      }

      if (!useLP) {
        equalizeFiltBufferExp(h_sbr_cal_env->filtBuffer,   /* buffered */
                              h_sbr_cal_env->filtBuffer_e, /* buffered */
                              pNrgs->nrgGain,              /* current  */
                              pNrgs->nrgGain_e,            /* current  */
                              noSubbands);

        /* Adapt exponent of buffered noise levels to the current exponent
           so they can easily be smoothed */
        if ((h_sbr_cal_env->filtBufferNoise_e - noise_e) >= 0) {
          int shift = fixMin(DFRACT_BITS - 1,
                             (int)(h_sbr_cal_env->filtBufferNoise_e - noise_e));
          for (k = 0; k < noSubbands; k++)
            h_sbr_cal_env->filtBufferNoise[k] <<= shift;
        } else {
          int shift =
              fixMin(DFRACT_BITS - 1,
                     -(int)(h_sbr_cal_env->filtBufferNoise_e - noise_e));
          for (k = 0; k < noSubbands; k++)
            h_sbr_cal_env->filtBufferNoise[k] >>= shift;
        }

        h_sbr_cal_env->filtBufferNoise_e = noise_e;
      }

      /* find best scaling! */
      scale_change = -(DFRACT_BITS - 1);
      for (k = 0; k < noSubbands; k++) {
        scale_change = fixMax(scale_change, (int)pNrgs->nrgGain_e[k]);
      }
      sc_change = (start_pos < no_cols) ? adj_e - input_e : final_e - input_e;

      if ((scale_change - sc_change + 1) < 0)
        scale_change -= (scale_change - sc_change + 1);

      scale_change = (scale_change - sc_change) + 1;

      for (k = 0; k < noSubbands; k++) {
        int sc = scale_change - pNrgs->nrgGain_e[k] + (sc_change - 1);
        pNrgs->nrgGain[k] >>= sc;
        pNrgs->nrgGain_e[k] += sc;
      }

      if (!useLP) {
        for (k = 0; k < noSubbands; k++) {
          int sc =
              scale_change - h_sbr_cal_env->filtBuffer_e[k] + (sc_change - 1);
          h_sbr_cal_env->filtBuffer[k] >>= sc;
        }
      }

      for (j = start_pos; j < stop_pos; j++) {
        /* This timeslot is located within the first part of the processing
           buffer and will be fed into the QMF-synthesis for the current frame.
               adj_e - input_e
           This timeslot will not yet be fed into the QMF so we do not care
           about the adj_e.
               sc_change = final_e - input_e
        */
        if ((j == no_cols) && (start_pos < no_cols)) {
          int shift = (int)(noise_e - final_e);
          if (!useLP)
            filtBufferNoiseShift = shift; /* shifting of
                                             h_sbr_cal_env->filtBufferNoise[k]
                                             will be applied in function
                                             adjustTimeSlotHQ() */
          if (shift >= 0) {
            shift = fixMin(DFRACT_BITS - 1, shift);
            for (k = 0; k < noSubbands; k++) {
              pNrgs->nrgSine[k] <<= shift;
              pNrgs->noiseLevel[k] <<= shift;
              /*
              if (!useLP)
                h_sbr_cal_env->filtBufferNoise[k]  <<= shift;
              */
            }
          } else {
            shift = fixMin(DFRACT_BITS - 1, -shift);
            for (k = 0; k < noSubbands; k++) {
              pNrgs->nrgSine[k] >>= shift;
              pNrgs->noiseLevel[k] >>= shift;
              /*
              if (!useLP)
                h_sbr_cal_env->filtBufferNoise[k]  >>= shift;
              */
            }
          }

          /* update noise scaling */
          noise_e = final_e;
          if (!useLP)
            h_sbr_cal_env->filtBufferNoise_e =
                noise_e; /* scaling value unused! */

          /* update gain buffer*/
          sc_change -= (final_e - input_e);

          if (sc_change < 0) {
            for (k = 0; k < noSubbands; k++) {
              pNrgs->nrgGain[k] >>= -sc_change;
              pNrgs->nrgGain_e[k] += -sc_change;
            }
            if (!useLP) {
              for (k = 0; k < noSubbands; k++) {
                h_sbr_cal_env->filtBuffer[k] >>= -sc_change;
              }
            }
          } else {
            scale_change += sc_change;
          }

        } /* if */

        if (!useLP) {
          /* Prevent the smoothing filter from running on constant levels */
          if (j - start_pos < smooth_length)
            smooth_ratio = FDK_sbrDecoder_sbr_smoothFilter[j - start_pos];
          else
            smooth_ratio = FL2FXCONST_SGL(0.0f);

          if (iTES_enable) {
            /* adjustTimeSlotHQ() without adding of additional harmonics */
            adjustTimeSlotHQ_GainAndNoise(
                &analysBufferReal[j][lowSubband],
                &analysBufferImag[j][lowSubband], h_sbr_cal_env, pNrgs,
                lowSubband, noSubbands, fMin(scale_change, DFRACT_BITS - 1),
                smooth_ratio, noNoiseFlag, filtBufferNoiseShift);
          } else {
            adjustTimeSlotHQ(&analysBufferReal[j][lowSubband],
                             &analysBufferImag[j][lowSubband], h_sbr_cal_env,
                             pNrgs, lowSubband, noSubbands,
                             fMin(scale_change, DFRACT_BITS - 1), smooth_ratio,
                             noNoiseFlag, filtBufferNoiseShift);
          }
        } else {
          FDK_ASSERT(!iTES_enable); /* not supported */
          if (flags & SBRDEC_ELD_GRID) {
            /* FDKmemset(analysBufferReal[j], 0, 64 * sizeof(FIXP_DBL)); */
            adjustTimeSlot_EldGrid(&analysBufferReal[j][lowSubband], pNrgs,
                                   &h_sbr_cal_env->harmIndex, lowSubband,
                                   noSubbands,
                                   fMin(scale_change, DFRACT_BITS - 1),
                                   noNoiseFlag, &h_sbr_cal_env->phaseIndex,
                                   EXP2SCALE(adj_e) - sbrScaleFactor->lb_scale);
          } else {
            adjustTimeSlotLC(&analysBufferReal[j][lowSubband], pNrgs,
                             &h_sbr_cal_env->harmIndex, lowSubband, noSubbands,
                             fMin(scale_change, DFRACT_BITS - 1), noNoiseFlag,
                             &h_sbr_cal_env->phaseIndex);
          }
        }
        /* In case the envelope spans accross the no_cols border both exponents
         * are needed. */
        /* nrgGain_e[0...(noSubbands-1)] are equalized by
         * equalizeFiltBufferExp() */
        pNrgs->exponent[(j < no_cols) ? 0 : 1] =
            (SCHAR)((15 - sbrScaleFactor->hb_scale) + pNrgs->nrgGain_e[0] + 1 -
                    scale_change);
      } /* for */

      if (iTES_enable) {
        apply_inter_tes(
            analysBufferReal, /* pABufR, */
            analysBufferImag, /* pABufI, */
            sbrScaleFactor, pNrgs->exponent, hHeaderData->timeStep, start_pos,
            stop_pos, lowSubband, noSubbands,
            hFrameData
                ->interTempShapeMode[i] /* frameData->interTempShapeMode[env] */
        );

        /* add additional harmonics */
        for (j = start_pos; j < stop_pos; j++) {
          /* match exponent of additional harmonics to scale change of QMF data
           * caused by apply_inter_tes() */
          scale_change = 0;

          if ((start_pos <= no_cols) && (stop_pos > no_cols)) {
            /* Scaling of analysBuffers was potentially changed within this
               envelope. The pNrgs->nrgSine_e match the second part of the
               envelope. For (j<=no_cols) the exponent of the sine energies has
               to be adapted. */
            scale_change = pNrgs->exponent[1] - pNrgs->exponent[0];
          }

          adjustTimeSlotHQ_AddHarmonics(
              &analysBufferReal[j][lowSubband],
              &analysBufferImag[j][lowSubband], h_sbr_cal_env, pNrgs,
              lowSubband, noSubbands,
              -iTES_scale_change + ((j < no_cols) ? scale_change : 0));
        }
      }

      if (!useLP) {
        /* Update time-smoothing-buffers for gains and noise levels
           The gains and the noise values of the current envelope are copied
           into the buffer. This has to be done at the end of each envelope as
           the values are required for a smooth transition to the next envelope.
         */
        FDKmemcpy(h_sbr_cal_env->filtBuffer, pNrgs->nrgGain,
                  noSubbands * sizeof(FIXP_DBL));
        FDKmemcpy(h_sbr_cal_env->filtBuffer_e, pNrgs->nrgGain_e,
                  noSubbands * sizeof(SCHAR));
        FDKmemcpy(h_sbr_cal_env->filtBufferNoise, pNrgs->noiseLevel,
                  noSubbands * sizeof(FIXP_DBL));
      }
    }
    C_ALLOC_SCRATCH_END(pNrgs, ENV_CALC_NRGS, 1);
  }

  /* adapt adj_e to the scale change caused by apply_inter_tes() */
  adj_e += iTES_scale_change;

  /* Rescale output samples */
  {
    FIXP_DBL maxVal;
    int ov_reserve, reserve;

    /* Determine headroom in old adjusted samples */
    maxVal =
        maxSubbandSample(analysBufferReal, (useLP) ? NULL : analysBufferImag,
                         lowSubband, ov_highSubband, 0, first_start);

    ov_reserve = fNorm(maxVal);

    /* Determine headroom in new adjusted samples */
    maxVal =
        maxSubbandSample(analysBufferReal, (useLP) ? NULL : analysBufferImag,
                         lowSubband, highSubband, first_start, no_cols);

    reserve = fNorm(maxVal);

    /* Determine common output exponent */
    output_e = fMax(ov_adj_e - ov_reserve, adj_e - reserve);

    /* Rescale old samples */
    rescaleSubbandSamples(analysBufferReal, (useLP) ? NULL : analysBufferImag,
                          lowSubband, ov_highSubband, 0, first_start,
                          ov_adj_e - output_e);

    /* Rescale new samples */
    rescaleSubbandSamples(analysBufferReal, (useLP) ? NULL : analysBufferImag,
                          lowSubband, highSubband, first_start, no_cols,
                          adj_e - output_e);
  }

  /* Update hb_scale */
  sbrScaleFactor->hb_scale = EXP2SCALE(output_e);

  /* Save the current final exponent for the next frame: */
  /* adapt final_e to the scale change caused by apply_inter_tes() */
  sbrScaleFactor->ov_hb_scale = EXP2SCALE(final_e + iTES_scale_change);

  /* We need to remember to the next frame that the transient
     will occur in the first envelope (if tranEnv == nEnvelopes). */
  if (hFrameData->frameInfo.tranEnv == hFrameData->frameInfo.nEnvelopes)
    h_sbr_cal_env->prevTranEnv = 0;
  else
    h_sbr_cal_env->prevTranEnv = -1;

  if (pvc_mode > 0) {
    /* Not more than just the last noise envelope reaches into the next PVC
       frame! This should be true because bs_noise_position is <= 15 */
    FDK_ASSERT(hFrameData->frameInfo
                   .bordersNoise[hFrameData->frameInfo.nNoiseEnvelopes - 1] <
               PVC_NTIMESLOT);
    if (hFrameData->frameInfo
            .bordersNoise[hFrameData->frameInfo.nNoiseEnvelopes] >
        PVC_NTIMESLOT) {
      FDK_ASSERT(noiseLevels ==
                 (hFrameData->sbrNoiseFloorLevel +
                  (hFrameData->frameInfo.nNoiseEnvelopes - 1) * noNoiseBands));
      h_sbr_cal_env->prevNNfb = noNoiseBands;

      h_sbr_cal_env->prevNSfb[0] = noSubFrameBands[0];
      h_sbr_cal_env->prevNSfb[1] = noSubFrameBands[1];

      h_sbr_cal_env->prevLoSubband = lowSubband;
      h_sbr_cal_env->prevHiSubband = highSubband;
      h_sbr_cal_env->prev_ov_highSubband = ov_highSubband;

      FDKmemcpy(h_sbr_cal_env->prevFreqBandTableLo, pFreqBandTable[0],
                noSubFrameBands[0] + 1);
      FDKmemcpy(h_sbr_cal_env->prevFreqBandTableHi, pFreqBandTable[1],
                noSubFrameBands[1] + 1);
      FDKmemcpy(h_sbr_cal_env->prevFreqBandTableNoise,
                hFreq->freqBandTableNoise, sizeof(hFreq->freqBandTableNoise));

      FDKmemcpy(h_sbr_cal_env->prevSbrNoiseFloorLevel, noiseLevels,
                MAX_NOISE_COEFFS * sizeof(FIXP_SGL));
    }
  }

  C_ALLOC_SCRATCH_END(useAliasReduction, UCHAR, 64)
}

/*!
  \brief   Create envelope instance

  Must be called once for each channel before calculateSbrEnvelope() can be
  used.

  \return  errorCode, 0 if successful
*/
SBR_ERROR
createSbrEnvelopeCalc(
    HANDLE_SBR_CALCULATE_ENVELOPE hs, /*!< pointer to envelope instance */
    HANDLE_SBR_HEADER_DATA
        hHeaderData, /*!< static SBR control data, initialized with defaults */
    const int chan,  /*!< Channel for which to assign buffers */
    const UINT flags) {
  SBR_ERROR err = SBRDEC_OK;
  int i;

  /* Clear previous missing harmonics flags */
  for (i = 0; i < ADD_HARMONICS_FLAGS_SIZE; i++) {
    hs->harmFlagsPrev[i] = 0;
    hs->harmFlagsPrevActive[i] = 0;
  }
  hs->harmIndex = 0;

  FDKmemclear(hs->prevSbrNoiseFloorLevel, sizeof(hs->prevSbrNoiseFloorLevel));
  hs->prevNNfb = 0;
  FDKmemclear(hs->prevFreqBandTableNoise, sizeof(hs->prevFreqBandTableNoise));
  hs->sinusoidal_positionPrev = 0;

  /*
    Setup pointers for time smoothing.
    The buffer itself will be initialized later triggered by the startUp-flag.
  */
  hs->prevTranEnv = -1;

  /* initialization */
  resetSbrEnvelopeCalc(hs);

  if (chan == 0) { /* do this only once */
    err = resetFreqBandTables(hHeaderData, flags);
  }

  return err;
}

/*!
  \brief   Create envelope instance

  Must be called once for each channel before calculateSbrEnvelope() can be
  used.

  \return  errorCode, 0 if successful
*/
int deleteSbrEnvelopeCalc(HANDLE_SBR_CALCULATE_ENVELOPE hs) { return 0; }

/*!
  \brief   Reset envelope instance

  This function must be called for each channel on a change of configuration.
  Note that resetFreqBandTables should also be called in this case.

  \return  errorCode, 0 if successful
*/
void resetSbrEnvelopeCalc(
    HANDLE_SBR_CALCULATE_ENVELOPE hCalEnv) /*!< pointer to envelope instance */
{
  hCalEnv->phaseIndex = 0;

  /* Noise exponent needs to be reset because the output exponent for the next
   * frame depends on it */
  hCalEnv->filtBufferNoise_e = 0;

  hCalEnv->startUp = 1;
}

/*!
  \brief  Equalize exponents of the buffered gain values and the new ones

  After equalization of exponents, the FIR-filter addition for smoothing
  can be performed.
  This function is called once for each envelope before adjusting.
*/
static void equalizeFiltBufferExp(
    FIXP_DBL *filtBuffer, /*!< bufferd gains */
    SCHAR *filtBuffer_e,  /*!< exponents of bufferd gains */
    FIXP_DBL *nrgGain,    /*!< gains for current envelope */
    SCHAR *nrgGain_e,     /*!< exponents of gains for current envelope */
    int subbands)         /*!< Number of QMF subbands */
{
  int band;
  int diff;

  for (band = 0; band < subbands; band++) {
    diff = (int)(nrgGain_e[band] - filtBuffer_e[band]);
    if (diff > 0) {
      filtBuffer[band] >>=
          diff; /* Compensate for the scale change by shifting the mantissa. */
      filtBuffer_e[band] += diff; /* New gain is bigger, use its exponent */
    } else if (diff < 0) {
      /* The buffered gains seem to be larger, but maybe there
         are some unused bits left in the mantissa */

      int reserve = CntLeadingZeros(fixp_abs(filtBuffer[band])) - 1;

      if ((-diff) <= reserve) {
        /* There is enough space in the buffered mantissa so
           that we can take the new exponent as common.
        */
        filtBuffer[band] <<= (-diff);
        filtBuffer_e[band] += diff; /* becomes equal to *ptrNewExp */
      } else {
        filtBuffer[band] <<=
            reserve; /* Shift the mantissa as far as possible: */
        filtBuffer_e[band] -= reserve; /* Compensate in the exponent: */

        /* For the remaining difference, change the new gain value */
        diff = fixMin(-(reserve + diff), DFRACT_BITS - 1);
        nrgGain[band] >>= diff;
        nrgGain_e[band] += diff;
      }
    }
  }
}

/*!
  \brief  Shift left the mantissas of all subband samples
          in the giventime and frequency range by the specified number of bits.

  This function is used to rescale the audio data in the overlap buffer
  which has already been envelope adjusted with the last frame.
*/
void rescaleSubbandSamples(
    FIXP_DBL **re,   /*!< Real part of input and output subband samples */
    FIXP_DBL **im,   /*!< Imaginary part of input and output subband samples */
    int lowSubband,  /*!< Begin of frequency range to process */
    int highSubband, /*!< End of frequency range to process */
    int start_pos,   /*!< Begin of time rage (QMF-timeslot) */
    int next_pos,    /*!< End of time rage (QMF-timeslot) */
    int shift)       /*!< number of bits to shift */
{
  int width = highSubband - lowSubband;

  if ((width > 0) && (shift != 0)) {
    if (im != NULL) {
      for (int l = start_pos; l < next_pos; l++) {
        scaleValues(&re[l][lowSubband], width, shift);
        scaleValues(&im[l][lowSubband], width, shift);
      }
    } else {
      for (int l = start_pos; l < next_pos; l++) {
        scaleValues(&re[l][lowSubband], width, shift);
      }
    }
  }
}

static inline FIXP_DBL FDK_get_maxval_real(FIXP_DBL maxVal, FIXP_DBL *reTmp,
                                           INT width) {
  maxVal = (FIXP_DBL)0;
  while (width-- != 0) {
    FIXP_DBL tmp = *(reTmp++);
    maxVal |= (FIXP_DBL)((LONG)(tmp) ^ ((LONG)tmp >> (DFRACT_BITS - 1)));
  }

  return maxVal;
}

/*!
  \brief   Determine headroom for shifting

  Determine by how much the spectrum can be shifted left
  for better accuracy in later processing.

  \return  Number of free bits in the biggest spectral value
*/

FIXP_DBL maxSubbandSample(
    FIXP_DBL **re,   /*!< Real part of input and output subband samples */
    FIXP_DBL **im,   /*!< Real part of input and output subband samples */
    int lowSubband,  /*!< Begin of frequency range to process */
    int highSubband, /*!< Number of QMF bands to process */
    int start_pos,   /*!< Begin of time rage (QMF-timeslot) */
    int next_pos     /*!< End of time rage (QMF-timeslot) */
) {
  FIXP_DBL maxVal = FL2FX_DBL(0.0f);
  unsigned int width = highSubband - lowSubband;

  FDK_ASSERT(width <= (64));

  if (width > 0) {
    if (im != NULL) {
      for (int l = start_pos; l < next_pos; l++) {
        int k = width;
        FIXP_DBL *reTmp = &re[l][lowSubband];
        FIXP_DBL *imTmp = &im[l][lowSubband];
        do {
          FIXP_DBL tmp1 = *(reTmp++);
          FIXP_DBL tmp2 = *(imTmp++);
          maxVal |=
              (FIXP_DBL)((LONG)(tmp1) ^ ((LONG)tmp1 >> (DFRACT_BITS - 1)));
          maxVal |=
              (FIXP_DBL)((LONG)(tmp2) ^ ((LONG)tmp2 >> (DFRACT_BITS - 1)));
        } while (--k != 0);
      }
    } else {
      for (int l = start_pos; l < next_pos; l++) {
        maxVal |= FDK_get_maxval_real(maxVal, &re[l][lowSubband], width);
      }
    }
  }

  if (maxVal > (FIXP_DBL)0) {
    /* For negative input values, maxVal is too small by 1. Add 1 only when
     * necessary: if maxVal is a power of 2 */
    FIXP_DBL lowerPow2 =
        (FIXP_DBL)(1 << (DFRACT_BITS - 1 - CntLeadingZeros(maxVal)));
    if (maxVal == lowerPow2) maxVal += (FIXP_DBL)1;
  }

  return (maxVal);
}

/* #define SHIFT_BEFORE_SQUARE (3) */ /* (7/2) */
/* Avoid assertion failures triggerd by overflows which occured in robustness
   tests. Setting the SHIFT_BEFORE_SQUARE to 4 has negligible effect on (USAC)
   conformance results. */
#define SHIFT_BEFORE_SQUARE (4) /* ((8 - 0) / 2) */

/*!<
  If the accumulator does not provide enough overflow bits or
  does not provide a high dynamic range, the below energy calculation
  requires an additional shift operation for each sample.
  On the other hand, doing the shift allows using a single-precision
  multiplication for the square (at least 16bit x 16bit).
  For even values of OVRFLW_BITS (0, 2, 4, 6), saturated arithmetic
  is required for the energy accumulation.
  Theoretically, the sample-squares can sum up to a value of 76,
  requiring 7 overflow bits. However since such situations are *very*
  rare, accu can be limited to 64.
  In case native saturated arithmetic is not available, overflows
  can be prevented by replacing the above #define by
    #define SHIFT_BEFORE_SQUARE ((8 - OVRFLW_BITS) / 2)
  which will result in slightly reduced accuracy.
*/

/*!
  \brief  Estimates the mean energy of each filter-bank channel for the
          duration of the current envelope

  This function is used when interpolFreq is true.
*/
static void calcNrgPerSubband(
    FIXP_DBL **analysBufferReal, /*!< Real part of subband samples */
    FIXP_DBL **analysBufferImag, /*!< Imaginary part of subband samples */
    int lowSubband,              /*!< Begin of the SBR frequency range */
    int highSubband,             /*!< High end of the SBR frequency range */
    int start_pos,               /*!< First QMF-slot of current envelope */
    int next_pos,                /*!< Last QMF-slot of current envelope + 1 */
    SCHAR frameExp,              /*!< Common exponent for all input samples */
    FIXP_DBL *nrgEst,            /*!< resulting Energy (0..1) */
    SCHAR *nrgEst_e)             /*!< Exponent of resulting Energy */
{
  FIXP_SGL invWidth;
  SCHAR preShift;
  SCHAR shift;
  FIXP_DBL sum;
  int k;

  /* Divide by width of envelope later: */
  invWidth = FX_DBL2FX_SGL(GetInvInt(next_pos - start_pos));
  /* The common exponent needs to be doubled because all mantissas are squared:
   */
  frameExp = frameExp << 1;

  for (k = lowSubband; k < highSubband; k++) {
    FIXP_DBL bufferReal[(((1024) / (32) * (4) / 2) + (3 * (4)))];
    FIXP_DBL bufferImag[(((1024) / (32) * (4) / 2) + (3 * (4)))];
    FIXP_DBL maxVal;

    if (analysBufferImag != NULL) {
      int l;
      maxVal = FL2FX_DBL(0.0f);
      for (l = start_pos; l < next_pos; l++) {
        bufferImag[l] = analysBufferImag[l][k];
        maxVal |= (FIXP_DBL)((LONG)(bufferImag[l]) ^
                             ((LONG)bufferImag[l] >> (DFRACT_BITS - 1)));
        bufferReal[l] = analysBufferReal[l][k];
        maxVal |= (FIXP_DBL)((LONG)(bufferReal[l]) ^
                             ((LONG)bufferReal[l] >> (DFRACT_BITS - 1)));
      }
    } else {
      int l;
      maxVal = FL2FX_DBL(0.0f);
      for (l = start_pos; l < next_pos; l++) {
        bufferReal[l] = analysBufferReal[l][k];
        maxVal |= (FIXP_DBL)((LONG)(bufferReal[l]) ^
                             ((LONG)bufferReal[l] >> (DFRACT_BITS - 1)));
      }
    }

    if (maxVal != FL2FXCONST_DBL(0.f)) {
      /* If the accu does not provide enough overflow bits, we cannot
         shift the samples up to the limit.
         Instead, keep up to 3 free bits in each sample, i.e. up to
         6 bits after calculation of square.
         Please note the comment on saturated arithmetic above!
      */
      FIXP_DBL accu;
      preShift = CntLeadingZeros(maxVal) - 1;
      preShift -= SHIFT_BEFORE_SQUARE;

      /* Limit preShift to a maximum value to prevent accumulator overflow in
         exceptional situations where the signal in the analysis-buffer is very
         small (small maxVal).
      */
      preShift = fMin(preShift, (SCHAR)25);

      accu = FL2FXCONST_DBL(0.0f);
      if (preShift >= 0) {
        int l;
        if (analysBufferImag != NULL) {
          for (l = start_pos; l < next_pos; l++) {
            FIXP_DBL temp1 = bufferReal[l] << (int)preShift;
            FIXP_DBL temp2 = bufferImag[l] << (int)preShift;
            accu = fPow2AddDiv2(accu, temp1);
            accu = fPow2AddDiv2(accu, temp2);
          }
        } else {
          for (l = start_pos; l < next_pos; l++) {
            FIXP_DBL temp = bufferReal[l] << (int)preShift;
            accu = fPow2AddDiv2(accu, temp);
          }
        }
      } else { /* if negative shift value */
        int l;
        int negpreShift = -preShift;
        if (analysBufferImag != NULL) {
          for (l = start_pos; l < next_pos; l++) {
            FIXP_DBL temp1 = bufferReal[l] >> (int)negpreShift;
            FIXP_DBL temp2 = bufferImag[l] >> (int)negpreShift;
            accu = fPow2AddDiv2(accu, temp1);
            accu = fPow2AddDiv2(accu, temp2);
          }
        } else {
          for (l = start_pos; l < next_pos; l++) {
            FIXP_DBL temp = bufferReal[l] >> (int)negpreShift;
            accu = fPow2AddDiv2(accu, temp);
          }
        }
      }
      accu <<= 1;

      /* Convert double precision to Mantissa/Exponent: */
      shift = fNorm(accu);
      sum = accu << (int)shift;

      /* Divide by width of envelope and apply frame scale: */
      *nrgEst++ = fMult(sum, invWidth);
      shift += 2 * preShift;
      if (analysBufferImag != NULL)
        *nrgEst_e++ = frameExp - shift;
      else
        *nrgEst_e++ = frameExp - shift + 1; /* +1 due to missing imag. part */
    }                                       /* maxVal!=0 */
    else {
      /* Prevent a zero-mantissa-number from being misinterpreted
         due to its exponent. */
      *nrgEst++ = FL2FXCONST_DBL(0.0f);
      *nrgEst_e++ = 0;
    }
  }
}

/*!
  \brief   Estimates the mean energy of each Scale factor band for the
           duration of the current envelope.

  This function is used when interpolFreq is false.
*/
static void calcNrgPerSfb(
    FIXP_DBL **analysBufferReal, /*!< Real part of subband samples */
    FIXP_DBL **analysBufferImag, /*!< Imaginary part of subband samples */
    int nSfb,                    /*!< Number of scale factor bands */
    UCHAR *freqBandTable,        /*!< First Subband for each Sfb */
    int start_pos,               /*!< First QMF-slot of current envelope */
    int next_pos,                /*!< Last QMF-slot of current envelope + 1 */
    SCHAR input_e,               /*!< Common exponent for all input samples */
    FIXP_DBL *nrgEst,            /*!< resulting Energy (0..1) */
    SCHAR *nrgEst_e)             /*!< Exponent of resulting Energy */
{
  FIXP_SGL invWidth;
  FIXP_DBL temp;
  SCHAR preShift;
  SCHAR shift, sum_e;
  FIXP_DBL sum;

  int j, k, l, li, ui;
  FIXP_DBL sumAll, sumLine; /* Single precision would be sufficient,
                             but overflow bits are required for accumulation */

  /* Divide by width of envelope later: */
  invWidth = FX_DBL2FX_SGL(GetInvInt(next_pos - start_pos));
  /* The common exponent needs to be doubled because all mantissas are squared:
   */
  input_e = input_e << 1;

  for (j = 0; j < nSfb; j++) {
    li = freqBandTable[j];
    ui = freqBandTable[j + 1];

    FIXP_DBL maxVal = maxSubbandSample(analysBufferReal, analysBufferImag, li,
                                       ui, start_pos, next_pos);

    if (maxVal != FL2FXCONST_DBL(0.f)) {
      preShift = CntLeadingZeros(maxVal) - 1;

      /* If the accu does not provide enough overflow bits, we cannot
         shift the samples up to the limit.
         Instead, keep up to 3 free bits in each sample, i.e. up to
         6 bits after calculation of square.
         Please note the comment on saturated arithmetic above!
      */
      preShift -= SHIFT_BEFORE_SQUARE;

      sumAll = FL2FXCONST_DBL(0.0f);

      for (k = li; k < ui; k++) {
        sumLine = FL2FXCONST_DBL(0.0f);

        if (analysBufferImag != NULL) {
          if (preShift >= 0) {
            for (l = start_pos; l < next_pos; l++) {
              temp = analysBufferReal[l][k] << (int)preShift;
              sumLine += fPow2Div2(temp);
              temp = analysBufferImag[l][k] << (int)preShift;
              sumLine += fPow2Div2(temp);
            }
          } else {
            for (l = start_pos; l < next_pos; l++) {
              temp = analysBufferReal[l][k] >> -(int)preShift;
              sumLine += fPow2Div2(temp);
              temp = analysBufferImag[l][k] >> -(int)preShift;
              sumLine += fPow2Div2(temp);
            }
          }
        } else {
          if (preShift >= 0) {
            for (l = start_pos; l < next_pos; l++) {
              temp = analysBufferReal[l][k] << (int)preShift;
              sumLine += fPow2Div2(temp);
            }
          } else {
            for (l = start_pos; l < next_pos; l++) {
              temp = analysBufferReal[l][k] >> -(int)preShift;
              sumLine += fPow2Div2(temp);
            }
          }
        }

        /* The number of QMF-channels per SBR bands may be up to 15.
           Shift right to avoid overflows in sum over all channels. */
        sumLine = sumLine >> (4 - 1);
        sumAll += sumLine;
      }

      /* Convert double precision to Mantissa/Exponent: */
      shift = fNorm(sumAll);
      sum = sumAll << (int)shift;

      /* Divide by width of envelope: */
      sum = fMult(sum, invWidth);

      /* Divide by width of Sfb: */
      sum = fMult(sum, FX_DBL2FX_SGL(GetInvInt(ui - li)));

      /* Set all Subband energies in the Sfb to the average energy: */
      if (analysBufferImag != NULL)
        sum_e = input_e + 4 - shift; /* -4 to compensate right-shift */
      else
        sum_e = input_e + 4 + 1 -
                shift; /* -4 to compensate right-shift; +1 due to missing
                          imag. part */

      sum_e -= 2 * preShift;
    } /* maxVal!=0 */
    else {
      /* Prevent a zero-mantissa-number from being misinterpreted
         due to its exponent. */
      sum = FL2FXCONST_DBL(0.0f);
      sum_e = 0;
    }

    for (k = li; k < ui; k++) {
      *nrgEst++ = sum;
      *nrgEst_e++ = sum_e;
    }
  }
}

/*!
  \brief  Calculate gain, noise, and additional sine level for one subband.

  The resulting energy gain is given by mantissa and exponent.
*/
static void calcSubbandGain(
    FIXP_DBL nrgRef, /*!< Reference Energy according to envelope data */
    SCHAR
        nrgRef_e, /*!< Reference Energy according to envelope data (exponent) */
    ENV_CALC_NRGS *nrgs, int i, FIXP_DBL tmpNoise, /*!< Relative noise level */
    SCHAR tmpNoise_e,      /*!< Relative noise level (exponent) */
    UCHAR sinePresentFlag, /*!< Indicates if sine is present on band */
    UCHAR sineMapped,      /*!< Indicates if sine must be added */
    int noNoiseFlag)       /*!< Flag to suppress noise addition */
{
  FIXP_DBL nrgEst = nrgs->nrgEst[i]; /*!< Energy in transposed signal */
  SCHAR nrgEst_e =
      nrgs->nrgEst_e[i]; /*!< Energy in transposed signal (exponent) */
  FIXP_DBL *ptrNrgGain = &nrgs->nrgGain[i]; /*!< Resulting energy gain */
  SCHAR *ptrNrgGain_e =
      &nrgs->nrgGain_e[i]; /*!< Resulting energy gain (exponent) */
  FIXP_DBL *ptrNoiseLevel =
      &nrgs->noiseLevel[i]; /*!< Resulting absolute noise energy */
  SCHAR *ptrNoiseLevel_e =
      &nrgs->noiseLevel_e[i]; /*!< Resulting absolute noise energy (exponent) */
  FIXP_DBL *ptrNrgSine = &nrgs->nrgSine[i]; /*!< Additional sine energy */
  SCHAR *ptrNrgSine_e =
      &nrgs->nrgSine_e[i]; /*!< Additional sine energy (exponent) */

  FIXP_DBL a, b, c;
  SCHAR a_e, b_e, c_e;

  /*
     This addition of 1 prevents divisions by zero in the reference code.
     For very small energies in nrgEst, it prevents the gains from becoming
     very high which could cause some trouble due to the smoothing.
  */
  b_e = (int)(nrgEst_e - 1);
  if (b_e >= 0) {
    nrgEst = (FL2FXCONST_DBL(0.5f) >> (INT)fixMin(b_e + 1, DFRACT_BITS - 1)) +
             (nrgEst >> 1);
    nrgEst_e += 1; /* shift by 1 bit to avoid overflow */

  } else {
    nrgEst = (nrgEst >> (INT)(fixMin(-b_e + 1, DFRACT_BITS - 1))) +
             (FL2FXCONST_DBL(0.5f) >> 1);
    nrgEst_e = 2; /* shift by 1 bit to avoid overflow */
  }

  /*  A = NrgRef * TmpNoise */
  a = fMult(nrgRef, tmpNoise);
  a_e = nrgRef_e + tmpNoise_e;

  /*  B = 1 + TmpNoise */
  b_e = (int)(tmpNoise_e - 1);
  if (b_e >= 0) {
    b = (FL2FXCONST_DBL(0.5f) >> (INT)fixMin(b_e + 1, DFRACT_BITS - 1)) +
        (tmpNoise >> 1);
    b_e = tmpNoise_e + 1; /* shift by 1 bit to avoid overflow */
  } else {
    b = (tmpNoise >> (INT)(fixMin(-b_e + 1, DFRACT_BITS - 1))) +
        (FL2FXCONST_DBL(0.5f) >> 1);
    b_e = 2; /* shift by 1 bit to avoid overflow */
  }

  /*  noiseLevel = A / B = (NrgRef * TmpNoise) / (1 + TmpNoise) */
  FDK_divide_MantExp(a, a_e, b, b_e, ptrNoiseLevel, ptrNoiseLevel_e);

  if (sinePresentFlag) {
    /*  C = (1 + TmpNoise) * NrgEst */
    c = fMult(b, nrgEst);
    c_e = b_e + nrgEst_e;

    /*  gain = A / C = (NrgRef * TmpNoise) / (1 + TmpNoise) * NrgEst */
    FDK_divide_MantExp(a, a_e, c, c_e, ptrNrgGain, ptrNrgGain_e);

    if (sineMapped) {
      /*  sineLevel = nrgRef/ (1 + TmpNoise) */
      FDK_divide_MantExp(nrgRef, nrgRef_e, b, b_e, ptrNrgSine, ptrNrgSine_e);
    }
  } else {
    if (noNoiseFlag) {
      /*  B = NrgEst */
      b = nrgEst;
      b_e = nrgEst_e;
    } else {
      /*  B = NrgEst * (1 + TmpNoise) */
      b = fMult(b, nrgEst);
      b_e = b_e + nrgEst_e;
    }

    /*  gain = nrgRef / B */
    FDK_divide_MantExp(nrgRef, nrgRef_e, b, b_e, ptrNrgGain, ptrNrgGain_e);
  }
}

/*!
  \brief  Calculate "average gain" for the specified subband range.

  This is rather a gain of the average magnitude than the average
  of gains!
  The result is used as a relative limit for all gains within the
  current "limiter band" (a certain frequency range).
*/
static void calcAvgGain(
    ENV_CALC_NRGS *nrgs, int lowSubband, /*!< Begin of the limiter band */
    int highSubband,                     /*!< High end of the limiter band */
    FIXP_DBL *ptrSumRef, SCHAR *ptrSumRef_e,
    FIXP_DBL *ptrAvgGain, /*!< Resulting overall gain (mantissa) */
    SCHAR *ptrAvgGain_e)  /*!< Resulting overall gain (exponent) */
{
  FIXP_DBL *nrgRef =
      nrgs->nrgRef; /*!< Reference Energy according to envelope data */
  SCHAR *nrgRef_e =
      nrgs->nrgRef_e; /*!< Reference Energy according to envelope data
                         (exponent) */
  FIXP_DBL *nrgEst = nrgs->nrgEst; /*!< Energy in transposed signal */
  SCHAR *nrgEst_e =
      nrgs->nrgEst_e; /*!< Energy in transposed signal (exponent) */

  FIXP_DBL sumRef = 1;
  FIXP_DBL sumEst = 1;
  SCHAR sumRef_e = -FRACT_BITS;
  SCHAR sumEst_e = -FRACT_BITS;
  int k;

  for (k = lowSubband; k < highSubband; k++) {
    /* Add nrgRef[k] to sumRef: */
    FDK_add_MantExp(sumRef, sumRef_e, nrgRef[k], nrgRef_e[k], &sumRef,
                    &sumRef_e);

    /* Add nrgEst[k] to sumEst: */
    FDK_add_MantExp(sumEst, sumEst_e, nrgEst[k], nrgEst_e[k], &sumEst,
                    &sumEst_e);
  }

  FDK_divide_MantExp(sumRef, sumRef_e, sumEst, sumEst_e, ptrAvgGain,
                     ptrAvgGain_e);

  *ptrSumRef = sumRef;
  *ptrSumRef_e = sumRef_e;
}

static void adjustTimeSlot_EldGrid(
    FIXP_DBL *RESTRICT
        ptrReal, /*!< Subband samples to be adjusted, real part */
    ENV_CALC_NRGS *nrgs, UCHAR *ptrHarmIndex, /*!< Harmonic index */
    int lowSubband, /*!< Lowest QMF-channel in the currently used SBR range. */
    int noSubbands, /*!< Number of QMF subbands */
    int scale_change,   /*!< Number of bits to shift adjusted samples */
    int noNoiseFlag,    /*!< Flag to suppress noise addition */
    int *ptrPhaseIndex, /*!< Start index to random number array */
    int scale_diff_low) /*!<  */

{
  int k;
  FIXP_DBL signalReal, sbNoise;
  int tone_count = 0;

  FIXP_DBL *pGain = nrgs->nrgGain; /*!< Gains of current envelope */
  FIXP_DBL *RESTRICT pNoiseLevel =
      nrgs->noiseLevel; /*!< Noise levels of current envelope */
  FIXP_DBL *RESTRICT pSineLevel = nrgs->nrgSine; /*!< Sine levels */

  int phaseIndex = *ptrPhaseIndex;
  UCHAR harmIndex = *ptrHarmIndex;

  static const INT harmonicPhase[4][2] = {{1, 0}, {0, 1}, {-1, 0}, {0, -1}};

  static const FIXP_DBL harmonicPhaseX[4][2] = {
      {FL2FXCONST_DBL(2.0 * 1.245183154539139e-001),
       FL2FXCONST_DBL(2.0 * 1.245183154539139e-001)},
      {FL2FXCONST_DBL(2.0 * -1.123767859325028e-001),
       FL2FXCONST_DBL(2.0 * 1.123767859325028e-001)},
      {FL2FXCONST_DBL(2.0 * -1.245183154539139e-001),
       FL2FXCONST_DBL(2.0 * -1.245183154539139e-001)},
      {FL2FXCONST_DBL(2.0 * 1.123767859325028e-001),
       FL2FXCONST_DBL(2.0 * -1.123767859325028e-001)}};

  const FIXP_DBL *p_harmonicPhaseX = &harmonicPhaseX[harmIndex][0];
  const INT *p_harmonicPhase = &harmonicPhase[harmIndex][0];

  *(ptrReal - 1) = fAddSaturate(
      *(ptrReal - 1),
      SATURATE_SHIFT(fMultDiv2(p_harmonicPhaseX[lowSubband & 1], pSineLevel[0]),
                     scale_diff_low, DFRACT_BITS));
  FIXP_DBL pSineLevel_prev = (FIXP_DBL)0;

  int idx_k = lowSubband & 1;

  for (k = 0; k < noSubbands; k++) {
    FIXP_DBL sineLevel_curr = *pSineLevel++;
    phaseIndex = (phaseIndex + 1) & (SBR_NF_NO_RANDOM_VAL - 1);

    signalReal = fMultDiv2(*ptrReal, *pGain++) << ((int)scale_change);
    sbNoise = *pNoiseLevel++;
    if (((INT)sineLevel_curr | noNoiseFlag) == 0) {
      signalReal +=
          (fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[phaseIndex][0], sbNoise)
           << 4);
    }
    signalReal += sineLevel_curr * p_harmonicPhase[0];
    signalReal =
        fMultAddDiv2(signalReal, pSineLevel_prev, p_harmonicPhaseX[idx_k]);
    pSineLevel_prev = sineLevel_curr;
    idx_k = !idx_k;
    if (k < noSubbands - 1) {
      signalReal =
          fMultAddDiv2(signalReal, pSineLevel[0], p_harmonicPhaseX[idx_k]);
    } else /* (k == noSubbands - 1)  */
    {
      if (k + lowSubband + 1 < 63) {
        *(ptrReal + 1) += fMultDiv2(pSineLevel_prev, p_harmonicPhaseX[idx_k]);
      }
    }
    *ptrReal++ = signalReal;

    if (pSineLevel_prev != FL2FXCONST_DBL(0.0f)) {
      if (++tone_count == 16) {
        k++;
        break;
      }
    }
  }
  /* Run again, if previous loop got breaked with tone_count = 16 */
  for (; k < noSubbands; k++) {
    FIXP_DBL sineLevel_curr = *pSineLevel++;
    phaseIndex = (phaseIndex + 1) & (SBR_NF_NO_RANDOM_VAL - 1);

    signalReal = fMultDiv2(*ptrReal, *pGain++) << ((int)scale_change);
    sbNoise = *pNoiseLevel++;
    if (((INT)sineLevel_curr | noNoiseFlag) == 0) {
      signalReal +=
          (fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[phaseIndex][0], sbNoise)
           << 4);
    }
    signalReal += sineLevel_curr * p_harmonicPhase[0];
    *ptrReal++ = signalReal;
  }

  *ptrHarmIndex = (harmIndex + 1) & 3;
  *ptrPhaseIndex = phaseIndex & (SBR_NF_NO_RANDOM_VAL - 1);
}

/*!
  \brief   Amplify one timeslot of the signal with the calculated gains
           and add the noisefloor.
*/

static void adjustTimeSlotLC(
    FIXP_DBL *ptrReal, /*!< Subband samples to be adjusted, real part */
    ENV_CALC_NRGS *nrgs, UCHAR *ptrHarmIndex, /*!< Harmonic index */
    int lowSubband, /*!< Lowest QMF-channel in the currently used SBR range. */
    int noSubbands, /*!< Number of QMF subbands */
    int scale_change,   /*!< Number of bits to shift adjusted samples */
    int noNoiseFlag,    /*!< Flag to suppress noise addition */
    int *ptrPhaseIndex) /*!< Start index to random number array */
{
  FIXP_DBL *pGain = nrgs->nrgGain; /*!< Gains of current envelope */
  FIXP_DBL *pNoiseLevel =
      nrgs->noiseLevel;                 /*!< Noise levels of current envelope */
  FIXP_DBL *pSineLevel = nrgs->nrgSine; /*!< Sine levels */

  int k;
  int index = *ptrPhaseIndex;
  UCHAR harmIndex = *ptrHarmIndex;
  UCHAR freqInvFlag = (lowSubband & 1);
  FIXP_DBL signalReal, sineLevel, sineLevelNext, sineLevelPrev;
  int tone_count = 0;
  int sineSign = 1;

#define C1 ((FIXP_SGL)FL2FXCONST_SGL(2.f * 0.00815f))
#define C1_CLDFB ((FIXP_SGL)FL2FXCONST_SGL(2.f * 0.16773f))

  /*
    First pass for k=0 pulled out of the loop:
  */

  index = (index + 1) & (SBR_NF_NO_RANDOM_VAL - 1);

  /*
    The next multiplication constitutes the actual envelope adjustment
    of the signal and should be carried out with full accuracy
    (supplying #FRACT_BITS valid bits).
  */
  signalReal = fMultDiv2(*ptrReal, *pGain++) << ((int)scale_change);
  sineLevel = *pSineLevel++;
  sineLevelNext = (noSubbands > 1) ? pSineLevel[0] : FL2FXCONST_DBL(0.0f);

  if (sineLevel != FL2FXCONST_DBL(0.0f))
    tone_count++;
  else if (!noNoiseFlag)
    /* Add noisefloor to the amplified signal */
    signalReal +=
        (fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][0], pNoiseLevel[0])
         << 4);

  {
    if (!(harmIndex & 0x1)) {
      /* harmIndex 0,2 */
      signalReal += (harmIndex & 0x2) ? -sineLevel : sineLevel;
      *ptrReal++ = signalReal;
    } else {
      /* harmIndex 1,3 in combination with freqInvFlag */
      int shift = (int)(scale_change + 1);
      shift = (shift >= 0) ? fixMin(DFRACT_BITS - 1, shift)
                           : fixMax(-(DFRACT_BITS - 1), shift);

      FIXP_DBL tmp1 = (shift >= 0) ? (fMultDiv2(C1, sineLevel) >> shift)
                                   : (fMultDiv2(C1, sineLevel) << (-shift));
      FIXP_DBL tmp2 = fMultDiv2(C1, sineLevelNext);

      /* save switch and compare operations and reduce to XOR statement */
      if (((harmIndex >> 1) & 0x1) ^ freqInvFlag) {
        *(ptrReal - 1) += tmp1;
        signalReal -= tmp2;
      } else {
        *(ptrReal - 1) -= tmp1;
        signalReal += tmp2;
      }
      *ptrReal++ = signalReal;
      freqInvFlag = !freqInvFlag;
    }
  }

  pNoiseLevel++;

  if (noSubbands > 2) {
    if (!(harmIndex & 0x1)) {
      /* harmIndex 0,2 */
      if (!harmIndex) {
        sineSign = 0;
      }

      for (k = noSubbands - 2; k != 0; k--) {
        FIXP_DBL sinelevel = *pSineLevel++;
        index++;
        if (((signalReal = (sineSign ? -sinelevel : sinelevel)) ==
             FL2FXCONST_DBL(0.0f)) &&
            !noNoiseFlag) {
          /* Add noisefloor to the amplified signal */
          index &= (SBR_NF_NO_RANDOM_VAL - 1);
          signalReal += (fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][0],
                                   pNoiseLevel[0])
                         << 4);
        }

        /* The next multiplication constitutes the actual envelope adjustment of
         * the signal. */
        signalReal += fMultDiv2(*ptrReal, *pGain++) << ((int)scale_change);

        pNoiseLevel++;
        *ptrReal++ = signalReal;
      } /* for ... */
    } else {
      /* harmIndex 1,3 in combination with freqInvFlag */
      if (harmIndex == 1) freqInvFlag = !freqInvFlag;

      for (k = noSubbands - 2; k != 0; k--) {
        index++;
        /* The next multiplication constitutes the actual envelope adjustment of
         * the signal. */
        signalReal = fMultDiv2(*ptrReal, *pGain++) << ((int)scale_change);

        if (*pSineLevel++ != FL2FXCONST_DBL(0.0f))
          tone_count++;
        else if (!noNoiseFlag) {
          /* Add noisefloor to the amplified signal */
          index &= (SBR_NF_NO_RANDOM_VAL - 1);
          signalReal += (fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][0],
                                   pNoiseLevel[0])
                         << 4);
        }

        pNoiseLevel++;

        if (tone_count <= 16) {
          FIXP_DBL addSine = fMultDiv2((pSineLevel[-2] - pSineLevel[0]), C1);
          signalReal += (freqInvFlag) ? (-addSine) : (addSine);
        }

        *ptrReal++ = signalReal;
        freqInvFlag = !freqInvFlag;
      } /* for ... */
    }
  }

  if (noSubbands > -1) {
    index++;
    /* The next multiplication constitutes the actual envelope adjustment of the
     * signal. */
    signalReal = fMultDiv2(*ptrReal, *pGain) << ((int)scale_change);
    sineLevelPrev = fMultDiv2(pSineLevel[-1], FL2FX_SGL(0.0163f));
    sineLevel = pSineLevel[0];

    if (pSineLevel[0] != FL2FXCONST_DBL(0.0f))
      tone_count++;
    else if (!noNoiseFlag) {
      /* Add noisefloor to the amplified signal */
      index &= (SBR_NF_NO_RANDOM_VAL - 1);
      signalReal =
          signalReal +
          (fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][0], pNoiseLevel[0])
           << 4);
    }

    if (!(harmIndex & 0x1)) {
      /* harmIndex 0,2 */
      *ptrReal = signalReal + ((sineSign) ? -sineLevel : sineLevel);
    } else {
      /* harmIndex 1,3 in combination with freqInvFlag */
      if (tone_count <= 16) {
        if (freqInvFlag) {
          *ptrReal++ = signalReal - sineLevelPrev;
          if (noSubbands + lowSubband < 63)
            *ptrReal = *ptrReal + fMultDiv2(C1, sineLevel);
        } else {
          *ptrReal++ = signalReal + sineLevelPrev;
          if (noSubbands + lowSubband < 63)
            *ptrReal = *ptrReal - fMultDiv2(C1, sineLevel);
        }
      } else
        *ptrReal = signalReal;
    }
  }
  *ptrHarmIndex = (harmIndex + 1) & 3;
  *ptrPhaseIndex = index & (SBR_NF_NO_RANDOM_VAL - 1);
}

static void adjustTimeSlotHQ_GainAndNoise(
    FIXP_DBL *RESTRICT
        ptrReal, /*!< Subband samples to be adjusted, real part */
    FIXP_DBL *RESTRICT
        ptrImag, /*!< Subband samples to be adjusted, imag part */
    HANDLE_SBR_CALCULATE_ENVELOPE h_sbr_cal_env, ENV_CALC_NRGS *nrgs,
    int lowSubband, /*!< Lowest QMF-channel in the currently used SBR range. */
    int noSubbands, /*!< Number of QMF subbands */
    int scale_change,         /*!< Number of bits to shift adjusted samples */
    FIXP_SGL smooth_ratio,    /*!< Impact of last envelope */
    int noNoiseFlag,          /*!< Start index to random number array */
    int filtBufferNoiseShift) /*!< Shift factor of filtBufferNoise */
{
  FIXP_DBL *RESTRICT gain = nrgs->nrgGain; /*!< Gains of current envelope */
  FIXP_DBL *RESTRICT noiseLevel =
      nrgs->noiseLevel; /*!< Noise levels of current envelope */
  FIXP_DBL *RESTRICT pSineLevel = nrgs->nrgSine; /*!< Sine levels */

  FIXP_DBL *RESTRICT filtBuffer =
      h_sbr_cal_env->filtBuffer; /*!< Gains of last envelope */
  FIXP_DBL *RESTRICT filtBufferNoise =
      h_sbr_cal_env->filtBufferNoise; /*!< Noise levels of last envelope */
  int *RESTRICT ptrPhaseIndex =
      &h_sbr_cal_env->phaseIndex; /*!< Start index to random number array */

  int k;
  FIXP_DBL signalReal, signalImag;
  FIXP_DBL noiseReal, noiseImag;
  FIXP_DBL smoothedGain, smoothedNoise;
  FIXP_SGL direct_ratio =
      /*FL2FXCONST_SGL(1.0f) */ (FIXP_SGL)MAXVAL_SGL - smooth_ratio;
  int index = *ptrPhaseIndex;
  int shift;

  *ptrPhaseIndex = (index + noSubbands) & (SBR_NF_NO_RANDOM_VAL - 1);

  filtBufferNoiseShift +=
      1; /* due to later use of fMultDiv2 instead of fMult */
  if (filtBufferNoiseShift < 0) {
    shift = fixMin(DFRACT_BITS - 1, -filtBufferNoiseShift);
  } else {
    shift = fixMin(DFRACT_BITS - 1, filtBufferNoiseShift);
  }

  if (smooth_ratio > FL2FXCONST_SGL(0.0f)) {
    for (k = 0; k < noSubbands; k++) {
      /*
        Smoothing: The old envelope has been bufferd and a certain ratio
        of the old gains and noise levels is used.
      */
      smoothedGain =
          fMult(smooth_ratio, filtBuffer[k]) + fMult(direct_ratio, gain[k]);

      if (filtBufferNoiseShift < 0) {
        smoothedNoise = (fMultDiv2(smooth_ratio, filtBufferNoise[k]) >> shift) +
                        fMult(direct_ratio, noiseLevel[k]);
      } else {
        smoothedNoise = (fMultDiv2(smooth_ratio, filtBufferNoise[k]) << shift) +
                        fMult(direct_ratio, noiseLevel[k]);
      }

      /*
        The next 2 multiplications constitute the actual envelope adjustment
        of the signal and should be carried out with full accuracy
        (supplying #DFRACT_BITS valid bits).
      */
      signalReal = fMultDiv2(*ptrReal, smoothedGain) << ((int)scale_change);
      signalImag = fMultDiv2(*ptrImag, smoothedGain) << ((int)scale_change);

      index++;

      if ((pSineLevel[k] != FL2FXCONST_DBL(0.0f)) || noNoiseFlag) {
        /* Just the amplified signal is saved */
        *ptrReal++ = signalReal;
        *ptrImag++ = signalImag;
      } else {
        /* Add noisefloor to the amplified signal */
        index &= (SBR_NF_NO_RANDOM_VAL - 1);
        noiseReal =
            fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][0], smoothedNoise)
            << 4;
        noiseImag =
            fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][1], smoothedNoise)
            << 4;
        *ptrReal++ = (signalReal + noiseReal);
        *ptrImag++ = (signalImag + noiseImag);
      }
    }
  } else {
    for (k = 0; k < noSubbands; k++) {
      smoothedGain = gain[k];
      signalReal = fMultDiv2(*ptrReal, smoothedGain) << scale_change;
      signalImag = fMultDiv2(*ptrImag, smoothedGain) << scale_change;

      index++;

      if ((pSineLevel[k] == FL2FXCONST_DBL(0.0f)) && (noNoiseFlag == 0)) {
        /* Add noisefloor to the amplified signal */
        smoothedNoise = noiseLevel[k];
        index &= (SBR_NF_NO_RANDOM_VAL - 1);
        noiseReal =
            fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][0], smoothedNoise);
        noiseImag =
            fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][1], smoothedNoise);

        /* FDK_sbrDecoder_sbr_randomPhase is downscaled by 2^3 */
        signalReal += noiseReal << 4;
        signalImag += noiseImag << 4;
      }
      *ptrReal++ = signalReal;
      *ptrImag++ = signalImag;
    }
  }
}

static void adjustTimeSlotHQ_AddHarmonics(
    FIXP_DBL *RESTRICT
        ptrReal, /*!< Subband samples to be adjusted, real part */
    FIXP_DBL *RESTRICT
        ptrImag, /*!< Subband samples to be adjusted, imag part */
    HANDLE_SBR_CALCULATE_ENVELOPE h_sbr_cal_env, ENV_CALC_NRGS *nrgs,
    int lowSubband,  /*!< Lowest QMF-channel in the currently used SBR range. */
    int noSubbands,  /*!< Number of QMF subbands */
    int scale_change /*!< Scale mismatch between QMF input and sineLevel
                        exponent. */
) {
  FIXP_DBL *RESTRICT pSineLevel = nrgs->nrgSine; /*!< Sine levels */
  UCHAR *RESTRICT ptrHarmIndex =
      &h_sbr_cal_env->harmIndex; /*!< Harmonic index */

  int k;
  FIXP_DBL signalReal, signalImag;
  UCHAR harmIndex = *ptrHarmIndex;
  int freqInvFlag = (lowSubband & 1);
  FIXP_DBL sineLevel;

  *ptrHarmIndex = (harmIndex + 1) & 3;

  for (k = 0; k < noSubbands; k++) {
    sineLevel = pSineLevel[k];
    freqInvFlag ^= 1;
    if (sineLevel != FL2FXCONST_DBL(0.f)) {
      signalReal = ptrReal[k];
      signalImag = ptrImag[k];
      sineLevel = scaleValue(sineLevel, scale_change);
      if (harmIndex & 2) {
        /* case 2,3 */
        sineLevel = -sineLevel;
      }
      if (!(harmIndex & 1)) {
        /* case 0,2: */
        ptrReal[k] = signalReal + sineLevel;
      } else {
        /* case 1,3 */
        if (!freqInvFlag) sineLevel = -sineLevel;
        ptrImag[k] = signalImag + sineLevel;
      }
    }
  }
}

static void adjustTimeSlotHQ(
    FIXP_DBL *RESTRICT
        ptrReal, /*!< Subband samples to be adjusted, real part */
    FIXP_DBL *RESTRICT
        ptrImag, /*!< Subband samples to be adjusted, imag part */
    HANDLE_SBR_CALCULATE_ENVELOPE h_sbr_cal_env, ENV_CALC_NRGS *nrgs,
    int lowSubband, /*!< Lowest QMF-channel in the currently used SBR range. */
    int noSubbands, /*!< Number of QMF subbands */
    int scale_change,         /*!< Number of bits to shift adjusted samples */
    FIXP_SGL smooth_ratio,    /*!< Impact of last envelope */
    int noNoiseFlag,          /*!< Start index to random number array */
    int filtBufferNoiseShift) /*!< Shift factor of filtBufferNoise */
{
  FIXP_DBL *RESTRICT gain = nrgs->nrgGain; /*!< Gains of current envelope */
  FIXP_DBL *RESTRICT noiseLevel =
      nrgs->noiseLevel; /*!< Noise levels of current envelope */
  FIXP_DBL *RESTRICT pSineLevel = nrgs->nrgSine; /*!< Sine levels */

  FIXP_DBL *RESTRICT filtBuffer =
      h_sbr_cal_env->filtBuffer; /*!< Gains of last envelope */
  FIXP_DBL *RESTRICT filtBufferNoise =
      h_sbr_cal_env->filtBufferNoise; /*!< Noise levels of last envelope */
  UCHAR *RESTRICT ptrHarmIndex =
      &h_sbr_cal_env->harmIndex; /*!< Harmonic index */
  int *RESTRICT ptrPhaseIndex =
      &h_sbr_cal_env->phaseIndex; /*!< Start index to random number array */

  int k;
  FIXP_DBL signalReal, signalImag;
  FIXP_DBL noiseReal, noiseImag;
  FIXP_DBL smoothedGain, smoothedNoise;
  FIXP_SGL direct_ratio =
      /*FL2FXCONST_SGL(1.0f) */ (FIXP_SGL)MAXVAL_SGL - smooth_ratio;
  int index = *ptrPhaseIndex;
  UCHAR harmIndex = *ptrHarmIndex;
  int freqInvFlag = (lowSubband & 1);
  FIXP_DBL sineLevel;
  int shift;

  *ptrPhaseIndex = (index + noSubbands) & (SBR_NF_NO_RANDOM_VAL - 1);
  *ptrHarmIndex = (harmIndex + 1) & 3;

  /*
    Possible optimization:
    smooth_ratio and harmIndex stay constant during the loop.
    It might be faster to include a separate loop in each path.

    the check for smooth_ratio is now outside the loop and the workload
    of the whole function decreased by about 20 %
  */

  filtBufferNoiseShift +=
      1; /* due to later use of fMultDiv2 instead of fMult */
  if (filtBufferNoiseShift < 0)
    shift = fixMin(DFRACT_BITS - 1, -filtBufferNoiseShift);
  else
    shift = fixMin(DFRACT_BITS - 1, filtBufferNoiseShift);

  if (smooth_ratio > FL2FXCONST_SGL(0.0f)) {
    for (k = 0; k < noSubbands; k++) {
      /*
        Smoothing: The old envelope has been bufferd and a certain ratio
        of the old gains and noise levels is used.
      */

      smoothedGain =
          fMult(smooth_ratio, filtBuffer[k]) + fMult(direct_ratio, gain[k]);

      if (filtBufferNoiseShift < 0) {
        smoothedNoise = (fMultDiv2(smooth_ratio, filtBufferNoise[k]) >> shift) +
                        fMult(direct_ratio, noiseLevel[k]);
      } else {
        smoothedNoise = (fMultDiv2(smooth_ratio, filtBufferNoise[k]) << shift) +
                        fMult(direct_ratio, noiseLevel[k]);
      }

      /*
        The next 2 multiplications constitute the actual envelope adjustment
        of the signal and should be carried out with full accuracy
        (supplying #DFRACT_BITS valid bits).
      */
      signalReal = fMultDiv2(*ptrReal, smoothedGain) << ((int)scale_change);
      signalImag = fMultDiv2(*ptrImag, smoothedGain) << ((int)scale_change);

      index++;

      if (pSineLevel[k] != FL2FXCONST_DBL(0.0f)) {
        sineLevel = pSineLevel[k];

        switch (harmIndex) {
          case 0:
            *ptrReal++ = (signalReal + sineLevel);
            *ptrImag++ = (signalImag);
            break;
          case 2:
            *ptrReal++ = (signalReal - sineLevel);
            *ptrImag++ = (signalImag);
            break;
          case 1:
            *ptrReal++ = (signalReal);
            if (freqInvFlag)
              *ptrImag++ = (signalImag - sineLevel);
            else
              *ptrImag++ = (signalImag + sineLevel);
            break;
          case 3:
            *ptrReal++ = signalReal;
            if (freqInvFlag)
              *ptrImag++ = (signalImag + sineLevel);
            else
              *ptrImag++ = (signalImag - sineLevel);
            break;
        }
      } else {
        if (noNoiseFlag) {
          /* Just the amplified signal is saved */
          *ptrReal++ = (signalReal);
          *ptrImag++ = (signalImag);
        } else {
          /* Add noisefloor to the amplified signal */
          index &= (SBR_NF_NO_RANDOM_VAL - 1);
          /* FDK_sbrDecoder_sbr_randomPhase is downscaled by 2^3 */
          noiseReal =
              fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][0], smoothedNoise)
              << 4;
          noiseImag =
              fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][1], smoothedNoise)
              << 4;
          *ptrReal++ = (signalReal + noiseReal);
          *ptrImag++ = (signalImag + noiseImag);
        }
      }
      freqInvFlag ^= 1;
    }

  } else {
    for (k = 0; k < noSubbands; k++) {
      smoothedGain = gain[k];
      signalReal = fMultDiv2(*ptrReal, smoothedGain) << scale_change;
      signalImag = fMultDiv2(*ptrImag, smoothedGain) << scale_change;

      index++;

      if ((sineLevel = pSineLevel[k]) != FL2FXCONST_DBL(0.0f)) {
        switch (harmIndex) {
          case 0:
            signalReal += sineLevel;
            break;
          case 1:
            if (freqInvFlag)
              signalImag -= sineLevel;
            else
              signalImag += sineLevel;
            break;
          case 2:
            signalReal -= sineLevel;
            break;
          case 3:
            if (freqInvFlag)
              signalImag += sineLevel;
            else
              signalImag -= sineLevel;
            break;
        }
      } else {
        if (noNoiseFlag == 0) {
          /* Add noisefloor to the amplified signal */
          smoothedNoise = noiseLevel[k];
          index &= (SBR_NF_NO_RANDOM_VAL - 1);
          noiseReal = fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][0],
                                smoothedNoise);
          noiseImag = fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][1],
                                smoothedNoise);

          /* FDK_sbrDecoder_sbr_randomPhase is downscaled by 2^3 */
          signalReal += noiseReal << 4;
          signalImag += noiseImag << 4;
        }
      }
      *ptrReal++ = signalReal;
      *ptrImag++ = signalImag;

      freqInvFlag ^= 1;
    }
  }
}

/*!
  \brief   Reset limiter bands.

  Build frequency band table for the gain limiter dependent on
  the previously generated transposer patch areas.

  \return  SBRDEC_OK if ok,  SBRDEC_UNSUPPORTED_CONFIG on error
*/
SBR_ERROR
ResetLimiterBands(
    UCHAR *limiterBandTable, /*!< Resulting band borders in QMF channels */
    UCHAR *noLimiterBands,   /*!< Resulting number of limiter band */
    UCHAR *freqBandTable,    /*!< Table with possible band borders */
    int noFreqBands,         /*!< Number of bands in freqBandTable */
    const PATCH_PARAM *patchParam, /*!< Transposer patch parameters */
    int noPatches,                 /*!< Number of transposer patches */
    int limiterBands, /*!< Selected 'band density' from bitstream */
    UCHAR sbrPatchingMode, int xOverQmf[MAX_NUM_PATCHES], int b41Sbr) {
  int i, k, isPatchBorder[2], loLimIndex, hiLimIndex, tempNoLim, nBands;
  UCHAR workLimiterBandTable[MAX_FREQ_COEFFS / 2 + MAX_NUM_PATCHES + 1];
  int patchBorders[MAX_NUM_PATCHES + 1];
  int kx, k2;

  int lowSubband = freqBandTable[0];
  int highSubband = freqBandTable[noFreqBands];

  /* 1 limiter band. */
  if (limiterBands == 0) {
    limiterBandTable[0] = 0;
    limiterBandTable[1] = highSubband - lowSubband;
    nBands = 1;
  } else {
    if (!sbrPatchingMode && xOverQmf != NULL) {
      noPatches = 0;

      if (b41Sbr == 1) {
        for (i = 1; i < MAX_NUM_PATCHES_HBE; i++)
          if (xOverQmf[i] != 0) noPatches++;
      } else {
        for (i = 1; i < MAX_STRETCH_HBE; i++)
          if (xOverQmf[i] != 0) noPatches++;
      }
      for (i = 0; i < noPatches; i++) {
        patchBorders[i] = xOverQmf[i] - lowSubband;
      }
    } else {
      for (i = 0; i < noPatches; i++) {
        patchBorders[i] = patchParam[i].guardStartBand - lowSubband;
      }
    }
    patchBorders[i] = highSubband - lowSubband;

    /* 1.2, 2, or 3 limiter bands/octave plus bandborders at patchborders. */
    for (k = 0; k <= noFreqBands; k++) {
      workLimiterBandTable[k] = freqBandTable[k] - lowSubband;
    }
    for (k = 1; k < noPatches; k++) {
      workLimiterBandTable[noFreqBands + k] = patchBorders[k];
    }

    tempNoLim = nBands = noFreqBands + noPatches - 1;
    shellsort(workLimiterBandTable, tempNoLim + 1);

    loLimIndex = 0;
    hiLimIndex = 1;

    while (hiLimIndex <= tempNoLim) {
      FIXP_DBL div_m, oct_m, temp;
      INT div_e = 0, oct_e = 0, temp_e = 0;

      k2 = workLimiterBandTable[hiLimIndex] + lowSubband;
      kx = workLimiterBandTable[loLimIndex] + lowSubband;

      div_m = fDivNorm(k2, kx, &div_e);

      /* calculate number of octaves */
      oct_m = fLog2(div_m, div_e, &oct_e);

      /* multiply with limiterbands per octave    */
      /* values 1, 1.2, 2, 3 -> scale factor of 2 */
      temp = fMultNorm(
          oct_m, FDK_sbrDecoder_sbr_limiterBandsPerOctaveDiv4_DBL[limiterBands],
          &temp_e);

      /* overall scale factor of temp ist addition of scalefactors from log2
         calculation, limiter bands scalefactor (2) and limiter bands
         multiplication */
      temp_e += oct_e + 2;

      /*    div can be a maximum of 64 (k2 = 64 and kx = 1)
         -> oct can be a maximum of 6
         -> temp can be a maximum of 18 (as limiterBandsPerOctoave is a maximum
         factor of 3)
         -> we need a scale factor of 5 for comparisson
      */
      if (temp >> (5 - temp_e) < FL2FXCONST_DBL(0.49f) >> 5) {
        if (workLimiterBandTable[hiLimIndex] ==
            workLimiterBandTable[loLimIndex]) {
          workLimiterBandTable[hiLimIndex] = highSubband;
          nBands--;
          hiLimIndex++;
          continue;
        }
        isPatchBorder[0] = isPatchBorder[1] = 0;
        for (k = 0; k <= noPatches; k++) {
          if (workLimiterBandTable[hiLimIndex] == patchBorders[k]) {
            isPatchBorder[1] = 1;
            break;
          }
        }
        if (!isPatchBorder[1]) {
          workLimiterBandTable[hiLimIndex] = highSubband;
          nBands--;
          hiLimIndex++;
          continue;
        }
        for (k = 0; k <= noPatches; k++) {
          if (workLimiterBandTable[loLimIndex] == patchBorders[k]) {
            isPatchBorder[0] = 1;
            break;
          }
        }
        if (!isPatchBorder[0]) {
          workLimiterBandTable[loLimIndex] = highSubband;
          nBands--;
        }
      }
      loLimIndex = hiLimIndex;
      hiLimIndex++;
    }
    shellsort(workLimiterBandTable, tempNoLim + 1);

    /* Test if algorithm exceeded maximum allowed limiterbands */
    if (nBands > MAX_NUM_LIMITERS || nBands <= 0) {
      return SBRDEC_UNSUPPORTED_CONFIG;
    }

    /* Copy limiterbands from working buffer into final destination */
    for (k = 0; k <= nBands; k++) {
      limiterBandTable[k] = workLimiterBandTable[k];
    }
  }
  *noLimiterBands = nBands;

  return SBRDEC_OK;
}
