/src/aac/libSACenc/src/sacenc_staticgain.cpp
Line | Count | Source (jump to first uncovered line) |
1 | | /* ----------------------------------------------------------------------------- |
2 | | Software License for The Fraunhofer FDK AAC Codec Library for Android |
3 | | |
4 | | © Copyright 1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten |
5 | | Forschung e.V. All rights reserved. |
6 | | |
7 | | 1. INTRODUCTION |
8 | | The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software |
9 | | that implements the MPEG Advanced Audio Coding ("AAC") encoding and decoding |
10 | | scheme for digital audio. This FDK AAC Codec software is intended to be used on |
11 | | a wide variety of Android devices. |
12 | | |
13 | | AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient |
14 | | general perceptual audio codecs. AAC-ELD is considered the best-performing |
15 | | full-bandwidth communications codec by independent studies and is widely |
16 | | deployed. AAC has been standardized by ISO and IEC as part of the MPEG |
17 | | specifications. |
18 | | |
19 | | Patent licenses for necessary patent claims for the FDK AAC Codec (including |
20 | | those of Fraunhofer) may be obtained through Via Licensing |
21 | | (www.vialicensing.com) or through the respective patent owners individually for |
22 | | the purpose of encoding or decoding bit streams in products that are compliant |
23 | | with the ISO/IEC MPEG audio standards. Please note that most manufacturers of |
24 | | Android devices already license these patent claims through Via Licensing or |
25 | | directly from the patent owners, and therefore FDK AAC Codec software may |
26 | | already be covered under those patent licenses when it is used for those |
27 | | licensed purposes only. |
28 | | |
29 | | Commercially-licensed AAC software libraries, including floating-point versions |
30 | | with enhanced sound quality, are also available from Fraunhofer. Users are |
31 | | encouraged to check the Fraunhofer website for additional applications |
32 | | information and documentation. |
33 | | |
34 | | 2. COPYRIGHT LICENSE |
35 | | |
36 | | Redistribution and use in source and binary forms, with or without modification, |
37 | | are permitted without payment of copyright license fees provided that you |
38 | | satisfy the following conditions: |
39 | | |
40 | | You must retain the complete text of this software license in redistributions of |
41 | | the FDK AAC Codec or your modifications thereto in source code form. |
42 | | |
43 | | You must retain the complete text of this software license in the documentation |
44 | | and/or other materials provided with redistributions of the FDK AAC Codec or |
45 | | your modifications thereto in binary form. You must make available free of |
46 | | charge copies of the complete source code of the FDK AAC Codec and your |
47 | | modifications thereto to recipients of copies in binary form. |
48 | | |
49 | | The name of Fraunhofer may not be used to endorse or promote products derived |
50 | | from this library without prior written permission. |
51 | | |
52 | | You may not charge copyright license fees for anyone to use, copy or distribute |
53 | | the FDK AAC Codec software or your modifications thereto. |
54 | | |
55 | | Your modified versions of the FDK AAC Codec must carry prominent notices stating |
56 | | that you changed the software and the date of any change. For modified versions |
57 | | of the FDK AAC Codec, the term "Fraunhofer FDK AAC Codec Library for Android" |
58 | | must be replaced by the term "Third-Party Modified Version of the Fraunhofer FDK |
59 | | AAC Codec Library for Android." |
60 | | |
61 | | 3. NO PATENT LICENSE |
62 | | |
63 | | NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without |
64 | | limitation the patents of Fraunhofer, ARE GRANTED BY THIS SOFTWARE LICENSE. |
65 | | Fraunhofer provides no warranty of patent non-infringement with respect to this |
66 | | software. |
67 | | |
68 | | You may use this FDK AAC Codec software or modifications thereto only for |
69 | | purposes that are authorized by appropriate patent licenses. |
70 | | |
71 | | 4. DISCLAIMER |
72 | | |
73 | | This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright |
74 | | holders and contributors "AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, |
75 | | including but not limited to the implied warranties of merchantability and |
76 | | fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR |
77 | | CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary, |
78 | | or consequential damages, including but not limited to procurement of substitute |
79 | | goods or services; loss of use, data, or profits, or business interruption, |
80 | | however caused and on any theory of liability, whether in contract, strict |
81 | | liability, or tort (including negligence), arising in any way out of the use of |
82 | | this software, even if advised of the possibility of such damage. |
83 | | |
84 | | 5. CONTACT INFORMATION |
85 | | |
86 | | Fraunhofer Institute for Integrated Circuits IIS |
87 | | Attention: Audio and Multimedia Departments - FDK AAC LL |
88 | | Am Wolfsmantel 33 |
89 | | 91058 Erlangen, Germany |
90 | | |
91 | | www.iis.fraunhofer.de/amm |
92 | | amm-info@iis.fraunhofer.de |
93 | | ----------------------------------------------------------------------------- */ |
94 | | |
95 | | /*********************** MPEG surround encoder library ************************* |
96 | | |
97 | | Author(s): Christian Goettlinger |
98 | | |
99 | | Description: Encoder Library Interface |
100 | | gain management of the encoder |
101 | | |
102 | | *******************************************************************************/ |
103 | | |
104 | | /***************************************************************************** |
105 | | \file |
106 | | This file contains all static gain infrastructure |
107 | | ******************************************************************************/ |
108 | | |
109 | | /* Includes ******************************************************************/ |
110 | | #include "sacenc_staticgain.h" |
111 | | |
112 | | /* Defines *******************************************************************/ |
113 | 0 | #define MP4SPACEENC_DMX_GAIN_DEFAULT SACENC_DMXGAIN_3_dB |
114 | 0 | #define GAINCF_SF (4) |
115 | | #define GAINCT1(x) FL2FXCONST_DBL(x) |
116 | | #define GAINCF(x) FL2FXCONST_DBL(x) |
117 | | |
118 | | #define GAINCT2(x) FL2FXCONST_DBL(x) |
119 | 0 | #define FX_DBL2FX_GAIN(x) (x) |
120 | | |
121 | | /* Data Types ****************************************************************/ |
122 | | struct STATIC_GAIN { |
123 | | /* External Config Values */ |
124 | | MP4SPACEENC_MODE encMode; |
125 | | MP4SPACEENC_DMX_GAIN fixedGainDMX; |
126 | | INT preGainFactorDb; |
127 | | |
128 | | /* Internal Values */ |
129 | | FIXP_GAIN PostGain__FDK; |
130 | | FIXP_GAIN pPreGain__FDK[SACENC_MAX_INPUT_CHANNELS]; |
131 | | }; |
132 | | |
133 | | /* Constants *****************************************************************/ |
134 | | /* |
135 | | preGainFactorTable: |
136 | | |
137 | | pre calculation: (float)pow(10.f,(((float) x)/20.f))/(float)(1<<GAINCF_SF), x |
138 | | = -20 ... +20 |
139 | | */ |
140 | | static const FIXP_DBL preGainFactorTable__FDK[41] = { |
141 | | GAINCF(6.2500000931e-003), GAINCF(7.0126154460e-003), |
142 | | GAINCF(7.8682834283e-003), GAINCF(8.8283596560e-003), |
143 | | GAINCF(9.9055822939e-003), GAINCF(1.1114246212e-002), |
144 | | GAINCF(1.2470389716e-002), GAINCF(1.3992006890e-002), |
145 | | GAINCF(1.5699289739e-002), GAINCF(1.7614893615e-002), |
146 | | GAINCF(1.9764235243e-002), GAINCF(2.2175837308e-002), |
147 | | GAINCF(2.4881698191e-002), GAINCF(2.7917724103e-002), |
148 | | GAINCF(3.1324200332e-002), GAINCF(3.5146333277e-002), |
149 | | GAINCF(3.9434835315e-002), GAINCF(4.4246610254e-002), |
150 | | GAINCF(4.9645513296e-002), GAINCF(5.5703181773e-002), |
151 | | GAINCF(6.2500000000e-002), GAINCF(7.0126153529e-002), |
152 | | GAINCF(7.8682839870e-002), GAINCF(8.8283598423e-002), |
153 | | GAINCF(9.9055826664e-002), GAINCF(1.1114246398e-001), |
154 | | GAINCF(1.2470389158e-001), GAINCF(1.3992007077e-001), |
155 | | GAINCF(1.5699289739e-001), GAINCF(1.7614893615e-001), |
156 | | GAINCF(1.9764235616e-001), GAINCF(2.2175836563e-001), |
157 | | GAINCF(2.4881698191e-001), GAINCF(2.7917724848e-001), |
158 | | GAINCF(3.1324201822e-001), GAINCF(3.5146331787e-001), |
159 | | GAINCF(3.9434835315e-001), GAINCF(4.4246610999e-001), |
160 | | GAINCF(4.9645513296e-001), GAINCF(5.5703181028e-001), |
161 | | GAINCF(6.2500000000e-001)}; |
162 | | |
163 | | static const FIXP_GAIN dmxGainTable__FDK[] = { |
164 | | /* GAINCT2(1.0), */ GAINCT2(0.84089650f), |
165 | | GAINCT2(0.70710706f), |
166 | | GAINCT2(0.59460385f), |
167 | | GAINCT2(0.50000000f), |
168 | | GAINCT2(0.42044825f), |
169 | | GAINCT2(0.35355341f), |
170 | | GAINCT2(0.25000000f)}; |
171 | | |
172 | | /* Function / Class Declarations *********************************************/ |
173 | | |
174 | | /* Function / Class Definition ***********************************************/ |
175 | | |
176 | | /*----------------------------------------------------------------------------- |
177 | | functionname: fdk_sacenc_staticGain_OpenConfig() |
178 | | description: opens and sets ConfigStruct to Default Values |
179 | | returns: noError on success, an apropriate error code else |
180 | | -----------------------------------------------------------------------------*/ |
181 | | FDK_SACENC_ERROR fdk_sacenc_staticGain_OpenConfig( |
182 | 0 | HANDLE_STATIC_GAIN_CONFIG *phStaticGainConfig) { |
183 | 0 | FDK_SACENC_ERROR error = SACENC_OK; |
184 | |
|
185 | 0 | if (NULL == phStaticGainConfig) { |
186 | 0 | error = SACENC_INVALID_HANDLE; |
187 | 0 | } else { |
188 | | /* Allocate Instance */ |
189 | 0 | FDK_ALLOCATE_MEMORY_1D(*phStaticGainConfig, 1, struct STATIC_GAIN_CONFIG); |
190 | 0 | } |
191 | 0 | return error; |
192 | | |
193 | 0 | bail: |
194 | 0 | fdk_sacenc_staticGain_CloseConfig(phStaticGainConfig); |
195 | 0 | return ((SACENC_OK == error) ? SACENC_MEMORY_ERROR : error); |
196 | 0 | } |
197 | | |
198 | | FDK_SACENC_ERROR fdk_sacenc_staticGain_InitDefaultConfig( |
199 | 0 | HANDLE_STATIC_GAIN_CONFIG hStaticGainConfig) { |
200 | 0 | FDK_SACENC_ERROR error = SACENC_OK; |
201 | |
|
202 | 0 | if (NULL == hStaticGainConfig) { |
203 | 0 | error = SACENC_INVALID_HANDLE; |
204 | 0 | } else { |
205 | | /* Necessary Input Variables */ |
206 | 0 | hStaticGainConfig->encMode = SACENC_INVALID_MODE; |
207 | | |
208 | | /* Optional Configs Set to Default Values */ |
209 | 0 | hStaticGainConfig->fixedGainDMX = MP4SPACEENC_DMX_GAIN_DEFAULT; |
210 | 0 | hStaticGainConfig->preGainFactorDb = 0; |
211 | 0 | } |
212 | 0 | return error; |
213 | 0 | } |
214 | | |
215 | | /*----------------------------------------------------------------------------- |
216 | | functionname: fdk_sacenc_staticGain_CloseConfig() |
217 | | description: destructs Static Gain Config Structure |
218 | | returns: noError on success, an apropriate error code else |
219 | | -----------------------------------------------------------------------------*/ |
220 | | FDK_SACENC_ERROR fdk_sacenc_staticGain_CloseConfig( |
221 | 0 | HANDLE_STATIC_GAIN_CONFIG *phStaticGainConfig) { |
222 | 0 | FDK_SACENC_ERROR error = SACENC_OK; |
223 | |
|
224 | 0 | if ((phStaticGainConfig == NULL) || (*phStaticGainConfig == NULL)) { |
225 | 0 | error = SACENC_INVALID_HANDLE; |
226 | 0 | } else { |
227 | 0 | FDKfree(*phStaticGainConfig); |
228 | 0 | *phStaticGainConfig = NULL; |
229 | 0 | } |
230 | 0 | return error; |
231 | 0 | } |
232 | | |
233 | | /*----------------------------------------------------------------------------- |
234 | | functionname: fdk_sacenc_staticGain_Open() |
235 | | description: initializes Static Gains |
236 | | returns: noError on success, an apropriate error code else |
237 | | -----------------------------------------------------------------------------*/ |
238 | 0 | FDK_SACENC_ERROR fdk_sacenc_staticGain_Open(HANDLE_STATIC_GAIN *phStaticGain) { |
239 | 0 | FDK_SACENC_ERROR error = SACENC_OK; |
240 | |
|
241 | 0 | if (NULL == phStaticGain) { |
242 | 0 | error = SACENC_INVALID_HANDLE; |
243 | 0 | } else { |
244 | | /* Allocate Instance */ |
245 | 0 | FDK_ALLOCATE_MEMORY_1D(*phStaticGain, 1, struct STATIC_GAIN); |
246 | 0 | } |
247 | 0 | return error; |
248 | | |
249 | 0 | bail: |
250 | 0 | return ((SACENC_OK == error) ? SACENC_MEMORY_ERROR : error); |
251 | 0 | } |
252 | | |
253 | | FDK_SACENC_ERROR fdk_sacenc_staticGain_Init( |
254 | | HANDLE_STATIC_GAIN hStaticGain, |
255 | 0 | const HANDLE_STATIC_GAIN_CONFIG hStaticGainConfig, INT *const scale) { |
256 | 0 | FDK_SACENC_ERROR error = SACENC_OK; |
257 | |
|
258 | 0 | if ((hStaticGain == NULL) || (hStaticGainConfig == NULL)) { |
259 | 0 | error = SACENC_INVALID_HANDLE; |
260 | 0 | } else { |
261 | 0 | hStaticGain->encMode = hStaticGainConfig->encMode; |
262 | 0 | hStaticGain->fixedGainDMX = hStaticGainConfig->fixedGainDMX; |
263 | 0 | hStaticGain->preGainFactorDb = hStaticGainConfig->preGainFactorDb; |
264 | |
|
265 | 0 | if ((hStaticGain->preGainFactorDb < -20) || |
266 | 0 | (hStaticGain->preGainFactorDb > 20)) { |
267 | 0 | error = SACENC_INVALID_CONFIG; |
268 | 0 | goto bail; |
269 | 0 | } |
270 | | |
271 | 0 | FIXP_DBL fPreGainFactor__FDK; |
272 | |
|
273 | 0 | if (hStaticGain->preGainFactorDb == 0) { |
274 | 0 | fPreGainFactor__FDK = (FIXP_DBL)MAXVAL_DBL; |
275 | 0 | *scale = 0; |
276 | 0 | } else { |
277 | 0 | int s; |
278 | 0 | fPreGainFactor__FDK = |
279 | 0 | preGainFactorTable__FDK[hStaticGain->preGainFactorDb + 20]; |
280 | 0 | s = fixMax(0, CntLeadingZeros(fPreGainFactor__FDK) - 1); |
281 | 0 | fPreGainFactor__FDK = fPreGainFactor__FDK << (s); |
282 | 0 | *scale = GAINCF_SF - s; |
283 | 0 | } |
284 | |
|
285 | 0 | if (hStaticGain->fixedGainDMX == 0) |
286 | 0 | hStaticGain->PostGain__FDK = MAXVAL_GAIN; |
287 | 0 | else |
288 | 0 | hStaticGain->PostGain__FDK = |
289 | 0 | dmxGainTable__FDK[hStaticGain->fixedGainDMX - 1]; |
290 | |
|
291 | 0 | FDKmemclear( |
292 | 0 | hStaticGain->pPreGain__FDK, |
293 | 0 | sizeof(hStaticGain->pPreGain__FDK)); /* zero all input channels */ |
294 | | |
295 | | /* Configure PreGain-Vector */ |
296 | 0 | if (hStaticGain->encMode == SACENC_212) { |
297 | 0 | hStaticGain->pPreGain__FDK[0] = |
298 | 0 | FX_DBL2FX_GAIN(fPreGainFactor__FDK); /* L */ |
299 | 0 | hStaticGain->pPreGain__FDK[1] = |
300 | 0 | FX_DBL2FX_GAIN(fPreGainFactor__FDK); /* R */ |
301 | 0 | } else { |
302 | 0 | error = SACENC_INVALID_CONFIG; |
303 | 0 | } |
304 | |
|
305 | 0 | } /* valid handle */ |
306 | | |
307 | 0 | bail: |
308 | |
|
309 | 0 | return error; |
310 | 0 | } |
311 | | |
312 | | /*----------------------------------------------------------------------------- |
313 | | functionname: fdk_sacenc_staticGain_Close() |
314 | | description: destructs Static Gains |
315 | | returns: noError on success, an apropriate error code else |
316 | | -----------------------------------------------------------------------------*/ |
317 | 0 | FDK_SACENC_ERROR fdk_sacenc_staticGain_Close(HANDLE_STATIC_GAIN *phStaticGain) { |
318 | 0 | FDK_SACENC_ERROR error = SACENC_OK; |
319 | |
|
320 | 0 | if ((phStaticGain == NULL) || (*phStaticGain == NULL)) { |
321 | 0 | error = SACENC_INVALID_HANDLE; |
322 | 0 | } else { |
323 | 0 | FDKfree(*phStaticGain); |
324 | 0 | *phStaticGain = NULL; |
325 | 0 | } |
326 | 0 | return error; |
327 | 0 | } |
328 | | |
329 | | /*----------------------------------------------------------------------------- |
330 | | functionname: fdk_sacenc_staticPostGain_Apply |
331 | | description: multiply the Output samples with the PostGain |
332 | | returns: noError on success, an apropriate error code else |
333 | | -----------------------------------------------------------------------------*/ |
334 | | FDK_SACENC_ERROR fdk_sacenc_staticPostGain_ApplyFDK( |
335 | | const HANDLE_STATIC_GAIN hStaticGain, INT_PCM *const pOutputSamples, |
336 | 0 | const INT nOutputSamples, const INT scale) { |
337 | 0 | FDK_SACENC_ERROR error = SACENC_OK; |
338 | |
|
339 | 0 | if (NULL == hStaticGain) { |
340 | 0 | error = SACENC_INVALID_HANDLE; |
341 | 0 | } else { |
342 | 0 | int i; |
343 | 0 | FIXP_GAIN postGain = hStaticGain->PostGain__FDK; |
344 | |
|
345 | 0 | if (scale < 0) { |
346 | 0 | if (postGain == MAXVAL_GAIN) { |
347 | 0 | for (i = 0; i < nOutputSamples; i++) { |
348 | 0 | pOutputSamples[i] = pOutputSamples[i] >> (-scale); |
349 | 0 | } |
350 | 0 | } else { |
351 | 0 | for (i = 0; i < nOutputSamples; i++) { |
352 | 0 | pOutputSamples[i] = FX_DBL2FX_PCM( |
353 | 0 | fMult(postGain, FX_PCM2FX_DBL(pOutputSamples[i])) >> (-scale)); |
354 | 0 | } |
355 | 0 | } |
356 | 0 | } else { |
357 | 0 | if (postGain == MAXVAL_GAIN) { |
358 | 0 | for (i = 0; i < nOutputSamples; i++) { |
359 | 0 | pOutputSamples[i] = FX_DBL2FX_PCM(SATURATE_LEFT_SHIFT( |
360 | 0 | FX_PCM2FX_DBL(pOutputSamples[i]), scale, DFRACT_BITS)); |
361 | 0 | } |
362 | 0 | } else { |
363 | 0 | for (i = 0; i < nOutputSamples; i++) { |
364 | 0 | pOutputSamples[i] = FX_DBL2FX_PCM(SATURATE_LEFT_SHIFT( |
365 | 0 | fMult(postGain, FX_PCM2FX_DBL(pOutputSamples[i])), scale, |
366 | 0 | DFRACT_BITS)); |
367 | 0 | } |
368 | 0 | } |
369 | 0 | } |
370 | 0 | } |
371 | 0 | return error; |
372 | 0 | } |
373 | | |
374 | | /*----------------------------------------------------------------------------- |
375 | | functionname: fdk_sacenc_getPreGainPtr()/ fdk_sacenc_getPostGain() |
376 | | description: get Gain-Pointers from struct |
377 | | returns: Pointer to PreGain or postGain |
378 | | -----------------------------------------------------------------------------*/ |
379 | 0 | FIXP_GAIN *fdk_sacenc_getPreGainPtrFDK(HANDLE_STATIC_GAIN hStaticGain) { |
380 | 0 | return ((hStaticGain == NULL) ? NULL : hStaticGain->pPreGain__FDK); |
381 | 0 | } |
382 | | |
383 | 0 | FIXP_GAIN fdk_sacenc_getPostGainFDK(HANDLE_STATIC_GAIN hStaticGain) { |
384 | 0 | return (hStaticGain->PostGain__FDK); |
385 | 0 | } |
386 | | |
387 | | /* get fixed downmix gain and map it to bitstream enum */ |
388 | | FIXEDGAINDMXCONFIG fdk_sacenc_staticGain_GetDmxGain( |
389 | 0 | const HANDLE_STATIC_GAIN hStaticGain) { |
390 | 0 | FIXEDGAINDMXCONFIG dmxGain = FIXEDGAINDMX_INVALID; |
391 | |
|
392 | 0 | switch (hStaticGain->fixedGainDMX) { |
393 | 0 | case 0: |
394 | 0 | dmxGain = FIXEDGAINDMX_0; |
395 | 0 | break; |
396 | 0 | case 1: |
397 | 0 | dmxGain = FIXEDGAINDMX_1; |
398 | 0 | break; |
399 | 0 | case 2: |
400 | 0 | dmxGain = FIXEDGAINDMX_2; |
401 | 0 | break; |
402 | 0 | case 3: |
403 | 0 | dmxGain = FIXEDGAINDMX_3; |
404 | 0 | break; |
405 | 0 | case 4: |
406 | 0 | dmxGain = FIXEDGAINDMX_4; |
407 | 0 | break; |
408 | 0 | case 5: |
409 | 0 | dmxGain = FIXEDGAINDMX_5; |
410 | 0 | break; |
411 | 0 | case 6: |
412 | 0 | dmxGain = FIXEDGAINDMX_6; |
413 | 0 | break; |
414 | 0 | case 7: |
415 | 0 | dmxGain = FIXEDGAINDMX_7; |
416 | 0 | break; |
417 | 0 | default: |
418 | 0 | dmxGain = FIXEDGAINDMX_INVALID; |
419 | 0 | } |
420 | 0 | return dmxGain; |
421 | 0 | } |
422 | | |
423 | | FDK_SACENC_ERROR fdk_sacenc_staticGain_SetDmxGain( |
424 | | HANDLE_STATIC_GAIN_CONFIG hStaticGainCfg, |
425 | 0 | const MP4SPACEENC_DMX_GAIN dmxGain) { |
426 | 0 | FDK_SACENC_ERROR error = SACENC_OK; |
427 | |
|
428 | 0 | if (NULL == hStaticGainCfg) { |
429 | 0 | error = SACENC_INVALID_HANDLE; |
430 | 0 | } else { |
431 | 0 | hStaticGainCfg->fixedGainDMX = dmxGain; |
432 | 0 | } |
433 | 0 | return error; |
434 | 0 | } |
435 | | |
436 | | FDK_SACENC_ERROR fdk_sacenc_staticGain_SetEncMode( |
437 | 0 | HANDLE_STATIC_GAIN_CONFIG hStaticGainCfg, const MP4SPACEENC_MODE encMode) { |
438 | 0 | FDK_SACENC_ERROR error = SACENC_OK; |
439 | |
|
440 | 0 | if (NULL == hStaticGainCfg) { |
441 | 0 | error = SACENC_INVALID_HANDLE; |
442 | 0 | } else { |
443 | 0 | hStaticGainCfg->encMode = encMode; |
444 | 0 | } |
445 | 0 | return error; |
446 | 0 | } |