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

/**************************** AAC decoder library ******************************

   Author(s):   Robert Weidner (DSP Solutions)

   Description: HCR Decoder: Prepare decoding of non-PCWs, segmentation- and
                bitfield-handling, HCR-Statemachine

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

#include "aacdec_hcrs.h"

#include "aacdec_hcr.h"

#include "aacdec_hcr_bit.h"
#include "aac_rom.h"
#include "aac_ram.h"

static UINT InitSegmentBitfield(UINT *pNumSegment,
                                SCHAR *pRemainingBitsInSegment,
                                UINT *pSegmentBitfield,
                                UCHAR *pNumWordForBitfield,
                                USHORT *pNumBitValidInLastWord);

static void InitNonPCWSideInformationForCurrentSet(H_HCR_INFO pHcr);

static INT ModuloValue(INT input, INT bufferlength);

static void ClearBitFromBitfield(STATEFUNC *ptrState, UINT offset,
                                 UINT *pBitfield);

/*---------------------------------------------------------------------------------------------
     description: This function decodes all non-priority codewords (non-PCWs) by
using a state-machine.
--------------------------------------------------------------------------------------------
*/
void DecodeNonPCWs(HANDLE_FDK_BITSTREAM bs, H_HCR_INFO pHcr) {
  UINT numValidSegment;
  INT segmentOffset;
  INT codewordOffsetBase;
  INT codewordOffset;
  UINT trial;

  UINT *pNumSegment;
  SCHAR *pRemainingBitsInSegment;
  UINT *pSegmentBitfield;
  UCHAR *pNumWordForBitfield;
  USHORT *pNumBitValidInLastWord;
  UINT *pCodewordBitfield;
  INT bitfieldWord;
  INT bitInWord;
  UINT tempWord;
  UINT interMediateWord;
  INT tempBit;
  INT carry;

  UINT numCodeword;
  UCHAR numSet;
  UCHAR currentSet;
  UINT codewordInSet;
  UINT remainingCodewordsInSet;
  SCHAR *pSta;
  UINT ret;

  pNumSegment = &(pHcr->segmentInfo.numSegment);
  pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
  pSegmentBitfield = pHcr->segmentInfo.pSegmentBitfield;
  pNumWordForBitfield = &(pHcr->segmentInfo.numWordForBitfield);
  pNumBitValidInLastWord = &(pHcr->segmentInfo.pNumBitValidInLastWord);
  pSta = pHcr->nonPcwSideinfo.pSta;

  numValidSegment = InitSegmentBitfield(pNumSegment, pRemainingBitsInSegment,
                                        pSegmentBitfield, pNumWordForBitfield,
                                        pNumBitValidInLastWord);

  if (numValidSegment != 0) {
    numCodeword = pHcr->sectionInfo.numCodeword;
    numSet = ((numCodeword - 1) / *pNumSegment) + 1;

    pHcr->segmentInfo.readDirection = FROM_RIGHT_TO_LEFT;

    /* Process sets subsequently */
    for (currentSet = 1; currentSet < numSet; currentSet++) {
      /* step 1 */
      numCodeword -=
          *pNumSegment; /* number of remaining non PCWs [for all sets] */
      if (numCodeword < *pNumSegment) {
        codewordInSet = numCodeword; /* for last set */
      } else {
        codewordInSet = *pNumSegment; /* for all sets except last set */
      }

      /* step 2 */
      /* prepare array 'CodewordBitfield'; as much ones are written from left in
       * all words, as much decodedCodewordInSetCounter nonPCWs exist in this
       * set */
      tempWord = 0xFFFFFFFF;
      pCodewordBitfield = pHcr->segmentInfo.pCodewordBitfield;

      for (bitfieldWord = *pNumWordForBitfield; bitfieldWord != 0;
           bitfieldWord--) { /* loop over all used words */
        if (codewordInSet > NUMBER_OF_BIT_IN_WORD) { /* more codewords than
                                                        number of bits => fill
                                                        ones */
          /* fill a whole word with ones */
          *pCodewordBitfield++ = tempWord;
          codewordInSet -= NUMBER_OF_BIT_IN_WORD; /* subtract number of bits */
        } else {
          /* prepare last tempWord */
          for (remainingCodewordsInSet = codewordInSet;
               remainingCodewordsInSet < NUMBER_OF_BIT_IN_WORD;
               remainingCodewordsInSet++) {
            tempWord =
                tempWord &
                ~(1
                  << (NUMBER_OF_BIT_IN_WORD - 1 -
                      remainingCodewordsInSet)); /* set a zero at bit number
                                                    (NUMBER_OF_BIT_IN_WORD-1-i)
                                                    in tempWord */
          }
          *pCodewordBitfield++ = tempWord;
          tempWord = 0x00000000;
        }
      }
      pCodewordBitfield = pHcr->segmentInfo.pCodewordBitfield;

      /* step 3 */
      /* build non-PCW sideinfo for each non-PCW of the current set */
      InitNonPCWSideInformationForCurrentSet(pHcr);

      /* step 4 */
      /* decode all non-PCWs belonging to this set */

      /* loop over trials */
      codewordOffsetBase = 0;
      for (trial = *pNumSegment; trial > 0; trial--) {
        /* loop over number of words in bitfields */
        segmentOffset = 0; /* start at zero in every segment */
        pHcr->segmentInfo.segmentOffset =
            segmentOffset; /* store in structure for states */
        codewordOffset = codewordOffsetBase;
        pHcr->nonPcwSideinfo.codewordOffset =
            codewordOffset; /* store in structure for states */

        for (bitfieldWord = 0; bitfieldWord < *pNumWordForBitfield;
             bitfieldWord++) {
          /* derive tempWord with bitwise and */
          tempWord =
              pSegmentBitfield[bitfieldWord] & pCodewordBitfield[bitfieldWord];

          /* if tempWord is not zero, decode something */
          if (tempWord != 0) {
            /* loop over all bits in tempWord; start state machine if & is true
             */
            for (bitInWord = NUMBER_OF_BIT_IN_WORD; bitInWord > 0;
                 bitInWord--) {
              interMediateWord = ((UINT)1 << (bitInWord - 1));
              if ((tempWord & interMediateWord) == interMediateWord) {
                /* get state and start state machine */
                pHcr->nonPcwSideinfo.pState =
                    aStateConstant2State[pSta[codewordOffset]];

                while (pHcr->nonPcwSideinfo.pState) {
                  ret = ((STATEFUNC)pHcr->nonPcwSideinfo.pState)(bs, pHcr);
                  if (ret != 0) {
                    return;
                  }
                }
              }

              /* update both offsets */
              segmentOffset += 1; /* add NUMBER_OF_BIT_IN_WORD times one */
              pHcr->segmentInfo.segmentOffset = segmentOffset;
              codewordOffset += 1; /* add NUMBER_OF_BIT_IN_WORD times one */
              codewordOffset =
                  ModuloValue(codewordOffset,
                              *pNumSegment); /* index of the current codeword
                                                lies within modulo range */
              pHcr->nonPcwSideinfo.codewordOffset = codewordOffset;
            }
          } else {
            segmentOffset +=
                NUMBER_OF_BIT_IN_WORD; /* add NUMBER_OF_BIT_IN_WORD at once */
            pHcr->segmentInfo.segmentOffset = segmentOffset;
            codewordOffset +=
                NUMBER_OF_BIT_IN_WORD; /* add NUMBER_OF_BIT_IN_WORD at once */
            codewordOffset = ModuloValue(
                codewordOffset,
                *pNumSegment); /* index of the current codeword lies within
                                  modulo range */
            pHcr->nonPcwSideinfo.codewordOffset = codewordOffset;
          }
        } /* end of bitfield word loop */

        /* decrement codeword - pointer */
        codewordOffsetBase -= 1;
        codewordOffsetBase =
            ModuloValue(codewordOffsetBase, *pNumSegment); /* index of the
                                                              current codeword
                                                              base lies within
                                                              modulo range */

        /* rotate numSegment bits in codewordBitfield */
        /* rotation of *numSegment bits in bitfield of codewords
         * (circle-rotation) */
        /* get last valid bit */
        tempBit = pCodewordBitfield[*pNumWordForBitfield - 1] &
                  (1 << (NUMBER_OF_BIT_IN_WORD - *pNumBitValidInLastWord));
        tempBit = tempBit >> (NUMBER_OF_BIT_IN_WORD - *pNumBitValidInLastWord);

        /* write zero into place where tempBit was fetched from */
        pCodewordBitfield[*pNumWordForBitfield - 1] =
            pCodewordBitfield[*pNumWordForBitfield - 1] &
            ~(1 << (NUMBER_OF_BIT_IN_WORD - *pNumBitValidInLastWord));

        /* rotate last valid word */
        pCodewordBitfield[*pNumWordForBitfield - 1] =
            pCodewordBitfield[*pNumWordForBitfield - 1] >> 1;

        /* transfare carry bit 0 from current word into bitposition 31 from next
         * word and rotate current word */
        for (bitfieldWord = *pNumWordForBitfield - 2; bitfieldWord > -1;
             bitfieldWord--) {
          /* get carry (=bit at position 0) from current word */
          carry = pCodewordBitfield[bitfieldWord] & 1;

          /* put the carry bit at position 31 into word right from current word
           */
          pCodewordBitfield[bitfieldWord + 1] =
              pCodewordBitfield[bitfieldWord + 1] |
              (carry << (NUMBER_OF_BIT_IN_WORD - 1));

          /* shift current word */
          pCodewordBitfield[bitfieldWord] =
              pCodewordBitfield[bitfieldWord] >> 1;
        }

        /* put tempBit into free bit-position 31 from first word */
        pCodewordBitfield[0] =
            pCodewordBitfield[0] | (tempBit << (NUMBER_OF_BIT_IN_WORD - 1));

      } /* end of trial loop */

      /* toggle read direction */
      pHcr->segmentInfo.readDirection =
          ToggleReadDirection(pHcr->segmentInfo.readDirection);
    }
    /* end of set loop */

    /* all non-PCWs of this spectrum are decoded */
  }

  /* all PCWs and all non PCWs are decoded. They are unbacksorted in output
   * buffer. Here is the Interface with comparing QSCs to asm decoding */
}

