1*e5436536SAndroid Build Coastguard Worker /* -----------------------------------------------------------------------------
2*e5436536SAndroid Build Coastguard Worker Software License for The Fraunhofer FDK AAC Codec Library for Android
3*e5436536SAndroid Build Coastguard Worker
4*e5436536SAndroid Build Coastguard Worker © Copyright 1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
5*e5436536SAndroid Build Coastguard Worker Forschung e.V. All rights reserved.
6*e5436536SAndroid Build Coastguard Worker
7*e5436536SAndroid Build Coastguard Worker 1. INTRODUCTION
8*e5436536SAndroid Build Coastguard Worker The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software
9*e5436536SAndroid Build Coastguard Worker that implements the MPEG Advanced Audio Coding ("AAC") encoding and decoding
10*e5436536SAndroid Build Coastguard Worker scheme for digital audio. This FDK AAC Codec software is intended to be used on
11*e5436536SAndroid Build Coastguard Worker a wide variety of Android devices.
12*e5436536SAndroid Build Coastguard Worker
13*e5436536SAndroid Build Coastguard Worker AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient
14*e5436536SAndroid Build Coastguard Worker general perceptual audio codecs. AAC-ELD is considered the best-performing
15*e5436536SAndroid Build Coastguard Worker full-bandwidth communications codec by independent studies and is widely
16*e5436536SAndroid Build Coastguard Worker deployed. AAC has been standardized by ISO and IEC as part of the MPEG
17*e5436536SAndroid Build Coastguard Worker specifications.
18*e5436536SAndroid Build Coastguard Worker
19*e5436536SAndroid Build Coastguard Worker Patent licenses for necessary patent claims for the FDK AAC Codec (including
20*e5436536SAndroid Build Coastguard Worker those of Fraunhofer) may be obtained through Via Licensing
21*e5436536SAndroid Build Coastguard Worker (www.vialicensing.com) or through the respective patent owners individually for
22*e5436536SAndroid Build Coastguard Worker the purpose of encoding or decoding bit streams in products that are compliant
23*e5436536SAndroid Build Coastguard Worker with the ISO/IEC MPEG audio standards. Please note that most manufacturers of
24*e5436536SAndroid Build Coastguard Worker Android devices already license these patent claims through Via Licensing or
25*e5436536SAndroid Build Coastguard Worker directly from the patent owners, and therefore FDK AAC Codec software may
26*e5436536SAndroid Build Coastguard Worker already be covered under those patent licenses when it is used for those
27*e5436536SAndroid Build Coastguard Worker licensed purposes only.
28*e5436536SAndroid Build Coastguard Worker
29*e5436536SAndroid Build Coastguard Worker Commercially-licensed AAC software libraries, including floating-point versions
30*e5436536SAndroid Build Coastguard Worker with enhanced sound quality, are also available from Fraunhofer. Users are
31*e5436536SAndroid Build Coastguard Worker encouraged to check the Fraunhofer website for additional applications
32*e5436536SAndroid Build Coastguard Worker information and documentation.
33*e5436536SAndroid Build Coastguard Worker
34*e5436536SAndroid Build Coastguard Worker 2. COPYRIGHT LICENSE
35*e5436536SAndroid Build Coastguard Worker
36*e5436536SAndroid Build Coastguard Worker Redistribution and use in source and binary forms, with or without modification,
37*e5436536SAndroid Build Coastguard Worker are permitted without payment of copyright license fees provided that you
38*e5436536SAndroid Build Coastguard Worker satisfy the following conditions:
39*e5436536SAndroid Build Coastguard Worker
40*e5436536SAndroid Build Coastguard Worker You must retain the complete text of this software license in redistributions of
41*e5436536SAndroid Build Coastguard Worker the FDK AAC Codec or your modifications thereto in source code form.
42*e5436536SAndroid Build Coastguard Worker
43*e5436536SAndroid Build Coastguard Worker You must retain the complete text of this software license in the documentation
44*e5436536SAndroid Build Coastguard Worker and/or other materials provided with redistributions of the FDK AAC Codec or
45*e5436536SAndroid Build Coastguard Worker your modifications thereto in binary form. You must make available free of
46*e5436536SAndroid Build Coastguard Worker charge copies of the complete source code of the FDK AAC Codec and your
47*e5436536SAndroid Build Coastguard Worker modifications thereto to recipients of copies in binary form.
48*e5436536SAndroid Build Coastguard Worker
49*e5436536SAndroid Build Coastguard Worker The name of Fraunhofer may not be used to endorse or promote products derived
50*e5436536SAndroid Build Coastguard Worker from this library without prior written permission.
51*e5436536SAndroid Build Coastguard Worker
52*e5436536SAndroid Build Coastguard Worker You may not charge copyright license fees for anyone to use, copy or distribute
53*e5436536SAndroid Build Coastguard Worker the FDK AAC Codec software or your modifications thereto.
54*e5436536SAndroid Build Coastguard Worker
55*e5436536SAndroid Build Coastguard Worker Your modified versions of the FDK AAC Codec must carry prominent notices stating
56*e5436536SAndroid Build Coastguard Worker that you changed the software and the date of any change. For modified versions
57*e5436536SAndroid Build Coastguard Worker of the FDK AAC Codec, the term "Fraunhofer FDK AAC Codec Library for Android"
58*e5436536SAndroid Build Coastguard Worker must be replaced by the term "Third-Party Modified Version of the Fraunhofer FDK
59*e5436536SAndroid Build Coastguard Worker AAC Codec Library for Android."
60*e5436536SAndroid Build Coastguard Worker
61*e5436536SAndroid Build Coastguard Worker 3. NO PATENT LICENSE
62*e5436536SAndroid Build Coastguard Worker
63*e5436536SAndroid Build Coastguard Worker NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without
64*e5436536SAndroid Build Coastguard Worker limitation the patents of Fraunhofer, ARE GRANTED BY THIS SOFTWARE LICENSE.
65*e5436536SAndroid Build Coastguard Worker Fraunhofer provides no warranty of patent non-infringement with respect to this
66*e5436536SAndroid Build Coastguard Worker software.
67*e5436536SAndroid Build Coastguard Worker
68*e5436536SAndroid Build Coastguard Worker You may use this FDK AAC Codec software or modifications thereto only for
69*e5436536SAndroid Build Coastguard Worker purposes that are authorized by appropriate patent licenses.
70*e5436536SAndroid Build Coastguard Worker
71*e5436536SAndroid Build Coastguard Worker 4. DISCLAIMER
72*e5436536SAndroid Build Coastguard Worker
73*e5436536SAndroid Build Coastguard Worker This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright
74*e5436536SAndroid Build Coastguard Worker holders and contributors "AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES,
75*e5436536SAndroid Build Coastguard Worker including but not limited to the implied warranties of merchantability and
76*e5436536SAndroid Build Coastguard Worker fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
77*e5436536SAndroid Build Coastguard Worker CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary,
78*e5436536SAndroid Build Coastguard Worker or consequential damages, including but not limited to procurement of substitute
79*e5436536SAndroid Build Coastguard Worker goods or services; loss of use, data, or profits, or business interruption,
80*e5436536SAndroid Build Coastguard Worker however caused and on any theory of liability, whether in contract, strict
81*e5436536SAndroid Build Coastguard Worker liability, or tort (including negligence), arising in any way out of the use of
82*e5436536SAndroid Build Coastguard Worker this software, even if advised of the possibility of such damage.
83*e5436536SAndroid Build Coastguard Worker
84*e5436536SAndroid Build Coastguard Worker 5. CONTACT INFORMATION
85*e5436536SAndroid Build Coastguard Worker
86*e5436536SAndroid Build Coastguard Worker Fraunhofer Institute for Integrated Circuits IIS
87*e5436536SAndroid Build Coastguard Worker Attention: Audio and Multimedia Departments - FDK AAC LL
88*e5436536SAndroid Build Coastguard Worker Am Wolfsmantel 33
89*e5436536SAndroid Build Coastguard Worker 91058 Erlangen, Germany
90*e5436536SAndroid Build Coastguard Worker
91*e5436536SAndroid Build Coastguard Worker www.iis.fraunhofer.de/amm
92*e5436536SAndroid Build Coastguard Worker [email protected]
93*e5436536SAndroid Build Coastguard Worker ----------------------------------------------------------------------------- */
94*e5436536SAndroid Build Coastguard Worker
95*e5436536SAndroid Build Coastguard Worker /**************************** AAC decoder library ******************************
96*e5436536SAndroid Build Coastguard Worker
97*e5436536SAndroid Build Coastguard Worker Author(s): Josef Hoepfl
98*e5436536SAndroid Build Coastguard Worker
99*e5436536SAndroid Build Coastguard Worker Description: temporal noise shaping tool
100*e5436536SAndroid Build Coastguard Worker
101*e5436536SAndroid Build Coastguard Worker *******************************************************************************/
102*e5436536SAndroid Build Coastguard Worker
103*e5436536SAndroid Build Coastguard Worker #include "aacdec_tns.h"
104*e5436536SAndroid Build Coastguard Worker #include "aac_rom.h"
105*e5436536SAndroid Build Coastguard Worker #include "FDK_bitstream.h"
106*e5436536SAndroid Build Coastguard Worker #include "channelinfo.h"
107*e5436536SAndroid Build Coastguard Worker
108*e5436536SAndroid Build Coastguard Worker #include "FDK_lpc.h"
109*e5436536SAndroid Build Coastguard Worker
110*e5436536SAndroid Build Coastguard Worker #define TNS_MAXIMUM_ORDER_AAC 12
111*e5436536SAndroid Build Coastguard Worker
112*e5436536SAndroid Build Coastguard Worker /*!
113*e5436536SAndroid Build Coastguard Worker \brief Reset tns data
114*e5436536SAndroid Build Coastguard Worker
115*e5436536SAndroid Build Coastguard Worker The function resets the tns data
116*e5436536SAndroid Build Coastguard Worker
117*e5436536SAndroid Build Coastguard Worker \return none
118*e5436536SAndroid Build Coastguard Worker */
CTns_Reset(CTnsData * pTnsData)119*e5436536SAndroid Build Coastguard Worker void CTns_Reset(CTnsData *pTnsData) {
120*e5436536SAndroid Build Coastguard Worker /* Note: the following FDKmemclear should not be required. */
121*e5436536SAndroid Build Coastguard Worker FDKmemclear(pTnsData->Filter,
122*e5436536SAndroid Build Coastguard Worker TNS_MAX_WINDOWS * TNS_MAXIMUM_FILTERS * sizeof(CFilter));
123*e5436536SAndroid Build Coastguard Worker FDKmemclear(pTnsData->NumberOfFilters, TNS_MAX_WINDOWS * sizeof(UCHAR));
124*e5436536SAndroid Build Coastguard Worker pTnsData->DataPresent = 0;
125*e5436536SAndroid Build Coastguard Worker pTnsData->Active = 0;
126*e5436536SAndroid Build Coastguard Worker }
127*e5436536SAndroid Build Coastguard Worker
CTns_ReadDataPresentFlag(HANDLE_FDK_BITSTREAM bs,CTnsData * pTnsData)128*e5436536SAndroid Build Coastguard Worker void CTns_ReadDataPresentFlag(
129*e5436536SAndroid Build Coastguard Worker HANDLE_FDK_BITSTREAM bs, /*!< pointer to bitstream */
130*e5436536SAndroid Build Coastguard Worker CTnsData *pTnsData) /*!< pointer to aac decoder channel info */
131*e5436536SAndroid Build Coastguard Worker {
132*e5436536SAndroid Build Coastguard Worker pTnsData->DataPresent = (UCHAR)FDKreadBits(bs, 1);
133*e5436536SAndroid Build Coastguard Worker }
134*e5436536SAndroid Build Coastguard Worker
135*e5436536SAndroid Build Coastguard Worker /*!
136*e5436536SAndroid Build Coastguard Worker \brief Read tns data from bitstream
137*e5436536SAndroid Build Coastguard Worker
138*e5436536SAndroid Build Coastguard Worker The function reads the elements for tns from
139*e5436536SAndroid Build Coastguard Worker the bitstream.
140*e5436536SAndroid Build Coastguard Worker
141*e5436536SAndroid Build Coastguard Worker \return none
142*e5436536SAndroid Build Coastguard Worker */
CTns_Read(HANDLE_FDK_BITSTREAM bs,CTnsData * pTnsData,const CIcsInfo * pIcsInfo,const UINT flags)143*e5436536SAndroid Build Coastguard Worker AAC_DECODER_ERROR CTns_Read(HANDLE_FDK_BITSTREAM bs, CTnsData *pTnsData,
144*e5436536SAndroid Build Coastguard Worker const CIcsInfo *pIcsInfo, const UINT flags) {
145*e5436536SAndroid Build Coastguard Worker UCHAR n_filt, order;
146*e5436536SAndroid Build Coastguard Worker UCHAR length, coef_res, coef_compress;
147*e5436536SAndroid Build Coastguard Worker UCHAR window;
148*e5436536SAndroid Build Coastguard Worker UCHAR wins_per_frame;
149*e5436536SAndroid Build Coastguard Worker UCHAR isLongFlag;
150*e5436536SAndroid Build Coastguard Worker UCHAR start_window;
151*e5436536SAndroid Build Coastguard Worker AAC_DECODER_ERROR ErrorStatus = AAC_DEC_OK;
152*e5436536SAndroid Build Coastguard Worker
153*e5436536SAndroid Build Coastguard Worker if (!pTnsData->DataPresent) {
154*e5436536SAndroid Build Coastguard Worker return ErrorStatus;
155*e5436536SAndroid Build Coastguard Worker }
156*e5436536SAndroid Build Coastguard Worker
157*e5436536SAndroid Build Coastguard Worker {
158*e5436536SAndroid Build Coastguard Worker start_window = 0;
159*e5436536SAndroid Build Coastguard Worker wins_per_frame = GetWindowsPerFrame(pIcsInfo);
160*e5436536SAndroid Build Coastguard Worker isLongFlag = IsLongBlock(pIcsInfo);
161*e5436536SAndroid Build Coastguard Worker }
162*e5436536SAndroid Build Coastguard Worker
163*e5436536SAndroid Build Coastguard Worker pTnsData->GainLd = 0;
164*e5436536SAndroid Build Coastguard Worker
165*e5436536SAndroid Build Coastguard Worker for (window = start_window; window < wins_per_frame; window++) {
166*e5436536SAndroid Build Coastguard Worker pTnsData->NumberOfFilters[window] = n_filt =
167*e5436536SAndroid Build Coastguard Worker (UCHAR)FDKreadBits(bs, isLongFlag ? 2 : 1);
168*e5436536SAndroid Build Coastguard Worker
169*e5436536SAndroid Build Coastguard Worker if (n_filt) {
170*e5436536SAndroid Build Coastguard Worker int index;
171*e5436536SAndroid Build Coastguard Worker UCHAR nextstopband;
172*e5436536SAndroid Build Coastguard Worker
173*e5436536SAndroid Build Coastguard Worker coef_res = (UCHAR)FDKreadBits(bs, 1);
174*e5436536SAndroid Build Coastguard Worker
175*e5436536SAndroid Build Coastguard Worker nextstopband = GetScaleFactorBandsTotal(pIcsInfo);
176*e5436536SAndroid Build Coastguard Worker
177*e5436536SAndroid Build Coastguard Worker for (index = 0; index < n_filt; index++) {
178*e5436536SAndroid Build Coastguard Worker CFilter *filter = &pTnsData->Filter[window][index];
179*e5436536SAndroid Build Coastguard Worker
180*e5436536SAndroid Build Coastguard Worker length = (UCHAR)FDKreadBits(bs, isLongFlag ? 6 : 4);
181*e5436536SAndroid Build Coastguard Worker
182*e5436536SAndroid Build Coastguard Worker if (length > nextstopband) {
183*e5436536SAndroid Build Coastguard Worker length = nextstopband;
184*e5436536SAndroid Build Coastguard Worker }
185*e5436536SAndroid Build Coastguard Worker
186*e5436536SAndroid Build Coastguard Worker filter->StartBand = nextstopband - length;
187*e5436536SAndroid Build Coastguard Worker filter->StopBand = nextstopband;
188*e5436536SAndroid Build Coastguard Worker nextstopband = filter->StartBand;
189*e5436536SAndroid Build Coastguard Worker
190*e5436536SAndroid Build Coastguard Worker if (flags & (AC_USAC | AC_RSVD50 | AC_RSV603DA)) {
191*e5436536SAndroid Build Coastguard Worker /* max(Order) = 15 (long), 7 (short) */
192*e5436536SAndroid Build Coastguard Worker filter->Order = order = (UCHAR)FDKreadBits(bs, isLongFlag ? 4 : 3);
193*e5436536SAndroid Build Coastguard Worker } else {
194*e5436536SAndroid Build Coastguard Worker filter->Order = order = (UCHAR)FDKreadBits(bs, isLongFlag ? 5 : 3);
195*e5436536SAndroid Build Coastguard Worker
196*e5436536SAndroid Build Coastguard Worker if (filter->Order > TNS_MAXIMUM_ORDER) {
197*e5436536SAndroid Build Coastguard Worker ErrorStatus = AAC_DEC_TNS_READ_ERROR;
198*e5436536SAndroid Build Coastguard Worker return ErrorStatus;
199*e5436536SAndroid Build Coastguard Worker }
200*e5436536SAndroid Build Coastguard Worker }
201*e5436536SAndroid Build Coastguard Worker
202*e5436536SAndroid Build Coastguard Worker FDK_ASSERT(order <=
203*e5436536SAndroid Build Coastguard Worker TNS_MAXIMUM_ORDER); /* avoid illegal memory access */
204*e5436536SAndroid Build Coastguard Worker if (order) {
205*e5436536SAndroid Build Coastguard Worker UCHAR coef, s_mask;
206*e5436536SAndroid Build Coastguard Worker UCHAR i;
207*e5436536SAndroid Build Coastguard Worker SCHAR n_mask;
208*e5436536SAndroid Build Coastguard Worker
209*e5436536SAndroid Build Coastguard Worker static const UCHAR sgn_mask[] = {0x2, 0x4, 0x8};
210*e5436536SAndroid Build Coastguard Worker static const SCHAR neg_mask[] = {~0x3, ~0x7, ~0xF};
211*e5436536SAndroid Build Coastguard Worker
212*e5436536SAndroid Build Coastguard Worker filter->Direction = FDKreadBits(bs, 1) ? -1 : 1;
213*e5436536SAndroid Build Coastguard Worker
214*e5436536SAndroid Build Coastguard Worker coef_compress = (UCHAR)FDKreadBits(bs, 1);
215*e5436536SAndroid Build Coastguard Worker
216*e5436536SAndroid Build Coastguard Worker filter->Resolution = coef_res + 3;
217*e5436536SAndroid Build Coastguard Worker
218*e5436536SAndroid Build Coastguard Worker s_mask = sgn_mask[coef_res + 1 - coef_compress];
219*e5436536SAndroid Build Coastguard Worker n_mask = neg_mask[coef_res + 1 - coef_compress];
220*e5436536SAndroid Build Coastguard Worker
221*e5436536SAndroid Build Coastguard Worker for (i = 0; i < order; i++) {
222*e5436536SAndroid Build Coastguard Worker coef = (UCHAR)FDKreadBits(bs, filter->Resolution - coef_compress);
223*e5436536SAndroid Build Coastguard Worker filter->Coeff[i] = (coef & s_mask) ? (coef | n_mask) : coef;
224*e5436536SAndroid Build Coastguard Worker }
225*e5436536SAndroid Build Coastguard Worker pTnsData->GainLd = 4;
226*e5436536SAndroid Build Coastguard Worker }
227*e5436536SAndroid Build Coastguard Worker }
228*e5436536SAndroid Build Coastguard Worker }
229*e5436536SAndroid Build Coastguard Worker }
230*e5436536SAndroid Build Coastguard Worker
231*e5436536SAndroid Build Coastguard Worker pTnsData->Active = 1;
232*e5436536SAndroid Build Coastguard Worker
233*e5436536SAndroid Build Coastguard Worker return ErrorStatus;
234*e5436536SAndroid Build Coastguard Worker }
235*e5436536SAndroid Build Coastguard Worker
CTns_ReadDataPresentUsac(HANDLE_FDK_BITSTREAM hBs,CTnsData * pTnsData0,CTnsData * pTnsData1,UCHAR * ptns_on_lr,const CIcsInfo * pIcsInfo,const UINT flags,const UINT elFlags,const int fCommonWindow)236*e5436536SAndroid Build Coastguard Worker void CTns_ReadDataPresentUsac(HANDLE_FDK_BITSTREAM hBs, CTnsData *pTnsData0,
237*e5436536SAndroid Build Coastguard Worker CTnsData *pTnsData1, UCHAR *ptns_on_lr,
238*e5436536SAndroid Build Coastguard Worker const CIcsInfo *pIcsInfo, const UINT flags,
239*e5436536SAndroid Build Coastguard Worker const UINT elFlags, const int fCommonWindow) {
240*e5436536SAndroid Build Coastguard Worker int common_tns = 0;
241*e5436536SAndroid Build Coastguard Worker
242*e5436536SAndroid Build Coastguard Worker if (fCommonWindow) {
243*e5436536SAndroid Build Coastguard Worker common_tns = FDKreadBit(hBs);
244*e5436536SAndroid Build Coastguard Worker }
245*e5436536SAndroid Build Coastguard Worker { *ptns_on_lr = FDKreadBit(hBs); }
246*e5436536SAndroid Build Coastguard Worker if (common_tns) {
247*e5436536SAndroid Build Coastguard Worker pTnsData0->DataPresent = 1;
248*e5436536SAndroid Build Coastguard Worker CTns_Read(hBs, pTnsData0, pIcsInfo, flags);
249*e5436536SAndroid Build Coastguard Worker
250*e5436536SAndroid Build Coastguard Worker pTnsData0->DataPresent = 0;
251*e5436536SAndroid Build Coastguard Worker pTnsData0->Active = 1;
252*e5436536SAndroid Build Coastguard Worker *pTnsData1 = *pTnsData0;
253*e5436536SAndroid Build Coastguard Worker } else {
254*e5436536SAndroid Build Coastguard Worker int tns_present_both;
255*e5436536SAndroid Build Coastguard Worker
256*e5436536SAndroid Build Coastguard Worker tns_present_both = FDKreadBit(hBs);
257*e5436536SAndroid Build Coastguard Worker if (tns_present_both) {
258*e5436536SAndroid Build Coastguard Worker pTnsData0->DataPresent = 1;
259*e5436536SAndroid Build Coastguard Worker pTnsData1->DataPresent = 1;
260*e5436536SAndroid Build Coastguard Worker } else {
261*e5436536SAndroid Build Coastguard Worker pTnsData1->DataPresent = FDKreadBit(hBs);
262*e5436536SAndroid Build Coastguard Worker pTnsData0->DataPresent = !pTnsData1->DataPresent;
263*e5436536SAndroid Build Coastguard Worker }
264*e5436536SAndroid Build Coastguard Worker }
265*e5436536SAndroid Build Coastguard Worker }
266*e5436536SAndroid Build Coastguard Worker
267*e5436536SAndroid Build Coastguard Worker /*!
268*e5436536SAndroid Build Coastguard Worker \brief Apply tns to spectral lines
269*e5436536SAndroid Build Coastguard Worker
270*e5436536SAndroid Build Coastguard Worker The function applies the tns to the spectrum,
271*e5436536SAndroid Build Coastguard Worker
272*e5436536SAndroid Build Coastguard Worker \return none
273*e5436536SAndroid Build Coastguard Worker */
CTns_Apply(CTnsData * RESTRICT pTnsData,const CIcsInfo * pIcsInfo,SPECTRAL_PTR pSpectralCoefficient,const SamplingRateInfo * pSamplingRateInfo,const INT granuleLength,const UCHAR nbands,const UCHAR igf_active,const UINT flags)274*e5436536SAndroid Build Coastguard Worker void CTns_Apply(CTnsData *RESTRICT pTnsData, /*!< pointer to aac decoder info */
275*e5436536SAndroid Build Coastguard Worker const CIcsInfo *pIcsInfo, SPECTRAL_PTR pSpectralCoefficient,
276*e5436536SAndroid Build Coastguard Worker const SamplingRateInfo *pSamplingRateInfo,
277*e5436536SAndroid Build Coastguard Worker const INT granuleLength, const UCHAR nbands,
278*e5436536SAndroid Build Coastguard Worker const UCHAR igf_active, const UINT flags) {
279*e5436536SAndroid Build Coastguard Worker int window, index, start, stop, size, start_window, wins_per_frame;
280*e5436536SAndroid Build Coastguard Worker
281*e5436536SAndroid Build Coastguard Worker if (pTnsData->Active) {
282*e5436536SAndroid Build Coastguard Worker C_AALLOC_SCRATCH_START(coeff, FIXP_TCC, TNS_MAXIMUM_ORDER)
283*e5436536SAndroid Build Coastguard Worker
284*e5436536SAndroid Build Coastguard Worker {
285*e5436536SAndroid Build Coastguard Worker start_window = 0;
286*e5436536SAndroid Build Coastguard Worker wins_per_frame = GetWindowsPerFrame(pIcsInfo);
287*e5436536SAndroid Build Coastguard Worker }
288*e5436536SAndroid Build Coastguard Worker
289*e5436536SAndroid Build Coastguard Worker for (window = start_window; window < wins_per_frame; window++) {
290*e5436536SAndroid Build Coastguard Worker FIXP_DBL *pSpectrum;
291*e5436536SAndroid Build Coastguard Worker
292*e5436536SAndroid Build Coastguard Worker { pSpectrum = SPEC(pSpectralCoefficient, window, granuleLength); }
293*e5436536SAndroid Build Coastguard Worker
294*e5436536SAndroid Build Coastguard Worker for (index = 0; index < pTnsData->NumberOfFilters[window]; index++) {
295*e5436536SAndroid Build Coastguard Worker CFilter *filter = &pTnsData->Filter[window][index];
296*e5436536SAndroid Build Coastguard Worker
297*e5436536SAndroid Build Coastguard Worker if (filter->Order > 0) {
298*e5436536SAndroid Build Coastguard Worker FIXP_TCC *pCoeff;
299*e5436536SAndroid Build Coastguard Worker UCHAR tns_max_bands;
300*e5436536SAndroid Build Coastguard Worker
301*e5436536SAndroid Build Coastguard Worker pCoeff = coeff;
302*e5436536SAndroid Build Coastguard Worker if (filter->Resolution == 3) {
303*e5436536SAndroid Build Coastguard Worker int i;
304*e5436536SAndroid Build Coastguard Worker for (i = 0; i < filter->Order; i++)
305*e5436536SAndroid Build Coastguard Worker *pCoeff++ = FDKaacDec_tnsCoeff3[filter->Coeff[i] + 4];
306*e5436536SAndroid Build Coastguard Worker } else {
307*e5436536SAndroid Build Coastguard Worker int i;
308*e5436536SAndroid Build Coastguard Worker for (i = 0; i < filter->Order; i++)
309*e5436536SAndroid Build Coastguard Worker *pCoeff++ = FDKaacDec_tnsCoeff4[filter->Coeff[i] + 8];
310*e5436536SAndroid Build Coastguard Worker }
311*e5436536SAndroid Build Coastguard Worker
312*e5436536SAndroid Build Coastguard Worker switch (granuleLength) {
313*e5436536SAndroid Build Coastguard Worker case 480:
314*e5436536SAndroid Build Coastguard Worker tns_max_bands =
315*e5436536SAndroid Build Coastguard Worker tns_max_bands_tbl_480[pSamplingRateInfo->samplingRateIndex];
316*e5436536SAndroid Build Coastguard Worker break;
317*e5436536SAndroid Build Coastguard Worker case 512:
318*e5436536SAndroid Build Coastguard Worker tns_max_bands =
319*e5436536SAndroid Build Coastguard Worker tns_max_bands_tbl_512[pSamplingRateInfo->samplingRateIndex];
320*e5436536SAndroid Build Coastguard Worker break;
321*e5436536SAndroid Build Coastguard Worker default:
322*e5436536SAndroid Build Coastguard Worker tns_max_bands = GetMaximumTnsBands(
323*e5436536SAndroid Build Coastguard Worker pIcsInfo, pSamplingRateInfo->samplingRateIndex);
324*e5436536SAndroid Build Coastguard Worker /* See redefinition of TNS_MAX_BANDS table */
325*e5436536SAndroid Build Coastguard Worker if ((flags & (AC_USAC | AC_RSVD50 | AC_RSV603DA)) &&
326*e5436536SAndroid Build Coastguard Worker (pSamplingRateInfo->samplingRateIndex > 5)) {
327*e5436536SAndroid Build Coastguard Worker tns_max_bands += 1;
328*e5436536SAndroid Build Coastguard Worker }
329*e5436536SAndroid Build Coastguard Worker break;
330*e5436536SAndroid Build Coastguard Worker }
331*e5436536SAndroid Build Coastguard Worker
332*e5436536SAndroid Build Coastguard Worker start = fixMin(fixMin(filter->StartBand, tns_max_bands), nbands);
333*e5436536SAndroid Build Coastguard Worker
334*e5436536SAndroid Build Coastguard Worker start = GetScaleFactorBandOffsets(pIcsInfo, pSamplingRateInfo)[start];
335*e5436536SAndroid Build Coastguard Worker
336*e5436536SAndroid Build Coastguard Worker if (igf_active) {
337*e5436536SAndroid Build Coastguard Worker stop = fixMin(filter->StopBand, nbands);
338*e5436536SAndroid Build Coastguard Worker } else {
339*e5436536SAndroid Build Coastguard Worker stop = fixMin(fixMin(filter->StopBand, tns_max_bands), nbands);
340*e5436536SAndroid Build Coastguard Worker }
341*e5436536SAndroid Build Coastguard Worker
342*e5436536SAndroid Build Coastguard Worker stop = GetScaleFactorBandOffsets(pIcsInfo, pSamplingRateInfo)[stop];
343*e5436536SAndroid Build Coastguard Worker
344*e5436536SAndroid Build Coastguard Worker size = stop - start;
345*e5436536SAndroid Build Coastguard Worker
346*e5436536SAndroid Build Coastguard Worker if (size) {
347*e5436536SAndroid Build Coastguard Worker C_ALLOC_SCRATCH_START(state, FIXP_DBL, TNS_MAXIMUM_ORDER)
348*e5436536SAndroid Build Coastguard Worker
349*e5436536SAndroid Build Coastguard Worker FDKmemclear(state, TNS_MAXIMUM_ORDER * sizeof(FIXP_DBL));
350*e5436536SAndroid Build Coastguard Worker CLpc_SynthesisLattice(pSpectrum + start, size, 0, 0,
351*e5436536SAndroid Build Coastguard Worker filter->Direction, coeff, filter->Order,
352*e5436536SAndroid Build Coastguard Worker state);
353*e5436536SAndroid Build Coastguard Worker
354*e5436536SAndroid Build Coastguard Worker C_ALLOC_SCRATCH_END(state, FIXP_DBL, TNS_MAXIMUM_ORDER)
355*e5436536SAndroid Build Coastguard Worker }
356*e5436536SAndroid Build Coastguard Worker }
357*e5436536SAndroid Build Coastguard Worker }
358*e5436536SAndroid Build Coastguard Worker }
359*e5436536SAndroid Build Coastguard Worker C_AALLOC_SCRATCH_END(coeff, FIXP_TCC, TNS_MAXIMUM_ORDER)
360*e5436536SAndroid Build Coastguard Worker }
361*e5436536SAndroid Build Coastguard Worker }
362