16cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/* -----------------------------------------------------------------------------
26cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKSoftware License for The Fraunhofer FDK AAC Codec Library for Android
36cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
46cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK© Copyright  1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
56cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKForschung e.V. All rights reserved.
66cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
76cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK 1.    INTRODUCTION
86cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKThe Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software
96cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKthat implements the MPEG Advanced Audio Coding ("AAC") encoding and decoding
106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKscheme for digital audio. This FDK AAC Codec software is intended to be used on
116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKa wide variety of Android devices.
126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKAAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient
146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKgeneral perceptual audio codecs. AAC-ELD is considered the best-performing
156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKfull-bandwidth communications codec by independent studies and is widely
166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKdeployed. AAC has been standardized by ISO and IEC as part of the MPEG
176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKspecifications.
186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKPatent licenses for necessary patent claims for the FDK AAC Codec (including
206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKthose of Fraunhofer) may be obtained through Via Licensing
216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK(www.vialicensing.com) or through the respective patent owners individually for
226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKthe purpose of encoding or decoding bit streams in products that are compliant
236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKwith the ISO/IEC MPEG audio standards. Please note that most manufacturers of
246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKAndroid devices already license these patent claims through Via Licensing or
256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKdirectly from the patent owners, and therefore FDK AAC Codec software may
266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKalready be covered under those patent licenses when it is used for those
276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKlicensed purposes only.
286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKCommercially-licensed AAC software libraries, including floating-point versions
306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKwith enhanced sound quality, are also available from Fraunhofer. Users are
316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKencouraged to check the Fraunhofer website for additional applications
326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKinformation and documentation.
336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK2.    COPYRIGHT LICENSE
356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKRedistribution and use in source and binary forms, with or without modification,
376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKare permitted without payment of copyright license fees provided that you
386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKsatisfy the following conditions:
396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKYou must retain the complete text of this software license in redistributions of
416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKthe FDK AAC Codec or your modifications thereto in source code form.
426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKYou must retain the complete text of this software license in the documentation
446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKand/or other materials provided with redistributions of the FDK AAC Codec or
456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKyour modifications thereto in binary form. You must make available free of
466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKcharge copies of the complete source code of the FDK AAC Codec and your
476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKmodifications thereto to recipients of copies in binary form.
486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKThe name of Fraunhofer may not be used to endorse or promote products derived
506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKfrom this library without prior written permission.
516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKYou may not charge copyright license fees for anyone to use, copy or distribute
536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKthe FDK AAC Codec software or your modifications thereto.
546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKYour modified versions of the FDK AAC Codec must carry prominent notices stating
566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKthat you changed the software and the date of any change. For modified versions
576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKof the FDK AAC Codec, the term "Fraunhofer FDK AAC Codec Library for Android"
586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKmust be replaced by the term "Third-Party Modified Version of the Fraunhofer FDK
596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKAAC Codec Library for Android."
606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK3.    NO PATENT LICENSE
626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKNO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without
646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKlimitation the patents of Fraunhofer, ARE GRANTED BY THIS SOFTWARE LICENSE.
656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKFraunhofer provides no warranty of patent non-infringement with respect to this
666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKsoftware.
676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKYou may use this FDK AAC Codec software or modifications thereto only for
696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKpurposes that are authorized by appropriate patent licenses.
706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK4.    DISCLAIMER
726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKThis FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright
746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKholders and contributors "AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES,
756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKincluding but not limited to the implied warranties of merchantability and
766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKfitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKCONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary,
786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKor consequential damages, including but not limited to procurement of substitute
796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKgoods or services; loss of use, data, or profits, or business interruption,
806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKhowever caused and on any theory of liability, whether in contract, strict
816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKliability, or tort (including negligence), arising in any way out of the use of
826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKthis software, even if advised of the possibility of such damage.
836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK5.    CONTACT INFORMATION
856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKFraunhofer Institute for Integrated Circuits IIS
876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKAttention: Audio and Multimedia Departments - FDK AAC LL
886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKAm Wolfsmantel 33
896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK91058 Erlangen, Germany
906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKwww.iis.fraunhofer.de/amm
926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKamm-info@iis.fraunhofer.de
936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK----------------------------------------------------------------------------- */
946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**************************** AAC decoder library ******************************
966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   Author(s):   Manuel Jander
986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   Description: USAC Linear Prediction Domain coding
1006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK*******************************************************************************/
1026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "usacdec_lpd.h"
1046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "usacdec_rom.h"
1066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "usacdec_fac.h"
1076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "usacdec_lpc.h"
1086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "FDK_tools_rom.h"
1096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "fft.h"
1106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "mdct.h"
1116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "usacdec_acelp.h"
1126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "overlapadd.h"
1136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "conceal.h"
1156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "block.h"
1176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define SF_PITCH_TRACK 6
1196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define SF_GAIN 3
1206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define MIN_VAL FL2FXCONST_DBL(0.0f)
1216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define MAX_VAL (FIXP_DBL) MAXVAL_DBL
1226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#include "ac_arith_coder.h"
1246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKvoid filtLP(const FIXP_DBL *syn, FIXP_PCM *syn_out, FIXP_DBL *noise,
1266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            const FIXP_SGL *filt, INT stop, int len) {
1276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  INT i, j;
1286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL tmp;
1296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  for (i = 0; i < stop; i++) {
1316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    tmp = fMultDiv2(noise[i], filt[0]);  // Filt in Q-1.16
1326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    for (j = 1; j <= len; j++) {
1336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp += fMultDiv2((noise[i - j] + noise[i + j]), filt[j]);
1346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
1356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    syn_out[i] = (FIXP_PCM)(IMDCT_SCALE(syn[i] - tmp));
1366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
1376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
1386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKvoid bass_pf_1sf_delay(
1406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL *syn,   /* (i) : 12.8kHz synthesis to postfilter              */
1416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    const INT *T_sf, /* (i) : Pitch period for all subframes (T_sf[16])    */
1426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL *pit_gain,
1436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    const int frame_length, /* (i) : frame length (should be 768|1024) */
1446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    const INT l_frame,
1456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    const INT l_next, /* (i) : look ahead for symmetric filtering           */
1466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_PCM *synth_out, /* (o) : filtered synthesis (with delay of 1 subfr) */
1476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL mem_bpf[]) /* i/o : memory state [L_FILT+L_SUBFR]                */
1486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK{
1496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  INT i, sf, i_subfr, T, T2, lg;
1506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL tmp, ener, corr, gain;
1526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL *noise, *noise_in;
1536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL
1546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  noise_buf[L_FILT + (2 * L_SUBFR)];  // L_FILT = 12, L_SUBFR = 64 => 140
1556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  const FIXP_DBL *x, *y;
1566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
1586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    noise = noise_buf + L_FILT;  // L_FILT = 12 delay of upsampling filter
1596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    noise_in = noise_buf + L_FILT + L_SUBFR;
1606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Input scaling of the BPF memory */
1616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    scaleValues(mem_bpf, (L_FILT + L_SUBFR), 1);
1626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
1636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int gain_exp = 17;
1656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  sf = 0;
1676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  for (i_subfr = 0; i_subfr < l_frame; i_subfr += L_SUBFR, sf++) {
1686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    T = T_sf[sf];
1696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    gain = pit_gain[sf];
1706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Gain is in Q17.14 */
1726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* If gain > 1 set to 1 */
1736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (gain > (FIXP_DBL)(1 << 14)) gain = (FIXP_DBL)(1 << 14);
1746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* If gain < 0 set to 0 */
1766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (gain < (FIXP_DBL)0) gain = (FIXP_DBL)0;
1776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (gain > (FIXP_DBL)0) {
1796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* pitch tracker: test pitch/2 to avoid continuous pitch doubling */
1806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Note: pitch is limited to PIT_MIN (34 = 376Hz) at the encoder  */
1816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      T2 = T >> 1;
1826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      x = &syn[i_subfr - L_EXTRA];
1836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      y = &syn[i_subfr - T2 - L_EXTRA];
1846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      ener = (FIXP_DBL)0;
1866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      corr = (FIXP_DBL)0;
1876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp = (FIXP_DBL)0;
1886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int headroom_x = getScalefactor(x, L_SUBFR + L_EXTRA);
1906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int headroom_y = getScalefactor(y, L_SUBFR + L_EXTRA);
1916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int width_shift = 7;
1936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
1946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      for (i = 0; i < (L_SUBFR + L_EXTRA); i++) {
1956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        ener += fPow2Div2((x[i] << headroom_x)) >> width_shift;
1966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        corr += fMultDiv2((x[i] << headroom_x), (y[i] << headroom_y)) >>
1976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                width_shift;
1986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp += fPow2Div2((y[i] << headroom_y)) >> width_shift;
1996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
2006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int exp_ener = ((17 - headroom_x) << 1) + width_shift + 1;
2026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int exp_corr = (17 - headroom_x) + (17 - headroom_y) + width_shift + 1;
2036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int exp_tmp = ((17 - headroom_y) << 1) + width_shift + 1;
2046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Add 0.01 to "ener". Adjust exponents */
2066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL point_zero_one = (FIXP_DBL)0x51eb851f; /* In Q-6.37 */
2076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int diff;
2086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      ener = fAddNorm(ener, exp_ener, point_zero_one, -6, &exp_ener);
2096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      corr = fAddNorm(corr, exp_corr, point_zero_one, -6, &exp_corr);
2106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp = fAddNorm(tmp, exp_tmp, point_zero_one, -6, &exp_tmp);
2116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* use T2 if normalized correlation > 0.95 */
2136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      INT s1, s2;
2146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      s1 = CntLeadingZeros(ener) - 1;
2156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      s2 = CntLeadingZeros(tmp) - 1;
2166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL ener_by_tmp = fMultDiv2(ener << s1, tmp << s2);
2186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int ener_by_tmp_exp = (exp_ener - s1) + (exp_tmp - s2) + 1;
2196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (ener_by_tmp_exp & 1) {
2216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        ener_by_tmp <<= 1;
2226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        ener_by_tmp_exp -= 1;
2236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
2246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int temp_exp = 0;
2266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL temp1 = invSqrtNorm2(ener_by_tmp, &temp_exp);
2286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int temp1_exp = temp_exp - (ener_by_tmp_exp >> 1);
2306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL tmp_result = fMult(corr, temp1);
2326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int tmp_result_exp = exp_corr + temp1_exp;
2346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      diff = tmp_result_exp - 0;
2366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL point95 = FL2FXCONST_DBL(0.95f);
2376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (diff >= 0) {
2386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        diff = fMin(diff, 31);
2396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        point95 = FL2FXCONST_DBL(0.95f) >> diff;
2406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } else {
2416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        diff = fMax(diff, -31);
2426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp_result >>= (-diff);
2436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
2446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (tmp_result > point95) T = T2;
2466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* prevent that noise calculation below reaches into not defined signal
2486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         parts at the end of the synth_buf or in other words restrict the below
2496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         used index (i+i_subfr+T) < l_frame + l_next
2506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      */
2516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      lg = l_frame + l_next - T - i_subfr;
2526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (lg > L_SUBFR)
2546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        lg = L_SUBFR;
2556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      else if (lg < 0)
2566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        lg = 0;
2576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* limit gain to avoid problem on burst */
2596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (lg > 0) {
2606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FIXP_DBL tmp1;
2616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* max(lg) = 64 => scale with 6 bits minus 1 (fPow2Div2) */
2636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        s1 = getScalefactor(&syn[i_subfr], lg);
2656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        s2 = getScalefactor(&syn[i_subfr + T], lg);
2666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        INT s = fixMin(s1, s2);
2676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp = (FIXP_DBL)0;
2696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        ener = (FIXP_DBL)0;
2706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        for (i = 0; i < lg; i++) {
2716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          tmp += fPow2Div2(syn[i + i_subfr] << s1) >> (SF_PITCH_TRACK);
2726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          ener += fPow2Div2(syn[i + i_subfr + T] << s2) >> (SF_PITCH_TRACK);
2736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
2746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp = tmp >> fMin(DFRACT_BITS - 1, (2 * (s1 - s)));
2756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        ener = ener >> fMin(DFRACT_BITS - 1, (2 * (s2 - s)));
2766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* error robustness: for the specific case syn[...] == -1.0f for all 64
2786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK           samples ener or tmp might overflow and become negative. For all sane
2796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK           cases we have enough headroom.
2806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        */
2816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (ener <= (FIXP_DBL)0) {
2826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          ener = (FIXP_DBL)1;
2836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
2846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (tmp <= (FIXP_DBL)0) {
2856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          tmp = (FIXP_DBL)1;
2866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
2876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FDK_ASSERT(ener > (FIXP_DBL)0);
2886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* tmp = sqrt(tmp/ener) */
2906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        int result_e = 0;
2916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp1 = fDivNorm(tmp, ener, &result_e);
2926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (result_e & 1) {
2936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          tmp1 >>= 1;
2946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          result_e += 1;
2956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
2966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp = sqrtFixp(tmp1);
2976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        result_e >>= 1;
2986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
2996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        gain_exp = 17;
3006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        diff = result_e - gain_exp;
3026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FIXP_DBL gain1 = gain;
3046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (diff >= 0) {
3066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          diff = fMin(diff, 31);
3076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          gain1 >>= diff;
3086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        } else {
3096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          result_e += (-diff);
3106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          diff = fMax(diff, -31);
3116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          tmp >>= (-diff);
3126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
3136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (tmp < gain1) {
3156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          gain = tmp;
3166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          gain_exp = result_e;
3176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
3186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
3196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* calculate noise based on voiced pitch */
3216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* fMultDiv2() replaces weighting of gain with 0.5 */
3226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      diff = gain_exp - 17;
3236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (diff >= 0) {
3246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        gain <<= diff;
3256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } else {
3266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        gain >>= (-diff);
3276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
3286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      s1 = CntLeadingZeros(gain) - 1;
3306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      s1 -= 16; /* Leading bits for SGL */
3316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_SGL gainSGL = FX_DBL2FX_SGL(gain << 16);
3336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      gainSGL = gainSGL << s1;
3356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      {
3376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        for (i = 0; i < lg; i++) {
3386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          /* scaled with SF_SYNTH + gain_sf + 1 */
3396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          noise_in[i] =
3406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              (fMult(gainSGL, syn[i + i_subfr] - (syn[i + i_subfr - T] >> 1) -
3416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                                  (syn[i + i_subfr + T] >> 1))) >>
3426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              s1;
3436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
3446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        for (i = lg; i < L_SUBFR; i++) {
3466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          /* scaled with SF_SYNTH + gain_sf + 1 */
3476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          noise_in[i] =
3486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              (fMult(gainSGL, syn[i + i_subfr] - syn[i + i_subfr - T])) >> s1;
3496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
3506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
3516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else {
3526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FDKmemset(noise_in, (FIXP_DBL)0, L_SUBFR * sizeof(FIXP_DBL));
3536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
3546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
3566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FDKmemcpy(noise_buf, mem_bpf, (L_FILT + L_SUBFR) * sizeof(FIXP_DBL));
3576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FDKmemcpy(mem_bpf, noise_buf + L_SUBFR,
3596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                (L_FILT + L_SUBFR) * sizeof(FIXP_DBL));
3606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
3616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* substract from voiced speech low-pass filtered noise */
3636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* filter coefficients are scaled with factor SF_FILT_LP (1) */
3646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
3666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      filtLP(&syn[i_subfr - L_SUBFR], &synth_out[i_subfr], noise,
3676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK             fdk_dec_filt_lp, L_SUBFR, L_FILT);
3686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
3696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
3706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
3726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
3746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  // To be determined (info from Ben)
3766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
3776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Output scaling of the BPF memory */
3786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    scaleValues(mem_bpf, (L_FILT + L_SUBFR), -1);
3796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Copy the rest of the signal (after the fac) */
3806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    scaleValuesSaturate((FIXP_PCM *)&synth_out[l_frame],
3816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        (FIXP_DBL *)&syn[l_frame - L_SUBFR],
3826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        (frame_length - l_frame), MDCT_OUT_HEADROOM);
3836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
3846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  return;
3866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
3876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/*
3896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * Frequency Domain Noise Shaping
3906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
3916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
3926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
3936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \brief Adaptive Low Frequencies Deemphasis of spectral coefficients.
3946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK *
3956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * Ensure quantization of low frequencies in case where the
3966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * signal dynamic is higher than the LPC noise shaping.
3976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * This is the inverse operation of adap_low_freq_emph().
3986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * Output gain of all blocks.
3996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK *
4006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param x pointer to the spectral coefficients, requires 1 bit headroom.
4016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lg length of x.
4026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param bUseNewAlfe if set, apply ALFD for fullband lpd.
4036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param gainLpc1 pointer to gain based on old input LPC coefficients.
4046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param gainLpc2 pointer to gain based on new input LPC coefficients.
4056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param alfd_gains pointer to output gains.
4066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param s current scale shift factor of x.
4076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
4086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define ALFDPOW2_SCALE 3
4096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/*static*/
4106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKvoid CLpd_AdaptLowFreqDeemph(FIXP_DBL x[], int lg, FIXP_DBL alfd_gains[],
4116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                             INT s) {
4126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
4136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int i, j, k, i_max;
4146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL max, fac;
4156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Note: This stack array saves temporary accumulation results to be used in
4166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     * a second run */
4176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /*       The size should be limited to (1024/4)/8=32 */
4186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL tmp_pow2[32];
4196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    s = s * 2 + ALFDPOW2_SCALE;
4216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    k = 8;
4236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    i_max = lg / 4; /* ALFD range = 1600Hz (lg = 6400Hz) */
4246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* find spectral peak */
4266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    max = FL2FX_DBL(0.01f) >> s;
4276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    for (i = 0; i < i_max; i += k) {
4286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL tmp;
4296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp = FIXP_DBL(0);
4316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL *pX = &x[i];
4326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      j = 8;
4346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      do {
4356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FIXP_DBL x0 = *pX++;
4366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FIXP_DBL x1 = *pX++;
4376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        x0 = fPow2Div2(x0);
4386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        x1 = fPow2Div2(x1);
4396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp = tmp + (x0 >> (ALFDPOW2_SCALE - 1));
4406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp = tmp + (x1 >> (ALFDPOW2_SCALE - 1));
4416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } while ((j = j - 2) != 0);
4426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp = fMax(tmp, (FL2FX_DBL(0.01f) >> s));
4436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp_pow2[i >> 3] = tmp;
4446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (tmp > max) {
4456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        max = tmp;
4466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
4476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
4486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* deemphasis of all blocks below the peak */
4506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    fac = FL2FX_DBL(0.1f) >> 1;
4516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    for (i = 0; i < i_max; i += k) {
4526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL tmp;
4536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      INT shifti;
4546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp = tmp_pow2[i >> 3];
4566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* tmp = (float)sqrt(tmp/max); */
4586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* value of tmp is between 8/2*max^2 and max^2 / 2. */
4606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* required shift factor of division can grow up to 27
4616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         (grows exponentially for values toward zero)
4626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         thus using normalized division to assure valid result. */
4636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      {
4646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        INT sd;
4656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (tmp != (FIXP_DBL)0) {
4676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          tmp = fDivNorm(max, tmp, &sd);
4686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          if (sd & 1) {
4696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            sd++;
4706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            tmp >>= 1;
4716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          }
4726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        } else {
4736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          tmp = (FIXP_DBL)MAXVAL_DBL;
4746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          sd = 0;
4756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
4766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp = invSqrtNorm2(tmp, &shifti);
4776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp = scaleValue(tmp, shifti - 1 - (sd / 2));
4786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
4796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (tmp > fac) {
4806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        fac = tmp;
4816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
4826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL *pX = &x[i];
4836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      j = 8;
4856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      do {
4866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FIXP_DBL x0 = pX[0];
4876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FIXP_DBL x1 = pX[1];
4886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        x0 = fMultDiv2(x0, fac);
4896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        x1 = fMultDiv2(x1, fac);
4906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        x0 = x0 << 2;
4916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        x1 = x1 << 2;
4926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        *pX++ = x0;
4936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        *pX++ = x1;
4946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
4956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } while ((j = j - 2) != 0);
4966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Store gains for FAC */
4976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      *alfd_gains++ = fac;
4986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
4996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
5006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
5016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
5036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \brief Interpolated Noise Shaping for mdct coefficients.
5046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * This algorithm shapes temporally the spectral noise between
5056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * the two spectral noise represention (FDNS_NPTS of resolution).
5066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * The noise is shaped monotonically between the two points
5076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * using a curved shape to favor the lower gain in mid-frame.
5086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * ODFT and amplitud calculation are applied to the 2 LPC coefficients first.
5096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK *
5106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param r pointer to spectrum data.
5116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param rms RMS of output spectrum.
5126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lg length of r.
5136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param A1 pointer to old input LPC coefficients of length M_LP_FILTER_ORDER
5146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * scaled by SF_A_COEFFS.
5156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param A2 pointer to new input LPC coefficients of length M_LP_FILTER_ORDER
5166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * scaled by SF_A_COEFFS.
5176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param bLpc2Mdct flags control lpc2mdct conversion and noise shaping.
5186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param gainLpc1 pointer to gain based on old input LPC coefficients.
5196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param gainLpc2 pointer to gain based on new input LPC coefficients.
5206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param gLpc_e pointer to exponent of gainLpc1 and gainLpc2.
5216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
5226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/* static */
5236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define NSHAPE_SCALE (4)
5246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define LPC2MDCT_CALC (1)
5266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define LPC2MDCT_GAIN_LOAD (2)
5276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define LPC2MDCT_GAIN_SAVE (4)
5286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK#define LPC2MDCT_APPLY_NSHAPE (8)
5296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKvoid lpc2mdctAndNoiseShaping(FIXP_DBL *r, SHORT *pScale, const INT lg,
5316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                             const INT fdns_npts, const FIXP_LPC *A1,
5326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                             const INT A1_exp, const FIXP_LPC *A2,
5336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                             const INT A2_exp) {
5346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL *tmp2 = NULL;
5356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL rr_minus_one;
5366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int i, k, s, step;
5376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  C_AALLOC_SCRATCH_START(tmp1, FIXP_DBL, FDNS_NPTS * 8)
5396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
5416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    tmp2 = tmp1 + fdns_npts * 4;
5426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* lpc2mdct() */
5446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* ODFT. E_LPC_a_weight() for A1 and A2 vectors is included into the loop
5466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     * below. */
5476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL f = FL2FXCONST_DBL(0.92f);
5486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    const FIXP_STP *SinTab;
5506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int k_step;
5516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* needed values: sin(phi), cos(phi); phi = i*PI/(2*fdns_npts), i = 0 ...
5526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     * M_LP_FILTER_ORDER */
5536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    switch (fdns_npts) {
5546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      case 64:
5556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        SinTab = SineTable512;
5566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        k_step = (512 / 64);
5576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FDK_ASSERT(512 >= 64);
5586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        break;
5596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      case 48:
5606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        SinTab = SineTable384;
5616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        k_step = 384 / 48;
5626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FDK_ASSERT(384 >= 48);
5636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        break;
5646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      default:
5656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FDK_ASSERT(0);
5666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        return;
5676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
5686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    for (i = 0, k = k_step; i < M_LP_FILTER_ORDER; i++, k += k_step) {
5706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_STP cs = SinTab[k];
5716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL wA1, wA2;
5726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      wA1 = fMult(A1[i], f);
5746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      wA2 = fMult(A2[i], f);
5756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* r[i] = A[i]*cos() */
5776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp1[2 + i * 2] = fMult(wA1, cs.v.re);
5786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp2[2 + i * 2] = fMult(wA2, cs.v.re);
5796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* i[i] = A[i]*sin() */
5806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp1[3 + i * 2] = -fMult(wA1, cs.v.im);
5816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp2[3 + i * 2] = -fMult(wA2, cs.v.im);
5826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      f = fMult(f, FL2FXCONST_DBL(0.92f));
5846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
5856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Guarantee at least 2 bits of headroom for the FFT */
5876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* "3" stands for 1.0 with 2 bits of headroom; (A1_exp + 2) guarantess 2
5886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     * bits of headroom if A1_exp > 1 */
5896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int A1_exp_fix = fMax(3, A1_exp + 2);
5906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int A2_exp_fix = fMax(3, A2_exp + 2);
5916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Set 1.0 in the proper format */
5936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    tmp1[0] = (FIXP_DBL)(INT)((ULONG)0x80000000 >> A1_exp_fix);
5946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    tmp2[0] = (FIXP_DBL)(INT)((ULONG)0x80000000 >> A2_exp_fix);
5956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    tmp1[1] = tmp2[1] = (FIXP_DBL)0;
5976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
5986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Clear the resto of the array */
5996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDKmemclear(
6006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp1 + 2 * (M_LP_FILTER_ORDER + 1),
6016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        2 * (fdns_npts * 2 - (M_LP_FILTER_ORDER + 1)) * sizeof(FIXP_DBL));
6026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDKmemclear(
6036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp2 + 2 * (M_LP_FILTER_ORDER + 1),
6046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        2 * (fdns_npts * 2 - (M_LP_FILTER_ORDER + 1)) * sizeof(FIXP_DBL));
6056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Guarantee 2 bits of headroom for FFT */
6076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    scaleValues(&tmp1[2], (2 * M_LP_FILTER_ORDER), (A1_exp - A1_exp_fix));
6086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    scaleValues(&tmp2[2], (2 * M_LP_FILTER_ORDER), (A2_exp - A2_exp_fix));
6096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    INT s2;
6116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    s = A1_exp_fix;
6126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    s2 = A2_exp_fix;
6136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    fft(2 * fdns_npts, tmp1, &s);
6156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    fft(2 * fdns_npts, tmp2, &s2);
6166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Adjust the exponents of both fft outputs if necessary*/
6186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (s > s2) {
6196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      scaleValues(tmp2, 2 * fdns_npts, s2 - s);
6206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      s2 = s;
6216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else if (s < s2) {
6226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      scaleValues(tmp1, 2 * fdns_npts, s - s2);
6236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      s = s2;
6246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
6256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDK_ASSERT(s == s2);
6276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
6286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Get amplitude and apply gains */
6306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  step = lg / fdns_npts;
6316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  rr_minus_one = (FIXP_DBL)0;
6326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  for (k = 0; k < fdns_npts; k++) {
6346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL g1, g2, inv_g1_g2, a, b;
6356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    INT inv_g1_g2_e;
6366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int g_e, shift;
6376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
6396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL real, imag;
6406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int si1, si2, sInput;
6416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      real = tmp1[k * 2];
6436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      imag = tmp1[k * 2 + 1];
6446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      sInput = fMax(fMin(fNorm(real), fNorm(imag)) - 1, 0);
6456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      real <<= sInput;
6466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      imag <<= sInput;
6476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* g1_e = si1 - 2*s/2 */
6486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      g1 = invSqrtNorm2(fPow2(real) + fPow2(imag), &si1);
6496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      si1 += sInput;
6506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      real = tmp2[k * 2];
6526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      imag = tmp2[k * 2 + 1];
6536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      sInput = fMax(fMin(fNorm(real), fNorm(imag)) - 1, 0);
6546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      real <<= sInput;
6556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      imag <<= sInput;
6566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* g2_e = si2 - 2*s/2 */
6576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      g2 = invSqrtNorm2(fPow2(real) + fPow2(imag), &si2);
6586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      si2 += sInput;
6596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Pick a common scale factor for g1 and g2 */
6616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (si1 > si2) {
6626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        g2 >>= si1 - si2;
6636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        g_e = si1 - s;
6646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } else {
6656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        g1 >>= si2 - si1;
6666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        g_e = si2 - s;
6676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
6686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
6696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* end of lpc2mdct() */
6716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDK_ASSERT(g1 >= (FIXP_DBL)0);
6736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDK_ASSERT(g2 >= (FIXP_DBL)0);
6746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* mdct_IntNoiseShaping() */
6766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
6776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* inv_g1_g2 * 2^inv_g1_g2_e = 1/(g1+g2) */
6786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      inv_g1_g2 = (g1 >> 1) + (g2 >> 1);
6796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (inv_g1_g2 != (FIXP_DBL)0) {
6806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        inv_g1_g2 = fDivNorm(FL2FXCONST_DBL(0.5f), inv_g1_g2, &inv_g1_g2_e);
6816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        inv_g1_g2_e = inv_g1_g2_e - g_e;
6826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } else {
6836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        inv_g1_g2 = (FIXP_DBL)MAXVAL_DBL;
6846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        inv_g1_g2_e = 0;
6856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
6866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
6876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (g_e < 0) {
6886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* a_e = g_e + inv_g1_g2_e + 1 */
6896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        a = scaleValue(fMult(fMult(g1, g2), inv_g1_g2), g_e);
6906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* b_e = g_e + inv_g1_g2_e */
6916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        b = fMult(g2 - g1, inv_g1_g2);
6926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        shift = g_e + inv_g1_g2_e + 1 - NSHAPE_SCALE;
6936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } else {
6946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* a_e = (g_e+g_e) + inv_g1_g2_e + 1 */
6956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        a = fMult(fMult(g1, g2), inv_g1_g2);
6966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* b_e = (g_e+g_e) + inv_g1_g2_e */
6976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        b = scaleValue(fMult(g2 - g1, inv_g1_g2), -g_e);
6986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        shift = (g_e + g_e) + inv_g1_g2_e + 1 - NSHAPE_SCALE;
6996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
7006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      for (i = k * step; i < (k + 1) * step; i++) {
7026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FIXP_DBL tmp;
7036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* rr[i] = 2*a*r[i] + b*rr[i-1] */
7056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp = fMult(a, r[i]);
7066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp += scaleValue(fMultDiv2(b, rr_minus_one), NSHAPE_SCALE);
7076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp = scaleValueSaturate(tmp, shift);
7086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        rr_minus_one = tmp;
7096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        r[i] = tmp;
7106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
7116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
7126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
7136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* end of mdct_IntNoiseShaping() */
7156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  { *pScale += NSHAPE_SCALE; }
7166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  C_AALLOC_SCRATCH_END(tmp1, FIXP_DBL, FDNS_NPTS * 8)
7186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
7196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
7216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \brief Calculates the energy.
7226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param r pointer to spectrum.
7236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param rs scale factor of spectrum r.
7246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lg frame length in audio samples.
7256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param rms_e pointer to exponent of energy value.
7266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \return mantissa of energy value.
7276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
7286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKstatic FIXP_DBL calcEnergy(const FIXP_DBL *r, const SHORT rs, const INT lg,
7296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                           INT *rms_e) {
7306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int headroom = getScalefactor(r, lg);
7316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL rms_m = 0;
7336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Calculate number of growth bits due to addition */
7356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  INT shift = (INT)(fNormz((FIXP_DBL)lg));
7366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  shift = 31 - shift;
7376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Generate 1e-2 in Q-6.37 */
7396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  const FIXP_DBL value0_01 = 0x51eb851e;
7406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  const INT value0_01_exp = -6;
7416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Find the exponent of the resulting energy value */
7436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  *rms_e = ((rs - headroom) << 1) + shift + 1;
7446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  INT delta = *rms_e - value0_01_exp;
7466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (delta > 0) {
7476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Limit shift_to 31*/
7486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    delta = fMin(31, delta);
7496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    rms_m = value0_01 >> delta;
7506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  } else {
7516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    rms_m = value0_01;
7526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    *rms_e = value0_01_exp;
7536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    shift = shift - delta;
7546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Limit shift_to 31*/
7556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    shift = fMin(31, shift);
7566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
7576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  for (int i = 0; i < lg; i++) {
7596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    rms_m += fPow2Div2(r[i] << headroom) >> shift;
7606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
7616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  return rms_m;
7636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
7646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
7666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \brief TCX gain calculation.
7676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param pAacDecoderChannelInfo channel context data.
7686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param r output spectrum.
7696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param rms_e pointer to mantissa of energy value.
7706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param rms_e pointer to exponent of energy value.
7716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param frame the frame index of the LPD super frame.
7726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lg the frame length in audio samples.
7736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param gain_m pointer to mantissa of TCX gain.
7746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param gain_e pointer to exponent of TCX gain.
7756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param elFlags element specific parser guidance flags.
7766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lg_fb the fullband frame length in audio samples.
7776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param IGF_bgn the IGF start index.
7786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
7796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKstatic void calcTCXGain(CAacDecoderChannelInfo *pAacDecoderChannelInfo,
7806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        FIXP_DBL *r, FIXP_DBL rms_m, INT rms_e, const INT frame,
7816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        const INT lg) {
7826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if ((rms_m != (FIXP_DBL)0)) {
7836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL tcx_gain_m;
7846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    INT tcx_gain_e;
7856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CLpd_DecodeGain(&tcx_gain_m, &tcx_gain_e,
7876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                    pAacDecoderChannelInfo->pDynData->specificTo.usac
7886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        .tcx_global_gain[frame]);
7896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* rms * 2^rms_e = lg/sqrt(sum(spec^2)) */
7916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (rms_e & 1) {
7926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      rms_m >>= 1;
7936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      rms_e++;
7946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
7956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
7966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
7976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL fx_lg;
7986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      INT fx_lg_e, s;
7996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      INT inv_e;
8006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* lg = fx_lg * 2^fx_lg_e */
8026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      s = fNorm((FIXP_DBL)lg);
8036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      fx_lg = (FIXP_DBL)lg << s;
8046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      fx_lg_e = DFRACT_BITS - 1 - s;
8056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* 1/sqrt(rms) */
8066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      rms_m = invSqrtNorm2(rms_m, &inv_e);
8076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      rms_m = fMult(rms_m, fx_lg);
8086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      rms_e = inv_e - (rms_e >> 1) + fx_lg_e;
8096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
8106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
8126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int s = fNorm(tcx_gain_m);
8136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tcx_gain_m = tcx_gain_m << s;
8146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tcx_gain_e -= s;
8156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
8166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    tcx_gain_m = fMultDiv2(tcx_gain_m, rms_m);
8186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    tcx_gain_e = tcx_gain_e + rms_e;
8196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* global_gain * 2^(global_gain_e+rms_e) = (10^(global_gain/28)) * rms *
8216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     * 2^rms_e */
8226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
8236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      { tcx_gain_e += 1; }
8246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
8256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->data.usac.tcx_gain[frame] = tcx_gain_m;
8276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->data.usac.tcx_gain_e[frame] = tcx_gain_e;
8286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->specScale[frame] += tcx_gain_e;
8306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
8316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
8326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
8346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \brief FDNS decoding.
8356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param pAacDecoderChannelInfo channel context data.
8366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param pAacDecoderStaticChannelInfo channel context static data.
8376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param r output spectrum.
8386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lg the frame length in audio samples.
8396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param frame the frame index of the LPD super frame.
8406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param pScale pointer to current scale shift factor of r[].
8416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param A1 old input LPC coefficients of length M_LP_FILTER_ORDER.
8426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param A2 new input LPC coefficients of length M_LP_FILTER_ORDER.
8436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param pAlfdGains pointer for ALFD gains output scaled by 1.
8446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param fdns_npts number of lines (FDNS_NPTS).
8456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param inf_mask pointer to noise mask.
8466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param IGF_win_mode IGF window mode (LONG, SHORT, TCX10, TCX20).
8476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param frameType (IGF_FRAME_DIVISION_AAC_OR_TCX_LONG or
8486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * IGF_FRAME_DIVISION_TCX_SHORT_1).
8496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param elFlags element specific parser guidance flags.
8506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lg_fb the fullband frame length in audio samples.
8516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param IGF_bgn the IGF start index.
8526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param rms_m mantisse of energy.
8536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param rms_e exponent of energy.
8546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
8556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/* static */
8566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKvoid CLpd_FdnsDecode(CAacDecoderChannelInfo *pAacDecoderChannelInfo,
8576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                     CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo,
8586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                     FIXP_DBL r[], const INT lg, const INT frame, SHORT *pScale,
8596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                     const FIXP_LPC A1[M_LP_FILTER_ORDER], const INT A1_exp,
8606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                     const FIXP_LPC A2[M_LP_FILTER_ORDER], const INT A2_exp,
8616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                     FIXP_DBL pAlfdGains[LFAC / 4], const INT fdns_npts) {
8626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Weight LPC coefficients using Rm values */
8636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  CLpd_AdaptLowFreqDeemph(r, lg, pAlfdGains, *pScale);
8646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL rms_m = (FIXP_DBL)0;
8666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  INT rms_e = 0;
8676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
8686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Calculate Energy */
8696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    rms_m = calcEnergy(r, *pScale, lg, &rms_e);
8706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
8716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  calcTCXGain(pAacDecoderChannelInfo, r, rms_m, rms_e, frame, lg);
8736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Apply ODFT and Noise Shaping. LP coefficient (A1, A2) weighting is done
8756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   * inside on the fly. */
8766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  lpc2mdctAndNoiseShaping(r, pScale, lg, fdns_npts, A1, A1_exp, A2, A2_exp);
8786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
8796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
8816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * find pitch for TCX20 (time domain) concealment.
8826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
8836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKstatic int find_mpitch(FIXP_DBL xri[], int lg) {
8846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL max, pitch;
8856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  INT pitch_e;
8866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int i, n;
8876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  max = (FIXP_DBL)0;
8896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  n = 2;
8906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
8916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* find maximum below 400Hz */
8926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  for (i = 2; i < (lg >> 4); i += 2) {
8936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL tmp = fPow2Div2(xri[i]) + fPow2Div2(xri[i + 1]);
8946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (tmp > max) {
8956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      max = tmp;
8966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      n = i;
8976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
8986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
8996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  // pitch = ((float)lg<<1)/(float)n;
9016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pitch = fDivNorm((FIXP_DBL)lg << 1, (FIXP_DBL)n, &pitch_e);
9026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pitch >>= fixMax(0, DFRACT_BITS - 1 - pitch_e - 16);
9036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* find pitch multiple under 20ms */
9056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (pitch >= (FIXP_DBL)((256 << 16) - 1)) { /*231.0f*/
9066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    n = 256;
9076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  } else {
9086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL mpitch = pitch;
9096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    while (mpitch < (FIXP_DBL)(255 << 16)) {
9106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      mpitch += pitch;
9116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
9126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    n = (int)(mpitch - pitch) >> 16;
9136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
9146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  return (n);
9166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
9176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
9196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * number of spectral coefficients / time domain samples using frame mode as
9206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * index.
9216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
9226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKstatic const int lg_table_ccfl[2][4] = {
9236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {256, 256, 512, 1024}, /* coreCoderFrameLength = 1024 */
9246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {192, 192, 384, 768}   /* coreCoderFrameLength = 768  */
9256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK};
9266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
9286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \brief Decode and render one MDCT-TCX frame.
9296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param pAacDecoderChannelInfo channel context data.
9306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lg the frame length in audio samples.
9316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param frame the frame index of the LPD super frame.
9326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
9336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKstatic void CLpd_TcxDecode(
9346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderChannelInfo *pAacDecoderChannelInfo,
9356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo, UINT flags,
9366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int mod, int last_mod, int frame, int frameOk) {
9376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL *pAlfd_gains = pAacDecoderStaticChannelInfo->last_alfd_gains;
9386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  ULONG *pSeed = &pAacDecoderStaticChannelInfo->nfRandomSeed;
9396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int lg = (pAacDecoderChannelInfo->granuleLength == 128)
9406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK               ? lg_table_ccfl[0][mod + 0]
9416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK               : lg_table_ccfl[1][mod + 0];
9426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int next_frame = frame + (1 << (mod - 1));
9436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int isFullBandLpd = 0;
9446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Obtain r[] vector by combining the quant[] and noise[] vectors */
9466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
9476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL noise_level;
9486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL *coeffs =
9496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        SPEC_TCX(pAacDecoderChannelInfo->pSpectralCoefficient, frame,
9506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                 pAacDecoderChannelInfo->granuleLength, isFullBandLpd);
9516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int scale = pAacDecoderChannelInfo->specScale[frame];
9526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int i, nfBgn, nfEnd;
9536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    UCHAR tcx_noise_factor = pAacDecoderChannelInfo->pDynData->specificTo.usac
9546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                                 .tcx_noise_factor[frame];
9556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* find pitch for bfi case */
9576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->last_tcx_pitch = find_mpitch(coeffs, lg);
9586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (frameOk) {
9606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* store for concealment */
9616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderStaticChannelInfo->last_tcx_noise_factor = tcx_noise_factor;
9626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else {
9636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* restore last frames value */
9646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tcx_noise_factor = pAacDecoderStaticChannelInfo->last_tcx_noise_factor;
9656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
9666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    noise_level =
9686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        (FIXP_DBL)((LONG)FL2FXCONST_DBL(0.0625f) * (8 - tcx_noise_factor));
9696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    noise_level = scaleValue(noise_level, -scale);
9706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    const FIXP_DBL neg_noise_level = -noise_level;
9726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
9746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      nfBgn = lg / 6;
9756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      nfEnd = lg;
9766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
9776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    for (i = nfBgn; i < nfEnd - 7; i += 8) {
9796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      LONG tmp;
9806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Fill all 8 consecutive zero coeffs with noise */
9826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      tmp = coeffs[i + 0] | coeffs[i + 1] | coeffs[i + 2] | coeffs[i + 3] |
9836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            coeffs[i + 4] | coeffs[i + 5] | coeffs[i + 6] | coeffs[i + 7];
9846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (tmp == 0) {
9866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        for (int k = i; k < i + 8; k++) {
9876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          UsacRandomSign(pSeed) ? (coeffs[k] = neg_noise_level)
9886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                                : (coeffs[k] = noise_level);
9896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
9906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
9916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
9926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if ((nfEnd - i) >
9936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        0) { /* noise filling for last "band" with less than 8 bins */
9946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      LONG tmp = (LONG)coeffs[i];
9956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int k;
9966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
9976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FDK_ASSERT((nfEnd - i) < 8);
9986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      for (k = 1; k < (nfEnd - i); k++) {
9996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        tmp |= (LONG)coeffs[i + k];
10006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
10016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (tmp == 0) {
10026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        for (k = i; k < nfEnd; k++) {
10036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          UsacRandomSign(pSeed) ? (coeffs[k] = neg_noise_level)
10046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                                : (coeffs[k] = noise_level);
10056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
10066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
10076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
10086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
10096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
10116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Convert LPC to LP domain */
10126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (last_mod == 0) {
10136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Note: The case where last_mod == 255 is handled by other means
10146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       * in CLpdChannelStream_Read() */
10156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      E_LPC_f_lsp_a_conversion(
10166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.lsp_coeff[frame],
10176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.lp_coeff[frame],
10186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          &pAacDecoderChannelInfo->data.usac.lp_coeff_exp[frame]);
10196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
10206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    E_LPC_f_lsp_a_conversion(
10226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lsp_coeff[next_frame],
10236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lp_coeff[next_frame],
10246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        &pAacDecoderChannelInfo->data.usac.lp_coeff_exp[next_frame]);
10256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* FDNS decoding */
10276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CLpd_FdnsDecode(
10286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo, pAacDecoderStaticChannelInfo,
10296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        SPEC_TCX(pAacDecoderChannelInfo->pSpectralCoefficient, frame,
10306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                 pAacDecoderChannelInfo->granuleLength, isFullBandLpd),
10316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        lg, frame, pAacDecoderChannelInfo->specScale + frame,
10326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lp_coeff[frame],
10336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lp_coeff_exp[frame],
10346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lp_coeff[next_frame],
10356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lp_coeff_exp[next_frame], pAlfd_gains,
10366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->granuleLength / 2 /* == FDNS_NPTS(ccfl) */
10376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    );
10386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
10396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
10406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
10426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \brief Read the tcx_coding bitstream part
10436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param hBs bitstream handle to read from.
10446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param pAacDecoderChannelInfo channel context info to store data into.
10456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lg the frame length in audio samples.
10466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param first_tcx_flag flag indicating that this is the first TCX frame.
10476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param frame the frame index of the LPD super frame.
10486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
10496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKstatic AAC_DECODER_ERROR CLpd_TCX_Read(
10506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    HANDLE_FDK_BITSTREAM hBs, CAacDecoderChannelInfo *pAacDecoderChannelInfo,
10516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo, int lg,
10526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int first_tcx_flag, int frame, UINT flags) {
10536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  AAC_DECODER_ERROR errorAAC = AAC_DEC_OK;
10546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  ARITH_CODING_ERROR error = ARITH_CODER_OK;
10556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL *pSpec;
10566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int arith_reset_flag = 0;
10576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int isFullBandLpd = 0;
10586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pSpec = SPEC_TCX(pAacDecoderChannelInfo->pSpectralCoefficient, frame,
10606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                   pAacDecoderChannelInfo->granuleLength, isFullBandLpd);
10616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* TCX noise level */
10636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
10646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->pDynData->specificTo.usac.tcx_noise_factor[frame] =
10656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FDKreadBits(hBs, 3);
10666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
10676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* TCX global gain */
10686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderChannelInfo->pDynData->specificTo.usac.tcx_global_gain[frame] =
10696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FDKreadBits(hBs, 7);
10706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Arithmetic coded residual/spectrum */
10726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (first_tcx_flag) {
10736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (flags & AC_INDEP) {
10746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      arith_reset_flag = 1;
10756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else {
10766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      arith_reset_flag = FDKreadBits(hBs, 1);
10776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
10786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
10796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* CArco_DecodeArithData() output scale of "pSpec" is DFRACT_BITS-1 */
10816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  error = CArco_DecodeArithData(pAacDecoderStaticChannelInfo->hArCo, hBs, pSpec,
10826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                                lg, lg, arith_reset_flag);
10836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Rescale residual/spectrum */
10856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
10866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int scale = getScalefactor(pSpec, lg) - 2; /* Leave 2 bits headroom */
10876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Exponent of CArco_DecodeArithData() output is DFRACT_BITS; integer
10896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     * values. */
10906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    scaleValues(pSpec, lg, scale);
10916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    scale = DFRACT_BITS - 1 - scale;
10926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->specScale[frame] = scale;
10946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
10956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (error == ARITH_CODER_ERROR) errorAAC = AAC_DEC_UNKNOWN;
10976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
10986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  return errorAAC;
10996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
11006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/**
11026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \brief translate lpd_mode into the mod[] array which describes the mode of
11036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * each each LPD frame
11046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param mod[] the array that will be filled with the mode indexes of the
11056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * inidividual frames.
11066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * \param lpd_mode the lpd_mode field read from the lpd_channel_stream
11076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
11086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKstatic AAC_DECODER_ERROR CLpd_ReadAndMapLpdModeToModArray(
11096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    UCHAR mod[4], HANDLE_FDK_BITSTREAM hBs, UINT elFlags) {
11106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int lpd_mode;
11116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
11136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    lpd_mode = FDKreadBits(hBs, 5);
11146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (lpd_mode > 25 || lpd_mode < 0) {
11166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      return AAC_DEC_PARSE_ERROR;
11176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
11186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    switch (lpd_mode) {
11206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      case 25:
11216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* 1 80MS frame */
11226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        mod[0] = mod[1] = mod[2] = mod[3] = 3;
11236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        break;
11246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      case 24:
11256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* 2 40MS frames */
11266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        mod[0] = mod[1] = mod[2] = mod[3] = 2;
11276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        break;
11286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      default:
11296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        switch (lpd_mode >> 2) {
11306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          case 4:
11316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            /* lpd_mode 19 - 16  => 1 40MS and 2 20MS frames */
11326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[0] = mod[1] = 2;
11336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[2] = (lpd_mode & 1) ? 1 : 0;
11346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[3] = (lpd_mode & 2) ? 1 : 0;
11356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            break;
11366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          case 5:
11376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            /* lpd_mode 23 - 20 => 2 20MS and 1 40MS frames */
11386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[2] = mod[3] = 2;
11396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[0] = (lpd_mode & 1) ? 1 : 0;
11406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[1] = (lpd_mode & 2) ? 1 : 0;
11416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            break;
11426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          default:
11436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            /* lpd_mode < 16 => 4 20MS frames */
11446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[0] = (lpd_mode & 1) ? 1 : 0;
11456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[1] = (lpd_mode & 2) ? 1 : 0;
11466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[2] = (lpd_mode & 4) ? 1 : 0;
11476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            mod[3] = (lpd_mode & 8) ? 1 : 0;
11486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            break;
11496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
11506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        break;
11516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
11526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
11536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  return AAC_DEC_OK;
11546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
11556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKstatic void CLpd_Reset(
11576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderChannelInfo *pAacDecoderChannelInfo,
11586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo,
11596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int keep_past_signal) {
11606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int i;
11616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Reset TCX / ACELP common memory */
11636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (!keep_past_signal) {
11646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDKmemclear(pAacDecoderStaticChannelInfo->old_synth,
11656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                sizeof(pAacDecoderStaticChannelInfo->old_synth));
11666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
11676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Initialize the LSFs */
11696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  for (i = 0; i < M_LP_FILTER_ORDER; i++) {
11706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->lpc4_lsf[i] = fdk_dec_lsf_init[i];
11716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
11726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Reset memory needed by bass post-filter */
11746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FDKmemclear(pAacDecoderStaticChannelInfo->mem_bpf,
11756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              sizeof(pAacDecoderStaticChannelInfo->mem_bpf));
11766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderStaticChannelInfo->old_bpf_control_info = 0;
11786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  for (i = 0; i < SYN_SFD; i++) {
11796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->old_T_pf[i] = 64;
11806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->old_gain_pf[i] = (FIXP_DBL)0;
11816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
11826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Reset ACELP memory */
11846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  CLpd_AcelpReset(&pAacDecoderStaticChannelInfo->acelp);
11856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderStaticChannelInfo->last_lpc_lost = 0;      /* prev_lpc_lost */
11876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderStaticChannelInfo->last_tcx_pitch = L_DIV; /* pitch_tcx     */
11886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderStaticChannelInfo->numLostLpdFrames = 0;   /* nbLostCmpt    */
11896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
11906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK/*
11926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK * Externally visible functions
11936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK */
11946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
11956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKAAC_DECODER_ERROR CLpdChannelStream_Read(
11966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    HANDLE_FDK_BITSTREAM hBs, CAacDecoderChannelInfo *pAacDecoderChannelInfo,
11976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo,
11986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    const SamplingRateInfo *pSamplingRateInfo, UINT flags) {
11996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  AAC_DECODER_ERROR error = AAC_DEC_OK;
12006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int first_tcx_flag;
12016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int k, nbDiv, fFacDataPresent, first_lpd_flag, acelp_core_mode,
12026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      facGetMemState = 0;
12036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  UCHAR *mod = pAacDecoderChannelInfo->data.usac.mod;
12046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int lpd_mode_last, prev_frame_was_lpd;
12056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  USAC_COREMODE core_mode_last;
12066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  const int lg_table_offset = 0;
12076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  const int *lg_table = (pAacDecoderChannelInfo->granuleLength == 128)
12086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                            ? &lg_table_ccfl[0][lg_table_offset]
12096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                            : &lg_table_ccfl[1][lg_table_offset];
12106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int last_lpc_lost = pAacDecoderStaticChannelInfo->last_lpc_lost;
12116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int last_frame_ok = CConcealment_GetLastFrameOk(
12136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      &pAacDecoderStaticChannelInfo->concealmentInfo, 1);
12146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  INT i_offset;
12166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  UINT samplingRate;
12176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  samplingRate = pSamplingRateInfo->samplingRate;
12196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  i_offset =
12216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      (INT)(samplingRate * PIT_MIN_12k8 + (FSCALE_DENOM / 2)) / FSCALE_DENOM -
12226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      (INT)PIT_MIN_12k8;
12236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (pSamplingRateInfo->samplingRate >
12256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FAC_FSCALE_MAX /* maximum allowed core sampling frequency */) {
12266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    error = AAC_DEC_PARSE_ERROR;
12276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    goto bail;
12286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
12296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  acelp_core_mode = FDKreadBits(hBs, 3);
12316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* lpd_mode */
12336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  error = CLpd_ReadAndMapLpdModeToModArray(mod, hBs, 0);
12346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (error != AAC_DEC_OK) {
12356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    goto bail;
12366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
12376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* bpf_control_info */
12396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderChannelInfo->data.usac.bpf_control_info = FDKreadBit(hBs);
12406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* last_core_mode */
12426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  prev_frame_was_lpd = FDKreadBit(hBs);
12436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* fac_data_present */
12446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  fFacDataPresent = FDKreadBit(hBs);
12456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Set valid values from
12476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   * pAacDecoderStaticChannelInfo->{last_core_mode,last_lpd_mode} */
12486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderChannelInfo->data.usac.core_mode_last =
12496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderStaticChannelInfo->last_core_mode;
12506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  lpd_mode_last = pAacDecoderChannelInfo->data.usac.lpd_mode_last =
12516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderStaticChannelInfo->last_lpd_mode;
12526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (prev_frame_was_lpd == 0) {
12546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Last frame was FD */
12556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->data.usac.core_mode_last = FD_LONG;
12566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->data.usac.lpd_mode_last = 255;
12576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  } else {
12586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Last frame was LPD */
12596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->data.usac.core_mode_last = LPD;
12606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (((mod[0] == 0) && fFacDataPresent) ||
12616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        ((mod[0] != 0) && !fFacDataPresent)) {
12626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Currend mod is ACELP, fac data present -> TCX, current mod TCX, no fac
12636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       * data -> TCX */
12646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (lpd_mode_last == 0) {
12656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* Bit stream interruption detected. Assume last TCX mode as TCX20. */
12666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lpd_mode_last = 1;
12676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
12686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Else assume that remembered TCX mode is correct. */
12696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else {
12706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.lpd_mode_last = 0;
12716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
12726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
12736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  first_lpd_flag = (pAacDecoderChannelInfo->data.usac.core_mode_last !=
12756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                    LPD); /* Depends on bitstream configuration */
12766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  first_tcx_flag = 1;
12776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (pAacDecoderStaticChannelInfo->last_core_mode !=
12796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      LPD) { /* ATTENTION: Reset depends on what we rendered before! */
12806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CLpd_Reset(pAacDecoderChannelInfo, pAacDecoderStaticChannelInfo, 0);
12816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (!last_frame_ok) {
12836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* If last rendered frame was not LPD and first lpd flag is not set, this
12846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       * must be an error - set last_lpc_lost flag */
12856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      last_lpc_lost |= (first_lpd_flag) ? 0 : 1;
12866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
12876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
12886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  core_mode_last = pAacDecoderChannelInfo->data.usac.core_mode_last;
12906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  lpd_mode_last = pAacDecoderChannelInfo->data.usac.lpd_mode_last;
12916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  nbDiv = NB_DIV;
12936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* k is the frame index. If a frame is of size 40MS or 80MS,
12956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     this frame index is incremented 2 or 4 instead of 1 respectively. */
12966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
12976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  k = 0;
12986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  while (k < nbDiv) {
12996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Reset FAC data pointers in order to avoid applying old random FAC data.
13006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     */
13016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->data.usac.fac_data[k] = NULL;
13026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if ((k == 0 && core_mode_last == LPD && fFacDataPresent) ||
13046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        (lpd_mode_last == 0 && mod[k] > 0) ||
13056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        ((lpd_mode_last != 255) && lpd_mode_last > 0 && mod[k] == 0)) {
13066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int err;
13076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Assign FAC memory */
13096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.fac_data[k] =
13106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          CLpd_FAC_GetMemory(pAacDecoderChannelInfo, mod, &facGetMemState);
13116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* FAC for (ACELP -> TCX) or (TCX -> ACELP) */
13136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      err = CLpd_FAC_Read(
13146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          hBs, pAacDecoderChannelInfo->data.usac.fac_data[k],
13156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.fac_data_e,
13166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->granuleLength, /* == fac_length */
13176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          0, k);
13186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (err != 0) {
13196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        error = AAC_DEC_PARSE_ERROR;
13206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        goto bail;
13216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
13226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
13236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (mod[k] == 0) /* acelp-mode */
13256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
13266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int err;
13276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      err = CLpd_AcelpRead(
13286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          hBs, &pAacDecoderChannelInfo->data.usac.acelp[k], acelp_core_mode,
13296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->granuleLength * 8 /* coreCoderFrameLength */,
13306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          i_offset);
13316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (err != 0) {
13326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        error = AAC_DEC_PARSE_ERROR;
13336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        goto bail;
13346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
13356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      lpd_mode_last = 0;
13376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      k++;
13386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else /* mode != 0  =>  TCX */
13396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
13406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      error = CLpd_TCX_Read(hBs, pAacDecoderChannelInfo,
13416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                            pAacDecoderStaticChannelInfo, lg_table[mod[k]],
13426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                            first_tcx_flag, k, flags);
13436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      lpd_mode_last = mod[k];
13456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      first_tcx_flag = 0;
13466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      k += 1 << (mod[k] - 1);
13476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
13486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (error != AAC_DEC_OK) {
13496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      error = AAC_DEC_PARSE_ERROR;
13506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      goto bail;
13516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
13526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
13536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
13556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int err;
13566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Read LPC coefficients */
13586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    err = CLpc_Read(
13596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        hBs, pAacDecoderChannelInfo->data.usac.lsp_coeff,
13606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderStaticChannelInfo->lpc4_lsf,
13616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lsf_adaptive_mean_cand,
13626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.aStability, mod, first_lpd_flag,
13636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* if last lpc4 is available from concealment do not extrapolate lpc0
13646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK           from lpc2 */
13656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        (mod[0] & 0x3) ? 0
13666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                       : (last_lpc_lost &&
13676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          pAacDecoderStaticChannelInfo->last_core_mode != LPD),
13686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        last_frame_ok);
13696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (err != 0) {
13706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      error = AAC_DEC_PARSE_ERROR;
13716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      goto bail;
13726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
13736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
13746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* adjust old lsp[] following to a bad frame (to avoid overshoot) (ref:
13766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   * dec_LPD.c) */
13776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (last_lpc_lost && !last_frame_ok) {
13786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int k_next;
13796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    k = 0;
13806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    while (k < nbDiv) {
13816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int i;
13826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      k_next = k + (((mod[k] & 0x3) == 0) ? 1 : (1 << (mod[k] - 1)));
13836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_LPC *lsp_old = pAacDecoderChannelInfo->data.usac.lsp_coeff[k];
13846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_LPC *lsp_new = pAacDecoderChannelInfo->data.usac.lsp_coeff[k_next];
13856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      for (i = 0; i < M_LP_FILTER_ORDER; i++) {
13876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (lsp_new[i] < lsp_old[i]) {
13886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          lsp_old[i] = lsp_new[i];
13896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
13906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
13916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      k = k_next;
13926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
13936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
13946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
13956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (!CConcealment_GetLastFrameOk(
13966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          &pAacDecoderStaticChannelInfo->concealmentInfo, 1)) {
13976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    E_LPC_f_lsp_a_conversion(
13986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lsp_coeff[0],
13996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lp_coeff[0],
14006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        &pAacDecoderChannelInfo->data.usac.lp_coeff_exp[0]);
14016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  } else if (pAacDecoderStaticChannelInfo->last_lpd_mode != 0) {
14026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (pAacDecoderStaticChannelInfo->last_lpd_mode == 255) {
14036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* We need it for TCX decoding or ACELP excitation update */
14046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      E_LPC_f_lsp_a_conversion(
14056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.lsp_coeff[0],
14066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.lp_coeff[0],
14076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          &pAacDecoderChannelInfo->data.usac.lp_coeff_exp[0]);
14086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else { /* last_lpd_mode was TCX */
14096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Copy old LPC4 LP domain coefficients to LPC0 LP domain buffer (to avoid
14106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       * converting LSP coefficients again). */
14116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FDKmemcpy(pAacDecoderChannelInfo->data.usac.lp_coeff[0],
14126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                pAacDecoderStaticChannelInfo->lp_coeff_old[0],
14136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                M_LP_FILTER_ORDER * sizeof(FIXP_LPC));
14146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.lp_coeff_exp[0] =
14156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderStaticChannelInfo->lp_coeff_old_exp[0];
14166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
14176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  } /* case last_lpd_mode was ACELP is handled by CLpd_TcxDecode() */
14186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (fFacDataPresent && (core_mode_last != LPD)) {
14206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int prev_frame_was_short;
14216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    prev_frame_was_short = FDKreadBit(hBs);
14236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (prev_frame_was_short) {
14256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      core_mode_last = pAacDecoderChannelInfo->data.usac.core_mode_last =
14266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          FD_SHORT;
14276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.lpd_mode_last = 255;
14286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if ((pAacDecoderStaticChannelInfo->last_core_mode != FD_SHORT) &&
14306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          CConcealment_GetLastFrameOk(
14316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              &pAacDecoderStaticChannelInfo->concealmentInfo, 1)) {
14326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* USAC Conformance document:
14336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK           short_fac_flag   shall be encoded with a value of 1 if the
14346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK           window_sequence of the previous frame was 2 (EIGHT_SHORT_SEQUENCE).
14356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                            Otherwise short_fac_flag shall be encoded with a
14366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK           value of 0. */
14376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        error = AAC_DEC_PARSE_ERROR;
14386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        goto bail;
14396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
14406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
14416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Assign memory */
14436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->data.usac.fac_data[0] =
14446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        CLpd_FAC_GetMemory(pAacDecoderChannelInfo, mod, &facGetMemState);
14456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
14476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int err;
14486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* FAC for FD -> ACELP */
14506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      err = CLpd_FAC_Read(
14516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          hBs, pAacDecoderChannelInfo->data.usac.fac_data[0],
14526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.fac_data_e,
14536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          CLpd_FAC_getLength(core_mode_last != FD_SHORT,
14546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                             pAacDecoderChannelInfo->granuleLength),
14556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          1, 0);
14566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (err != 0) {
14576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        error = AAC_DEC_PARSE_ERROR;
14586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        goto bail;
14596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
14606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
14616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
14626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKbail:
14646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (error == AAC_DEC_OK) {
14656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* check consitency of last core/lpd mode values */
14666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if ((pAacDecoderChannelInfo->data.usac.core_mode_last !=
14676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         pAacDecoderStaticChannelInfo->last_core_mode) &&
14686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        (pAacDecoderStaticChannelInfo->last_lpc_lost == 0)) {
14696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Something got wrong! */
14706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* error = AAC_DEC_PARSE_ERROR; */ /* Throwing errors does not help */
14716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else if ((pAacDecoderChannelInfo->data.usac.core_mode_last == LPD) &&
14726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK               (pAacDecoderChannelInfo->data.usac.lpd_mode_last !=
14736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                pAacDecoderStaticChannelInfo->last_lpd_mode) &&
14746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK               (pAacDecoderStaticChannelInfo->last_lpc_lost == 0)) {
14756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Something got wrong! */
14766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* error = AAC_DEC_PARSE_ERROR; */ /* Throwing errors does not help */
14776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
14786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
14796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  return error;
14816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
14826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKvoid CLpdChannelStream_Decode(
14846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderChannelInfo *pAacDecoderChannelInfo,
14856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo, UINT flags) {
14866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  UCHAR *mod = pAacDecoderChannelInfo->data.usac.mod;
14876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int k;
14886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  UCHAR last_lpd_mode;
14896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int nbDiv = NB_DIV;
14906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
14916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* k is the frame index. If a frame is of size 40MS or 80MS,
14926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     this frame index is incremented 2 or 4 instead of 1 respectively. */
14936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  k = 0;
14946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  last_lpd_mode =
14956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac
14966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          .lpd_mode_last; /* could be different to what has been rendered */
14976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  while (k < nbDiv) {
14986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (mod[k] == 0) {
14996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* ACELP */
15006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* If FAC (fac_data[k] != NULL), and previous frame was TCX, apply (TCX)
15026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       * gains to FAC data */
15036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (last_lpd_mode > 0 && last_lpd_mode != 255 &&
15046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.fac_data[k]) {
15056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        CFac_ApplyGains(pAacDecoderChannelInfo->data.usac.fac_data[k],
15066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        pAacDecoderChannelInfo->granuleLength,
15076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        pAacDecoderStaticChannelInfo->last_tcx_gain,
15086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        pAacDecoderStaticChannelInfo->last_alfd_gains,
15096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        (last_lpd_mode < 4) ? last_lpd_mode : 3);
15106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.fac_data_e[k] +=
15126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderStaticChannelInfo->last_tcx_gain_e;
15136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
15146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else {
15156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* TCX */
15166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      CLpd_TcxDecode(pAacDecoderChannelInfo, pAacDecoderStaticChannelInfo,
15176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                     flags, mod[k], last_lpd_mode, k, 1 /* frameOk == 1 */
15186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      );
15196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Store TCX gain scale for next possible FAC transition. */
15216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderStaticChannelInfo->last_tcx_gain =
15226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.tcx_gain[k];
15236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderStaticChannelInfo->last_tcx_gain_e =
15246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.tcx_gain_e[k];
15256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* If FAC (fac_data[k] != NULL), apply gains */
15276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (last_lpd_mode == 0 && pAacDecoderChannelInfo->data.usac.fac_data[k]) {
15286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        CFac_ApplyGains(
15296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.fac_data[k],
15306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->granuleLength /* == fac_length */,
15316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.tcx_gain[k],
15326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderStaticChannelInfo->last_alfd_gains, mod[k]);
15336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.fac_data_e[k] +=
15356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.tcx_gain_e[k];
15366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
15376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
15386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* remember previous mode */
15406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    last_lpd_mode = mod[k];
15416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Increase k to next frame */
15436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    k += (mod[k] == 0) ? 1 : (1 << (mod[k] - 1));
15446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
15456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
15466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDKAAC_DECODER_ERROR CLpd_RenderTimeSignal(
15486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo,
15496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CAacDecoderChannelInfo *pAacDecoderChannelInfo, FIXP_PCM *pTimeData,
15506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    INT lFrame, SamplingRateInfo *pSamplingRateInfo, UINT frameOk, UINT flags,
15516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    UINT strmFlags) {
15526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  UCHAR *mod = pAacDecoderChannelInfo->data.usac.mod;
15536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  AAC_DECODER_ERROR error = AAC_DEC_OK;
15546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int k, i_offset;
15556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int last_k;
15566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int nrSamples = 0;
15576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int facFB = 1;
15586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int nbDiv = NB_DIV;
15596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int lDiv = lFrame / nbDiv; /* length of division (acelp or tcx20 frame)*/
15606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int lFac = lDiv / 2;
15616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int nbSubfr =
15626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      lFrame / (nbDiv * L_SUBFR); /* number of subframes per division */
15636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int nbSubfrSuperfr = nbDiv * nbSubfr;
15646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int synSfd = (nbSubfrSuperfr / 2) - BPF_SFD;
15656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int SynDelay = synSfd * L_SUBFR;
15666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int aacDelay = lFrame / 2;
15676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /*
15696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   In respect to the reference software, the synth pointer here is lagging by
15706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   aacDelay ( == SYN_DELAY + BPF_DELAY ) samples. The corresponding old
15716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   synthesis samples are handled by the IMDCT overlap.
15726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   */
15736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL *synth_buf =
15756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->pComStaticData->pWorkBufferCore1->synth_buf;
15766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL *synth = synth_buf + PIT_MAX_MAX - BPF_DELAY;
15776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  UCHAR last_lpd_mode, last_last_lpd_mode, last_lpc_lost, last_frame_lost;
15786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  INT pitch[NB_SUBFR_SUPERFR + SYN_SFD];
15806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FIXP_DBL pit_gain[NB_SUBFR_SUPERFR + SYN_SFD];
15816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  const int *lg_table;
15836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  int lg_table_offset = 0;
15846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  UINT samplingRate = pSamplingRateInfo->samplingRate;
15866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FDKmemclear(pitch, (NB_SUBFR_SUPERFR + SYN_SFD) * sizeof(INT));
15886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (flags & AACDEC_FLUSH) {
15906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CLpd_Reset(pAacDecoderChannelInfo, pAacDecoderStaticChannelInfo,
15916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK               flags & AACDEC_FLUSH);
15926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    frameOk = 0;
15936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
15946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
15956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  switch (lFrame) {
15966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    case 1024:
15976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      lg_table = &lg_table_ccfl[0][lg_table_offset];
15986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      break;
15996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    case 768:
16006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      lg_table = &lg_table_ccfl[1][lg_table_offset];
16016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      break;
16026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    default:
16036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FDK_ASSERT(0);
16046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      return AAC_DEC_UNKNOWN;
16056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
16066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  last_frame_lost = !CConcealment_GetLastFrameOk(
16086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      &pAacDecoderStaticChannelInfo->concealmentInfo, 0);
16096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Maintain LPD mode from previous frame */
16116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if ((pAacDecoderStaticChannelInfo->last_core_mode == FD_LONG) ||
16126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      (pAacDecoderStaticChannelInfo->last_core_mode == FD_SHORT)) {
16136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->last_lpd_mode = 255;
16146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
16156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (!frameOk) {
16176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL old_tcx_gain;
16186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_SGL old_stab;
16196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    SCHAR old_tcx_gain_e;
16206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int nLostSf;
16216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    last_lpd_mode = pAacDecoderStaticChannelInfo->last_lpd_mode;
16236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    old_tcx_gain = pAacDecoderStaticChannelInfo->last_tcx_gain;
16246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    old_tcx_gain_e = pAacDecoderStaticChannelInfo->last_tcx_gain_e;
16256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    old_stab = pAacDecoderStaticChannelInfo->oldStability;
16266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    nLostSf = pAacDecoderStaticChannelInfo->numLostLpdFrames;
16276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* patch the last LPD mode */
16296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderChannelInfo->data.usac.lpd_mode_last = last_lpd_mode;
16306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Do mode extrapolation and repeat the previous mode:
16326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       if previous mode = ACELP        -> ACELP
16336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       if previous mode = TCX-20/40    -> TCX-20
16346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       if previous mode = TCX-80       -> TCX-80
16356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       notes:
16366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       - ACELP is not allowed after TCX (no pitch information to reuse)
16376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       - TCX-40 is not allowed in the mode repetition to keep the logic simple
16386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     */
16396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    switch (last_lpd_mode) {
16406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      case 0:
16416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        mod[0] = mod[1] = mod[2] = mod[3] = 0; /* -> ACELP concealment */
16426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        break;
16436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      case 3:
16446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        mod[0] = mod[1] = mod[2] = mod[3] = 3; /* -> TCX FD concealment */
16456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        break;
16466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      case 2:
16476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        mod[0] = mod[1] = mod[2] = mod[3] = 2; /* -> TCX FD concealment */
16486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        break;
16496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      case 1:
16506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      default:
16516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        mod[0] = mod[1] = mod[2] = mod[3] = 4; /* -> TCX TD concealment */
16526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        break;
16536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
16546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* LPC extrapolation */
16566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    CLpc_Conceal(pAacDecoderChannelInfo->data.usac.lsp_coeff,
16576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                 pAacDecoderStaticChannelInfo->lpc4_lsf,
16586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                 pAacDecoderStaticChannelInfo->lsf_adaptive_mean,
16596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                 /*(pAacDecoderStaticChannelInfo->numLostLpdFrames == 0) ||*/
16606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                 (last_lpd_mode == 255));
16616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if ((last_lpd_mode > 0) && (last_lpd_mode < 255)) {
16636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Copy old LPC4 LP domain coefficients to LPC0 LP domain buffer (to avoid
16646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       * converting LSP coefficients again). */
16656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FDKmemcpy(pAacDecoderChannelInfo->data.usac.lp_coeff[0],
16666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                pAacDecoderStaticChannelInfo->lp_coeff_old[0],
16676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                M_LP_FILTER_ORDER * sizeof(FIXP_LPC));
16686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.lp_coeff_exp[0] =
16696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderStaticChannelInfo->lp_coeff_old_exp[0];
16706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } /* case last_lpd_mode was ACELP is handled by CLpd_TcxDecode() */
16716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* case last_lpd_mode was Time domain TCX concealment is handled after this
16726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     * "if (!frameOk)"-block */
16736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* k is the frame index. If a frame is of size 40MS or 80MS,
16756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       this frame index is incremented 2 or 4 instead of 1 respectively. */
16766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    k = 0;
16776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    while (k < nbDiv) {
16786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.tcx_gain[k] = old_tcx_gain;
16796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.tcx_gain_e[k] = old_tcx_gain_e;
16806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* restore stability value from last frame */
16826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.aStability[k] = old_stab;
16836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Increase k to next frame */
16856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      k += ((mod[k] & 0x3) == 0) ? 1 : (1 << ((mod[k] & 0x3) - 1));
16866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
16876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      nLostSf++;
16886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
16896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  } else {
16906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if ((pAacDecoderStaticChannelInfo->last_lpd_mode == 4) && (mod[0] > 0)) {
16916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* Copy old LPC4 LP domain coefficients to LPC0 LP domain buffer (to avoid
16926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK       * converting LSP coefficients again). */
16936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FDKmemcpy(pAacDecoderChannelInfo->data.usac.lp_coeff[0],
16946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                pAacDecoderStaticChannelInfo->lp_coeff_old[0],
16956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                M_LP_FILTER_ORDER * sizeof(FIXP_LPC));
16966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.lp_coeff_exp[0] =
16976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderStaticChannelInfo->lp_coeff_old_exp[0];
16986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
16996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
17006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  Acelp_PreProcessing(synth_buf, pAacDecoderStaticChannelInfo->old_synth, pitch,
17026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                      pAacDecoderStaticChannelInfo->old_T_pf, pit_gain,
17036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                      pAacDecoderStaticChannelInfo->old_gain_pf, samplingRate,
17046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                      &i_offset, lFrame, synSfd, nbSubfrSuperfr);
17056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* k is the frame index. If a frame is of size 40MS or 80MS,
17076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     this frame index is incremented 2 or 4 instead of 1 respectively. */
17086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  k = 0;
17096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  last_k = -1; /* mark invalid */
17106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  last_lpd_mode = pAacDecoderStaticChannelInfo->last_lpd_mode;
17116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  last_last_lpd_mode = pAacDecoderStaticChannelInfo->last_last_lpd_mode;
17126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  last_lpc_lost = pAacDecoderStaticChannelInfo->last_lpc_lost | last_frame_lost;
17136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* This buffer must be avalable for the case of FD->ACELP transition. The
17156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  beginning of the buffer is used after the BPF to overwrite the output signal.
17166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  Only the FAC area must be affected by the BPF */
17176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  while (k < nbDiv) {
17196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (frameOk == 0) {
17206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderStaticChannelInfo->numLostLpdFrames++;
17216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else {
17226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      last_frame_lost |=
17236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          (pAacDecoderStaticChannelInfo->numLostLpdFrames > 0) ? 1 : 0;
17246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderStaticChannelInfo->numLostLpdFrames = 0;
17256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
17266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (mod[k] == 0 || mod[k] == 4) {
17276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* ACELP or TCX time domain concealment */
17286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL *acelp_out;
17296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* FAC management */
17316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if ((last_lpd_mode != 0) && (last_lpd_mode != 4)) /* TCX TD concealment */
17326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      {
17336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FIXP_DBL *pFacData = NULL;
17346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (frameOk && !last_frame_lost) {
17366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pFacData = pAacDecoderChannelInfo->data.usac.fac_data[k];
17376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
17386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        nrSamples += CLpd_FAC_Mdct2Acelp(
17406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            &pAacDecoderStaticChannelInfo->IMdct, synth + nrSamples, pFacData,
17416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.fac_data_e[k],
17426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.lp_coeff[k],
17436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.lp_coeff_exp[k],
17446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            lFrame - nrSamples,
17456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            CLpd_FAC_getLength(
17466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                (pAacDecoderStaticChannelInfo->last_core_mode != FD_SHORT) ||
17476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                    (k > 0),
17486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                lFac),
17496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            (pAacDecoderStaticChannelInfo->last_core_mode != LPD) && (k == 0),
17506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            0);
17516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FDKmemcpy(
17536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            synth + nrSamples, pAacDecoderStaticChannelInfo->IMdct.overlap.time,
17546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderStaticChannelInfo->IMdct.ov_offset * sizeof(FIXP_DBL));
17556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        {
17566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          FIXP_LPC *lp_prev =
17576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              pAacDecoderChannelInfo->data.usac
17586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                  .lp_coeff[0]; /* init value does not real matter */
17596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          INT lp_prev_exp = pAacDecoderChannelInfo->data.usac.lp_coeff_exp[0];
17606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          if (last_lpd_mode != 255) { /* last mode was tcx */
17626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            last_k = k - (1 << (last_lpd_mode - 1));
17636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            if (last_k < 0) {
17646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              lp_prev = pAacDecoderStaticChannelInfo->lp_coeff_old[1];
17656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              lp_prev_exp = pAacDecoderStaticChannelInfo->lp_coeff_old_exp[1];
17666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            } else {
17676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              lp_prev = pAacDecoderChannelInfo->data.usac.lp_coeff[last_k];
17686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              lp_prev_exp =
17696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                  pAacDecoderChannelInfo->data.usac.lp_coeff_exp[last_k];
17706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            }
17716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          }
17726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          CLpd_AcelpPrepareInternalMem(
17746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              synth + aacDelay + k * lDiv, last_lpd_mode,
17756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              (last_last_lpd_mode == 4) ? 0 : last_last_lpd_mode,
17766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              pAacDecoderChannelInfo->data.usac.lp_coeff[k],
17776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              pAacDecoderChannelInfo->data.usac.lp_coeff_exp[k], lp_prev,
17786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              lp_prev_exp, &pAacDecoderStaticChannelInfo->acelp, lFrame,
1779a4d1f0ad52e2cf6f168d2193216602f52033fc27Fraunhofer IIS FDK              (last_frame_lost && k < 2), mod[k]);
17806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
17816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } else {
17826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (k == 0 && pAacDecoderStaticChannelInfo->IMdct.ov_offset !=
17836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          lFrame / facFB / 2) {
17846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderStaticChannelInfo->IMdct.ov_offset = lFrame / facFB / 2;
17856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
17866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        nrSamples += imdct_drain(&pAacDecoderStaticChannelInfo->IMdct,
17876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                                 synth + nrSamples, lFrame / facFB - nrSamples);
17886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
17896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (nrSamples >= lFrame / facFB) {
17916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* Write ACELP time domain samples into IMDCT overlap buffer at
17926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         * pAacDecoderStaticChannelInfo->IMdct.overlap.time +
17936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         * pAacDecoderStaticChannelInfo->IMdct.ov_offset
17946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         */
17956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        acelp_out = pAacDecoderStaticChannelInfo->IMdct.overlap.time +
17966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                    pAacDecoderStaticChannelInfo->IMdct.ov_offset;
17976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
17986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* Account ACELP time domain output samples to overlap buffer */
17996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderStaticChannelInfo->IMdct.ov_offset += lDiv;
18006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } else {
18016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* Write ACELP time domain samples into output buffer at pTimeData +
18026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         * nrSamples */
18036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        acelp_out = synth + nrSamples;
18046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
18056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* Account ACELP time domain output samples to output buffer */
18066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        nrSamples += lDiv;
18076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
18086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
18096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (mod[k] == 4) {
18106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderStaticChannelInfo->acelp.wsyn_rms = scaleValue(
18116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.tcx_gain[k],
18126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            fixMin(0,
18136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                   pAacDecoderChannelInfo->data.usac.tcx_gain_e[k] - SF_EXC));
18146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        CLpd_TcxTDConceal(&pAacDecoderStaticChannelInfo->acelp,
18156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          &pAacDecoderStaticChannelInfo->last_tcx_pitch,
18166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          pAacDecoderChannelInfo->data.usac.lsp_coeff[k],
18176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          pAacDecoderChannelInfo->data.usac.lsp_coeff[k + 1],
18186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          pAacDecoderChannelInfo->data.usac.aStability[k],
18196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          pAacDecoderStaticChannelInfo->numLostLpdFrames,
18206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          acelp_out, lFrame,
18216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          pAacDecoderStaticChannelInfo->last_tcx_noise_factor);
18226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
18236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } else {
18246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        FDK_ASSERT(pAacDecoderChannelInfo->data.usac.aStability[k] >=
18256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                   (FIXP_SGL)0);
18266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        CLpd_AcelpDecode(&pAacDecoderStaticChannelInfo->acelp, i_offset,
18276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                         pAacDecoderChannelInfo->data.usac.lsp_coeff[k],
18286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                         pAacDecoderChannelInfo->data.usac.lsp_coeff[k + 1],
18296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                         pAacDecoderChannelInfo->data.usac.aStability[k],
18306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                         &pAacDecoderChannelInfo->data.usac.acelp[k],
18316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                         pAacDecoderStaticChannelInfo->numLostLpdFrames,
18326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                         last_lpc_lost, k, acelp_out,
18336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                         &pitch[(k * nbSubfr) + synSfd],
18346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                         &pit_gain[(k * nbSubfr) + synSfd], lFrame);
18356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
18366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
18376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (mod[k] != 4) {
18386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (last_lpd_mode != 0 &&
18396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac
18406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                .bpf_control_info) { /* FD/TCX -> ACELP transition */
18416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          /* bass post-filter past FAC area (past two (one for FD short)
18426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK           * subframes) */
18436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          int currentSf = synSfd + k * nbSubfr;
18446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
18456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          if ((k > 0) || (pAacDecoderStaticChannelInfo->last_core_mode !=
18466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                          FD_SHORT)) { /* TCX or FD long -> ACELP */
18476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pitch[currentSf - 2] = pitch[currentSf - 1] = pitch[currentSf];
18486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pit_gain[currentSf - 2] = pit_gain[currentSf - 1] =
18496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                pit_gain[currentSf];
18506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          } else { /* FD short -> ACELP */
18516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pitch[currentSf - 1] = pitch[currentSf];
18526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pit_gain[currentSf - 1] = pit_gain[currentSf];
18536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          }
18546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
18556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
18566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else { /* TCX */
18576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int lg = lg_table[mod[k]];
18586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int isFullBandLpd = 0;
18596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
18606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      /* FAC management */
18616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if ((last_lpd_mode == 0) || (last_lpd_mode == 4)) /* TCX TD concealment */
18626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      {
18636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        C_AALLOC_SCRATCH_START(fac_buf, FIXP_DBL, 1024 / 8);
18646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
18656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        /* pAacDecoderChannelInfo->data.usac.fac_data[k] == NULL means no FAC
18666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK         * data available. */
18676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        if (last_frame_lost == 1 ||
18686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.fac_data[k] == NULL) {
18696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          FDKmemclear(fac_buf, 1024 / 8 * sizeof(FIXP_DBL));
18706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.fac_data[k] = fac_buf;
18716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK          pAacDecoderChannelInfo->data.usac.fac_data_e[k] = 0;
18726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        }
18736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
18746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        nrSamples += CLpd_FAC_Acelp2Mdct(
18756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            &pAacDecoderStaticChannelInfo->IMdct, synth + nrSamples,
18766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            SPEC_TCX(pAacDecoderChannelInfo->pSpectralCoefficient, k,
18776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                     pAacDecoderChannelInfo->granuleLength, isFullBandLpd),
18786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->specScale + k, 1,
18796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.fac_data[k],
18806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.fac_data_e[k],
18816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->granuleLength /* == fac_length */,
18826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            lFrame - nrSamples, lg,
18836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            FDKgetWindowSlope(lDiv,
18846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                              GetWindowShape(&pAacDecoderChannelInfo->icsInfo)),
18856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            lDiv, pAacDecoderChannelInfo->data.usac.lp_coeff[k],
18866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.lp_coeff_exp[k],
18876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            &pAacDecoderStaticChannelInfo->acelp,
18886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->data.usac.tcx_gain[k],
18896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            (last_frame_lost || !frameOk), 0 /* is not FD FAC */
18906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            ,
18916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            last_lpd_mode, k,
18926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo
18936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                ->currAliasingSymmetry /* Note: The current aliasing
18946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                                          symmetry for a TCX (i.e. LPD)
18956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                                          frame must always be 0 */
18966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        );
18976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
18986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pitch[(k * nbSubfr) + synSfd + 1] = pitch[(k * nbSubfr) + synSfd] =
18996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pitch[(k * nbSubfr) + synSfd - 1];
19006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pit_gain[(k * nbSubfr) + synSfd + 1] =
19016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pit_gain[(k * nbSubfr) + synSfd] =
19026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                pit_gain[(k * nbSubfr) + synSfd - 1];
19036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        C_AALLOC_SCRATCH_END(fac_buf, FIXP_DBL, 1024 / 8);
19056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      } else {
19066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        int tl = lg;
19076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        int fl = lDiv;
19086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        int fr = lDiv;
19096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        nrSamples += imlt_block(
19116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            &pAacDecoderStaticChannelInfo->IMdct, synth + nrSamples,
19126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            SPEC_TCX(pAacDecoderChannelInfo->pSpectralCoefficient, k,
19136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                     pAacDecoderChannelInfo->granuleLength, isFullBandLpd),
19146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->specScale + k, 1, lFrame - nrSamples, tl,
19156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            FDKgetWindowSlope(fl,
19166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                              GetWindowShape(&pAacDecoderChannelInfo->icsInfo)),
19176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            fl,
19186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            FDKgetWindowSlope(fr,
19196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                              GetWindowShape(&pAacDecoderChannelInfo->icsInfo)),
19206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            fr, pAacDecoderChannelInfo->data.usac.tcx_gain[k],
19216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK            pAacDecoderChannelInfo->currAliasingSymmetry
19226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                ? MLT_FLAG_CURR_ALIAS_SYMMETRY
19236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                : 0);
19246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
19256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
19266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* remember previous mode */
19276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    last_last_lpd_mode = last_lpd_mode;
19286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    last_lpd_mode = mod[k];
19296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    last_lpc_lost = (frameOk == 0) ? 1 : 0;
19306cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19316cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Increase k to next frame */
19326cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    last_k = k;
19336cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    k += ((mod[k] & 0x3) == 0) ? 1 : (1 << (mod[k] - 1));
19346cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
19356cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19366cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (frameOk) {
19376cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* assume data was ok => store for concealment */
19386cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDK_ASSERT(pAacDecoderChannelInfo->data.usac.aStability[last_k] >=
19396cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK               (FIXP_SGL)0);
19406cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->oldStability =
19416cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.aStability[last_k];
19426cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDKmemcpy(pAacDecoderStaticChannelInfo->lsf_adaptive_mean,
19436cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              pAacDecoderChannelInfo->data.usac.lsf_adaptive_mean_cand,
19446cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              M_LP_FILTER_ORDER * sizeof(FIXP_LPC));
19456cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
19466cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19476cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* store past lp coeffs for next superframe (they are only valid and needed if
19486cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   * last_lpd_mode was tcx) */
19496cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (last_lpd_mode > 0) {
19506cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDKmemcpy(pAacDecoderStaticChannelInfo->lp_coeff_old[0],
19516cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              pAacDecoderChannelInfo->data.usac.lp_coeff[nbDiv],
19526cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              M_LP_FILTER_ORDER * sizeof(FIXP_LPC));
19536cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->lp_coeff_old_exp[0] =
19546cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lp_coeff_exp[nbDiv];
19556cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDKmemcpy(pAacDecoderStaticChannelInfo->lp_coeff_old[1],
19566cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              pAacDecoderChannelInfo->data.usac.lp_coeff[last_k],
19576cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK              M_LP_FILTER_ORDER * sizeof(FIXP_LPC));
19586cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->lp_coeff_old_exp[1] =
19596cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pAacDecoderChannelInfo->data.usac.lp_coeff_exp[last_k];
19606cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
19616cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19626cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  FDK_ASSERT(nrSamples == lFrame);
19636cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19646cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* check whether usage of bass postfilter was de-activated in the bitstream;
19656cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK   if yes, set pitch gain to 0 */
19666cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  if (!(pAacDecoderChannelInfo->data.usac.bpf_control_info)) {
19676cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    if (mod[0] != 0 && (pAacDecoderStaticChannelInfo->old_bpf_control_info)) {
19686cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      for (int i = 2; i < nbSubfrSuperfr; i++)
19696cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pit_gain[synSfd + i] = (FIXP_DBL)0;
19706cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    } else {
19716cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      for (int i = 0; i < nbSubfrSuperfr; i++)
19726cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pit_gain[synSfd + i] = (FIXP_DBL)0;
19736cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
19746cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
19756cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19766cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* for bass postfilter */
19776cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  for (int n = 0; n < synSfd; n++) {
19786cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->old_T_pf[n] = pitch[nbSubfrSuperfr + n];
19796cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    pAacDecoderStaticChannelInfo->old_gain_pf[n] = pit_gain[nbSubfrSuperfr + n];
19806cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
19816cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19826cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderStaticChannelInfo->old_bpf_control_info =
19836cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      pAacDecoderChannelInfo->data.usac.bpf_control_info;
19846cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19856cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  {
19866cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    INT lookahead = -BPF_DELAY;
19876cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    int copySamp = (mod[nbDiv - 1] == 0) ? (aacDelay) : (aacDelay - lFac);
19886cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19896cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* Copy enough time domain samples from MDCT to synthesis buffer as needed
19906cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK     * by the bass postfilter */
19916cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19926cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    lookahead += imdct_copy_ov_and_nr(&pAacDecoderStaticChannelInfo->IMdct,
19936cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                                      synth + nrSamples, copySamp);
19946cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19956cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FDK_ASSERT(lookahead == copySamp - BPF_DELAY);
19966cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19976cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    FIXP_DBL *p2_synth = synth + BPF_DELAY;
19986cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
19996cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    /* recalculate pitch gain to allow postfilering on FAC area */
20006cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    for (int i = 0; i < nbSubfrSuperfr; i++) {
20016cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      int T = pitch[i];
20026cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      FIXP_DBL gain = pit_gain[i];
20036cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
20046cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      if (gain > (FIXP_DBL)0) {
20056cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        gain = get_gain(&p2_synth[i * L_SUBFR], &p2_synth[(i * L_SUBFR) - T],
20066cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        L_SUBFR);
20076cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK        pit_gain[i] = gain;
20086cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      }
20096cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
20106cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
20116cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    {
20126cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK      bass_pf_1sf_delay(p2_synth, pitch, pit_gain, lFrame, lFrame / facFB,
20136cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        mod[nbDiv - 1] ? (SynDelay - (lDiv / 2)) : SynDelay,
20146cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                        pTimeData, pAacDecoderStaticChannelInfo->mem_bpf);
20156cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK    }
20166cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  }
20176cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
20186cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  Acelp_PostProcessing(synth_buf, pAacDecoderStaticChannelInfo->old_synth,
20196cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                       pitch, pAacDecoderStaticChannelInfo->old_T_pf, lFrame,
20206cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK                       synSfd, nbSubfrSuperfr);
20216cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
20226cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  /* Store last mode for next super frame */
20236cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  { pAacDecoderStaticChannelInfo->last_core_mode = LPD; }
20246cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderStaticChannelInfo->last_lpd_mode = last_lpd_mode;
20256cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderStaticChannelInfo->last_last_lpd_mode = last_last_lpd_mode;
20266cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  pAacDecoderStaticChannelInfo->last_lpc_lost = last_lpc_lost;
20276cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK
20286cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK  return error;
20296cfabd35363c3ef5e3b209b867169a500b3ccc3cFraunhofer IIS FDK}
2030