/*---------------------------------------------------------------------------------------------
     description:   This function prepares the bitfield used for the
                    segments. The list is set up once to be used in all
following sets. If a segment is decoded empty, the according bit from the
Bitfield is removed.
-----------------------------------------------------------------------------------------------
        return:     numValidSegment = the number of valid segments
--------------------------------------------------------------------------------------------
*/
static UINT InitSegmentBitfield(UINT *pNumSegment,
                                SCHAR *pRemainingBitsInSegment,
                                UINT *pSegmentBitfield,
                                UCHAR *pNumWordForBitfield,
                                USHORT *pNumBitValidInLastWord) {
  SHORT i;
  USHORT r;
  UCHAR bitfieldWord;
  UINT tempWord;
  USHORT numValidSegment;

  *pNumWordForBitfield = ((*pNumSegment - 1) >> THIRTYTWO_LOG_DIV_TWO_LOG) + 1;

  /* loop over all words, which are completely used or only partial */
  /* bit in pSegmentBitfield is zero if segment is empty; bit in
   * pSegmentBitfield is one if segment is not empty */
  numValidSegment = 0;
  *pNumBitValidInLastWord = *pNumSegment;

  /* loop over words */
  for (bitfieldWord = 0; bitfieldWord < *pNumWordForBitfield - 1;
       bitfieldWord++) {
    tempWord = 0xFFFFFFFF; /* set ones */
    r = bitfieldWord << THIRTYTWO_LOG_DIV_TWO_LOG;
    for (i = 0; i < NUMBER_OF_BIT_IN_WORD; i++) {
      if (pRemainingBitsInSegment[r + i] == 0) {
        tempWord = tempWord & ~(1 << (NUMBER_OF_BIT_IN_WORD - 1 -
                                      i)); /* set a zero at bit number
                                              (NUMBER_OF_BIT_IN_WORD-1-i) in
                                              tempWord */
      } else {
        numValidSegment += 1; /* count segments which are not empty */
      }
    }
    pSegmentBitfield[bitfieldWord] = tempWord;        /* store result */
    *pNumBitValidInLastWord -= NUMBER_OF_BIT_IN_WORD; /* calculate number of
                                                         zeros on LSB side in
                                                         the last word */
  }

  /* calculate last word: prepare special tempWord */
  tempWord = 0xFFFFFFFF;
  for (i = 0; i < (NUMBER_OF_BIT_IN_WORD - *pNumBitValidInLastWord); i++) {
    tempWord = tempWord & ~(1 << i); /* clear bit i in tempWord */
  }

  /* calculate last word */
  r = bitfieldWord << THIRTYTWO_LOG_DIV_TWO_LOG;
  for (i = 0; i < *pNumBitValidInLastWord; i++) {
    if (pRemainingBitsInSegment[r + i] == 0) {
      tempWord = tempWord & ~(1 << (NUMBER_OF_BIT_IN_WORD - 1 -
                                    i)); /* set a zero at bit number
                                            (NUMBER_OF_BIT_IN_WORD-1-i) in
                                            tempWord */
    } else {
      numValidSegment += 1; /* count segments which are not empty */
    }
  }
  pSegmentBitfield[bitfieldWord] = tempWord; /* store result */

  return numValidSegment;
}

