xref: /aosp_15_r20/external/aac/libSBRdec/src/HFgen_preFlat.cpp (revision e54365361535b070c2db7374cec45c159c7d0e7a)
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 - 2019 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 /**************************** SBR decoder library ******************************
96*e5436536SAndroid Build Coastguard Worker 
97*e5436536SAndroid Build Coastguard Worker    Author(s):   Oliver Moser, Manuel Jander, Matthias Hildenbrand
98*e5436536SAndroid Build Coastguard Worker 
99*e5436536SAndroid Build Coastguard Worker    Description: QMF frequency pre-whitening for SBR.
100*e5436536SAndroid Build Coastguard Worker                 In the documentation the terms "scale factor" and "exponent"
101*e5436536SAndroid Build Coastguard Worker                 mean the same. Variables containing such information have
102*e5436536SAndroid Build Coastguard Worker                 the suffix "_sf".
103*e5436536SAndroid Build Coastguard Worker 
104*e5436536SAndroid Build Coastguard Worker *******************************************************************************/
105*e5436536SAndroid Build Coastguard Worker 
106*e5436536SAndroid Build Coastguard Worker #include "HFgen_preFlat.h"
107*e5436536SAndroid Build Coastguard Worker 
108*e5436536SAndroid Build Coastguard Worker #define POLY_ORDER 3
109*e5436536SAndroid Build Coastguard Worker #define MAXLOWBANDS 32
110*e5436536SAndroid Build Coastguard Worker #define LOG10FAC 0.752574989159953f     /* == 10/log2(10) * 2^-2 */
111*e5436536SAndroid Build Coastguard Worker #define LOG10FAC_INV 0.664385618977472f /* == log2(10)/20 * 2^2  */
112*e5436536SAndroid Build Coastguard Worker 
113*e5436536SAndroid Build Coastguard Worker #define FIXP_CHB FIXP_SGL /* STB sinus Tab used in transformation */
114*e5436536SAndroid Build Coastguard Worker #define CHC(a) (FX_DBL2FXCONST_SGL(a))
115*e5436536SAndroid Build Coastguard Worker #define FX_CHB2FX_DBL(a) FX_SGL2FX_DBL(a)
116*e5436536SAndroid Build Coastguard Worker 
117*e5436536SAndroid Build Coastguard Worker typedef struct backsubst_data {
118*e5436536SAndroid Build Coastguard Worker   FIXP_CHB Lnorm1d[3]; /*!< Normalized L matrix */
119*e5436536SAndroid Build Coastguard Worker   SCHAR Lnorm1d_sf[3];
120*e5436536SAndroid Build Coastguard Worker   FIXP_CHB Lnormii
121*e5436536SAndroid Build Coastguard Worker       [3]; /*!< The diagonal data points [i][i] of the normalized L matrix */
122*e5436536SAndroid Build Coastguard Worker   SCHAR Lnormii_sf[3];
123*e5436536SAndroid Build Coastguard Worker   FIXP_CHB Bmul0
124*e5436536SAndroid Build Coastguard Worker       [4]; /*!< To normalize L*x=b, Bmul0 is what we need to multiply b with. */
125*e5436536SAndroid Build Coastguard Worker   SCHAR Bmul0_sf[4];
126*e5436536SAndroid Build Coastguard Worker   FIXP_CHB LnormInv1d[6]; /*!< Normalized inverted L matrix (L') */
127*e5436536SAndroid Build Coastguard Worker   SCHAR LnormInv1d_sf[6];
128*e5436536SAndroid Build Coastguard Worker   FIXP_CHB
129*e5436536SAndroid Build Coastguard Worker   Bmul1[4]; /*!< To normalize L'*x=b, Bmul1 is what we need to multiply b
130*e5436536SAndroid Build Coastguard Worker                with. */
131*e5436536SAndroid Build Coastguard Worker   SCHAR Bmul1_sf[4];
132*e5436536SAndroid Build Coastguard Worker } backsubst_data;
133*e5436536SAndroid Build Coastguard Worker 
134*e5436536SAndroid Build Coastguard Worker /* for each element n do, f(n) = trunc(log2(n))+1  */
135*e5436536SAndroid Build Coastguard Worker const UCHAR getLog2[32] = {0, 1, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4,
136*e5436536SAndroid Build Coastguard Worker                            5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5};
137*e5436536SAndroid Build Coastguard Worker 
138*e5436536SAndroid Build Coastguard Worker /** \def  BSD_IDX_OFFSET
139*e5436536SAndroid Build Coastguard Worker  *
140*e5436536SAndroid Build Coastguard Worker  *  bsd[] begins at index 0 with data for numBands=5. The correct bsd[] is
141*e5436536SAndroid Build Coastguard Worker  *  indexed like bsd[numBands-BSD_IDX_OFFSET].
142*e5436536SAndroid Build Coastguard Worker  */
143*e5436536SAndroid Build Coastguard Worker #define BSD_IDX_OFFSET 5
144*e5436536SAndroid Build Coastguard Worker 
145*e5436536SAndroid Build Coastguard Worker #define N_NUMBANDS               \
146*e5436536SAndroid Build Coastguard Worker   MAXLOWBANDS - BSD_IDX_OFFSET + \
147*e5436536SAndroid Build Coastguard Worker       1 /*!< Number of backsubst_data elements in bsd */
148*e5436536SAndroid Build Coastguard Worker 
149*e5436536SAndroid Build Coastguard Worker const backsubst_data bsd[N_NUMBANDS] = {
150*e5436536SAndroid Build Coastguard Worker     {
151*e5436536SAndroid Build Coastguard Worker         /* numBands=5 */
152*e5436536SAndroid Build Coastguard Worker         {CHC(0x66c85a52), CHC(0x4278e587), CHC(0x697dcaff)},
153*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
154*e5436536SAndroid Build Coastguard Worker         {CHC(0x66a61789), CHC(0x5253b8e3), CHC(0x5addad81)},
155*e5436536SAndroid Build Coastguard Worker         {3, 4, 1},
156*e5436536SAndroid Build Coastguard Worker         {CHC(0x7525ee90), CHC(0x6e2a1210), CHC(0x6523bb40), CHC(0x59822ead)},
157*e5436536SAndroid Build Coastguard Worker         {-6, -4, -2, 0},
158*e5436536SAndroid Build Coastguard Worker         {CHC(0x609e4cad), CHC(0x59c7e312), CHC(0x681eecac), CHC(0x440ea893),
159*e5436536SAndroid Build Coastguard Worker          CHC(0x4a214bb3), CHC(0x53c345a1)},
160*e5436536SAndroid Build Coastguard Worker         {1, 0, -1, -1, -3, -5},
161*e5436536SAndroid Build Coastguard Worker         {CHC(0x7525ee90), CHC(0x58587936), CHC(0x410d0b38), CHC(0x7f1519d6)},
162*e5436536SAndroid Build Coastguard Worker         {-6, -1, 2, 0},
163*e5436536SAndroid Build Coastguard Worker     },
164*e5436536SAndroid Build Coastguard Worker     {
165*e5436536SAndroid Build Coastguard Worker         /* numBands=6 */
166*e5436536SAndroid Build Coastguard Worker         {CHC(0x68943285), CHC(0x4841d2c3), CHC(0x6a6214c7)},
167*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
168*e5436536SAndroid Build Coastguard Worker         {CHC(0x63c5923e), CHC(0x4e906e18), CHC(0x6285af8a)},
169*e5436536SAndroid Build Coastguard Worker         {3, 4, 1},
170*e5436536SAndroid Build Coastguard Worker         {CHC(0x7263940b), CHC(0x424a69a5), CHC(0x4ae8383a), CHC(0x517b7730)},
171*e5436536SAndroid Build Coastguard Worker         {-7, -4, -2, 0},
172*e5436536SAndroid Build Coastguard Worker         {CHC(0x518aee5f), CHC(0x4823a096), CHC(0x43764a39), CHC(0x6e6faf23),
173*e5436536SAndroid Build Coastguard Worker          CHC(0x61bba44f), CHC(0x59d8b132)},
174*e5436536SAndroid Build Coastguard Worker         {1, 0, -1, -2, -4, -6},
175*e5436536SAndroid Build Coastguard Worker         {CHC(0x7263940b), CHC(0x6757bff2), CHC(0x5bf40fe0), CHC(0x7d6f4292)},
176*e5436536SAndroid Build Coastguard Worker         {-7, -2, 1, 0},
177*e5436536SAndroid Build Coastguard Worker     },
178*e5436536SAndroid Build Coastguard Worker     {
179*e5436536SAndroid Build Coastguard Worker         /* numBands=7 */
180*e5436536SAndroid Build Coastguard Worker         {CHC(0x699b4c3c), CHC(0x4b8b702f), CHC(0x6ae51a4f)},
181*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
182*e5436536SAndroid Build Coastguard Worker         {CHC(0x623a7f49), CHC(0x4ccc91fc), CHC(0x68f048dd)},
183*e5436536SAndroid Build Coastguard Worker         {3, 4, 1},
184*e5436536SAndroid Build Coastguard Worker         {CHC(0x7e6ebe18), CHC(0x5701daf2), CHC(0x74a8198b), CHC(0x4b399aa1)},
185*e5436536SAndroid Build Coastguard Worker         {-8, -5, -3, 0},
186*e5436536SAndroid Build Coastguard Worker         {CHC(0x464a64a6), CHC(0x78e42633), CHC(0x5ee174ba), CHC(0x5d0008c8),
187*e5436536SAndroid Build Coastguard Worker          CHC(0x455cff0f), CHC(0x6b9100e7)},
188*e5436536SAndroid Build Coastguard Worker         {1, -1, -2, -2, -4, -7},
189*e5436536SAndroid Build Coastguard Worker         {CHC(0x7e6ebe18), CHC(0x42c52efe), CHC(0x45fe401f), CHC(0x7b5808ef)},
190*e5436536SAndroid Build Coastguard Worker         {-8, -2, 1, 0},
191*e5436536SAndroid Build Coastguard Worker     },
192*e5436536SAndroid Build Coastguard Worker     {
193*e5436536SAndroid Build Coastguard Worker         /* numBands=8 */
194*e5436536SAndroid Build Coastguard Worker         {CHC(0x6a3fd9b4), CHC(0x4d99823f), CHC(0x6b372a94)},
195*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
196*e5436536SAndroid Build Coastguard Worker         {CHC(0x614c6ef7), CHC(0x4bd06699), CHC(0x6e59cfca)},
197*e5436536SAndroid Build Coastguard Worker         {3, 4, 1},
198*e5436536SAndroid Build Coastguard Worker         {CHC(0x4c389cc5), CHC(0x79686681), CHC(0x5e2544c2), CHC(0x46305b43)},
199*e5436536SAndroid Build Coastguard Worker         {-8, -6, -3, 0},
200*e5436536SAndroid Build Coastguard Worker         {CHC(0x7b4ca7c6), CHC(0x68270ac5), CHC(0x467c644c), CHC(0x505c1b0f),
201*e5436536SAndroid Build Coastguard Worker          CHC(0x67a14778), CHC(0x45801767)},
202*e5436536SAndroid Build Coastguard Worker         {0, -1, -2, -2, -5, -7},
203*e5436536SAndroid Build Coastguard Worker         {CHC(0x4c389cc5), CHC(0x5c499ceb), CHC(0x6f863c9f), CHC(0x79059bfc)},
204*e5436536SAndroid Build Coastguard Worker         {-8, -3, 0, 0},
205*e5436536SAndroid Build Coastguard Worker     },
206*e5436536SAndroid Build Coastguard Worker     {
207*e5436536SAndroid Build Coastguard Worker         /* numBands=9 */
208*e5436536SAndroid Build Coastguard Worker         {CHC(0x6aad9988), CHC(0x4ef8ac18), CHC(0x6b6df116)},
209*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
210*e5436536SAndroid Build Coastguard Worker         {CHC(0x60b159b0), CHC(0x4b33f772), CHC(0x72f5573d)},
211*e5436536SAndroid Build Coastguard Worker         {3, 4, 1},
212*e5436536SAndroid Build Coastguard Worker         {CHC(0x6206cb18), CHC(0x58a7d8dc), CHC(0x4e0b2d0b), CHC(0x4207ad84)},
213*e5436536SAndroid Build Coastguard Worker         {-9, -6, -3, 0},
214*e5436536SAndroid Build Coastguard Worker         {CHC(0x6dadadae), CHC(0x5b8b2cfc), CHC(0x6cf61db2), CHC(0x46c3c90b),
215*e5436536SAndroid Build Coastguard Worker          CHC(0x506314ea), CHC(0x5f034acd)},
216*e5436536SAndroid Build Coastguard Worker         {0, -1, -3, -2, -5, -8},
217*e5436536SAndroid Build Coastguard Worker         {CHC(0x6206cb18), CHC(0x42f8b8de), CHC(0x5bb4776f), CHC(0x769acc79)},
218*e5436536SAndroid Build Coastguard Worker         {-9, -3, 0, 0},
219*e5436536SAndroid Build Coastguard Worker     },
220*e5436536SAndroid Build Coastguard Worker     {
221*e5436536SAndroid Build Coastguard Worker         /* numBands=10 */
222*e5436536SAndroid Build Coastguard Worker         {CHC(0x6afa7252), CHC(0x4feed3ed), CHC(0x6b94504d)},
223*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
224*e5436536SAndroid Build Coastguard Worker         {CHC(0x60467899), CHC(0x4acbafba), CHC(0x76eb327f)},
225*e5436536SAndroid Build Coastguard Worker         {3, 4, 1},
226*e5436536SAndroid Build Coastguard Worker         {CHC(0x42415b15), CHC(0x431080da), CHC(0x420f1c32), CHC(0x7d0c1aeb)},
227*e5436536SAndroid Build Coastguard Worker         {-9, -6, -3, -1},
228*e5436536SAndroid Build Coastguard Worker         {CHC(0x62b2c7a4), CHC(0x51b040a6), CHC(0x56caddb4), CHC(0x7e74a2c8),
229*e5436536SAndroid Build Coastguard Worker          CHC(0x4030adf5), CHC(0x43d1dc4f)},
230*e5436536SAndroid Build Coastguard Worker         {0, -1, -3, -3, -5, -8},
231*e5436536SAndroid Build Coastguard Worker         {CHC(0x42415b15), CHC(0x64e299b3), CHC(0x4d33b5e8), CHC(0x742cee5f)},
232*e5436536SAndroid Build Coastguard Worker         {-9, -4, 0, 0},
233*e5436536SAndroid Build Coastguard Worker     },
234*e5436536SAndroid Build Coastguard Worker     {
235*e5436536SAndroid Build Coastguard Worker         /* numBands=11 */
236*e5436536SAndroid Build Coastguard Worker         {CHC(0x6b3258bb), CHC(0x50a21233), CHC(0x6bb03c19)},
237*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
238*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ff997c6), CHC(0x4a82706e), CHC(0x7a5aae36)},
239*e5436536SAndroid Build Coastguard Worker         {3, 4, 1},
240*e5436536SAndroid Build Coastguard Worker         {CHC(0x5d2fb4fb), CHC(0x685bddd8), CHC(0x71b5e983), CHC(0x7708c90b)},
241*e5436536SAndroid Build Coastguard Worker         {-10, -7, -4, -1},
242*e5436536SAndroid Build Coastguard Worker         {CHC(0x59aceea2), CHC(0x49c428a0), CHC(0x46ca5527), CHC(0x724be884),
243*e5436536SAndroid Build Coastguard Worker          CHC(0x68e586da), CHC(0x643485b6)},
244*e5436536SAndroid Build Coastguard Worker         {0, -1, -3, -3, -6, -9},
245*e5436536SAndroid Build Coastguard Worker         {CHC(0x5d2fb4fb), CHC(0x4e3fad1a), CHC(0x42310ba2), CHC(0x71c8b3ce)},
246*e5436536SAndroid Build Coastguard Worker         {-10, -4, 0, 0},
247*e5436536SAndroid Build Coastguard Worker     },
248*e5436536SAndroid Build Coastguard Worker     {
249*e5436536SAndroid Build Coastguard Worker         /* numBands=12 */
250*e5436536SAndroid Build Coastguard Worker         {CHC(0x6b5c4726), CHC(0x5128a4a8), CHC(0x6bc52ee1)},
251*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
252*e5436536SAndroid Build Coastguard Worker         {CHC(0x5fc06618), CHC(0x4a4ce559), CHC(0x7d5c16e9)},
253*e5436536SAndroid Build Coastguard Worker         {3, 4, 1},
254*e5436536SAndroid Build Coastguard Worker         {CHC(0x43af8342), CHC(0x531533d3), CHC(0x633660a6), CHC(0x71ce6052)},
255*e5436536SAndroid Build Coastguard Worker         {-10, -7, -4, -1},
256*e5436536SAndroid Build Coastguard Worker         {CHC(0x522373d7), CHC(0x434150cb), CHC(0x75b58afc), CHC(0x68474f2d),
257*e5436536SAndroid Build Coastguard Worker          CHC(0x575348a5), CHC(0x4c20973f)},
258*e5436536SAndroid Build Coastguard Worker         {0, -1, -4, -3, -6, -9},
259*e5436536SAndroid Build Coastguard Worker         {CHC(0x43af8342), CHC(0x7c4d3d11), CHC(0x732e13db), CHC(0x6f756ac4)},
260*e5436536SAndroid Build Coastguard Worker         {-10, -5, -1, 0},
261*e5436536SAndroid Build Coastguard Worker     },
262*e5436536SAndroid Build Coastguard Worker     {
263*e5436536SAndroid Build Coastguard Worker         /* numBands=13 */
264*e5436536SAndroid Build Coastguard Worker         {CHC(0x6b7c8953), CHC(0x51903fcd), CHC(0x6bd54d2e)},
265*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
266*e5436536SAndroid Build Coastguard Worker         {CHC(0x5f94abf0), CHC(0x4a2480fa), CHC(0x40013553)},
267*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
268*e5436536SAndroid Build Coastguard Worker         {CHC(0x6501236e), CHC(0x436b9c4e), CHC(0x578d7881), CHC(0x6d34f92e)},
269*e5436536SAndroid Build Coastguard Worker         {-11, -7, -4, -1},
270*e5436536SAndroid Build Coastguard Worker         {CHC(0x4bc0e2b2), CHC(0x7b9d12ac), CHC(0x636c1c1b), CHC(0x5fe15c2b),
271*e5436536SAndroid Build Coastguard Worker          CHC(0x49d54879), CHC(0x7662cfa5)},
272*e5436536SAndroid Build Coastguard Worker         {0, -2, -4, -3, -6, -10},
273*e5436536SAndroid Build Coastguard Worker         {CHC(0x6501236e), CHC(0x64b059fe), CHC(0x656d8359), CHC(0x6d370900)},
274*e5436536SAndroid Build Coastguard Worker         {-11, -5, -1, 0},
275*e5436536SAndroid Build Coastguard Worker     },
276*e5436536SAndroid Build Coastguard Worker     {
277*e5436536SAndroid Build Coastguard Worker         /* numBands=14 */
278*e5436536SAndroid Build Coastguard Worker         {CHC(0x6b95e276), CHC(0x51e1b637), CHC(0x6be1f7ed)},
279*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
280*e5436536SAndroid Build Coastguard Worker         {CHC(0x5f727a1c), CHC(0x4a053e9c), CHC(0x412e528c)},
281*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
282*e5436536SAndroid Build Coastguard Worker         {CHC(0x4d178bd4), CHC(0x6f33b4e8), CHC(0x4e028f7f), CHC(0x691ee104)},
283*e5436536SAndroid Build Coastguard Worker         {-11, -8, -4, -1},
284*e5436536SAndroid Build Coastguard Worker         {CHC(0x46473d3f), CHC(0x725bd0a6), CHC(0x55199885), CHC(0x58bcc56b),
285*e5436536SAndroid Build Coastguard Worker          CHC(0x7e7e6288), CHC(0x5ddef6eb)},
286*e5436536SAndroid Build Coastguard Worker         {0, -2, -4, -3, -7, -10},
287*e5436536SAndroid Build Coastguard Worker         {CHC(0x4d178bd4), CHC(0x52ebd467), CHC(0x5a395a6e), CHC(0x6b0f724f)},
288*e5436536SAndroid Build Coastguard Worker         {-11, -5, -1, 0},
289*e5436536SAndroid Build Coastguard Worker     },
290*e5436536SAndroid Build Coastguard Worker     {
291*e5436536SAndroid Build Coastguard Worker         /* numBands=15 */
292*e5436536SAndroid Build Coastguard Worker         {CHC(0x6baa2a22), CHC(0x5222eb91), CHC(0x6bec1a86)},
293*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
294*e5436536SAndroid Build Coastguard Worker         {CHC(0x5f57393b), CHC(0x49ec8934), CHC(0x423b5b58)},
295*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
296*e5436536SAndroid Build Coastguard Worker         {CHC(0x77fd2486), CHC(0x5cfbdf2c), CHC(0x46153bd1), CHC(0x65757ed9)},
297*e5436536SAndroid Build Coastguard Worker         {-12, -8, -4, -1},
298*e5436536SAndroid Build Coastguard Worker         {CHC(0x41888ee6), CHC(0x6a661db3), CHC(0x49abc8c8), CHC(0x52965848),
299*e5436536SAndroid Build Coastguard Worker          CHC(0x6d9301b7), CHC(0x4bb04721)},
300*e5436536SAndroid Build Coastguard Worker         {0, -2, -4, -3, -7, -10},
301*e5436536SAndroid Build Coastguard Worker         {CHC(0x77fd2486), CHC(0x45424c68), CHC(0x50f33cc6), CHC(0x68ff43f0)},
302*e5436536SAndroid Build Coastguard Worker         {-12, -5, -1, 0},
303*e5436536SAndroid Build Coastguard Worker     },
304*e5436536SAndroid Build Coastguard Worker     {
305*e5436536SAndroid Build Coastguard Worker         /* numBands=16 */
306*e5436536SAndroid Build Coastguard Worker         {CHC(0x6bbaa499), CHC(0x5257ed94), CHC(0x6bf456e4)},
307*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
308*e5436536SAndroid Build Coastguard Worker         {CHC(0x5f412594), CHC(0x49d8a766), CHC(0x432d1dbd)},
309*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
310*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ef5cfde), CHC(0x4eafcd2d), CHC(0x7ed36893), CHC(0x62274b45)},
311*e5436536SAndroid Build Coastguard Worker         {-12, -8, -5, -1},
312*e5436536SAndroid Build Coastguard Worker         {CHC(0x7ac438f5), CHC(0x637aab21), CHC(0x4067617a), CHC(0x4d3c6ec7),
313*e5436536SAndroid Build Coastguard Worker          CHC(0x5fd6e0dd), CHC(0x7bd5f024)},
314*e5436536SAndroid Build Coastguard Worker         {-1, -2, -4, -3, -7, -11},
315*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ef5cfde), CHC(0x751d0d4f), CHC(0x492b3c41), CHC(0x67065409)},
316*e5436536SAndroid Build Coastguard Worker         {-12, -6, -1, 0},
317*e5436536SAndroid Build Coastguard Worker     },
318*e5436536SAndroid Build Coastguard Worker     {
319*e5436536SAndroid Build Coastguard Worker         /* numBands=17 */
320*e5436536SAndroid Build Coastguard Worker         {CHC(0x6bc836c9), CHC(0x5283997e), CHC(0x6bfb1f5e)},
321*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
322*e5436536SAndroid Build Coastguard Worker         {CHC(0x5f2f02b6), CHC(0x49c868e9), CHC(0x44078151)},
323*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
324*e5436536SAndroid Build Coastguard Worker         {CHC(0x4c43b65a), CHC(0x4349dcf6), CHC(0x73799e2d), CHC(0x5f267274)},
325*e5436536SAndroid Build Coastguard Worker         {-12, -8, -5, -1},
326*e5436536SAndroid Build Coastguard Worker         {CHC(0x73726394), CHC(0x5d68511a), CHC(0x7191bbcc), CHC(0x48898c70),
327*e5436536SAndroid Build Coastguard Worker          CHC(0x548956e1), CHC(0x66981ce8)},
328*e5436536SAndroid Build Coastguard Worker         {-1, -2, -5, -3, -7, -11},
329*e5436536SAndroid Build Coastguard Worker         {CHC(0x4c43b65a), CHC(0x64131116), CHC(0x429028e2), CHC(0x65240211)},
330*e5436536SAndroid Build Coastguard Worker         {-12, -6, -1, 0},
331*e5436536SAndroid Build Coastguard Worker     },
332*e5436536SAndroid Build Coastguard Worker     {
333*e5436536SAndroid Build Coastguard Worker         /* numBands=18 */
334*e5436536SAndroid Build Coastguard Worker         {CHC(0x6bd3860d), CHC(0x52a80156), CHC(0x6c00c68d)},
335*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
336*e5436536SAndroid Build Coastguard Worker         {CHC(0x5f1fed86), CHC(0x49baf636), CHC(0x44cdb9dc)},
337*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
338*e5436536SAndroid Build Coastguard Worker         {CHC(0x7c189389), CHC(0x742666d8), CHC(0x69b8c776), CHC(0x5c67e27d)},
339*e5436536SAndroid Build Coastguard Worker         {-13, -9, -5, -1},
340*e5436536SAndroid Build Coastguard Worker         {CHC(0x6cf1ea76), CHC(0x58095703), CHC(0x64e351a9), CHC(0x4460da90),
341*e5436536SAndroid Build Coastguard Worker          CHC(0x4b1f8083), CHC(0x55f2d3e1)},
342*e5436536SAndroid Build Coastguard Worker         {-1, -2, -5, -3, -7, -11},
343*e5436536SAndroid Build Coastguard Worker         {CHC(0x7c189389), CHC(0x5651792a), CHC(0x79cb9b3d), CHC(0x635769c0)},
344*e5436536SAndroid Build Coastguard Worker         {-13, -6, -2, 0},
345*e5436536SAndroid Build Coastguard Worker     },
346*e5436536SAndroid Build Coastguard Worker     {
347*e5436536SAndroid Build Coastguard Worker         /* numBands=19 */
348*e5436536SAndroid Build Coastguard Worker         {CHC(0x6bdd0c40), CHC(0x52c6abf6), CHC(0x6c058950)},
349*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
350*e5436536SAndroid Build Coastguard Worker         {CHC(0x5f133f88), CHC(0x49afb305), CHC(0x45826d73)},
351*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
352*e5436536SAndroid Build Coastguard Worker         {CHC(0x6621a164), CHC(0x6512528e), CHC(0x61449fc8), CHC(0x59e2a0c0)},
353*e5436536SAndroid Build Coastguard Worker         {-13, -9, -5, -1},
354*e5436536SAndroid Build Coastguard Worker         {CHC(0x6721cadb), CHC(0x53404cd4), CHC(0x5a389e91), CHC(0x40abcbd2),
355*e5436536SAndroid Build Coastguard Worker          CHC(0x43332f01), CHC(0x48b82e46)},
356*e5436536SAndroid Build Coastguard Worker         {-1, -2, -5, -3, -7, -11},
357*e5436536SAndroid Build Coastguard Worker         {CHC(0x6621a164), CHC(0x4b12cc28), CHC(0x6ffd4df8), CHC(0x619f835e)},
358*e5436536SAndroid Build Coastguard Worker         {-13, -6, -2, 0},
359*e5436536SAndroid Build Coastguard Worker     },
360*e5436536SAndroid Build Coastguard Worker     {
361*e5436536SAndroid Build Coastguard Worker         /* numBands=20 */
362*e5436536SAndroid Build Coastguard Worker         {CHC(0x6be524c5), CHC(0x52e0beb3), CHC(0x6c099552)},
363*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
364*e5436536SAndroid Build Coastguard Worker         {CHC(0x5f087c68), CHC(0x49a62bb5), CHC(0x4627d175)},
365*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
366*e5436536SAndroid Build Coastguard Worker         {CHC(0x54ec6afe), CHC(0x58991a42), CHC(0x59e23e8c), CHC(0x578f4ef4)},
367*e5436536SAndroid Build Coastguard Worker         {-13, -9, -5, -1},
368*e5436536SAndroid Build Coastguard Worker         {CHC(0x61e78f6f), CHC(0x4ef5e1e9), CHC(0x5129c3b8), CHC(0x7ab0f7b2),
369*e5436536SAndroid Build Coastguard Worker          CHC(0x78efb076), CHC(0x7c2567ea)},
370*e5436536SAndroid Build Coastguard Worker         {-1, -2, -5, -4, -8, -12},
371*e5436536SAndroid Build Coastguard Worker         {CHC(0x54ec6afe), CHC(0x41c7812c), CHC(0x676f6f8d), CHC(0x5ffb383f)},
372*e5436536SAndroid Build Coastguard Worker         {-13, -6, -2, 0},
373*e5436536SAndroid Build Coastguard Worker     },
374*e5436536SAndroid Build Coastguard Worker     {
375*e5436536SAndroid Build Coastguard Worker         /* numBands=21 */
376*e5436536SAndroid Build Coastguard Worker         {CHC(0x6bec1542), CHC(0x52f71929), CHC(0x6c0d0d5e)},
377*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
378*e5436536SAndroid Build Coastguard Worker         {CHC(0x5eff45c5), CHC(0x499e092d), CHC(0x46bfc0c9)},
379*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
380*e5436536SAndroid Build Coastguard Worker         {CHC(0x47457a78), CHC(0x4e2d99b3), CHC(0x53637ea5), CHC(0x5567d0e9)},
381*e5436536SAndroid Build Coastguard Worker         {-13, -9, -5, -1},
382*e5436536SAndroid Build Coastguard Worker         {CHC(0x5d2dc61b), CHC(0x4b1760c8), CHC(0x4967cf39), CHC(0x74b113d8),
383*e5436536SAndroid Build Coastguard Worker          CHC(0x6d6676b6), CHC(0x6ad114e9)},
384*e5436536SAndroid Build Coastguard Worker         {-1, -2, -5, -4, -8, -12},
385*e5436536SAndroid Build Coastguard Worker         {CHC(0x47457a78), CHC(0x740accaa), CHC(0x5feb6609), CHC(0x5e696f95)},
386*e5436536SAndroid Build Coastguard Worker         {-13, -7, -2, 0},
387*e5436536SAndroid Build Coastguard Worker     },
388*e5436536SAndroid Build Coastguard Worker     {
389*e5436536SAndroid Build Coastguard Worker         /* numBands=22 */
390*e5436536SAndroid Build Coastguard Worker         {CHC(0x6bf21387), CHC(0x530a683c), CHC(0x6c100c59)},
391*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
392*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ef752ea), CHC(0x499708c6), CHC(0x474bcd1b)},
393*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
394*e5436536SAndroid Build Coastguard Worker         {CHC(0x78a21ab7), CHC(0x45658aec), CHC(0x4da3c4fe), CHC(0x5367094b)},
395*e5436536SAndroid Build Coastguard Worker         {-14, -9, -5, -1},
396*e5436536SAndroid Build Coastguard Worker         {CHC(0x58e2df6a), CHC(0x4795990e), CHC(0x42b5e0f7), CHC(0x6f408c64),
397*e5436536SAndroid Build Coastguard Worker          CHC(0x6370bebf), CHC(0x5c91ca85)},
398*e5436536SAndroid Build Coastguard Worker         {-1, -2, -5, -4, -8, -12},
399*e5436536SAndroid Build Coastguard Worker         {CHC(0x78a21ab7), CHC(0x66f951d6), CHC(0x594605bb), CHC(0x5ce91657)},
400*e5436536SAndroid Build Coastguard Worker         {-14, -7, -2, 0},
401*e5436536SAndroid Build Coastguard Worker     },
402*e5436536SAndroid Build Coastguard Worker     {
403*e5436536SAndroid Build Coastguard Worker         /* numBands=23 */
404*e5436536SAndroid Build Coastguard Worker         {CHC(0x6bf749b2), CHC(0x531b3348), CHC(0x6c12a750)},
405*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
406*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ef06b17), CHC(0x4990f6c9), CHC(0x47cd4c5b)},
407*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
408*e5436536SAndroid Build Coastguard Worker         {CHC(0x66dede36), CHC(0x7bdf90a9), CHC(0x4885b2b9), CHC(0x5188a6b7)},
409*e5436536SAndroid Build Coastguard Worker         {-14, -10, -5, -1},
410*e5436536SAndroid Build Coastguard Worker         {CHC(0x54f85812), CHC(0x446414ae), CHC(0x79c8d519), CHC(0x6a4c2f31),
411*e5436536SAndroid Build Coastguard Worker          CHC(0x5ac8325f), CHC(0x50bf9200)},
412*e5436536SAndroid Build Coastguard Worker         {-1, -2, -6, -4, -8, -12},
413*e5436536SAndroid Build Coastguard Worker         {CHC(0x66dede36), CHC(0x5be0d90e), CHC(0x535cc453), CHC(0x5b7923f0)},
414*e5436536SAndroid Build Coastguard Worker         {-14, -7, -2, 0},
415*e5436536SAndroid Build Coastguard Worker     },
416*e5436536SAndroid Build Coastguard Worker     {
417*e5436536SAndroid Build Coastguard Worker         /* numBands=24 */
418*e5436536SAndroid Build Coastguard Worker         {CHC(0x6bfbd91d), CHC(0x5329e580), CHC(0x6c14eeed)},
419*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
420*e5436536SAndroid Build Coastguard Worker         {CHC(0x5eea6179), CHC(0x498baa90), CHC(0x4845635d)},
421*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
422*e5436536SAndroid Build Coastguard Worker         {CHC(0x58559b7e), CHC(0x6f1b231f), CHC(0x43f1789b), CHC(0x4fc8fcb8)},
423*e5436536SAndroid Build Coastguard Worker         {-14, -10, -5, -1},
424*e5436536SAndroid Build Coastguard Worker         {CHC(0x51621775), CHC(0x417881a3), CHC(0x6f9ba9b6), CHC(0x65c412b2),
425*e5436536SAndroid Build Coastguard Worker          CHC(0x53352c61), CHC(0x46db9caf)},
426*e5436536SAndroid Build Coastguard Worker         {-1, -2, -6, -4, -8, -12},
427*e5436536SAndroid Build Coastguard Worker         {CHC(0x58559b7e), CHC(0x52636003), CHC(0x4e13b316), CHC(0x5a189cdf)},
428*e5436536SAndroid Build Coastguard Worker         {-14, -7, -2, 0},
429*e5436536SAndroid Build Coastguard Worker     },
430*e5436536SAndroid Build Coastguard Worker     {
431*e5436536SAndroid Build Coastguard Worker         /* numBands=25 */
432*e5436536SAndroid Build Coastguard Worker         {CHC(0x6bffdc73), CHC(0x5336d4af), CHC(0x6c16f084)},
433*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
434*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ee51249), CHC(0x498703cc), CHC(0x48b50e4f)},
435*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
436*e5436536SAndroid Build Coastguard Worker         {CHC(0x4c5616cf), CHC(0x641b9fad), CHC(0x7fa735e0), CHC(0x4e24e57a)},
437*e5436536SAndroid Build Coastguard Worker         {-14, -10, -6, -1},
438*e5436536SAndroid Build Coastguard Worker         {CHC(0x4e15f47a), CHC(0x7d9481d6), CHC(0x66a82f8a), CHC(0x619ae971),
439*e5436536SAndroid Build Coastguard Worker          CHC(0x4c8b2f5f), CHC(0x7d09ec11)},
440*e5436536SAndroid Build Coastguard Worker         {-1, -3, -6, -4, -8, -13},
441*e5436536SAndroid Build Coastguard Worker         {CHC(0x4c5616cf), CHC(0x4a3770fb), CHC(0x495402de), CHC(0x58c693fa)},
442*e5436536SAndroid Build Coastguard Worker         {-14, -7, -2, 0},
443*e5436536SAndroid Build Coastguard Worker     },
444*e5436536SAndroid Build Coastguard Worker     {
445*e5436536SAndroid Build Coastguard Worker         /* numBands=26 */
446*e5436536SAndroid Build Coastguard Worker         {CHC(0x6c036943), CHC(0x53424625), CHC(0x6c18b6dc)},
447*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
448*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ee060aa), CHC(0x4982e88a), CHC(0x491d277f)},
449*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
450*e5436536SAndroid Build Coastguard Worker         {CHC(0x425ada5b), CHC(0x5a9368ac), CHC(0x78380a42), CHC(0x4c99aa05)},
451*e5436536SAndroid Build Coastguard Worker         {-14, -10, -6, -1},
452*e5436536SAndroid Build Coastguard Worker         {CHC(0x4b0b569c), CHC(0x78a420da), CHC(0x5ebdf203), CHC(0x5dc57e63),
453*e5436536SAndroid Build Coastguard Worker          CHC(0x46a650ff), CHC(0x6ee13fb8)},
454*e5436536SAndroid Build Coastguard Worker         {-1, -3, -6, -4, -8, -13},
455*e5436536SAndroid Build Coastguard Worker         {CHC(0x425ada5b), CHC(0x4323073c), CHC(0x450ae92b), CHC(0x57822ad5)},
456*e5436536SAndroid Build Coastguard Worker         {-14, -7, -2, 0},
457*e5436536SAndroid Build Coastguard Worker     },
458*e5436536SAndroid Build Coastguard Worker     {
459*e5436536SAndroid Build Coastguard Worker         /* numBands=27 */
460*e5436536SAndroid Build Coastguard Worker         {CHC(0x6c06911a), CHC(0x534c7261), CHC(0x6c1a4aba)},
461*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
462*e5436536SAndroid Build Coastguard Worker         {CHC(0x5edc3524), CHC(0x497f43c0), CHC(0x497e6cd8)},
463*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
464*e5436536SAndroid Build Coastguard Worker         {CHC(0x73fb550e), CHC(0x5244894f), CHC(0x717aad78), CHC(0x4b24ef6c)},
465*e5436536SAndroid Build Coastguard Worker         {-15, -10, -6, -1},
466*e5436536SAndroid Build Coastguard Worker         {CHC(0x483aebe4), CHC(0x74139116), CHC(0x57b58037), CHC(0x5a3a4f3c),
467*e5436536SAndroid Build Coastguard Worker          CHC(0x416950fe), CHC(0x62c7f4f2)},
468*e5436536SAndroid Build Coastguard Worker         {-1, -3, -6, -4, -8, -13},
469*e5436536SAndroid Build Coastguard Worker         {CHC(0x73fb550e), CHC(0x79efb994), CHC(0x4128cab7), CHC(0x564a919a)},
470*e5436536SAndroid Build Coastguard Worker         {-15, -8, -2, 0},
471*e5436536SAndroid Build Coastguard Worker     },
472*e5436536SAndroid Build Coastguard Worker     {
473*e5436536SAndroid Build Coastguard Worker         /* numBands=28 */
474*e5436536SAndroid Build Coastguard Worker         {CHC(0x6c096264), CHC(0x535587cd), CHC(0x6c1bb355)},
475*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
476*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ed87c76), CHC(0x497c0439), CHC(0x49d98452)},
477*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
478*e5436536SAndroid Build Coastguard Worker         {CHC(0x65dec5bf), CHC(0x4afd1ba3), CHC(0x6b58b4b3), CHC(0x49c4a7b0)},
479*e5436536SAndroid Build Coastguard Worker         {-15, -10, -6, -1},
480*e5436536SAndroid Build Coastguard Worker         {CHC(0x459e6eb1), CHC(0x6fd850b7), CHC(0x516e7be9), CHC(0x56f13d05),
481*e5436536SAndroid Build Coastguard Worker          CHC(0x79785594), CHC(0x58617de7)},
482*e5436536SAndroid Build Coastguard Worker         {-1, -3, -6, -4, -9, -13},
483*e5436536SAndroid Build Coastguard Worker         {CHC(0x65dec5bf), CHC(0x6f2168aa), CHC(0x7b41310f), CHC(0x551f0692)},
484*e5436536SAndroid Build Coastguard Worker         {-15, -8, -3, 0},
485*e5436536SAndroid Build Coastguard Worker     },
486*e5436536SAndroid Build Coastguard Worker     {
487*e5436536SAndroid Build Coastguard Worker         /* numBands=29 */
488*e5436536SAndroid Build Coastguard Worker         {CHC(0x6c0be913), CHC(0x535dacd5), CHC(0x6c1cf6a3)},
489*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
490*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ed526b4), CHC(0x49791bc5), CHC(0x4a2eff99)},
491*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
492*e5436536SAndroid Build Coastguard Worker         {CHC(0x59e44afe), CHC(0x44949ada), CHC(0x65bf36f5), CHC(0x487705a0)},
493*e5436536SAndroid Build Coastguard Worker         {-15, -10, -6, -1},
494*e5436536SAndroid Build Coastguard Worker         {CHC(0x43307779), CHC(0x6be959c4), CHC(0x4bce2122), CHC(0x53e34d89),
495*e5436536SAndroid Build Coastguard Worker          CHC(0x7115ff82), CHC(0x4f6421a1)},
496*e5436536SAndroid Build Coastguard Worker         {-1, -3, -6, -4, -9, -13},
497*e5436536SAndroid Build Coastguard Worker         {CHC(0x59e44afe), CHC(0x659eab7d), CHC(0x74cea459), CHC(0x53fed574)},
498*e5436536SAndroid Build Coastguard Worker         {-15, -8, -3, 0},
499*e5436536SAndroid Build Coastguard Worker     },
500*e5436536SAndroid Build Coastguard Worker     {
501*e5436536SAndroid Build Coastguard Worker         /* numBands=30 */
502*e5436536SAndroid Build Coastguard Worker         {CHC(0x6c0e2f17), CHC(0x53650181), CHC(0x6c1e199d)},
503*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
504*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ed2269f), CHC(0x49767e9e), CHC(0x4a7f5f0b)},
505*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
506*e5436536SAndroid Build Coastguard Worker         {CHC(0x4faa4ae6), CHC(0x7dd3bf11), CHC(0x609e2732), CHC(0x473a72e9)},
507*e5436536SAndroid Build Coastguard Worker         {-15, -11, -6, -1},
508*e5436536SAndroid Build Coastguard Worker         {CHC(0x40ec57c6), CHC(0x683ee147), CHC(0x46be261d), CHC(0x510a7983),
509*e5436536SAndroid Build Coastguard Worker          CHC(0x698a84cb), CHC(0x4794a927)},
510*e5436536SAndroid Build Coastguard Worker         {-1, -3, -6, -4, -9, -13},
511*e5436536SAndroid Build Coastguard Worker         {CHC(0x4faa4ae6), CHC(0x5d3615ad), CHC(0x6ee74773), CHC(0x52e956a1)},
512*e5436536SAndroid Build Coastguard Worker         {-15, -8, -3, 0},
513*e5436536SAndroid Build Coastguard Worker     },
514*e5436536SAndroid Build Coastguard Worker     {
515*e5436536SAndroid Build Coastguard Worker         /* numBands=31 */
516*e5436536SAndroid Build Coastguard Worker         {CHC(0x6c103cc9), CHC(0x536ba0ac), CHC(0x6c1f2070)},
517*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
518*e5436536SAndroid Build Coastguard Worker         {CHC(0x5ecf711e), CHC(0x497422ea), CHC(0x4acb1438)},
519*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
520*e5436536SAndroid Build Coastguard Worker         {CHC(0x46e322ad), CHC(0x73c32f3c), CHC(0x5be7d172), CHC(0x460d8800)},
521*e5436536SAndroid Build Coastguard Worker         {-15, -11, -6, -1},
522*e5436536SAndroid Build Coastguard Worker         {CHC(0x7d9bf8ad), CHC(0x64d22351), CHC(0x422bdc81), CHC(0x4e6184aa),
523*e5436536SAndroid Build Coastguard Worker          CHC(0x62ba2375), CHC(0x40c325de)},
524*e5436536SAndroid Build Coastguard Worker         {-2, -3, -6, -4, -9, -13},
525*e5436536SAndroid Build Coastguard Worker         {CHC(0x46e322ad), CHC(0x55bef2a3), CHC(0x697b3135), CHC(0x51ddee4d)},
526*e5436536SAndroid Build Coastguard Worker         {-15, -8, -3, 0},
527*e5436536SAndroid Build Coastguard Worker     },
528*e5436536SAndroid Build Coastguard Worker     {
529*e5436536SAndroid Build Coastguard Worker         // numBands=32
530*e5436536SAndroid Build Coastguard Worker         {CHC(0x6c121933), CHC(0x5371a104), CHC(0x6c200ea0)},
531*e5436536SAndroid Build Coastguard Worker         {-1, 0, 0},
532*e5436536SAndroid Build Coastguard Worker         {CHC(0x5eccfcd3), CHC(0x49720060), CHC(0x4b1283f0)},
533*e5436536SAndroid Build Coastguard Worker         {3, 4, 2},
534*e5436536SAndroid Build Coastguard Worker         {CHC(0x7ea12a52), CHC(0x6aca3303), CHC(0x579072bf), CHC(0x44ef056e)},
535*e5436536SAndroid Build Coastguard Worker         {-16, -11, -6, -1},
536*e5436536SAndroid Build Coastguard Worker         {CHC(0x79a3a9ab), CHC(0x619d38fc), CHC(0x7c0f0734), CHC(0x4be3dd5d),
537*e5436536SAndroid Build Coastguard Worker          CHC(0x5c8d7163), CHC(0x7591065f)},
538*e5436536SAndroid Build Coastguard Worker         {-2, -3, -7, -4, -9, -14},
539*e5436536SAndroid Build Coastguard Worker         {CHC(0x7ea12a52), CHC(0x4f1782a6), CHC(0x647cbcb2), CHC(0x50dc0bb1)},
540*e5436536SAndroid Build Coastguard Worker         {-16, -8, -3, 0},
541*e5436536SAndroid Build Coastguard Worker     },
542*e5436536SAndroid Build Coastguard Worker };
543*e5436536SAndroid Build Coastguard Worker 
544*e5436536SAndroid Build Coastguard Worker /** \def  SUM_SAFETY
545*e5436536SAndroid Build Coastguard Worker  *
546*e5436536SAndroid Build Coastguard Worker  *  SUM_SAFTEY defines the bits needed to right-shift every summand in
547*e5436536SAndroid Build Coastguard Worker  *  order to be overflow-safe. In the two backsubst functions we sum up 4
548*e5436536SAndroid Build Coastguard Worker  *  values. Since one of which is definitely not MAXVAL_DBL (the L[x][y]),
549*e5436536SAndroid Build Coastguard Worker  *  we spare just 2 safety bits instead of 3.
550*e5436536SAndroid Build Coastguard Worker  */
551*e5436536SAndroid Build Coastguard Worker #define SUM_SAFETY 2
552*e5436536SAndroid Build Coastguard Worker 
553*e5436536SAndroid Build Coastguard Worker /**
554*e5436536SAndroid Build Coastguard Worker  * \brief  Solves L*x=b via backsubstitution according to the following
555*e5436536SAndroid Build Coastguard Worker  * structure:
556*e5436536SAndroid Build Coastguard Worker  *
557*e5436536SAndroid Build Coastguard Worker  *  x[0] =  b[0];
558*e5436536SAndroid Build Coastguard Worker  *  x[1] = (b[1]                               - x[0]) / L[1][1];
559*e5436536SAndroid Build Coastguard Worker  *  x[2] = (b[2] - x[1]*L[2][1]                - x[0]) / L[2][2];
560*e5436536SAndroid Build Coastguard Worker  *  x[3] = (b[3] - x[2]*L[3][2] - x[1]*L[3][1] - x[0]) / L[3][3];
561*e5436536SAndroid Build Coastguard Worker  *
562*e5436536SAndroid Build Coastguard Worker  * \param[in]  numBands  SBR crossover band index
563*e5436536SAndroid Build Coastguard Worker  * \param[in]  b         the b in L*x=b (one-dimensional)
564*e5436536SAndroid Build Coastguard Worker  * \param[out] x         output polynomial coefficients (mantissa)
565*e5436536SAndroid Build Coastguard Worker  * \param[out] x_sf      exponents of x[]
566*e5436536SAndroid Build Coastguard Worker  */
backsubst_fw(const int numBands,const FIXP_DBL * const b,FIXP_DBL * RESTRICT x,int * RESTRICT x_sf)567*e5436536SAndroid Build Coastguard Worker static void backsubst_fw(const int numBands, const FIXP_DBL *const b,
568*e5436536SAndroid Build Coastguard Worker                          FIXP_DBL *RESTRICT x, int *RESTRICT x_sf) {
569*e5436536SAndroid Build Coastguard Worker   int i, k;
570*e5436536SAndroid Build Coastguard Worker   int m; /* the trip counter that indexes incrementally through Lnorm1d[] */
571*e5436536SAndroid Build Coastguard Worker 
572*e5436536SAndroid Build Coastguard Worker   const FIXP_CHB *RESTRICT pLnorm1d = bsd[numBands - BSD_IDX_OFFSET].Lnorm1d;
573*e5436536SAndroid Build Coastguard Worker   const SCHAR *RESTRICT pLnorm1d_sf = bsd[numBands - BSD_IDX_OFFSET].Lnorm1d_sf;
574*e5436536SAndroid Build Coastguard Worker   const FIXP_CHB *RESTRICT pLnormii = bsd[numBands - BSD_IDX_OFFSET].Lnormii;
575*e5436536SAndroid Build Coastguard Worker   const SCHAR *RESTRICT pLnormii_sf = bsd[numBands - BSD_IDX_OFFSET].Lnormii_sf;
576*e5436536SAndroid Build Coastguard Worker 
577*e5436536SAndroid Build Coastguard Worker   x[0] = b[0];
578*e5436536SAndroid Build Coastguard Worker 
579*e5436536SAndroid Build Coastguard Worker   for (i = 1, m = 0; i <= POLY_ORDER; ++i) {
580*e5436536SAndroid Build Coastguard Worker     FIXP_DBL sum = b[i] >> SUM_SAFETY;
581*e5436536SAndroid Build Coastguard Worker     int sum_sf = x_sf[i];
582*e5436536SAndroid Build Coastguard Worker     for (k = i - 1; k > 0; --k, ++m) {
583*e5436536SAndroid Build Coastguard Worker       int e;
584*e5436536SAndroid Build Coastguard Worker       FIXP_DBL mult = fMultNorm(FX_CHB2FX_DBL(pLnorm1d[m]), x[k], &e);
585*e5436536SAndroid Build Coastguard Worker       int mult_sf = pLnorm1d_sf[m] + x_sf[k] + e;
586*e5436536SAndroid Build Coastguard Worker 
587*e5436536SAndroid Build Coastguard Worker       /* check if the new summand mult has a different sf than the sum currently
588*e5436536SAndroid Build Coastguard Worker        * has */
589*e5436536SAndroid Build Coastguard Worker       int diff = mult_sf - sum_sf;
590*e5436536SAndroid Build Coastguard Worker 
591*e5436536SAndroid Build Coastguard Worker       if (diff > 0) {
592*e5436536SAndroid Build Coastguard Worker         /* yes, and it requires the sum to be adjusted (scaled down) */
593*e5436536SAndroid Build Coastguard Worker         sum >>= diff;
594*e5436536SAndroid Build Coastguard Worker         sum_sf = mult_sf;
595*e5436536SAndroid Build Coastguard Worker       } else if (diff < 0) {
596*e5436536SAndroid Build Coastguard Worker         /* yes, but here mult needs to be scaled down */
597*e5436536SAndroid Build Coastguard Worker         mult >>= -diff;
598*e5436536SAndroid Build Coastguard Worker       }
599*e5436536SAndroid Build Coastguard Worker       sum -= (mult >> SUM_SAFETY);
600*e5436536SAndroid Build Coastguard Worker     }
601*e5436536SAndroid Build Coastguard Worker 
602*e5436536SAndroid Build Coastguard Worker     /* - x[0] */
603*e5436536SAndroid Build Coastguard Worker     if (x_sf[0] > sum_sf) {
604*e5436536SAndroid Build Coastguard Worker       sum >>= (x_sf[0] - sum_sf);
605*e5436536SAndroid Build Coastguard Worker       sum_sf = x_sf[0];
606*e5436536SAndroid Build Coastguard Worker     }
607*e5436536SAndroid Build Coastguard Worker     sum -= (x[0] >> (sum_sf - x_sf[0] + SUM_SAFETY));
608*e5436536SAndroid Build Coastguard Worker 
609*e5436536SAndroid Build Coastguard Worker     /* instead of the division /L[i][i], we multiply by the inverse */
610*e5436536SAndroid Build Coastguard Worker     int e;
611*e5436536SAndroid Build Coastguard Worker     x[i] = fMultNorm(sum, FX_CHB2FX_DBL(pLnormii[i - 1]), &e);
612*e5436536SAndroid Build Coastguard Worker     x_sf[i] = sum_sf + pLnormii_sf[i - 1] + e + SUM_SAFETY;
613*e5436536SAndroid Build Coastguard Worker   }
614*e5436536SAndroid Build Coastguard Worker }
615*e5436536SAndroid Build Coastguard Worker 
616*e5436536SAndroid Build Coastguard Worker /**
617*e5436536SAndroid Build Coastguard Worker  * \brief Solves L*x=b via backsubstitution according to the following
618*e5436536SAndroid Build Coastguard Worker  * structure:
619*e5436536SAndroid Build Coastguard Worker  *
620*e5436536SAndroid Build Coastguard Worker  *  x[3] = b[3];
621*e5436536SAndroid Build Coastguard Worker  *  x[2] = b[2] - L[2][3]*x[3];
622*e5436536SAndroid Build Coastguard Worker  *  x[1] = b[1] - L[1][2]*x[2] - L[1][3]*x[3];
623*e5436536SAndroid Build Coastguard Worker  *  x[0] = b[0] - L[0][1]*x[1] - L[0][2]*x[2] - L[0][3]*x[3];
624*e5436536SAndroid Build Coastguard Worker  *
625*e5436536SAndroid Build Coastguard Worker  * \param[in]  numBands  SBR crossover band index
626*e5436536SAndroid Build Coastguard Worker  * \param[in]  b         the b in L*x=b (one-dimensional)
627*e5436536SAndroid Build Coastguard Worker  * \param[out] x         solution vector
628*e5436536SAndroid Build Coastguard Worker  * \param[out] x_sf      exponents of x[]
629*e5436536SAndroid Build Coastguard Worker  */
backsubst_bw(const int numBands,const FIXP_DBL * const b,FIXP_DBL * RESTRICT x,int * RESTRICT x_sf)630*e5436536SAndroid Build Coastguard Worker static void backsubst_bw(const int numBands, const FIXP_DBL *const b,
631*e5436536SAndroid Build Coastguard Worker                          FIXP_DBL *RESTRICT x, int *RESTRICT x_sf) {
632*e5436536SAndroid Build Coastguard Worker   int i, k;
633*e5436536SAndroid Build Coastguard Worker   int m; /* the trip counter that indexes incrementally through LnormInv1d[] */
634*e5436536SAndroid Build Coastguard Worker 
635*e5436536SAndroid Build Coastguard Worker   const FIXP_CHB *RESTRICT pLnormInv1d =
636*e5436536SAndroid Build Coastguard Worker       bsd[numBands - BSD_IDX_OFFSET].LnormInv1d;
637*e5436536SAndroid Build Coastguard Worker   const SCHAR *RESTRICT pLnormInv1d_sf =
638*e5436536SAndroid Build Coastguard Worker       bsd[numBands - BSD_IDX_OFFSET].LnormInv1d_sf;
639*e5436536SAndroid Build Coastguard Worker 
640*e5436536SAndroid Build Coastguard Worker   x[POLY_ORDER] = b[POLY_ORDER];
641*e5436536SAndroid Build Coastguard Worker 
642*e5436536SAndroid Build Coastguard Worker   for (i = POLY_ORDER - 1, m = 0; i >= 0; i--) {
643*e5436536SAndroid Build Coastguard Worker     FIXP_DBL sum = b[i] >> SUM_SAFETY;
644*e5436536SAndroid Build Coastguard Worker     int sum_sf = x_sf[i]; /* sum's sf but disregarding SUM_SAFETY (added at the
645*e5436536SAndroid Build Coastguard Worker                              iteration's end) */
646*e5436536SAndroid Build Coastguard Worker 
647*e5436536SAndroid Build Coastguard Worker     for (k = i + 1; k <= POLY_ORDER; ++k, ++m) {
648*e5436536SAndroid Build Coastguard Worker       int e;
649*e5436536SAndroid Build Coastguard Worker       FIXP_DBL mult = fMultNorm(FX_CHB2FX_DBL(pLnormInv1d[m]), x[k], &e);
650*e5436536SAndroid Build Coastguard Worker       int mult_sf = pLnormInv1d_sf[m] + x_sf[k] + e;
651*e5436536SAndroid Build Coastguard Worker 
652*e5436536SAndroid Build Coastguard Worker       /* check if the new summand mult has a different sf than sum currently has
653*e5436536SAndroid Build Coastguard Worker        */
654*e5436536SAndroid Build Coastguard Worker       int diff = mult_sf - sum_sf;
655*e5436536SAndroid Build Coastguard Worker 
656*e5436536SAndroid Build Coastguard Worker       if (diff > 0) {
657*e5436536SAndroid Build Coastguard Worker         /* yes, and it requires the sum v to be adjusted (scaled down) */
658*e5436536SAndroid Build Coastguard Worker         sum >>= diff;
659*e5436536SAndroid Build Coastguard Worker         sum_sf = mult_sf;
660*e5436536SAndroid Build Coastguard Worker       } else if (diff < 0) {
661*e5436536SAndroid Build Coastguard Worker         /* yes, but here mult needs to be scaled down */
662*e5436536SAndroid Build Coastguard Worker         mult >>= -diff;
663*e5436536SAndroid Build Coastguard Worker       }
664*e5436536SAndroid Build Coastguard Worker 
665*e5436536SAndroid Build Coastguard Worker       /* mult has now the same sf than what it is about to be added to. */
666*e5436536SAndroid Build Coastguard Worker       /* scale mult down additionally so that building the sum is overflow-safe.
667*e5436536SAndroid Build Coastguard Worker        */
668*e5436536SAndroid Build Coastguard Worker       sum -= (mult >> SUM_SAFETY);
669*e5436536SAndroid Build Coastguard Worker     }
670*e5436536SAndroid Build Coastguard Worker 
671*e5436536SAndroid Build Coastguard Worker     x_sf[i] = sum_sf + SUM_SAFETY;
672*e5436536SAndroid Build Coastguard Worker     x[i] = sum;
673*e5436536SAndroid Build Coastguard Worker   }
674*e5436536SAndroid Build Coastguard Worker }
675*e5436536SAndroid Build Coastguard Worker 
676*e5436536SAndroid Build Coastguard Worker /**
677*e5436536SAndroid Build Coastguard Worker  * \brief  Solves a system of linear equations (L*x=b) with the Cholesky
678*e5436536SAndroid Build Coastguard Worker  * algorithm.
679*e5436536SAndroid Build Coastguard Worker  *
680*e5436536SAndroid Build Coastguard Worker  * \param[in]     numBands  SBR crossover band index
681*e5436536SAndroid Build Coastguard Worker  * \param[in,out] b         input: vector b, output: solution vector p.
682*e5436536SAndroid Build Coastguard Worker  * \param[in,out] b_sf      input: exponent of b; output: exponent of solution
683*e5436536SAndroid Build Coastguard Worker  * p.
684*e5436536SAndroid Build Coastguard Worker  */
choleskySolve(const int numBands,FIXP_DBL * RESTRICT b,int * RESTRICT b_sf)685*e5436536SAndroid Build Coastguard Worker static void choleskySolve(const int numBands, FIXP_DBL *RESTRICT b,
686*e5436536SAndroid Build Coastguard Worker                           int *RESTRICT b_sf) {
687*e5436536SAndroid Build Coastguard Worker   int i, e;
688*e5436536SAndroid Build Coastguard Worker 
689*e5436536SAndroid Build Coastguard Worker   const FIXP_CHB *RESTRICT pBmul0 = bsd[numBands - BSD_IDX_OFFSET].Bmul0;
690*e5436536SAndroid Build Coastguard Worker   const SCHAR *RESTRICT pBmul0_sf = bsd[numBands - BSD_IDX_OFFSET].Bmul0_sf;
691*e5436536SAndroid Build Coastguard Worker   const FIXP_CHB *RESTRICT pBmul1 = bsd[numBands - BSD_IDX_OFFSET].Bmul1;
692*e5436536SAndroid Build Coastguard Worker   const SCHAR *RESTRICT pBmul1_sf = bsd[numBands - BSD_IDX_OFFSET].Bmul1_sf;
693*e5436536SAndroid Build Coastguard Worker 
694*e5436536SAndroid Build Coastguard Worker   /* normalize b */
695*e5436536SAndroid Build Coastguard Worker   FIXP_DBL bnormed[POLY_ORDER + 1];
696*e5436536SAndroid Build Coastguard Worker   for (i = 0; i <= POLY_ORDER; ++i) {
697*e5436536SAndroid Build Coastguard Worker     bnormed[i] = fMultNorm(b[i], FX_CHB2FX_DBL(pBmul0[i]), &e);
698*e5436536SAndroid Build Coastguard Worker     b_sf[i] += pBmul0_sf[i] + e;
699*e5436536SAndroid Build Coastguard Worker   }
700*e5436536SAndroid Build Coastguard Worker 
701*e5436536SAndroid Build Coastguard Worker   backsubst_fw(numBands, bnormed, b, b_sf);
702*e5436536SAndroid Build Coastguard Worker 
703*e5436536SAndroid Build Coastguard Worker   /* normalize b again */
704*e5436536SAndroid Build Coastguard Worker   for (i = 0; i <= POLY_ORDER; ++i) {
705*e5436536SAndroid Build Coastguard Worker     bnormed[i] = fMultNorm(b[i], FX_CHB2FX_DBL(pBmul1[i]), &e);
706*e5436536SAndroid Build Coastguard Worker     b_sf[i] += pBmul1_sf[i] + e;
707*e5436536SAndroid Build Coastguard Worker   }
708*e5436536SAndroid Build Coastguard Worker 
709*e5436536SAndroid Build Coastguard Worker   backsubst_bw(numBands, bnormed, b, b_sf);
710*e5436536SAndroid Build Coastguard Worker }
711*e5436536SAndroid Build Coastguard Worker 
712*e5436536SAndroid Build Coastguard Worker /**
713*e5436536SAndroid Build Coastguard Worker  * \brief  Find polynomial approximation of vector y with implicit abscisas
714*e5436536SAndroid Build Coastguard Worker  * x=0,1,2,3..n-1
715*e5436536SAndroid Build Coastguard Worker  *
716*e5436536SAndroid Build Coastguard Worker  *  The problem (V^T * V * p = V^T * y) is solved with Cholesky.
717*e5436536SAndroid Build Coastguard Worker  *  V is the Vandermode Matrix constructed with x = 0...n-1;
718*e5436536SAndroid Build Coastguard Worker  *  A = V^T * V; b = V^T * y;
719*e5436536SAndroid Build Coastguard Worker  *
720*e5436536SAndroid Build Coastguard Worker  * \param[in]  numBands  SBR crossover band index (BSD_IDX_OFFSET <= numBands <=
721*e5436536SAndroid Build Coastguard Worker  * MAXLOWBANDS)
722*e5436536SAndroid Build Coastguard Worker  * \param[in]  y         input vector (mantissa)
723*e5436536SAndroid Build Coastguard Worker  * \param[in]  y_sf      exponents of y[]
724*e5436536SAndroid Build Coastguard Worker  * \param[out] p         output polynomial coefficients (mantissa)
725*e5436536SAndroid Build Coastguard Worker  * \param[out] p_sf      exponents of p[]
726*e5436536SAndroid Build Coastguard Worker  */
polyfit(const int numBands,const FIXP_DBL * const y,const int y_sf,FIXP_DBL * RESTRICT p,int * RESTRICT p_sf)727*e5436536SAndroid Build Coastguard Worker static void polyfit(const int numBands, const FIXP_DBL *const y, const int y_sf,
728*e5436536SAndroid Build Coastguard Worker                     FIXP_DBL *RESTRICT p, int *RESTRICT p_sf) {
729*e5436536SAndroid Build Coastguard Worker   int i, k;
730*e5436536SAndroid Build Coastguard Worker   LONG v[POLY_ORDER + 1];
731*e5436536SAndroid Build Coastguard Worker   int sum_saftey = getLog2[numBands - 1];
732*e5436536SAndroid Build Coastguard Worker 
733*e5436536SAndroid Build Coastguard Worker   FDK_ASSERT((numBands >= BSD_IDX_OFFSET) && (numBands <= MAXLOWBANDS));
734*e5436536SAndroid Build Coastguard Worker 
735*e5436536SAndroid Build Coastguard Worker   /* construct vector b[] temporarily stored in array p[] */
736*e5436536SAndroid Build Coastguard Worker   FDKmemclear(p, (POLY_ORDER + 1) * sizeof(FIXP_DBL));
737*e5436536SAndroid Build Coastguard Worker 
738*e5436536SAndroid Build Coastguard Worker   /* p[] are the sums over n values and each p[i] has its own sf */
739*e5436536SAndroid Build Coastguard Worker   for (i = 0; i <= POLY_ORDER; ++i) p_sf[i] = 1 - DFRACT_BITS;
740*e5436536SAndroid Build Coastguard Worker 
741*e5436536SAndroid Build Coastguard Worker   for (k = 0; k < numBands; k++) {
742*e5436536SAndroid Build Coastguard Worker     v[0] = (LONG)1;
743*e5436536SAndroid Build Coastguard Worker     for (i = 1; i <= POLY_ORDER; i++) {
744*e5436536SAndroid Build Coastguard Worker       v[i] = k * v[i - 1];
745*e5436536SAndroid Build Coastguard Worker     }
746*e5436536SAndroid Build Coastguard Worker 
747*e5436536SAndroid Build Coastguard Worker     for (i = 0; i <= POLY_ORDER; i++) {
748*e5436536SAndroid Build Coastguard Worker       if (v[POLY_ORDER - i] != 0 && y[k] != FIXP_DBL(0)) {
749*e5436536SAndroid Build Coastguard Worker         int e;
750*e5436536SAndroid Build Coastguard Worker         FIXP_DBL mult = fMultNorm((FIXP_DBL)v[POLY_ORDER - i], y[k], &e);
751*e5436536SAndroid Build Coastguard Worker         int sf = DFRACT_BITS - 1 + y_sf + e;
752*e5436536SAndroid Build Coastguard Worker 
753*e5436536SAndroid Build Coastguard Worker         /* check if the new summand has a different sf than the sum p[i]
754*e5436536SAndroid Build Coastguard Worker          * currently has */
755*e5436536SAndroid Build Coastguard Worker         int diff = sf - p_sf[i];
756*e5436536SAndroid Build Coastguard Worker 
757*e5436536SAndroid Build Coastguard Worker         if (diff > 0) {
758*e5436536SAndroid Build Coastguard Worker           /* yes, and it requires the sum p[i] to be adjusted (scaled down) */
759*e5436536SAndroid Build Coastguard Worker           p[i] >>= fMin(DFRACT_BITS - 1, diff);
760*e5436536SAndroid Build Coastguard Worker           p_sf[i] = sf;
761*e5436536SAndroid Build Coastguard Worker         } else if (diff < 0) {
762*e5436536SAndroid Build Coastguard Worker           /* yes, but here mult needs to be scaled down */
763*e5436536SAndroid Build Coastguard Worker           mult >>= -diff;
764*e5436536SAndroid Build Coastguard Worker         }
765*e5436536SAndroid Build Coastguard Worker 
766*e5436536SAndroid Build Coastguard Worker         /* mult has now the same sf than what it is about to be added to.
767*e5436536SAndroid Build Coastguard Worker            scale mult down additionally so that building the sum is
768*e5436536SAndroid Build Coastguard Worker            overflow-safe. */
769*e5436536SAndroid Build Coastguard Worker         p[i] += mult >> sum_saftey;
770*e5436536SAndroid Build Coastguard Worker       }
771*e5436536SAndroid Build Coastguard Worker     }
772*e5436536SAndroid Build Coastguard Worker   }
773*e5436536SAndroid Build Coastguard Worker 
774*e5436536SAndroid Build Coastguard Worker   p_sf[0] += sum_saftey;
775*e5436536SAndroid Build Coastguard Worker   p_sf[1] += sum_saftey;
776*e5436536SAndroid Build Coastguard Worker   p_sf[2] += sum_saftey;
777*e5436536SAndroid Build Coastguard Worker   p_sf[3] += sum_saftey;
778*e5436536SAndroid Build Coastguard Worker 
779*e5436536SAndroid Build Coastguard Worker   choleskySolve(numBands, p, p_sf);
780*e5436536SAndroid Build Coastguard Worker }
781*e5436536SAndroid Build Coastguard Worker 
782*e5436536SAndroid Build Coastguard Worker /**
783*e5436536SAndroid Build Coastguard Worker  * \brief  Calculates the output of a POLY_ORDER-degree polynomial function
784*e5436536SAndroid Build Coastguard Worker  *         with Horner scheme:
785*e5436536SAndroid Build Coastguard Worker  *
786*e5436536SAndroid Build Coastguard Worker  *         y(x) = p3 + p2*x + p1*x^2 + p0*x^3
787*e5436536SAndroid Build Coastguard Worker  *              = p3 + x*(p2 + x*(p1 + x*p0))
788*e5436536SAndroid Build Coastguard Worker  *
789*e5436536SAndroid Build Coastguard Worker  *         The for loop iterates through the mult/add parts in y(x) as above,
790*e5436536SAndroid Build Coastguard Worker  *         during which regular upscaling ensures a stable exponent of the
791*e5436536SAndroid Build Coastguard Worker  *         result.
792*e5436536SAndroid Build Coastguard Worker  *
793*e5436536SAndroid Build Coastguard Worker  * \param[in]  p       coefficients as in y(x)
794*e5436536SAndroid Build Coastguard Worker  * \param[in]  p_sf    exponents of p[]
795*e5436536SAndroid Build Coastguard Worker  * \param[in]  x_int   non-fractional integer representation of x as in y(x)
796*e5436536SAndroid Build Coastguard Worker  * \param[out] out_sf  exponent of return value
797*e5436536SAndroid Build Coastguard Worker  *
798*e5436536SAndroid Build Coastguard Worker  * \return             result y(x)
799*e5436536SAndroid Build Coastguard Worker  */
polyval(const FIXP_DBL * const p,const int * const p_sf,const int x_int,int * out_sf)800*e5436536SAndroid Build Coastguard Worker static FIXP_DBL polyval(const FIXP_DBL *const p, const int *const p_sf,
801*e5436536SAndroid Build Coastguard Worker                         const int x_int, int *out_sf) {
802*e5436536SAndroid Build Coastguard Worker   FDK_ASSERT(x_int <= 31); /* otherwise getLog2[] needs more elements */
803*e5436536SAndroid Build Coastguard Worker 
804*e5436536SAndroid Build Coastguard Worker   int k, x_sf;
805*e5436536SAndroid Build Coastguard Worker   int result_sf;   /* working space to compute return value *out_sf */
806*e5436536SAndroid Build Coastguard Worker   FIXP_DBL x;      /* fractional value of x_int */
807*e5436536SAndroid Build Coastguard Worker   FIXP_DBL result; /* return value */
808*e5436536SAndroid Build Coastguard Worker 
809*e5436536SAndroid Build Coastguard Worker   /* if x == 0, then y(x) is just p3 */
810*e5436536SAndroid Build Coastguard Worker   if (x_int != 0) {
811*e5436536SAndroid Build Coastguard Worker     x_sf = getLog2[x_int];
812*e5436536SAndroid Build Coastguard Worker     x = (FIXP_DBL)x_int << (DFRACT_BITS - 1 - x_sf);
813*e5436536SAndroid Build Coastguard Worker   } else {
814*e5436536SAndroid Build Coastguard Worker     *out_sf = p_sf[3];
815*e5436536SAndroid Build Coastguard Worker     return p[3];
816*e5436536SAndroid Build Coastguard Worker   }
817*e5436536SAndroid Build Coastguard Worker 
818*e5436536SAndroid Build Coastguard Worker   result = p[0];
819*e5436536SAndroid Build Coastguard Worker   result_sf = p_sf[0];
820*e5436536SAndroid Build Coastguard Worker 
821*e5436536SAndroid Build Coastguard Worker   for (k = 1; k <= POLY_ORDER; ++k) {
822*e5436536SAndroid Build Coastguard Worker     FIXP_DBL mult = fMult(x, result);
823*e5436536SAndroid Build Coastguard Worker     int mult_sf = x_sf + result_sf;
824*e5436536SAndroid Build Coastguard Worker 
825*e5436536SAndroid Build Coastguard Worker     int room = CountLeadingBits(mult);
826*e5436536SAndroid Build Coastguard Worker     mult <<= room;
827*e5436536SAndroid Build Coastguard Worker     mult_sf -= room;
828*e5436536SAndroid Build Coastguard Worker 
829*e5436536SAndroid Build Coastguard Worker     FIXP_DBL pp = p[k];
830*e5436536SAndroid Build Coastguard Worker     int pp_sf = p_sf[k];
831*e5436536SAndroid Build Coastguard Worker 
832*e5436536SAndroid Build Coastguard Worker     /* equalize the shift factors of pp and mult so that we can sum them up */
833*e5436536SAndroid Build Coastguard Worker     int diff = pp_sf - mult_sf;
834*e5436536SAndroid Build Coastguard Worker 
835*e5436536SAndroid Build Coastguard Worker     if (diff > 0) {
836*e5436536SAndroid Build Coastguard Worker       diff = fMin(diff, DFRACT_BITS - 1);
837*e5436536SAndroid Build Coastguard Worker       mult >>= diff;
838*e5436536SAndroid Build Coastguard Worker     } else if (diff < 0) {
839*e5436536SAndroid Build Coastguard Worker       diff = fMax(diff, 1 - DFRACT_BITS);
840*e5436536SAndroid Build Coastguard Worker       pp >>= -diff;
841*e5436536SAndroid Build Coastguard Worker     }
842*e5436536SAndroid Build Coastguard Worker 
843*e5436536SAndroid Build Coastguard Worker     /* downshift by 1 to ensure safe summation */
844*e5436536SAndroid Build Coastguard Worker     mult >>= 1;
845*e5436536SAndroid Build Coastguard Worker     mult_sf++;
846*e5436536SAndroid Build Coastguard Worker     pp >>= 1;
847*e5436536SAndroid Build Coastguard Worker     pp_sf++;
848*e5436536SAndroid Build Coastguard Worker 
849*e5436536SAndroid Build Coastguard Worker     result_sf = fMax(pp_sf, mult_sf);
850*e5436536SAndroid Build Coastguard Worker 
851*e5436536SAndroid Build Coastguard Worker     result = mult + pp;
852*e5436536SAndroid Build Coastguard Worker     /* rarely, mult and pp happen to be almost equal except their sign,
853*e5436536SAndroid Build Coastguard Worker     and then upon summation, result becomes so small, that it is within
854*e5436536SAndroid Build Coastguard Worker     the inaccuracy range of a few bits, and then the relative error
855*e5436536SAndroid Build Coastguard Worker     produced by this function may become HUGE */
856*e5436536SAndroid Build Coastguard Worker   }
857*e5436536SAndroid Build Coastguard Worker 
858*e5436536SAndroid Build Coastguard Worker   *out_sf = result_sf;
859*e5436536SAndroid Build Coastguard Worker   return result;
860*e5436536SAndroid Build Coastguard Worker }
861*e5436536SAndroid Build Coastguard Worker 
sbrDecoder_calculateGainVec(FIXP_DBL ** sourceBufferReal,FIXP_DBL ** sourceBufferImag,int sourceBuf_e_overlap,int sourceBuf_e_current,int overlap,FIXP_DBL * RESTRICT GainVec,int * GainVec_exp,int numBands,const int startSample,const int stopSample)862*e5436536SAndroid Build Coastguard Worker void sbrDecoder_calculateGainVec(FIXP_DBL **sourceBufferReal,
863*e5436536SAndroid Build Coastguard Worker                                  FIXP_DBL **sourceBufferImag,
864*e5436536SAndroid Build Coastguard Worker                                  int sourceBuf_e_overlap,
865*e5436536SAndroid Build Coastguard Worker                                  int sourceBuf_e_current, int overlap,
866*e5436536SAndroid Build Coastguard Worker                                  FIXP_DBL *RESTRICT GainVec, int *GainVec_exp,
867*e5436536SAndroid Build Coastguard Worker                                  int numBands, const int startSample,
868*e5436536SAndroid Build Coastguard Worker                                  const int stopSample) {
869*e5436536SAndroid Build Coastguard Worker   FIXP_DBL p[POLY_ORDER + 1];
870*e5436536SAndroid Build Coastguard Worker   FIXP_DBL meanNrg;
871*e5436536SAndroid Build Coastguard Worker   FIXP_DBL LowEnv[MAXLOWBANDS];
872*e5436536SAndroid Build Coastguard Worker   FIXP_DBL invNumBands = GetInvInt(numBands);
873*e5436536SAndroid Build Coastguard Worker   FIXP_DBL invNumSlots = GetInvInt(stopSample - startSample);
874*e5436536SAndroid Build Coastguard Worker   int i, loBand, exp, scale_nrg, scale_nrg_ov;
875*e5436536SAndroid Build Coastguard Worker   int sum_scale = 5, sum_scale_ov = 3;
876*e5436536SAndroid Build Coastguard Worker 
877*e5436536SAndroid Build Coastguard Worker   if (overlap > 8) {
878*e5436536SAndroid Build Coastguard Worker     FDK_ASSERT(overlap <= 16);
879*e5436536SAndroid Build Coastguard Worker     sum_scale_ov += 1;
880*e5436536SAndroid Build Coastguard Worker     sum_scale += 1;
881*e5436536SAndroid Build Coastguard Worker   }
882*e5436536SAndroid Build Coastguard Worker 
883*e5436536SAndroid Build Coastguard Worker   /* exponents of energy values */
884*e5436536SAndroid Build Coastguard Worker   sourceBuf_e_overlap = sourceBuf_e_overlap * 2 + sum_scale_ov;
885*e5436536SAndroid Build Coastguard Worker   sourceBuf_e_current = sourceBuf_e_current * 2 + sum_scale;
886*e5436536SAndroid Build Coastguard Worker   exp = fMax(sourceBuf_e_overlap, sourceBuf_e_current);
887*e5436536SAndroid Build Coastguard Worker   scale_nrg = sourceBuf_e_current - exp;
888*e5436536SAndroid Build Coastguard Worker   scale_nrg_ov = sourceBuf_e_overlap - exp;
889*e5436536SAndroid Build Coastguard Worker 
890*e5436536SAndroid Build Coastguard Worker   meanNrg = (FIXP_DBL)0;
891*e5436536SAndroid Build Coastguard Worker   /* Calculate the spectral envelope in dB over the current copy-up frame. */
892*e5436536SAndroid Build Coastguard Worker   for (loBand = 0; loBand < numBands; loBand++) {
893*e5436536SAndroid Build Coastguard Worker     FIXP_DBL nrg_ov, nrg;
894*e5436536SAndroid Build Coastguard Worker     INT reserve = 0, exp_new;
895*e5436536SAndroid Build Coastguard Worker     FIXP_DBL maxVal = FL2FX_DBL(0.0f);
896*e5436536SAndroid Build Coastguard Worker 
897*e5436536SAndroid Build Coastguard Worker     for (i = startSample; i < stopSample; i++) {
898*e5436536SAndroid Build Coastguard Worker       maxVal |=
899*e5436536SAndroid Build Coastguard Worker           (FIXP_DBL)((LONG)(sourceBufferReal[i][loBand]) ^
900*e5436536SAndroid Build Coastguard Worker                      ((LONG)sourceBufferReal[i][loBand] >> (DFRACT_BITS - 1)));
901*e5436536SAndroid Build Coastguard Worker       maxVal |=
902*e5436536SAndroid Build Coastguard Worker           (FIXP_DBL)((LONG)(sourceBufferImag[i][loBand]) ^
903*e5436536SAndroid Build Coastguard Worker                      ((LONG)sourceBufferImag[i][loBand] >> (DFRACT_BITS - 1)));
904*e5436536SAndroid Build Coastguard Worker     }
905*e5436536SAndroid Build Coastguard Worker 
906*e5436536SAndroid Build Coastguard Worker     if (maxVal != FL2FX_DBL(0.0f)) {
907*e5436536SAndroid Build Coastguard Worker       reserve = CntLeadingZeros(maxVal) - 2;
908*e5436536SAndroid Build Coastguard Worker     }
909*e5436536SAndroid Build Coastguard Worker 
910*e5436536SAndroid Build Coastguard Worker     nrg_ov = nrg = (FIXP_DBL)0;
911*e5436536SAndroid Build Coastguard Worker     if (scale_nrg_ov > -31) {
912*e5436536SAndroid Build Coastguard Worker       for (i = startSample; i < overlap; i++) {
913*e5436536SAndroid Build Coastguard Worker         nrg_ov +=
914*e5436536SAndroid Build Coastguard Worker             (fPow2Div2(scaleValue(sourceBufferReal[i][loBand], reserve)) +
915*e5436536SAndroid Build Coastguard Worker              fPow2Div2(scaleValue(sourceBufferImag[i][loBand], reserve))) >>
916*e5436536SAndroid Build Coastguard Worker             sum_scale_ov;
917*e5436536SAndroid Build Coastguard Worker       }
918*e5436536SAndroid Build Coastguard Worker     } else {
919*e5436536SAndroid Build Coastguard Worker       scale_nrg_ov = 0;
920*e5436536SAndroid Build Coastguard Worker     }
921*e5436536SAndroid Build Coastguard Worker     if (scale_nrg > -31) {
922*e5436536SAndroid Build Coastguard Worker       for (i = overlap; i < stopSample; i++) {
923*e5436536SAndroid Build Coastguard Worker         nrg += (fPow2Div2(scaleValue(sourceBufferReal[i][loBand], reserve)) +
924*e5436536SAndroid Build Coastguard Worker                 fPow2Div2(scaleValue(sourceBufferImag[i][loBand], reserve))) >>
925*e5436536SAndroid Build Coastguard Worker                sum_scale;
926*e5436536SAndroid Build Coastguard Worker       }
927*e5436536SAndroid Build Coastguard Worker     } else {
928*e5436536SAndroid Build Coastguard Worker       scale_nrg = 0;
929*e5436536SAndroid Build Coastguard Worker     }
930*e5436536SAndroid Build Coastguard Worker 
931*e5436536SAndroid Build Coastguard Worker     nrg = (scaleValue(nrg_ov, scale_nrg_ov) >> 1) +
932*e5436536SAndroid Build Coastguard Worker           (scaleValue(nrg, scale_nrg) >> 1);
933*e5436536SAndroid Build Coastguard Worker     nrg = fMult(nrg, invNumSlots);
934*e5436536SAndroid Build Coastguard Worker 
935*e5436536SAndroid Build Coastguard Worker     exp_new =
936*e5436536SAndroid Build Coastguard Worker         exp - (2 * reserve) +
937*e5436536SAndroid Build Coastguard Worker         2; /* +1 for addition directly above, +1 for fPow2Div2 in loops above */
938*e5436536SAndroid Build Coastguard Worker 
939*e5436536SAndroid Build Coastguard Worker     /* LowEnv = 10*log10(nrg) = log2(nrg) * 10/log2(10) */
940*e5436536SAndroid Build Coastguard Worker     /* exponent of logarithmic energy is 8 */
941*e5436536SAndroid Build Coastguard Worker     if (nrg > (FIXP_DBL)0) {
942*e5436536SAndroid Build Coastguard Worker       int exp_log2;
943*e5436536SAndroid Build Coastguard Worker       nrg = CalcLog2(nrg, exp_new, &exp_log2);
944*e5436536SAndroid Build Coastguard Worker       nrg = scaleValue(nrg, exp_log2 - 6);
945*e5436536SAndroid Build Coastguard Worker       nrg = fMult(FL2FXCONST_SGL(LOG10FAC), nrg);
946*e5436536SAndroid Build Coastguard Worker     } else {
947*e5436536SAndroid Build Coastguard Worker       nrg = (FIXP_DBL)0;
948*e5436536SAndroid Build Coastguard Worker     }
949*e5436536SAndroid Build Coastguard Worker     LowEnv[loBand] = nrg;
950*e5436536SAndroid Build Coastguard Worker     meanNrg += fMult(nrg, invNumBands);
951*e5436536SAndroid Build Coastguard Worker   }
952*e5436536SAndroid Build Coastguard Worker   exp = 6 + 2; /* exponent of LowEnv: +2 is exponent of LOG10FAC */
953*e5436536SAndroid Build Coastguard Worker 
954*e5436536SAndroid Build Coastguard Worker   /* subtract mean before polynomial approximation to reduce dynamic of p[] */
955*e5436536SAndroid Build Coastguard Worker   for (loBand = 0; loBand < numBands; loBand++) {
956*e5436536SAndroid Build Coastguard Worker     LowEnv[loBand] = meanNrg - LowEnv[loBand];
957*e5436536SAndroid Build Coastguard Worker   }
958*e5436536SAndroid Build Coastguard Worker 
959*e5436536SAndroid Build Coastguard Worker   /* For numBands < BSD_IDX_OFFSET (== POLY_ORDER+2) we dont get an
960*e5436536SAndroid Build Coastguard Worker      overdetermined equation system. The calculated polynomial will exactly fit
961*e5436536SAndroid Build Coastguard Worker      the input data and evaluating the polynomial will lead to the same vector
962*e5436536SAndroid Build Coastguard Worker      than the original input vector: lowEnvSlope[] == lowEnv[]
963*e5436536SAndroid Build Coastguard Worker   */
964*e5436536SAndroid Build Coastguard Worker   if (numBands > POLY_ORDER + 1) {
965*e5436536SAndroid Build Coastguard Worker     /* Find polynomial approximation of LowEnv */
966*e5436536SAndroid Build Coastguard Worker     int p_sf[POLY_ORDER + 1];
967*e5436536SAndroid Build Coastguard Worker 
968*e5436536SAndroid Build Coastguard Worker     polyfit(numBands, LowEnv, exp, p, p_sf);
969*e5436536SAndroid Build Coastguard Worker 
970*e5436536SAndroid Build Coastguard Worker     for (i = 0; i < numBands; i++) {
971*e5436536SAndroid Build Coastguard Worker       int sf;
972*e5436536SAndroid Build Coastguard Worker 
973*e5436536SAndroid Build Coastguard Worker       /* lowBandEnvSlope[i] = tmp; */
974*e5436536SAndroid Build Coastguard Worker       FIXP_DBL tmp = polyval(p, p_sf, i, &sf);
975*e5436536SAndroid Build Coastguard Worker 
976*e5436536SAndroid Build Coastguard Worker       /* GainVec = 10^((mean(y)-y)/20) = 2^( (mean(y)-y) * log2(10)/20 ) */
977*e5436536SAndroid Build Coastguard Worker       tmp = fMult(tmp, FL2FXCONST_SGL(LOG10FAC_INV));
978*e5436536SAndroid Build Coastguard Worker       GainVec[i] = f2Pow(tmp, sf - 2,
979*e5436536SAndroid Build Coastguard Worker                          &GainVec_exp[i]); /* -2 is exponent of LOG10FAC_INV */
980*e5436536SAndroid Build Coastguard Worker     }
981*e5436536SAndroid Build Coastguard Worker   } else { /* numBands <= POLY_ORDER+1 */
982*e5436536SAndroid Build Coastguard Worker     for (i = 0; i < numBands; i++) {
983*e5436536SAndroid Build Coastguard Worker       int sf = exp; /* exponent of LowEnv[] */
984*e5436536SAndroid Build Coastguard Worker 
985*e5436536SAndroid Build Coastguard Worker       /* lowBandEnvSlope[i] = LowEnv[i]; */
986*e5436536SAndroid Build Coastguard Worker       FIXP_DBL tmp = LowEnv[i];
987*e5436536SAndroid Build Coastguard Worker 
988*e5436536SAndroid Build Coastguard Worker       /* GainVec = 10^((mean(y)-y)/20) = 2^( (mean(y)-y) * log2(10)/20 ) */
989*e5436536SAndroid Build Coastguard Worker       tmp = fMult(tmp, FL2FXCONST_SGL(LOG10FAC_INV));
990*e5436536SAndroid Build Coastguard Worker       GainVec[i] = f2Pow(tmp, sf - 2,
991*e5436536SAndroid Build Coastguard Worker                          &GainVec_exp[i]); /* -2 is exponent of LOG10FAC_INV */
992*e5436536SAndroid Build Coastguard Worker     }
993*e5436536SAndroid Build Coastguard Worker   }
994*e5436536SAndroid Build Coastguard Worker }
995