/*---------------------------------------------------------------------------------------------
  description:  This function sets up sideinfo for the non-PCW decoder (for the
current set).
---------------------------------------------------------------------------------------------*/
static void InitNonPCWSideInformationForCurrentSet(H_HCR_INFO pHcr) {
  USHORT i, k;
  UCHAR codebookDim;
  UINT startNode;

  UCHAR *pCodebook = pHcr->nonPcwSideinfo.pCodebook;
  UINT *iNode = pHcr->nonPcwSideinfo.iNode;
  UCHAR *pCntSign = pHcr->nonPcwSideinfo.pCntSign;
  USHORT *iResultPointer = pHcr->nonPcwSideinfo.iResultPointer;
  UINT *pEscapeSequenceInfo = pHcr->nonPcwSideinfo.pEscapeSequenceInfo;
  SCHAR *pSta = pHcr->nonPcwSideinfo.pSta;
  USHORT *pNumExtendedSortedCodewordInSection =
      pHcr->sectionInfo.pNumExtendedSortedCodewordInSection;
  int numExtendedSortedCodewordInSectionIdx =
      pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx;
  UCHAR *pExtendedSortedCodebook = pHcr->sectionInfo.pExtendedSortedCodebook;
  int extendedSortedCodebookIdx = pHcr->sectionInfo.extendedSortedCodebookIdx;
  USHORT *pNumExtendedSortedSectionsInSets =
      pHcr->sectionInfo.pNumExtendedSortedSectionsInSets;
  int numExtendedSortedSectionsInSetsIdx =
      pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx;
  int quantizedSpectralCoefficientsIdx =
      pHcr->decInOut.quantizedSpectralCoefficientsIdx;
  const UCHAR *pCbDimension = aDimCb;
  int iterationCounter = 0;

  /* loop over number of extended sorted sections in the current set so all
   * codewords sideinfo variables within this set can be prepared for decoding
   */
  for (i = pNumExtendedSortedSectionsInSets[numExtendedSortedSectionsInSetsIdx];
       i != 0; i--) {
    codebookDim =
        pCbDimension[pExtendedSortedCodebook[extendedSortedCodebookIdx]];
    startNode = *aHuffTable[pExtendedSortedCodebook[extendedSortedCodebookIdx]];

    for (k = pNumExtendedSortedCodewordInSection
             [numExtendedSortedCodewordInSectionIdx];
         k != 0; k--) {
      iterationCounter++;
      if (iterationCounter > (1024 >> 2)) {
        return;
      }
      *pSta++ = aCodebook2StartInt
          [pExtendedSortedCodebook[extendedSortedCodebookIdx]];
      *pCodebook++ = pExtendedSortedCodebook[extendedSortedCodebookIdx];
      *iNode++ = startNode;
      *pCntSign++ = 0;
      *iResultPointer++ = quantizedSpectralCoefficientsIdx;
      *pEscapeSequenceInfo++ = 0;
      quantizedSpectralCoefficientsIdx +=
          codebookDim; /* update pointer by codebookDim --> point to next
                          starting value for writing out */
      if (quantizedSpectralCoefficientsIdx >= 1024) {
        return;
      }
    }
    numExtendedSortedCodewordInSectionIdx++; /* inc ptr for next ext sort sec in
                                                current set */
    extendedSortedCodebookIdx++; /* inc ptr for next ext sort sec in current set
                                  */
    if (numExtendedSortedCodewordInSectionIdx >= (MAX_SFB_HCR + MAX_HCR_SETS) ||
        extendedSortedCodebookIdx >= (MAX_SFB_HCR + MAX_HCR_SETS)) {
      return;
    }
  }
  numExtendedSortedSectionsInSetsIdx++; /* inc ptr for next set of non-PCWs */
  if (numExtendedSortedCodewordInSectionIdx >= (MAX_SFB_HCR + MAX_HCR_SETS)) {
    return;
  }

  /* Write back indexes */
  pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx =
      numExtendedSortedCodewordInSectionIdx;
  pHcr->sectionInfo.extendedSortedCodebookIdx = extendedSortedCodebookIdx;
  pHcr->sectionInfo.numExtendedSortedSectionsInSetsIdx =
      numExtendedSortedSectionsInSetsIdx;
  pHcr->sectionInfo.numExtendedSortedCodewordInSectionIdx =
      numExtendedSortedCodewordInSectionIdx;
  pHcr->decInOut.quantizedSpectralCoefficientsIdx =
      quantizedSpectralCoefficientsIdx;
}

/*---------------------------------------------------------------------------------------------
     description: This function returns the input value if the value is in the
                  range of bufferlength. If <input> is smaller, one bufferlength
is added, if <input> is bigger one bufferlength is subtracted.
-----------------------------------------------------------------------------------------------
        return:   modulo result
--------------------------------------------------------------------------------------------
*/
static INT ModuloValue(INT input, INT bufferlength) {
  if (input > (bufferlength - 1)) {
    return (input - bufferlength);
  }
  if (input < 0) {
    return (input + bufferlength);
  }
  return input;
}

/*---------------------------------------------------------------------------------------------
     description: This function clears a bit from current bitfield and
                  switches off the statemachine.

                  A bit is cleared in two cases:
                  a) a codeword is decoded, then a bit is cleared in codeword
bitfield b) a segment is decoded empty, then a bit is cleared in segment
bitfield
--------------------------------------------------------------------------------------------
*/
static void ClearBitFromBitfield(STATEFUNC *ptrState, UINT offset,
                                 UINT *pBitfield) {
  UINT numBitfieldWord;
  UINT numBitfieldBit;

  /* get both values needed for clearing the bit */
  numBitfieldWord = offset >> THIRTYTWO_LOG_DIV_TWO_LOG; /* int   = wordNr */
  numBitfieldBit = offset - (numBitfieldWord
                             << THIRTYTWO_LOG_DIV_TWO_LOG); /* fract = bitNr  */

  /* clear a bit in bitfield */
  pBitfield[numBitfieldWord] =
      pBitfield[numBitfieldWord] &
      ~(1 << (NUMBER_OF_BIT_IN_WORD - 1 - numBitfieldBit));

  /* switch off state machine because codeword is decoded and/or because segment
   * is empty */
  *ptrState = NULL;
}

/* =========================================================================================
                              the states of the statemachine
   =========================================================================================
 */

/*---------------------------------------------------------------------------------------------
     description:  Decodes the body of a codeword. This State is used for
codebooks 1,2,5 and 6. No sign bits are decoded, because the table of the
quantized spectral values has got a valid sign at the quantized spectral lines.
-----------------------------------------------------------------------------------------------
        output:   Two or four quantizes spectral values written at position
where pResultPointr points to
-----------------------------------------------------------------------------------------------
        return:   0
--------------------------------------------------------------------------------------------
*/
UINT Hcr_State_BODY_ONLY(HANDLE_FDK_BITSTREAM bs, void *ptr) {
  H_HCR_INFO pHcr = (H_HCR_INFO)ptr;
  UINT *pSegmentBitfield;
  UINT *pCodewordBitfield;
  UINT segmentOffset;
  FIXP_DBL *pResultBase;
  UINT *iNode;
  USHORT *iResultPointer;
  UINT codewordOffset;
  UINT branchNode;
  UINT branchValue;
  UINT iQSC;
  UINT treeNode;
  UCHAR carryBit;
  INT *pLeftStartOfSegment;
  INT *pRightStartOfSegment;
  SCHAR *pRemainingBitsInSegment;
  UCHAR readDirection;
  UCHAR *pCodebook;
  UCHAR dimCntr;
  const UINT *pCurrentTree;
  const UCHAR *pCbDimension;
  const SCHAR *pQuantVal;
  const SCHAR *pQuantValBase;

  pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
  pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment;
  pRightStartOfSegment = pHcr->segmentInfo.pRightStartOfSegment;
  readDirection = pHcr->segmentInfo.readDirection;
  pSegmentBitfield = pHcr->segmentInfo.pSegmentBitfield;
  pCodewordBitfield = pHcr->segmentInfo.pCodewordBitfield;
  segmentOffset = pHcr->segmentInfo.segmentOffset;

  pCodebook = pHcr->nonPcwSideinfo.pCodebook;
  iNode = pHcr->nonPcwSideinfo.iNode;
  pResultBase = pHcr->nonPcwSideinfo.pResultBase;
  iResultPointer = pHcr->nonPcwSideinfo.iResultPointer;
  codewordOffset = pHcr->nonPcwSideinfo.codewordOffset;

  pCbDimension = aDimCb;

  treeNode = iNode[codewordOffset];
  pCurrentTree = aHuffTable[pCodebook[codewordOffset]];

  for (; pRemainingBitsInSegment[segmentOffset] > 0;
       pRemainingBitsInSegment[segmentOffset] -= 1) {
    carryBit = HcrGetABitFromBitstream(bs, &pLeftStartOfSegment[segmentOffset],
                                       &pRightStartOfSegment[segmentOffset],
                                       readDirection);

    CarryBitToBranchValue(carryBit, /* make a step in decoding tree */
                          treeNode, &branchValue, &branchNode);

    /* if end of branch reached write out lines and count bits needed for sign,
     * otherwise store node in codeword sideinfo */
    if ((branchNode & TEST_BIT_10) ==
        TEST_BIT_10) { /* test bit 10 ; ==> body is complete */
      pQuantValBase = aQuantTable[pCodebook[codewordOffset]]; /* get base
                                                                 address of
                                                                 quantized
                                                                 values
                                                                 belonging to
                                                                 current
                                                                 codebook */
      pQuantVal = pQuantValBase + branchValue; /* set pointer to first valid
                                                  line [of 2 or 4 quantized
                                                  values] */

      iQSC = iResultPointer[codewordOffset]; /* get position of first line for
                                                writing out result */

      for (dimCntr = pCbDimension[pCodebook[codewordOffset]]; dimCntr != 0;
           dimCntr--) {
        pResultBase[iQSC++] =
            (FIXP_DBL)*pQuantVal++; /* write out 2 or 4 lines into
                                       spectrum; no Sign bits
                                       available in this state */
      }

      ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                           pCodewordBitfield); /* clear a bit in bitfield and
                                                  switch off statemachine */
      pRemainingBitsInSegment[segmentOffset] -= 1; /* last reinitialzation of
                                                      for loop counter (see
                                                      above) is done here */
      break; /* end of branch in tree reached  i.e. a whole nonPCW-Body is
                decoded */
    } else { /* body is not decoded completely: */
      treeNode = *(
          pCurrentTree +
          branchValue); /* update treeNode for further step in decoding tree */
    }
  }
  iNode[codewordOffset] = treeNode; /* store updated treeNode because maybe
                                       decoding of codeword body not finished
                                       yet */

  if (pRemainingBitsInSegment[segmentOffset] <= 0) {
    ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                         pSegmentBitfield); /* clear a bit in bitfield and
                                               switch off statemachine */

    if (pRemainingBitsInSegment[segmentOffset] < 0) {
      pHcr->decInOut.errorLog |= STATE_ERROR_BODY_ONLY;
      return BODY_ONLY;
    }
  }

  return STOP_THIS_STATE;
}

/*---------------------------------------------------------------------------------------------
     description: Decodes the codeword body, writes out result and counts the
number of quantized spectral values, which are different form zero. For those
values sign bits are needed.

                  If sign bit counter cntSign is different from zero, switch to
next state to decode sign Bits there. If sign bit counter cntSign is zero, no
sign bits are needed and codeword is decoded.
-----------------------------------------------------------------------------------------------
        output:   Two or four written quantizes spectral values written at
position where pResultPointr points to. The signs of those lines may be wrong.
If the signs [on just one signle sign] is wrong, the next state will correct it.
-----------------------------------------------------------------------------------------------
        return:   0
--------------------------------------------------------------------------------------------
*/
UINT Hcr_State_BODY_SIGN__BODY(HANDLE_FDK_BITSTREAM bs, void *ptr) {
  H_HCR_INFO pHcr = (H_HCR_INFO)ptr;
  SCHAR *pRemainingBitsInSegment;
  INT *pLeftStartOfSegment;
  INT *pRightStartOfSegment;
  UCHAR readDirection;
  UINT *pSegmentBitfield;
  UINT *pCodewordBitfield;
  UINT segmentOffset;

  UCHAR *pCodebook;
  UINT *iNode;
  UCHAR *pCntSign;
  FIXP_DBL *pResultBase;
  USHORT *iResultPointer;
  UINT codewordOffset;

  UINT iQSC;
  UINT cntSign;
  UCHAR dimCntr;
  UCHAR carryBit;
  SCHAR *pSta;
  UINT treeNode;
  UINT branchValue;
  UINT branchNode;
  const UCHAR *pCbDimension;
  const UINT *pCurrentTree;
  const SCHAR *pQuantValBase;
  const SCHAR *pQuantVal;

  pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
  pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment;
  pRightStartOfSegment = pHcr->segmentInfo.pRightStartOfSegment;
  readDirection = pHcr->segmentInfo.readDirection;
  pSegmentBitfield = pHcr->segmentInfo.pSegmentBitfield;
  pCodewordBitfield = pHcr->segmentInfo.pCodewordBitfield;
  segmentOffset = pHcr->segmentInfo.segmentOffset;

  pCodebook = pHcr->nonPcwSideinfo.pCodebook;
  iNode = pHcr->nonPcwSideinfo.iNode;
  pCntSign = pHcr->nonPcwSideinfo.pCntSign;
  pResultBase = pHcr->nonPcwSideinfo.pResultBase;
  iResultPointer = pHcr->nonPcwSideinfo.iResultPointer;
  codewordOffset = pHcr->nonPcwSideinfo.codewordOffset;
  pSta = pHcr->nonPcwSideinfo.pSta;

  pCbDimension = aDimCb;

  treeNode = iNode[codewordOffset];
  pCurrentTree = aHuffTable[pCodebook[codewordOffset]];

  for (; pRemainingBitsInSegment[segmentOffset] > 0;
       pRemainingBitsInSegment[segmentOffset] -= 1) {
    carryBit = HcrGetABitFromBitstream(bs, &pLeftStartOfSegment[segmentOffset],
                                       &pRightStartOfSegment[segmentOffset],
                                       readDirection);

    CarryBitToBranchValue(carryBit, /* make a step in decoding tree */
                          treeNode, &branchValue, &branchNode);

    /* if end of branch reached write out lines and count bits needed for sign,
     * otherwise store node in codeword sideinfo */
    if ((branchNode & TEST_BIT_10) ==
        TEST_BIT_10) { /* test bit 10 ; if set body complete */
      /* body completely decoded; branchValue is valid, set pQuantVal to first
       * (of two or four) quantized spectral coefficients */
      pQuantValBase = aQuantTable[pCodebook[codewordOffset]]; /* get base
                                                                 address of
                                                                 quantized
                                                                 values
                                                                 belonging to
                                                                 current
                                                                 codebook */
      pQuantVal = pQuantValBase + branchValue; /* set pointer to first valid
                                                  line [of 2 or 4 quantized
                                                  values] */

      iQSC = iResultPointer[codewordOffset]; /* get position of first line for
                                                writing result */

      /* codeword decoding result is written out here: Write out 2 or 4
       * quantized spectral values with probably */
      /* wrong sign and count number of values which are different from zero for
       * sign bit decoding [which happens in next state] */
      cntSign = 0;
      for (dimCntr = pCbDimension[pCodebook[codewordOffset]]; dimCntr != 0;
           dimCntr--) {
        pResultBase[iQSC++] =
            (FIXP_DBL)*pQuantVal; /* write quant. spec. coef. into spectrum */
        if (*pQuantVal++ != 0) {
          cntSign += 1;
        }
      }

      if (cntSign == 0) {
        ClearBitFromBitfield(
            &(pHcr->nonPcwSideinfo.pState), segmentOffset,
            pCodewordBitfield); /* clear a bit in bitfield and switch off
                                   statemachine */
      } else {
        pCntSign[codewordOffset] = cntSign;     /* write sign count result into
                                                   codewordsideinfo of current
                                                   codeword */
        pSta[codewordOffset] = BODY_SIGN__SIGN; /* change state */
        pHcr->nonPcwSideinfo.pState =
            aStateConstant2State[pSta[codewordOffset]]; /* get state from
                                                           separate array of
                                                           cw-sideinfo */
      }
      pRemainingBitsInSegment[segmentOffset] -= 1; /* last reinitialzation of
                                                      for loop counter (see
                                                      above) is done here */
      break; /* end of branch in tree reached  i.e. a whole nonPCW-Body is
                decoded */
    } else { /* body is not decoded completely: */
      treeNode = *(
          pCurrentTree +
          branchValue); /* update treeNode for further step in decoding tree */
    }
  }
  iNode[codewordOffset] = treeNode; /* store updated treeNode because maybe
                                       decoding of codeword body not finished
                                       yet */

  if (pRemainingBitsInSegment[segmentOffset] <= 0) {
    ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                         pSegmentBitfield); /* clear a bit in bitfield and
                                               switch off statemachine */

    if (pRemainingBitsInSegment[segmentOffset] < 0) {
      pHcr->decInOut.errorLog |= STATE_ERROR_BODY_SIGN__BODY;
      return BODY_SIGN__BODY;
    }
  }

  return STOP_THIS_STATE;
}

/*---------------------------------------------------------------------------------------------
     description: This state decodes the sign bits belonging to a codeword. The
state is called as often in different "trials" until pCntSgn[codewordOffset] is
zero.
-----------------------------------------------------------------------------------------------
        output:   The two or four quantizes spectral values (written in previous
state) have now the correct sign.
-----------------------------------------------------------------------------------------------
        return:   0
--------------------------------------------------------------------------------------------
*/
UINT Hcr_State_BODY_SIGN__SIGN(HANDLE_FDK_BITSTREAM bs, void *ptr) {
  H_HCR_INFO pHcr = (H_HCR_INFO)ptr;
  SCHAR *pRemainingBitsInSegment;
  INT *pLeftStartOfSegment;
  INT *pRightStartOfSegment;
  UCHAR readDirection;
  UINT *pSegmentBitfield;
  UINT *pCodewordBitfield;
  UINT segmentOffset;

  UCHAR *pCntSign;
  FIXP_DBL *pResultBase;
  USHORT *iResultPointer;
  UINT codewordOffset;

  UCHAR carryBit;
  UINT iQSC;
  UCHAR cntSign;

  pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
  pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment;
  pRightStartOfSegment = pHcr->segmentInfo.pRightStartOfSegment;
  readDirection = pHcr->segmentInfo.readDirection;
  pSegmentBitfield = pHcr->segmentInfo.pSegmentBitfield;
  pCodewordBitfield = pHcr->segmentInfo.pCodewordBitfield;
  segmentOffset = pHcr->segmentInfo.segmentOffset;

  /*pCodebook               = */
  pCntSign = pHcr->nonPcwSideinfo.pCntSign;
  pResultBase = pHcr->nonPcwSideinfo.pResultBase;
  iResultPointer = pHcr->nonPcwSideinfo.iResultPointer;
  codewordOffset = pHcr->nonPcwSideinfo.codewordOffset;

  iQSC = iResultPointer[codewordOffset];
  cntSign = pCntSign[codewordOffset];

  /* loop for sign bit decoding */
  for (; pRemainingBitsInSegment[segmentOffset] > 0;
       pRemainingBitsInSegment[segmentOffset] -= 1) {
    carryBit = HcrGetABitFromBitstream(bs, &pLeftStartOfSegment[segmentOffset],
                                       &pRightStartOfSegment[segmentOffset],
                                       readDirection);
    cntSign -=
        1; /* decrement sign counter because one sign bit has been read */

    /* search for a line (which was decoded in previous state) which is not
     * zero. [This value will get a sign] */
    while (pResultBase[iQSC] == (FIXP_DBL)0) {
      if (++iQSC >= 1024) { /* points to current value different from zero */
        return BODY_SIGN__SIGN;
      }
    }

    /* put sign together with line; if carryBit is zero, the sign is ok already;
     * no write operation necessary in this case */
    if (carryBit != 0) {
      pResultBase[iQSC] = -pResultBase[iQSC]; /* carryBit = 1 --> minus */
    }

    iQSC++; /* update pointer to next (maybe valid) value */

    if (cntSign == 0) { /* if (cntSign==0)  ==>  set state CODEWORD_DECODED */
      ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                           pCodewordBitfield); /* clear a bit in bitfield and
                                                  switch off statemachine */
      pRemainingBitsInSegment[segmentOffset] -= 1; /* last reinitialzation of
                                                      for loop counter (see
                                                      above) is done here */
      break; /* whole nonPCW-Body and according sign bits are decoded */
    }
  }
  pCntSign[codewordOffset] = cntSign;
  iResultPointer[codewordOffset] = iQSC; /* store updated pResultPointer */

  if (pRemainingBitsInSegment[segmentOffset] <= 0) {
    ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                         pSegmentBitfield); /* clear a bit in bitfield and
                                               switch off statemachine */

    if (pRemainingBitsInSegment[segmentOffset] < 0) {
      pHcr->decInOut.errorLog |= STATE_ERROR_BODY_SIGN__SIGN;
      return BODY_SIGN__SIGN;
    }
  }

  return STOP_THIS_STATE;
}

/*---------------------------------------------------------------------------------------------
     description: Decodes the codeword body in case of codebook is 11. Writes
out resulting two or four lines [with probably wrong sign] and counts the number
of lines, which are different form zero. This information is needed in next
                  state where sign bits will be decoded, if necessary.
                  If sign bit counter cntSign is zero, no sign bits are needed
and codeword is decoded completely.
-----------------------------------------------------------------------------------------------
        output:   Two lines (quantizes spectral coefficients) which are probably
wrong. The sign may be wrong and if one or two values is/are 16, the following
states will decode the escape sequence to correct the values which are wirtten
here.
-----------------------------------------------------------------------------------------------
        return:   0
--------------------------------------------------------------------------------------------
*/
UINT Hcr_State_BODY_SIGN_ESC__BODY(HANDLE_FDK_BITSTREAM bs, void *ptr) {
  H_HCR_INFO pHcr = (H_HCR_INFO)ptr;
  SCHAR *pRemainingBitsInSegment;
  INT *pLeftStartOfSegment;
  INT *pRightStartOfSegment;
  UCHAR readDirection;
  UINT *pSegmentBitfield;
  UINT *pCodewordBitfield;
  UINT segmentOffset;

  UINT *iNode;
  UCHAR *pCntSign;
  FIXP_DBL *pResultBase;
  USHORT *iResultPointer;
  UINT codewordOffset;

  UCHAR carryBit;
  UINT iQSC;
  UINT cntSign;
  UINT dimCntr;
  UINT treeNode;
  SCHAR *pSta;
  UINT branchNode;
  UINT branchValue;
  const UINT *pCurrentTree;
  const SCHAR *pQuantValBase;
  const SCHAR *pQuantVal;

  pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
  pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment;
  pRightStartOfSegment = pHcr->segmentInfo.pRightStartOfSegment;
  readDirection = pHcr->segmentInfo.readDirection;
  pSegmentBitfield = pHcr->segmentInfo.pSegmentBitfield;
  pCodewordBitfield = pHcr->segmentInfo.pCodewordBitfield;
  segmentOffset = pHcr->segmentInfo.segmentOffset;

  iNode = pHcr->nonPcwSideinfo.iNode;
  pCntSign = pHcr->nonPcwSideinfo.pCntSign;
  pResultBase = pHcr->nonPcwSideinfo.pResultBase;
  iResultPointer = pHcr->nonPcwSideinfo.iResultPointer;
  codewordOffset = pHcr->nonPcwSideinfo.codewordOffset;
  pSta = pHcr->nonPcwSideinfo.pSta;

  treeNode = iNode[codewordOffset];
  pCurrentTree = aHuffTable[ESCAPE_CODEBOOK];

  for (; pRemainingBitsInSegment[segmentOffset] > 0;
       pRemainingBitsInSegment[segmentOffset] -= 1) {
    carryBit = HcrGetABitFromBitstream(bs, &pLeftStartOfSegment[segmentOffset],
                                       &pRightStartOfSegment[segmentOffset],
                                       readDirection);

    /* make a step in tree */
    CarryBitToBranchValue(carryBit, treeNode, &branchValue, &branchNode);

    /* if end of branch reached write out lines and count bits needed for sign,
     * otherwise store node in codeword sideinfo */
    if ((branchNode & TEST_BIT_10) ==
        TEST_BIT_10) { /* test bit 10 ; if set body complete */

      /* body completely decoded; branchValue is valid */
      /* set pQuantVol to first (of two or four) quantized spectral coefficients
       */
      pQuantValBase = aQuantTable[ESCAPE_CODEBOOK]; /* get base address of
                                                       quantized values
                                                       belonging to current
                                                       codebook */
      pQuantVal = pQuantValBase + branchValue; /* set pointer to first valid
                                                  line [of 2 or 4 quantized
                                                  values] */

      /* make backup from original resultPointer in node storage for state
       * BODY_SIGN_ESC__SIGN */
      iNode[codewordOffset] = iResultPointer[codewordOffset];

      /* get position of first line for writing result */
      iQSC = iResultPointer[codewordOffset];

      /* codeword decoding result is written out here: Write out 2 or 4
       * quantized spectral values with probably */
      /* wrong sign and count number of values which are different from zero for
       * sign bit decoding [which happens in next state] */
      cntSign = 0;

      for (dimCntr = DIMENSION_OF_ESCAPE_CODEBOOK; dimCntr != 0; dimCntr--) {
        pResultBase[iQSC++] =
            (FIXP_DBL)*pQuantVal; /* write quant. spec. coef. into spectrum */
        if (*pQuantVal++ != 0) {
          cntSign += 1;
        }
      }

      if (cntSign == 0) {
        ClearBitFromBitfield(
            &(pHcr->nonPcwSideinfo.pState), segmentOffset,
            pCodewordBitfield); /* clear a bit in bitfield and switch off
                                   statemachine */
        /* codeword decoded */
      } else {
        /* write sign count result into codewordsideinfo of current codeword */
        pCntSign[codewordOffset] = cntSign;
        pSta[codewordOffset] = BODY_SIGN_ESC__SIGN; /* change state */
        pHcr->nonPcwSideinfo.pState =
            aStateConstant2State[pSta[codewordOffset]]; /* get state from
                                                           separate array of
                                                           cw-sideinfo */
      }
      pRemainingBitsInSegment[segmentOffset] -= 1; /* the last reinitialzation
                                                      of for loop counter (see
                                                      above) is done here */
      break; /* end of branch in tree reached  i.e. a whole nonPCW-Body is
                decoded */
    } else { /* body is not decoded completely: */
      /* update treeNode for further step in decoding tree and store updated
       * treeNode because maybe no more bits left in segment */
      treeNode = *(pCurrentTree + branchValue);
      iNode[codewordOffset] = treeNode;
    }
  }

  if (pRemainingBitsInSegment[segmentOffset] <= 0) {
    ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                         pSegmentBitfield); /* clear a bit in bitfield and
                                               switch off statemachine */

    if (pRemainingBitsInSegment[segmentOffset] < 0) {
      pHcr->decInOut.errorLog |= STATE_ERROR_BODY_SIGN_ESC__BODY;
      return BODY_SIGN_ESC__BODY;
    }
  }

  return STOP_THIS_STATE;
}

/*---------------------------------------------------------------------------------------------
     description: This state decodes the sign bits, if a codeword of codebook 11
needs some. A flag named 'flagB' in codeword sideinfo is set, if the second line
of quantized spectral values is 16. The 'flagB' is used in case of decoding of a
escape sequence is necessary as far as the second line is concerned.

                  If only the first line needs an escape sequence, the flagB is
cleared. If only the second line needs an escape sequence, the flagB is not
used.

                  For storing sideinfo in case of escape sequence decoding one
single word can be used for both escape sequences because they are decoded not
at the same time:


                  bit 23 22 21 20 19 18 17 16 15 14 13 12 11 10  9  8  7  6  5
4  3  2  1  0
                      ===== == == =========== ===========
=================================== ^      ^  ^         ^            ^
^ |      |  |         |            |                    | res. flagA  flagB
escapePrefixUp  escapePrefixDown  escapeWord

-----------------------------------------------------------------------------------------------
        output:   Two lines with correct sign. If one or two values is/are 16,
the lines are not valid, otherwise they are.
-----------------------------------------------------------------------------------------------
        return:   0
--------------------------------------------------------------------------------------------
*/
UINT Hcr_State_BODY_SIGN_ESC__SIGN(HANDLE_FDK_BITSTREAM bs, void *ptr) {
  H_HCR_INFO pHcr = (H_HCR_INFO)ptr;
  SCHAR *pRemainingBitsInSegment;
  INT *pLeftStartOfSegment;
  INT *pRightStartOfSegment;
  UCHAR readDirection;
  UINT *pSegmentBitfield;
  UINT *pCodewordBitfield;
  UINT segmentOffset;

  UINT *iNode;
  UCHAR *pCntSign;
  FIXP_DBL *pResultBase;
  USHORT *iResultPointer;
  UINT *pEscapeSequenceInfo;
  UINT codewordOffset;

  UINT iQSC;
  UCHAR cntSign;
  UINT flagA;
  UINT flagB;
  UINT flags;
  UCHAR carryBit;
  SCHAR *pSta;

  pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
  pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment;
  pRightStartOfSegment = pHcr->segmentInfo.pRightStartOfSegment;
  readDirection = pHcr->segmentInfo.readDirection;
  pSegmentBitfield = pHcr->segmentInfo.pSegmentBitfield;
  pCodewordBitfield = pHcr->segmentInfo.pCodewordBitfield;
  segmentOffset = pHcr->segmentInfo.segmentOffset;

  iNode = pHcr->nonPcwSideinfo.iNode;
  pCntSign = pHcr->nonPcwSideinfo.pCntSign;
  pResultBase = pHcr->nonPcwSideinfo.pResultBase;
  iResultPointer = pHcr->nonPcwSideinfo.iResultPointer;
  pEscapeSequenceInfo = pHcr->nonPcwSideinfo.pEscapeSequenceInfo;
  codewordOffset = pHcr->nonPcwSideinfo.codewordOffset;
  pSta = pHcr->nonPcwSideinfo.pSta;

  iQSC = iResultPointer[codewordOffset];
  cntSign = pCntSign[codewordOffset];

  /* loop for sign bit decoding */
  for (; pRemainingBitsInSegment[segmentOffset] > 0;
       pRemainingBitsInSegment[segmentOffset] -= 1) {
    carryBit = HcrGetABitFromBitstream(bs, &pLeftStartOfSegment[segmentOffset],
                                       &pRightStartOfSegment[segmentOffset],
                                       readDirection);

    /* decrement sign counter because one sign bit has been read */
    cntSign -= 1;
    pCntSign[codewordOffset] = cntSign;

    /* get a quantized spectral value (which was decoded in previous state)
     * which is not zero. [This value will get a sign] */
    while (pResultBase[iQSC] == (FIXP_DBL)0) {
      if (++iQSC >= 1024) {
        return BODY_SIGN_ESC__SIGN;
      }
    }
    iResultPointer[codewordOffset] = iQSC;

    /* put negative sign together with quantized spectral value; if carryBit is
     * zero, the sign is ok already; no write operation necessary in this case
     */
    if (carryBit != 0) {
      pResultBase[iQSC] = -pResultBase[iQSC]; /* carryBit = 1 --> minus */
    }
    iQSC++; /* update index to next (maybe valid) value */
    iResultPointer[codewordOffset] = iQSC;

    if (cntSign == 0) {
      /* all sign bits are decoded now */
      pRemainingBitsInSegment[segmentOffset] -= 1; /* last reinitialzation of
                                                      for loop counter (see
                                                      above) is done here */

      /* check decoded values if codeword is decoded: Check if one or two escape
       * sequences 16 follow */

      /* step 0 */
      /* restore pointer to first decoded quantized value [ = original
       * pResultPointr] from index iNode prepared in State_BODY_SIGN_ESC__BODY
       */
      iQSC = iNode[codewordOffset];

      /* step 1 */
      /* test first value if escape sequence follows */
      flagA = 0; /* for first possible escape sequence */
      if (fixp_abs(pResultBase[iQSC++]) == (FIXP_DBL)ESCAPE_VALUE) {
        flagA = 1;
      }

      /* step 2 */
      /* test second value if escape sequence follows */
      flagB = 0; /* for second possible escape sequence */
      if (fixp_abs(pResultBase[iQSC]) == (FIXP_DBL)ESCAPE_VALUE) {
        flagB = 1;
      }

      /* step 3 */
      /* evaluate flag result and go on if necessary */
      if (!flagA && !flagB) {
        ClearBitFromBitfield(
            &(pHcr->nonPcwSideinfo.pState), segmentOffset,
            pCodewordBitfield); /* clear a bit in bitfield and switch off
                                   statemachine */
      } else {
        /* at least one of two lines is 16 */
        /* store both flags at correct positions in non PCW codeword sideinfo
         * pEscapeSequenceInfo[codewordOffset] */
        flags = flagA << POSITION_OF_FLAG_A;
        flags |= (flagB << POSITION_OF_FLAG_B);
        pEscapeSequenceInfo[codewordOffset] = flags;

        /* set next state */
        pSta[codewordOffset] = BODY_SIGN_ESC__ESC_PREFIX;
        pHcr->nonPcwSideinfo.pState =
            aStateConstant2State[pSta[codewordOffset]]; /* get state from
                                                           separate array of
                                                           cw-sideinfo */

        /* set result pointer to the first line of the two decoded lines */
        iResultPointer[codewordOffset] = iNode[codewordOffset];

        if (!flagA && flagB) {
          /* update pResultPointr ==> state Stat_BODY_SIGN_ESC__ESC_WORD writes
           * to correct position. Second value is the one and only escape value
           */
          iQSC = iResultPointer[codewordOffset];
          iQSC++;
          iResultPointer[codewordOffset] = iQSC;
        }

      }      /* at least one of two lines is 16 */
      break; /* nonPCW-Body at cb 11 and according sign bits are decoded */

    } /* if ( cntSign == 0 ) */
  }   /* loop over remaining Bits in segment */

  if (pRemainingBitsInSegment[segmentOffset] <= 0) {
    ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                         pSegmentBitfield); /* clear a bit in bitfield and
                                               switch off statemachine */

    if (pRemainingBitsInSegment[segmentOffset] < 0) {
      pHcr->decInOut.errorLog |= STATE_ERROR_BODY_SIGN_ESC__SIGN;
      return BODY_SIGN_ESC__SIGN;
    }
  }
  return STOP_THIS_STATE;
}

/*---------------------------------------------------------------------------------------------
     description: Decode escape prefix of first or second escape sequence. The
escape prefix consists of ones. The following zero is also decoded here.
-----------------------------------------------------------------------------------------------
        output:   If the single separator-zero which follows the
escape-prefix-ones is not yet decoded: The value 'escapePrefixUp' in word
pEscapeSequenceInfo[codewordOffset] is updated.

                  If the single separator-zero which follows the
escape-prefix-ones is decoded: Two updated values 'escapePrefixUp' and
'escapePrefixDown' in word pEscapeSequenceInfo[codewordOffset]. This State is
finished. Switch to next state.
-----------------------------------------------------------------------------------------------
        return:   0
--------------------------------------------------------------------------------------------
*/
UINT Hcr_State_BODY_SIGN_ESC__ESC_PREFIX(HANDLE_FDK_BITSTREAM bs, void *ptr) {
  H_HCR_INFO pHcr = (H_HCR_INFO)ptr;
  SCHAR *pRemainingBitsInSegment;
  INT *pLeftStartOfSegment;
  INT *pRightStartOfSegment;
  UCHAR readDirection;
  UINT *pSegmentBitfield;
  UINT segmentOffset;
  UINT *pEscapeSequenceInfo;
  UINT codewordOffset;
  UCHAR carryBit;
  UINT escapePrefixUp;
  SCHAR *pSta;

  pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
  pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment;
  pRightStartOfSegment = pHcr->segmentInfo.pRightStartOfSegment;
  readDirection = pHcr->segmentInfo.readDirection;
  pSegmentBitfield = pHcr->segmentInfo.pSegmentBitfield;
  segmentOffset = pHcr->segmentInfo.segmentOffset;
  pEscapeSequenceInfo = pHcr->nonPcwSideinfo.pEscapeSequenceInfo;
  codewordOffset = pHcr->nonPcwSideinfo.codewordOffset;
  pSta = pHcr->nonPcwSideinfo.pSta;

  escapePrefixUp =
      (pEscapeSequenceInfo[codewordOffset] & MASK_ESCAPE_PREFIX_UP) >>
      LSB_ESCAPE_PREFIX_UP;

  /* decode escape prefix */
  for (; pRemainingBitsInSegment[segmentOffset] > 0;
       pRemainingBitsInSegment[segmentOffset] -= 1) {
    carryBit = HcrGetABitFromBitstream(bs, &pLeftStartOfSegment[segmentOffset],
                                       &pRightStartOfSegment[segmentOffset],
                                       readDirection);

    /* count ones and store sum in escapePrefixUp */
    if (carryBit == 1) {
      escapePrefixUp += 1; /* update conter for ones */

      /* store updated counter in sideinfo of current codeword */
      pEscapeSequenceInfo[codewordOffset] &=
          ~MASK_ESCAPE_PREFIX_UP;              /* delete old escapePrefixUp */
      escapePrefixUp <<= LSB_ESCAPE_PREFIX_UP; /* shift to correct position */
      pEscapeSequenceInfo[codewordOffset] |=
          escapePrefixUp;                      /* insert new escapePrefixUp */
      escapePrefixUp >>= LSB_ESCAPE_PREFIX_UP; /* shift back down */
    } else {                                   /* separator [zero] reached */
      pRemainingBitsInSegment[segmentOffset] -= 1; /* last reinitialzation of
                                                      for loop counter (see
                                                      above) is done here */
      escapePrefixUp +=
          4; /* if escape_separator '0' appears, add 4 and ==> break */

      /* store escapePrefixUp in pEscapeSequenceInfo[codewordOffset] at bit
       * position escapePrefixUp */
      pEscapeSequenceInfo[codewordOffset] &=
          ~MASK_ESCAPE_PREFIX_UP;              /* delete old escapePrefixUp */
      escapePrefixUp <<= LSB_ESCAPE_PREFIX_UP; /* shift to correct position */
      pEscapeSequenceInfo[codewordOffset] |=
          escapePrefixUp;                      /* insert new escapePrefixUp */
      escapePrefixUp >>= LSB_ESCAPE_PREFIX_UP; /* shift back down */

      /* store escapePrefixUp in pEscapeSequenceInfo[codewordOffset] at bit
       * position escapePrefixDown */
      pEscapeSequenceInfo[codewordOffset] &=
          ~MASK_ESCAPE_PREFIX_DOWN; /* delete old escapePrefixDown */
      escapePrefixUp <<= LSB_ESCAPE_PREFIX_DOWN; /* shift to correct position */
      pEscapeSequenceInfo[codewordOffset] |=
          escapePrefixUp; /* insert new escapePrefixDown */

      pSta[codewordOffset] = BODY_SIGN_ESC__ESC_WORD; /* set next state */
      pHcr->nonPcwSideinfo.pState =
          aStateConstant2State[pSta[codewordOffset]]; /* get state from separate
                                                         array of cw-sideinfo */
      break;
    }
  }

  if (pRemainingBitsInSegment[segmentOffset] <= 0) {
    ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                         pSegmentBitfield); /* clear a bit in bitfield and
                                               switch off statemachine */

    if (pRemainingBitsInSegment[segmentOffset] < 0) {
      pHcr->decInOut.errorLog |= STATE_ERROR_BODY_SIGN_ESC__ESC_PREFIX;
      return BODY_SIGN_ESC__ESC_PREFIX;
    }
  }

  return STOP_THIS_STATE;
}

/*---------------------------------------------------------------------------------------------
     description: Decode escapeWord of escape sequence. If the escape sequence
is decoded completely, assemble quantized-spectral-escape-coefficient and
replace the previous decoded 16 by the new value. Test flagB. If flagB is set,
the second escape sequence must be decoded. If flagB is not set, the codeword is
decoded and the state machine is switched off.
-----------------------------------------------------------------------------------------------
        output:   Two lines with valid sign. At least one of both lines has got
the correct value.
-----------------------------------------------------------------------------------------------
        return:   0
--------------------------------------------------------------------------------------------
*/
UINT Hcr_State_BODY_SIGN_ESC__ESC_WORD(HANDLE_FDK_BITSTREAM bs, void *ptr) {
  H_HCR_INFO pHcr = (H_HCR_INFO)ptr;
  SCHAR *pRemainingBitsInSegment;
  INT *pLeftStartOfSegment;
  INT *pRightStartOfSegment;
  UCHAR readDirection;
  UINT *pSegmentBitfield;
  UINT *pCodewordBitfield;
  UINT segmentOffset;

  FIXP_DBL *pResultBase;
  USHORT *iResultPointer;
  UINT *pEscapeSequenceInfo;
  UINT codewordOffset;

  UINT escapeWord;
  UINT escapePrefixDown;
  UINT escapePrefixUp;
  UCHAR carryBit;
  UINT iQSC;
  INT sign;
  UINT flagA;
  UINT flagB;
  SCHAR *pSta;

  pRemainingBitsInSegment = pHcr->segmentInfo.pRemainingBitsInSegment;
  pLeftStartOfSegment = pHcr->segmentInfo.pLeftStartOfSegment;
  pRightStartOfSegment = pHcr->segmentInfo.pRightStartOfSegment;
  readDirection = pHcr->segmentInfo.readDirection;
  pSegmentBitfield = pHcr->segmentInfo.pSegmentBitfield;
  pCodewordBitfield = pHcr->segmentInfo.pCodewordBitfield;
  segmentOffset = pHcr->segmentInfo.segmentOffset;

  pResultBase = pHcr->nonPcwSideinfo.pResultBase;
  iResultPointer = pHcr->nonPcwSideinfo.iResultPointer;
  pEscapeSequenceInfo = pHcr->nonPcwSideinfo.pEscapeSequenceInfo;
  codewordOffset = pHcr->nonPcwSideinfo.codewordOffset;
  pSta = pHcr->nonPcwSideinfo.pSta;

  escapeWord = pEscapeSequenceInfo[codewordOffset] & MASK_ESCAPE_WORD;
  escapePrefixDown =
      (pEscapeSequenceInfo[codewordOffset] & MASK_ESCAPE_PREFIX_DOWN) >>
      LSB_ESCAPE_PREFIX_DOWN;

  /* decode escape word */
  for (; pRemainingBitsInSegment[segmentOffset] > 0;
       pRemainingBitsInSegment[segmentOffset] -= 1) {
    carryBit = HcrGetABitFromBitstream(bs, &pLeftStartOfSegment[segmentOffset],
                                       &pRightStartOfSegment[segmentOffset],
                                       readDirection);

    /* build escape word */
    escapeWord <<=
        1; /* left shift previous decoded part of escapeWord by on bit */
    escapeWord = escapeWord | carryBit; /* assemble escape word by bitwise or */

    /* decrement counter for length of escape word because one more bit was
     * decoded */
    escapePrefixDown -= 1;

    /* store updated escapePrefixDown */
    pEscapeSequenceInfo[codewordOffset] &=
        ~MASK_ESCAPE_PREFIX_DOWN; /* delete old escapePrefixDown */
    escapePrefixDown <<= LSB_ESCAPE_PREFIX_DOWN; /* shift to correct position */
    pEscapeSequenceInfo[codewordOffset] |=
        escapePrefixDown; /* insert new escapePrefixDown */
    escapePrefixDown >>= LSB_ESCAPE_PREFIX_DOWN; /* shift back */

    /* store updated escapeWord */
    pEscapeSequenceInfo[codewordOffset] &=
        ~MASK_ESCAPE_WORD; /* delete old escapeWord */
    pEscapeSequenceInfo[codewordOffset] |=
        escapeWord; /* insert new escapeWord */

    if (escapePrefixDown == 0) {
      pRemainingBitsInSegment[segmentOffset] -= 1; /* last reinitialzation of
                                                      for loop counter (see
                                                      above) is done here */

      /* escape sequence decoded. Assemble escape-line and replace original line
       */

      /* step 0 */
      /* derive sign */
      iQSC = iResultPointer[codewordOffset];
      sign = (pResultBase[iQSC] >= (FIXP_DBL)0)
                 ? 1
                 : -1; /* get sign of escape value 16 */

      /* step 1 */
      /* get escapePrefixUp */
      escapePrefixUp =
          (pEscapeSequenceInfo[codewordOffset] & MASK_ESCAPE_PREFIX_UP) >>
          LSB_ESCAPE_PREFIX_UP;

      /* step 2 */
      /* calculate escape value */
      pResultBase[iQSC] =
          (FIXP_DBL)(sign * (((INT)1 << escapePrefixUp) + (INT)escapeWord));

      /* get both flags from sideinfo (flags are not shifted to the
       * lsb-position) */
      flagA = pEscapeSequenceInfo[codewordOffset] & MASK_FLAG_A;
      flagB = pEscapeSequenceInfo[codewordOffset] & MASK_FLAG_B;

      /* step 3 */
      /* clear the whole escape sideinfo word */
      pEscapeSequenceInfo[codewordOffset] = 0;

      /* change state in dependence of flag flagB */
      if (flagA != 0) {
        /* first escape sequence decoded; previous decoded 16 has been replaced
         * by valid line */

        /* clear flagA in sideinfo word because this escape sequence has already
         * beed decoded */
        pEscapeSequenceInfo[codewordOffset] &= ~MASK_FLAG_A;

        if (flagB == 0) {
          ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                               pCodewordBitfield); /* clear a bit in bitfield
                                                      and switch off
                                                      statemachine */
        } else {
          /* updated pointer to next and last 16 */
          iQSC++;
          iResultPointer[codewordOffset] = iQSC;

          /* change state */
          pSta[codewordOffset] = BODY_SIGN_ESC__ESC_PREFIX;
          pHcr->nonPcwSideinfo.pState =
              aStateConstant2State[pSta[codewordOffset]]; /* get state from
                                                             separate array of
                                                             cw-sideinfo */
        }
      } else {
        ClearBitFromBitfield(
            &(pHcr->nonPcwSideinfo.pState), segmentOffset,
            pCodewordBitfield); /* clear a bit in bitfield and switch off
                                   statemachine */
      }
      break;
    }
  }

  if (pRemainingBitsInSegment[segmentOffset] <= 0) {
    ClearBitFromBitfield(&(pHcr->nonPcwSideinfo.pState), segmentOffset,
                         pSegmentBitfield); /* clear a bit in bitfield and
                                               switch off statemachine */

    if (pRemainingBitsInSegment[segmentOffset] < 0) {
      pHcr->decInOut.errorLog |= STATE_ERROR_BODY_SIGN_ESC__ESC_WORD;
      return BODY_SIGN_ESC__ESC_WORD;
    }
  }

  return STOP_THIS_STATE;
}
