EffectBundle.cpp revision 29b83cbb9018e53a18cf6e0fb34893f9774dcb96
1/*
2 * Copyright (C) 2010-2010 NXP Software
3 * Copyright (C) 2009 The Android Open Source Project
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 *      http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17
18#define LOG_TAG "Bundle"
19#define ARRAY_SIZE(array) (sizeof array / sizeof array[0])
20//#define LOG_NDEBUG 0
21
22#include <cutils/log.h>
23#include <assert.h>
24#include <stdlib.h>
25#include <string.h>
26#include <new>
27#include "EffectBundle.h"
28
29
30// effect_handle_t interface implementation for bass boost
31extern "C" const struct effect_interface_s gLvmEffectInterface;
32
33#define LVM_ERROR_CHECK(LvmStatus, callingFunc, calledFunc){\
34        if (LvmStatus == LVM_NULLADDRESS){\
35            ALOGV("\tLVM_ERROR : Parameter error - "\
36                    "null pointer returned by %s in %s\n\n\n\n", callingFunc, calledFunc);\
37        }\
38        if (LvmStatus == LVM_ALIGNMENTERROR){\
39            ALOGV("\tLVM_ERROR : Parameter error - "\
40                    "bad alignment returned by %s in %s\n\n\n\n", callingFunc, calledFunc);\
41        }\
42        if (LvmStatus == LVM_INVALIDNUMSAMPLES){\
43            ALOGV("\tLVM_ERROR : Parameter error - "\
44                    "bad number of samples returned by %s in %s\n\n\n\n", callingFunc, calledFunc);\
45        }\
46        if (LvmStatus == LVM_OUTOFRANGE){\
47            ALOGV("\tLVM_ERROR : Parameter error - "\
48                    "out of range returned by %s in %s\n", callingFunc, calledFunc);\
49        }\
50    }
51
52
53static inline int16_t clamp16(int32_t sample)
54{
55    // check overflow for both positive and negative values:
56    // all bits above short range must me equal to sign bit
57    if ((sample>>15) ^ (sample>>31))
58        sample = 0x7FFF ^ (sample>>31);
59    return sample;
60}
61
62// Namespaces
63namespace android {
64namespace {
65
66// Flag to allow a one time init of global memory, only happens on first call ever
67int LvmInitFlag = LVM_FALSE;
68SessionContext GlobalSessionMemory[LVM_MAX_SESSIONS];
69int SessionIndex[LVM_MAX_SESSIONS];
70
71/* local functions */
72#define CHECK_ARG(cond) {                     \
73    if (!(cond)) {                            \
74        ALOGV("\tLVM_ERROR : Invalid argument: "#cond);      \
75        return -EINVAL;                       \
76    }                                         \
77}
78
79
80// NXP SW BassBoost UUID
81const effect_descriptor_t gBassBoostDescriptor = {
82        {0x0634f220, 0xddd4, 0x11db, 0xa0fc, { 0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b }},
83        {0x8631f300, 0x72e2, 0x11df, 0xb57e, {0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b}}, // uuid
84        EFFECT_CONTROL_API_VERSION,
85        (EFFECT_FLAG_TYPE_INSERT | EFFECT_FLAG_INSERT_FIRST | EFFECT_FLAG_DEVICE_IND
86        | EFFECT_FLAG_VOLUME_CTRL),
87        BASS_BOOST_CUP_LOAD_ARM9E,
88        BUNDLE_MEM_USAGE,
89        "Dynamic Bass Boost",
90        "NXP Software Ltd.",
91};
92
93// NXP SW Virtualizer UUID
94const effect_descriptor_t gVirtualizerDescriptor = {
95        {0x37cc2c00, 0xdddd, 0x11db, 0x8577, {0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b}},
96        {0x1d4033c0, 0x8557, 0x11df, 0x9f2d, {0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b}},
97        EFFECT_CONTROL_API_VERSION,
98        (EFFECT_FLAG_TYPE_INSERT | EFFECT_FLAG_INSERT_LAST | EFFECT_FLAG_DEVICE_IND
99        | EFFECT_FLAG_VOLUME_CTRL),
100        VIRTUALIZER_CUP_LOAD_ARM9E,
101        BUNDLE_MEM_USAGE,
102        "Virtualizer",
103        "NXP Software Ltd.",
104};
105
106// NXP SW Equalizer UUID
107const effect_descriptor_t gEqualizerDescriptor = {
108        {0x0bed4300, 0xddd6, 0x11db, 0x8f34, {0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b}}, // type
109        {0xce772f20, 0x847d, 0x11df, 0xbb17, {0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b}}, // uuid Eq NXP
110        EFFECT_CONTROL_API_VERSION,
111        (EFFECT_FLAG_TYPE_INSERT | EFFECT_FLAG_INSERT_FIRST | EFFECT_FLAG_VOLUME_CTRL),
112        EQUALIZER_CUP_LOAD_ARM9E,
113        BUNDLE_MEM_USAGE,
114        "Equalizer",
115        "NXP Software Ltd.",
116};
117
118// NXP SW Volume UUID
119const effect_descriptor_t gVolumeDescriptor = {
120        {0x09e8ede0, 0xddde, 0x11db, 0xb4f6, { 0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b }},
121        {0x119341a0, 0x8469, 0x11df, 0x81f9, { 0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b }}, //uuid VOL NXP
122        EFFECT_CONTROL_API_VERSION,
123        (EFFECT_FLAG_TYPE_INSERT | EFFECT_FLAG_INSERT_LAST | EFFECT_FLAG_VOLUME_CTRL),
124        VOLUME_CUP_LOAD_ARM9E,
125        BUNDLE_MEM_USAGE,
126        "Volume",
127        "NXP Software Ltd.",
128};
129
130//--- local function prototypes
131void LvmGlobalBundle_init      (void);
132int  LvmBundle_init            (EffectContext *pContext);
133int  LvmEffect_enable          (EffectContext *pContext);
134int  LvmEffect_disable         (EffectContext *pContext);
135void LvmEffect_free            (EffectContext *pContext);
136int  Effect_setConfig          (EffectContext *pContext, effect_config_t *pConfig);
137void Effect_getConfig          (EffectContext *pContext, effect_config_t *pConfig);
138int  BassBoost_setParameter    (EffectContext *pContext, void *pParam, void *pValue);
139int  BassBoost_getParameter    (EffectContext *pContext,
140                               void           *pParam,
141                               size_t         *pValueSize,
142                               void           *pValue);
143int  Virtualizer_setParameter  (EffectContext *pContext, void *pParam, void *pValue);
144int  Virtualizer_getParameter  (EffectContext *pContext,
145                               void           *pParam,
146                               size_t         *pValueSize,
147                               void           *pValue);
148int  Equalizer_setParameter    (EffectContext *pContext, void *pParam, void *pValue);
149int  Equalizer_getParameter    (EffectContext *pContext,
150                                void          *pParam,
151                                size_t        *pValueSize,
152                                void          *pValue);
153int  Volume_setParameter       (EffectContext *pContext, void *pParam, void *pValue);
154int  Volume_getParameter       (EffectContext *pContext,
155                                void          *pParam,
156                                size_t        *pValueSize,
157                                void          *pValue);
158int Effect_setEnabled(EffectContext *pContext, bool enabled);
159
160/* Effect Library Interface Implementation */
161
162extern "C" int EffectCreate(const effect_uuid_t *uuid,
163                            int32_t             sessionId,
164                            int32_t             ioId,
165                            effect_handle_t  *pHandle){
166    int ret = 0;
167    int sessionNo;
168    int i;
169    EffectContext *pContext = NULL;
170    bool newBundle = false;
171    SessionContext *pSessionContext;
172
173    ALOGV("\n\tEffectCreate start session %d", sessionId);
174
175    if (pHandle == NULL || uuid == NULL){
176        ALOGV("\tLVM_ERROR : EffectCreate() called with NULL pointer");
177        ret = -EINVAL;
178        goto exit;
179    }
180
181    if(LvmInitFlag == LVM_FALSE){
182        LvmInitFlag = LVM_TRUE;
183        ALOGV("\tEffectCreate - Initializing all global memory");
184        LvmGlobalBundle_init();
185    }
186
187    // Find next available sessionNo
188    for(i=0; i<LVM_MAX_SESSIONS; i++){
189        if((SessionIndex[i] == LVM_UNUSED_SESSION)||(SessionIndex[i] == sessionId)){
190            sessionNo       = i;
191            SessionIndex[i] = sessionId;
192            ALOGV("\tEffectCreate: Allocating SessionNo %d for SessionId %d\n", sessionNo,sessionId);
193            break;
194        }
195    }
196
197    if(i==LVM_MAX_SESSIONS){
198        ALOGV("\tLVM_ERROR : Cannot find memory to allocate for current session");
199        ret = -EINVAL;
200        goto exit;
201    }
202
203    pContext = new EffectContext;
204
205    // If this is the first create in this session
206    if(GlobalSessionMemory[sessionNo].bBundledEffectsEnabled == LVM_FALSE){
207        ALOGV("\tEffectCreate - This is the first effect in current sessionId %d sessionNo %d",
208                sessionId, sessionNo);
209
210        GlobalSessionMemory[sessionNo].bBundledEffectsEnabled = LVM_TRUE;
211        GlobalSessionMemory[sessionNo].pBundledContext        = new BundledEffectContext;
212        newBundle = true;
213
214        pContext->pBundledContext = GlobalSessionMemory[sessionNo].pBundledContext;
215        pContext->pBundledContext->SessionNo                = sessionNo;
216        pContext->pBundledContext->SessionId                = sessionId;
217        pContext->pBundledContext->hInstance                = NULL;
218        pContext->pBundledContext->bVolumeEnabled           = LVM_FALSE;
219        pContext->pBundledContext->bEqualizerEnabled        = LVM_FALSE;
220        pContext->pBundledContext->bBassEnabled             = LVM_FALSE;
221        pContext->pBundledContext->bBassTempDisabled        = LVM_FALSE;
222        pContext->pBundledContext->bVirtualizerEnabled      = LVM_FALSE;
223        pContext->pBundledContext->bVirtualizerTempDisabled = LVM_FALSE;
224        pContext->pBundledContext->NumberEffectsEnabled     = 0;
225        pContext->pBundledContext->NumberEffectsCalled      = 0;
226        pContext->pBundledContext->firstVolume              = LVM_TRUE;
227        pContext->pBundledContext->volume                   = 0;
228
229        #ifdef LVM_PCM
230        char fileName[256];
231        snprintf(fileName, 256, "/data/tmp/bundle_%p_pcm_in.pcm", pContext->pBundledContext);
232        pContext->pBundledContext->PcmInPtr = fopen(fileName, "w");
233        if (pContext->pBundledContext->PcmInPtr == NULL) {
234            ALOGV("cannot open %s", fileName);
235            ret = -EINVAL;
236            goto exit;
237        }
238
239        snprintf(fileName, 256, "/data/tmp/bundle_%p_pcm_out.pcm", pContext->pBundledContext);
240        pContext->pBundledContext->PcmOutPtr = fopen(fileName, "w");
241        if (pContext->pBundledContext->PcmOutPtr == NULL) {
242            ALOGV("cannot open %s", fileName);
243            fclose(pContext->pBundledContext->PcmInPtr);
244           pContext->pBundledContext->PcmInPtr = NULL;
245           ret = -EINVAL;
246           goto exit;
247        }
248        #endif
249
250        /* Saved strength is used to return the exact strength that was used in the set to the get
251         * because we map the original strength range of 0:1000 to 1:15, and this will avoid
252         * quantisation like effect when returning
253         */
254        pContext->pBundledContext->BassStrengthSaved        = 0;
255        pContext->pBundledContext->VirtStrengthSaved        = 0;
256        pContext->pBundledContext->CurPreset                = PRESET_CUSTOM;
257        pContext->pBundledContext->levelSaved               = 0;
258        pContext->pBundledContext->bMuteEnabled             = LVM_FALSE;
259        pContext->pBundledContext->bStereoPositionEnabled   = LVM_FALSE;
260        pContext->pBundledContext->positionSaved            = 0;
261        pContext->pBundledContext->workBuffer               = NULL;
262        pContext->pBundledContext->frameCount               = -1;
263        pContext->pBundledContext->SamplesToExitCountVirt   = 0;
264        pContext->pBundledContext->SamplesToExitCountBb     = 0;
265        pContext->pBundledContext->SamplesToExitCountEq     = 0;
266
267        for (int i = 0; i < FIVEBAND_NUMBANDS; i++) {
268            pContext->pBundledContext->bandGaindB[i] = EQNB_5BandSoftPresets[i];
269        }
270
271        ALOGV("\tEffectCreate - Calling LvmBundle_init");
272        ret = LvmBundle_init(pContext);
273
274        if (ret < 0){
275            ALOGV("\tLVM_ERROR : EffectCreate() Bundle init failed");
276            goto exit;
277        }
278    }
279    else{
280        ALOGV("\tEffectCreate - Assigning memory for previously created effect on sessionNo %d",
281                sessionNo);
282        pContext->pBundledContext =
283                GlobalSessionMemory[sessionNo].pBundledContext;
284    }
285    ALOGV("\tEffectCreate - pBundledContext is %p", pContext->pBundledContext);
286
287    pSessionContext = &GlobalSessionMemory[pContext->pBundledContext->SessionNo];
288
289    // Create each Effect
290    if (memcmp(uuid, &gBassBoostDescriptor.uuid, sizeof(effect_uuid_t)) == 0){
291        // Create Bass Boost
292        ALOGV("\tEffectCreate - Effect to be created is LVM_BASS_BOOST");
293        pSessionContext->bBassInstantiated = LVM_TRUE;
294        pContext->pBundledContext->SamplesToExitCountBb = 0;
295
296        pContext->itfe       = &gLvmEffectInterface;
297        pContext->EffectType = LVM_BASS_BOOST;
298    } else if (memcmp(uuid, &gVirtualizerDescriptor.uuid, sizeof(effect_uuid_t)) == 0){
299        // Create Virtualizer
300        ALOGV("\tEffectCreate - Effect to be created is LVM_VIRTUALIZER");
301        pSessionContext->bVirtualizerInstantiated=LVM_TRUE;
302        pContext->pBundledContext->SamplesToExitCountVirt = 0;
303
304        pContext->itfe       = &gLvmEffectInterface;
305        pContext->EffectType = LVM_VIRTUALIZER;
306    } else if (memcmp(uuid, &gEqualizerDescriptor.uuid, sizeof(effect_uuid_t)) == 0){
307        // Create Equalizer
308        ALOGV("\tEffectCreate - Effect to be created is LVM_EQUALIZER");
309        pSessionContext->bEqualizerInstantiated = LVM_TRUE;
310        pContext->pBundledContext->SamplesToExitCountEq = 0;
311
312        pContext->itfe       = &gLvmEffectInterface;
313        pContext->EffectType = LVM_EQUALIZER;
314    } else if (memcmp(uuid, &gVolumeDescriptor.uuid, sizeof(effect_uuid_t)) == 0){
315        // Create Volume
316        ALOGV("\tEffectCreate - Effect to be created is LVM_VOLUME");
317        pSessionContext->bVolumeInstantiated = LVM_TRUE;
318
319        pContext->itfe       = &gLvmEffectInterface;
320        pContext->EffectType = LVM_VOLUME;
321    }
322    else{
323        ALOGV("\tLVM_ERROR : EffectCreate() invalid UUID");
324        ret = -EINVAL;
325        goto exit;
326    }
327
328exit:
329    if (ret != 0) {
330        if (pContext != NULL) {
331            if (newBundle) {
332                GlobalSessionMemory[sessionNo].bBundledEffectsEnabled = LVM_FALSE;
333                SessionIndex[sessionNo] = LVM_UNUSED_SESSION;
334                delete pContext->pBundledContext;
335            }
336            delete pContext;
337        }
338        *pHandle = (effect_handle_t)NULL;
339    } else {
340        *pHandle = (effect_handle_t)pContext;
341    }
342    ALOGV("\tEffectCreate end..\n\n");
343    return ret;
344} /* end EffectCreate */
345
346extern "C" int EffectRelease(effect_handle_t handle){
347    ALOGV("\n\tEffectRelease start %p", handle);
348    EffectContext * pContext = (EffectContext *)handle;
349
350    ALOGV("\tEffectRelease start handle: %p, context %p", handle, pContext->pBundledContext);
351    if (pContext == NULL){
352        ALOGV("\tLVM_ERROR : EffectRelease called with NULL pointer");
353        return -EINVAL;
354    }
355
356    SessionContext *pSessionContext = &GlobalSessionMemory[pContext->pBundledContext->SessionNo];
357
358    // Clear the instantiated flag for the effect
359    // protect agains the case where an effect is un-instantiated without being disabled
360    if(pContext->EffectType == LVM_BASS_BOOST) {
361        ALOGV("\tEffectRelease LVM_BASS_BOOST Clearing global intstantiated flag");
362        pSessionContext->bBassInstantiated = LVM_FALSE;
363        if(pContext->pBundledContext->SamplesToExitCountBb > 0){
364            pContext->pBundledContext->NumberEffectsEnabled--;
365        }
366        pContext->pBundledContext->SamplesToExitCountBb = 0;
367    } else if(pContext->EffectType == LVM_VIRTUALIZER) {
368        ALOGV("\tEffectRelease LVM_VIRTUALIZER Clearing global intstantiated flag");
369        pSessionContext->bVirtualizerInstantiated = LVM_FALSE;
370        if(pContext->pBundledContext->SamplesToExitCountVirt > 0){
371            pContext->pBundledContext->NumberEffectsEnabled--;
372        }
373        pContext->pBundledContext->SamplesToExitCountVirt = 0;
374    } else if(pContext->EffectType == LVM_EQUALIZER) {
375        ALOGV("\tEffectRelease LVM_EQUALIZER Clearing global intstantiated flag");
376        pSessionContext->bEqualizerInstantiated =LVM_FALSE;
377        if(pContext->pBundledContext->SamplesToExitCountEq > 0){
378            pContext->pBundledContext->NumberEffectsEnabled--;
379        }
380        pContext->pBundledContext->SamplesToExitCountEq = 0;
381    } else if(pContext->EffectType == LVM_VOLUME) {
382        ALOGV("\tEffectRelease LVM_VOLUME Clearing global intstantiated flag");
383        pSessionContext->bVolumeInstantiated = LVM_FALSE;
384        if (pContext->pBundledContext->bVolumeEnabled == LVM_TRUE){
385            pContext->pBundledContext->NumberEffectsEnabled--;
386        }
387    } else {
388        ALOGV("\tLVM_ERROR : EffectRelease : Unsupported effect\n\n\n\n\n\n\n");
389    }
390
391    // Disable effect, in this case ignore errors (return codes)
392    // if an effect has already been disabled
393    Effect_setEnabled(pContext, LVM_FALSE);
394
395    // if all effects are no longer instantiaed free the lvm memory and delete BundledEffectContext
396    if ((pSessionContext->bBassInstantiated == LVM_FALSE) &&
397            (pSessionContext->bVolumeInstantiated == LVM_FALSE) &&
398            (pSessionContext->bEqualizerInstantiated ==LVM_FALSE) &&
399            (pSessionContext->bVirtualizerInstantiated==LVM_FALSE))
400    {
401        #ifdef LVM_PCM
402        if (pContext->pBundledContext->PcmInPtr != NULL) {
403            fclose(pContext->pBundledContext->PcmInPtr);
404            pContext->pBundledContext->PcmInPtr = NULL;
405        }
406        if (pContext->pBundledContext->PcmOutPtr != NULL) {
407            fclose(pContext->pBundledContext->PcmOutPtr);
408            pContext->pBundledContext->PcmOutPtr = NULL;
409        }
410        #endif
411
412
413        // Clear the SessionIndex
414        for(int i=0; i<LVM_MAX_SESSIONS; i++){
415            if(SessionIndex[i] == pContext->pBundledContext->SessionId){
416                SessionIndex[i] = LVM_UNUSED_SESSION;
417                ALOGV("\tEffectRelease: Clearing SessionIndex SessionNo %d for SessionId %d\n",
418                        i, pContext->pBundledContext->SessionId);
419                break;
420            }
421        }
422
423        ALOGV("\tEffectRelease: All effects are no longer instantiated\n");
424        pSessionContext->bBundledEffectsEnabled = LVM_FALSE;
425        pSessionContext->pBundledContext = LVM_NULL;
426        ALOGV("\tEffectRelease: Freeing LVM Bundle memory\n");
427        LvmEffect_free(pContext);
428        ALOGV("\tEffectRelease: Deleting LVM Bundle context %p\n", pContext->pBundledContext);
429        if (pContext->pBundledContext->workBuffer != NULL) {
430            free(pContext->pBundledContext->workBuffer);
431        }
432        delete pContext->pBundledContext;
433        pContext->pBundledContext = LVM_NULL;
434    }
435    // free the effect context for current effect
436    delete pContext;
437
438    ALOGV("\tEffectRelease end\n");
439    return 0;
440
441} /* end EffectRelease */
442
443extern "C" int EffectGetDescriptor(const effect_uuid_t *uuid,
444                                   effect_descriptor_t *pDescriptor) {
445    const effect_descriptor_t *desc = NULL;
446
447    if (pDescriptor == NULL || uuid == NULL){
448        ALOGV("EffectGetDescriptor() called with NULL pointer");
449        return -EINVAL;
450    }
451
452    if (memcmp(uuid, &gBassBoostDescriptor.uuid, sizeof(effect_uuid_t)) == 0) {
453        desc = &gBassBoostDescriptor;
454    } else if (memcmp(uuid, &gVirtualizerDescriptor.uuid, sizeof(effect_uuid_t)) == 0) {
455        desc = &gVirtualizerDescriptor;
456    } else if (memcmp(uuid, &gEqualizerDescriptor.uuid, sizeof(effect_uuid_t)) == 0) {
457        desc = &gEqualizerDescriptor;
458    } else if (memcmp(uuid, &gVolumeDescriptor.uuid, sizeof(effect_uuid_t)) == 0) {
459        desc = &gVolumeDescriptor;
460    }
461
462    if (desc == NULL) {
463        return  -EINVAL;
464    }
465
466    *pDescriptor = *desc;
467
468    return 0;
469} /* end EffectGetDescriptor */
470
471void LvmGlobalBundle_init(){
472    ALOGV("\tLvmGlobalBundle_init start");
473    for(int i=0; i<LVM_MAX_SESSIONS; i++){
474        GlobalSessionMemory[i].bBundledEffectsEnabled   = LVM_FALSE;
475        GlobalSessionMemory[i].bVolumeInstantiated      = LVM_FALSE;
476        GlobalSessionMemory[i].bEqualizerInstantiated   = LVM_FALSE;
477        GlobalSessionMemory[i].bBassInstantiated        = LVM_FALSE;
478        GlobalSessionMemory[i].bVirtualizerInstantiated = LVM_FALSE;
479        GlobalSessionMemory[i].pBundledContext          = LVM_NULL;
480
481        SessionIndex[i] = LVM_UNUSED_SESSION;
482    }
483    return;
484}
485//----------------------------------------------------------------------------
486// LvmBundle_init()
487//----------------------------------------------------------------------------
488// Purpose: Initialize engine with default configuration, creates instance
489// with all effects disabled.
490//
491// Inputs:
492//  pContext:   effect engine context
493//
494// Outputs:
495//
496//----------------------------------------------------------------------------
497
498int LvmBundle_init(EffectContext *pContext){
499    int status;
500
501    ALOGV("\tLvmBundle_init start");
502
503    pContext->config.inputCfg.accessMode                    = EFFECT_BUFFER_ACCESS_READ;
504    pContext->config.inputCfg.channels                      = AUDIO_CHANNEL_OUT_STEREO;
505    pContext->config.inputCfg.format                        = AUDIO_FORMAT_PCM_16_BIT;
506    pContext->config.inputCfg.samplingRate                  = 44100;
507    pContext->config.inputCfg.bufferProvider.getBuffer      = NULL;
508    pContext->config.inputCfg.bufferProvider.releaseBuffer  = NULL;
509    pContext->config.inputCfg.bufferProvider.cookie         = NULL;
510    pContext->config.inputCfg.mask                          = EFFECT_CONFIG_ALL;
511    pContext->config.outputCfg.accessMode                   = EFFECT_BUFFER_ACCESS_ACCUMULATE;
512    pContext->config.outputCfg.channels                     = AUDIO_CHANNEL_OUT_STEREO;
513    pContext->config.outputCfg.format                       = AUDIO_FORMAT_PCM_16_BIT;
514    pContext->config.outputCfg.samplingRate                 = 44100;
515    pContext->config.outputCfg.bufferProvider.getBuffer     = NULL;
516    pContext->config.outputCfg.bufferProvider.releaseBuffer = NULL;
517    pContext->config.outputCfg.bufferProvider.cookie        = NULL;
518    pContext->config.outputCfg.mask                         = EFFECT_CONFIG_ALL;
519
520    CHECK_ARG(pContext != NULL);
521
522    if (pContext->pBundledContext->hInstance != NULL){
523        ALOGV("\tLvmBundle_init pContext->pBassBoost != NULL "
524                "-> Calling pContext->pBassBoost->free()");
525
526        LvmEffect_free(pContext);
527
528        ALOGV("\tLvmBundle_init pContext->pBassBoost != NULL "
529                "-> Called pContext->pBassBoost->free()");
530    }
531
532    LVM_ReturnStatus_en     LvmStatus=LVM_SUCCESS;          /* Function call status */
533    LVM_ControlParams_t     params;                         /* Control Parameters */
534    LVM_InstParams_t        InstParams;                     /* Instance parameters */
535    LVM_EQNB_BandDef_t      BandDefs[MAX_NUM_BANDS];        /* Equaliser band definitions */
536    LVM_HeadroomParams_t    HeadroomParams;                 /* Headroom parameters */
537    LVM_HeadroomBandDef_t   HeadroomBandDef[LVM_HEADROOM_MAX_NBANDS];
538    LVM_MemTab_t            MemTab;                         /* Memory allocation table */
539    bool                    bMallocFailure = LVM_FALSE;
540
541    /* Set the capabilities */
542    InstParams.BufferMode       = LVM_UNMANAGED_BUFFERS;
543    InstParams.MaxBlockSize     = MAX_CALL_SIZE;
544    InstParams.EQNB_NumBands    = MAX_NUM_BANDS;
545    InstParams.PSA_Included     = LVM_PSA_ON;
546
547    /* Allocate memory, forcing alignment */
548    LvmStatus = LVM_GetMemoryTable(LVM_NULL,
549                                  &MemTab,
550                                  &InstParams);
551
552    LVM_ERROR_CHECK(LvmStatus, "LVM_GetMemoryTable", "LvmBundle_init")
553    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
554
555    ALOGV("\tCreateInstance Succesfully called LVM_GetMemoryTable\n");
556
557    /* Allocate memory */
558    for (int i=0; i<LVM_NR_MEMORY_REGIONS; i++){
559        if (MemTab.Region[i].Size != 0){
560            MemTab.Region[i].pBaseAddress = malloc(MemTab.Region[i].Size);
561
562            if (MemTab.Region[i].pBaseAddress == LVM_NULL){
563                ALOGV("\tLVM_ERROR :LvmBundle_init CreateInstance Failed to allocate %ld bytes "
564                        "for region %u\n", MemTab.Region[i].Size, i );
565                bMallocFailure = LVM_TRUE;
566            }else{
567                ALOGV("\tLvmBundle_init CreateInstance allocated %ld bytes for region %u at %p\n",
568                        MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress);
569            }
570        }
571    }
572
573    /* If one or more of the memory regions failed to allocate, free the regions that were
574     * succesfully allocated and return with an error
575     */
576    if(bMallocFailure == LVM_TRUE){
577        for (int i=0; i<LVM_NR_MEMORY_REGIONS; i++){
578            if (MemTab.Region[i].pBaseAddress == LVM_NULL){
579                ALOGV("\tLVM_ERROR :LvmBundle_init CreateInstance Failed to allocate %ld bytes "
580                        "for region %u Not freeing\n", MemTab.Region[i].Size, i );
581            }else{
582                ALOGV("\tLVM_ERROR :LvmBundle_init CreateInstance Failed: but allocated %ld bytes "
583                     "for region %u at %p- free\n",
584                     MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress);
585                free(MemTab.Region[i].pBaseAddress);
586            }
587        }
588        return -EINVAL;
589    }
590    ALOGV("\tLvmBundle_init CreateInstance Succesfully malloc'd memory\n");
591
592    /* Initialise */
593    pContext->pBundledContext->hInstance = LVM_NULL;
594
595    /* Init sets the instance handle */
596    LvmStatus = LVM_GetInstanceHandle(&pContext->pBundledContext->hInstance,
597                                      &MemTab,
598                                      &InstParams);
599
600    LVM_ERROR_CHECK(LvmStatus, "LVM_GetInstanceHandle", "LvmBundle_init")
601    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
602
603    ALOGV("\tLvmBundle_init CreateInstance Succesfully called LVM_GetInstanceHandle\n");
604
605    /* Set the initial process parameters */
606    /* General parameters */
607    params.OperatingMode          = LVM_MODE_ON;
608    params.SampleRate             = LVM_FS_44100;
609    params.SourceFormat           = LVM_STEREO;
610    params.SpeakerType            = LVM_HEADPHONES;
611
612    pContext->pBundledContext->SampleRate = LVM_FS_44100;
613
614    /* Concert Sound parameters */
615    params.VirtualizerOperatingMode   = LVM_MODE_OFF;
616    params.VirtualizerType            = LVM_CONCERTSOUND;
617    params.VirtualizerReverbLevel     = 100;
618    params.CS_EffectLevel             = LVM_CS_EFFECT_NONE;
619
620    /* N-Band Equaliser parameters */
621    params.EQNB_OperatingMode     = LVM_EQNB_OFF;
622    params.EQNB_NBands            = FIVEBAND_NUMBANDS;
623    params.pEQNB_BandDefinition   = &BandDefs[0];
624
625    for (int i=0; i<FIVEBAND_NUMBANDS; i++)
626    {
627        BandDefs[i].Frequency = EQNB_5BandPresetsFrequencies[i];
628        BandDefs[i].QFactor   = EQNB_5BandPresetsQFactors[i];
629        BandDefs[i].Gain      = EQNB_5BandSoftPresets[i];
630    }
631
632    /* Volume Control parameters */
633    params.VC_EffectLevel         = 0;
634    params.VC_Balance             = 0;
635
636    /* Treble Enhancement parameters */
637    params.TE_OperatingMode       = LVM_TE_OFF;
638    params.TE_EffectLevel         = 0;
639
640    /* PSA Control parameters */
641    params.PSA_Enable             = LVM_PSA_OFF;
642    params.PSA_PeakDecayRate      = (LVM_PSA_DecaySpeed_en)0;
643
644    /* Bass Enhancement parameters */
645    params.BE_OperatingMode       = LVM_BE_OFF;
646    params.BE_EffectLevel         = 0;
647    params.BE_CentreFreq          = LVM_BE_CENTRE_90Hz;
648    params.BE_HPF                 = LVM_BE_HPF_ON;
649
650    /* PSA Control parameters */
651    params.PSA_Enable             = LVM_PSA_OFF;
652    params.PSA_PeakDecayRate      = LVM_PSA_SPEED_MEDIUM;
653
654    /* TE Control parameters */
655    params.TE_OperatingMode       = LVM_TE_OFF;
656    params.TE_EffectLevel         = 0;
657
658    /* Activate the initial settings */
659    LvmStatus = LVM_SetControlParameters(pContext->pBundledContext->hInstance,
660                                         &params);
661
662    LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "LvmBundle_init")
663    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
664
665    ALOGV("\tLvmBundle_init CreateInstance Succesfully called LVM_SetControlParameters\n");
666
667    /* Set the headroom parameters */
668    HeadroomBandDef[0].Limit_Low          = 20;
669    HeadroomBandDef[0].Limit_High         = 4999;
670    HeadroomBandDef[0].Headroom_Offset    = 0;
671    HeadroomBandDef[1].Limit_Low          = 5000;
672    HeadroomBandDef[1].Limit_High         = 24000;
673    HeadroomBandDef[1].Headroom_Offset    = 0;
674    HeadroomParams.pHeadroomDefinition    = &HeadroomBandDef[0];
675    HeadroomParams.Headroom_OperatingMode = LVM_HEADROOM_ON;
676    HeadroomParams.NHeadroomBands         = 2;
677
678    LvmStatus = LVM_SetHeadroomParams(pContext->pBundledContext->hInstance,
679                                      &HeadroomParams);
680
681    LVM_ERROR_CHECK(LvmStatus, "LVM_SetHeadroomParams", "LvmBundle_init")
682    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
683
684    ALOGV("\tLvmBundle_init CreateInstance Succesfully called LVM_SetHeadroomParams\n");
685    ALOGV("\tLvmBundle_init End");
686    return 0;
687}   /* end LvmBundle_init */
688
689
690//----------------------------------------------------------------------------
691// LvmBundle_process()
692//----------------------------------------------------------------------------
693// Purpose:
694// Apply LVM Bundle effects
695//
696// Inputs:
697//  pIn:        pointer to stereo 16 bit input data
698//  pOut:       pointer to stereo 16 bit output data
699//  frameCount: Frames to process
700//  pContext:   effect engine context
701//  strength    strength to be applied
702//
703//  Outputs:
704//  pOut:       pointer to updated stereo 16 bit output data
705//
706//----------------------------------------------------------------------------
707
708int LvmBundle_process(LVM_INT16        *pIn,
709                      LVM_INT16        *pOut,
710                      int              frameCount,
711                      EffectContext    *pContext){
712
713    LVM_ControlParams_t     ActiveParams;                           /* Current control Parameters */
714    LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;                /* Function call status */
715    LVM_INT16               *pOutTmp;
716
717    if (pContext->config.outputCfg.accessMode == EFFECT_BUFFER_ACCESS_WRITE){
718        pOutTmp = pOut;
719    }else if (pContext->config.outputCfg.accessMode == EFFECT_BUFFER_ACCESS_ACCUMULATE){
720        if (pContext->pBundledContext->frameCount != frameCount) {
721            if (pContext->pBundledContext->workBuffer != NULL) {
722                free(pContext->pBundledContext->workBuffer);
723            }
724            pContext->pBundledContext->workBuffer =
725                    (LVM_INT16 *)malloc(frameCount * sizeof(LVM_INT16) * 2);
726            pContext->pBundledContext->frameCount = frameCount;
727        }
728        pOutTmp = pContext->pBundledContext->workBuffer;
729    }else{
730        ALOGV("LVM_ERROR : LvmBundle_process invalid access mode");
731        return -EINVAL;
732    }
733
734    #ifdef LVM_PCM
735    fwrite(pIn, frameCount*sizeof(LVM_INT16)*2, 1, pContext->pBundledContext->PcmInPtr);
736    fflush(pContext->pBundledContext->PcmInPtr);
737    #endif
738
739    //ALOGV("Calling LVM_Process");
740
741    /* Process the samples */
742    LvmStatus = LVM_Process(pContext->pBundledContext->hInstance, /* Instance handle */
743                            pIn,                                  /* Input buffer */
744                            pOutTmp,                              /* Output buffer */
745                            (LVM_UINT16)frameCount,               /* Number of samples to read */
746                            0);                                   /* Audo Time */
747
748    LVM_ERROR_CHECK(LvmStatus, "LVM_Process", "LvmBundle_process")
749    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
750
751    #ifdef LVM_PCM
752    fwrite(pOutTmp, frameCount*sizeof(LVM_INT16)*2, 1, pContext->pBundledContext->PcmOutPtr);
753    fflush(pContext->pBundledContext->PcmOutPtr);
754    #endif
755
756    if (pContext->config.outputCfg.accessMode == EFFECT_BUFFER_ACCESS_ACCUMULATE){
757        for (int i=0; i<frameCount*2; i++){
758            pOut[i] = clamp16((LVM_INT32)pOut[i] + (LVM_INT32)pOutTmp[i]);
759        }
760    }
761    return 0;
762}    /* end LvmBundle_process */
763
764//----------------------------------------------------------------------------
765// LvmEffect_enable()
766//----------------------------------------------------------------------------
767// Purpose: Enable the effect in the bundle
768//
769// Inputs:
770//  pContext:   effect engine context
771//
772// Outputs:
773//
774//----------------------------------------------------------------------------
775
776int LvmEffect_enable(EffectContext *pContext){
777    //ALOGV("\tLvmEffect_enable start");
778
779    LVM_ControlParams_t     ActiveParams;                           /* Current control Parameters */
780    LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;                /* Function call status */
781
782    /* Get the current settings */
783    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance,
784                                         &ActiveParams);
785
786    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "LvmEffect_enable")
787    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
788    //ALOGV("\tLvmEffect_enable Succesfully called LVM_GetControlParameters\n");
789
790    if(pContext->EffectType == LVM_BASS_BOOST) {
791        ALOGV("\tLvmEffect_enable : Enabling LVM_BASS_BOOST");
792        ActiveParams.BE_OperatingMode       = LVM_BE_ON;
793    }
794    if(pContext->EffectType == LVM_VIRTUALIZER) {
795        ALOGV("\tLvmEffect_enable : Enabling LVM_VIRTUALIZER");
796        ActiveParams.VirtualizerOperatingMode   = LVM_MODE_ON;
797    }
798    if(pContext->EffectType == LVM_EQUALIZER) {
799        ALOGV("\tLvmEffect_enable : Enabling LVM_EQUALIZER");
800        ActiveParams.EQNB_OperatingMode     = LVM_EQNB_ON;
801    }
802    if(pContext->EffectType == LVM_VOLUME) {
803        ALOGV("\tLvmEffect_enable : Enabling LVM_VOLUME");
804    }
805
806    LvmStatus = LVM_SetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
807    LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "LvmEffect_enable")
808    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
809
810    //ALOGV("\tLvmEffect_enable Succesfully called LVM_SetControlParameters\n");
811    //ALOGV("\tLvmEffect_enable end");
812    return 0;
813}
814
815//----------------------------------------------------------------------------
816// LvmEffect_disable()
817//----------------------------------------------------------------------------
818// Purpose: Disable the effect in the bundle
819//
820// Inputs:
821//  pContext:   effect engine context
822//
823// Outputs:
824//
825//----------------------------------------------------------------------------
826
827int LvmEffect_disable(EffectContext *pContext){
828    //ALOGV("\tLvmEffect_disable start");
829
830    LVM_ControlParams_t     ActiveParams;                           /* Current control Parameters */
831    LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;                /* Function call status */
832    /* Get the current settings */
833    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance,
834                                         &ActiveParams);
835
836    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "LvmEffect_disable")
837    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
838    //ALOGV("\tLvmEffect_disable Succesfully called LVM_GetControlParameters\n");
839
840    if(pContext->EffectType == LVM_BASS_BOOST) {
841        ALOGV("\tLvmEffect_disable : Disabling LVM_BASS_BOOST");
842        ActiveParams.BE_OperatingMode       = LVM_BE_OFF;
843    }
844    if(pContext->EffectType == LVM_VIRTUALIZER) {
845        ALOGV("\tLvmEffect_disable : Disabling LVM_VIRTUALIZER");
846        ActiveParams.VirtualizerOperatingMode   = LVM_MODE_OFF;
847    }
848    if(pContext->EffectType == LVM_EQUALIZER) {
849        ALOGV("\tLvmEffect_disable : Disabling LVM_EQUALIZER");
850        ActiveParams.EQNB_OperatingMode     = LVM_EQNB_OFF;
851    }
852    if(pContext->EffectType == LVM_VOLUME) {
853        ALOGV("\tLvmEffect_disable : Disabling LVM_VOLUME");
854    }
855
856    LvmStatus = LVM_SetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
857    LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "LvmEffect_disable")
858    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
859
860    //ALOGV("\tLvmEffect_disable Succesfully called LVM_SetControlParameters\n");
861    //ALOGV("\tLvmEffect_disable end");
862    return 0;
863}
864
865//----------------------------------------------------------------------------
866// LvmEffect_free()
867//----------------------------------------------------------------------------
868// Purpose: Free all memory associated with the Bundle.
869//
870// Inputs:
871//  pContext:   effect engine context
872//
873// Outputs:
874//
875//----------------------------------------------------------------------------
876
877void LvmEffect_free(EffectContext *pContext){
878    LVM_ReturnStatus_en     LvmStatus=LVM_SUCCESS;         /* Function call status */
879    LVM_ControlParams_t     params;                        /* Control Parameters */
880    LVM_MemTab_t            MemTab;
881
882    /* Free the algorithm memory */
883    LvmStatus = LVM_GetMemoryTable(pContext->pBundledContext->hInstance,
884                                   &MemTab,
885                                   LVM_NULL);
886
887    LVM_ERROR_CHECK(LvmStatus, "LVM_GetMemoryTable", "LvmEffect_free")
888
889    for (int i=0; i<LVM_NR_MEMORY_REGIONS; i++){
890        if (MemTab.Region[i].Size != 0){
891            if (MemTab.Region[i].pBaseAddress != NULL){
892                ALOGV("\tLvmEffect_free - START freeing %ld bytes for region %u at %p\n",
893                        MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress);
894
895                free(MemTab.Region[i].pBaseAddress);
896
897                ALOGV("\tLvmEffect_free - END   freeing %ld bytes for region %u at %p\n",
898                        MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress);
899            }else{
900                ALOGV("\tLVM_ERROR : LvmEffect_free - trying to free with NULL pointer %ld bytes "
901                        "for region %u at %p ERROR\n",
902                        MemTab.Region[i].Size, i, MemTab.Region[i].pBaseAddress);
903            }
904        }
905    }
906}    /* end LvmEffect_free */
907
908//----------------------------------------------------------------------------
909// Effect_setConfig()
910//----------------------------------------------------------------------------
911// Purpose: Set input and output audio configuration.
912//
913// Inputs:
914//  pContext:   effect engine context
915//  pConfig:    pointer to effect_config_t structure holding input and output
916//      configuration parameters
917//
918// Outputs:
919//
920//----------------------------------------------------------------------------
921
922int Effect_setConfig(EffectContext *pContext, effect_config_t *pConfig){
923    LVM_Fs_en   SampleRate;
924    //ALOGV("\tEffect_setConfig start");
925
926    CHECK_ARG(pContext != NULL);
927    CHECK_ARG(pConfig != NULL);
928
929    CHECK_ARG(pConfig->inputCfg.samplingRate == pConfig->outputCfg.samplingRate);
930    CHECK_ARG(pConfig->inputCfg.channels == pConfig->outputCfg.channels);
931    CHECK_ARG(pConfig->inputCfg.format == pConfig->outputCfg.format);
932    CHECK_ARG(pConfig->inputCfg.channels == AUDIO_CHANNEL_OUT_STEREO);
933    CHECK_ARG(pConfig->outputCfg.accessMode == EFFECT_BUFFER_ACCESS_WRITE
934              || pConfig->outputCfg.accessMode == EFFECT_BUFFER_ACCESS_ACCUMULATE);
935    CHECK_ARG(pConfig->inputCfg.format == AUDIO_FORMAT_PCM_16_BIT);
936
937    pContext->config = *pConfig;
938
939    switch (pConfig->inputCfg.samplingRate) {
940    case 8000:
941        SampleRate = LVM_FS_8000;
942        pContext->pBundledContext->SamplesPerSecond = 8000*2; // 2 secs Stereo
943        break;
944    case 16000:
945        SampleRate = LVM_FS_16000;
946        pContext->pBundledContext->SamplesPerSecond = 16000*2; // 2 secs Stereo
947        break;
948    case 22050:
949        SampleRate = LVM_FS_22050;
950        pContext->pBundledContext->SamplesPerSecond = 22050*2; // 2 secs Stereo
951        break;
952    case 32000:
953        SampleRate = LVM_FS_32000;
954        pContext->pBundledContext->SamplesPerSecond = 32000*2; // 2 secs Stereo
955        break;
956    case 44100:
957        SampleRate = LVM_FS_44100;
958        pContext->pBundledContext->SamplesPerSecond = 44100*2; // 2 secs Stereo
959        break;
960    case 48000:
961        SampleRate = LVM_FS_48000;
962        pContext->pBundledContext->SamplesPerSecond = 48000*2; // 2 secs Stereo
963        break;
964    default:
965        ALOGV("\tEffect_setConfig invalid sampling rate %d", pConfig->inputCfg.samplingRate);
966        return -EINVAL;
967    }
968
969    if(pContext->pBundledContext->SampleRate != SampleRate){
970
971        LVM_ControlParams_t     ActiveParams;
972        LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;
973
974        ALOGV("\tEffect_setConfig change sampling rate to %d", SampleRate);
975
976        /* Get the current settings */
977        LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance,
978                                         &ActiveParams);
979
980        LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "Effect_setConfig")
981        if(LvmStatus != LVM_SUCCESS) return -EINVAL;
982
983        ActiveParams.SampleRate = SampleRate;
984
985        LvmStatus = LVM_SetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
986
987        LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "Effect_setConfig")
988        ALOGV("\tEffect_setConfig Succesfully called LVM_SetControlParameters\n");
989        pContext->pBundledContext->SampleRate = SampleRate;
990
991    }else{
992        //ALOGV("\tEffect_setConfig keep sampling rate at %d", SampleRate);
993    }
994
995    //ALOGV("\tEffect_setConfig End....");
996    return 0;
997}   /* end Effect_setConfig */
998
999//----------------------------------------------------------------------------
1000// Effect_getConfig()
1001//----------------------------------------------------------------------------
1002// Purpose: Get input and output audio configuration.
1003//
1004// Inputs:
1005//  pContext:   effect engine context
1006//  pConfig:    pointer to effect_config_t structure holding input and output
1007//      configuration parameters
1008//
1009// Outputs:
1010//
1011//----------------------------------------------------------------------------
1012
1013void Effect_getConfig(EffectContext *pContext, effect_config_t *pConfig)
1014{
1015    *pConfig = pContext->config;
1016}   /* end Effect_getConfig */
1017
1018//----------------------------------------------------------------------------
1019// BassGetStrength()
1020//----------------------------------------------------------------------------
1021// Purpose:
1022// get the effect strength currently being used, what is actually returned is the strengh that was
1023// previously used in the set, this is because the app uses a strength in the range 0-1000 while
1024// the bassboost uses 1-15, so to avoid a quantisation the original set value is used. However the
1025// actual used value is checked to make sure it corresponds to the one being returned
1026//
1027// Inputs:
1028//  pContext:   effect engine context
1029//
1030//----------------------------------------------------------------------------
1031
1032uint32_t BassGetStrength(EffectContext *pContext){
1033    //ALOGV("\tBassGetStrength() (0-1000) -> %d\n", pContext->pBundledContext->BassStrengthSaved);
1034
1035    LVM_ControlParams_t     ActiveParams;                           /* Current control Parameters */
1036    LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;                /* Function call status */
1037    /* Get the current settings */
1038    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance,
1039                                         &ActiveParams);
1040
1041    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "BassGetStrength")
1042    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
1043
1044    //ALOGV("\tBassGetStrength Succesfully returned from LVM_GetControlParameters\n");
1045
1046    /* Check that the strength returned matches the strength that was set earlier */
1047    if(ActiveParams.BE_EffectLevel !=
1048       (LVM_INT16)((15*pContext->pBundledContext->BassStrengthSaved)/1000)){
1049        ALOGV("\tLVM_ERROR : BassGetStrength module strength does not match savedStrength %d %d\n",
1050                ActiveParams.BE_EffectLevel, pContext->pBundledContext->BassStrengthSaved);
1051        return -EINVAL;
1052    }
1053
1054    //ALOGV("\tBassGetStrength() (0-15)   -> %d\n", ActiveParams.BE_EffectLevel );
1055    //ALOGV("\tBassGetStrength() (saved)  -> %d\n", pContext->pBundledContext->BassStrengthSaved );
1056    return pContext->pBundledContext->BassStrengthSaved;
1057}    /* end BassGetStrength */
1058
1059//----------------------------------------------------------------------------
1060// BassSetStrength()
1061//----------------------------------------------------------------------------
1062// Purpose:
1063// Apply the strength to the BassBosst. Must first be converted from the range 0-1000 to 1-15
1064//
1065// Inputs:
1066//  pContext:   effect engine context
1067//  strength    strength to be applied
1068//
1069//----------------------------------------------------------------------------
1070
1071void BassSetStrength(EffectContext *pContext, uint32_t strength){
1072    //ALOGV("\tBassSetStrength(%d)", strength);
1073
1074    pContext->pBundledContext->BassStrengthSaved = (int)strength;
1075
1076    LVM_ControlParams_t     ActiveParams;              /* Current control Parameters */
1077    LVM_ReturnStatus_en     LvmStatus=LVM_SUCCESS;     /* Function call status */
1078
1079    /* Get the current settings */
1080    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance,
1081                                         &ActiveParams);
1082
1083    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "BassSetStrength")
1084    //ALOGV("\tBassSetStrength Succesfully returned from LVM_GetControlParameters\n");
1085
1086    /* Bass Enhancement parameters */
1087    ActiveParams.BE_EffectLevel    = (LVM_INT16)((15*strength)/1000);
1088    ActiveParams.BE_CentreFreq     = LVM_BE_CENTRE_90Hz;
1089
1090    //ALOGV("\tBassSetStrength() (0-15)   -> %d\n", ActiveParams.BE_EffectLevel );
1091
1092    /* Activate the initial settings */
1093    LvmStatus = LVM_SetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1094
1095    LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "BassSetStrength")
1096    //ALOGV("\tBassSetStrength Succesfully called LVM_SetControlParameters\n");
1097}    /* end BassSetStrength */
1098
1099//----------------------------------------------------------------------------
1100// VirtualizerGetStrength()
1101//----------------------------------------------------------------------------
1102// Purpose:
1103// get the effect strength currently being used, what is actually returned is the strengh that was
1104// previously used in the set, this is because the app uses a strength in the range 0-1000 while
1105// the Virtualizer uses 1-100, so to avoid a quantisation the original set value is used.However the
1106// actual used value is checked to make sure it corresponds to the one being returned
1107//
1108// Inputs:
1109//  pContext:   effect engine context
1110//
1111//----------------------------------------------------------------------------
1112
1113uint32_t VirtualizerGetStrength(EffectContext *pContext){
1114    //ALOGV("\tVirtualizerGetStrength (0-1000) -> %d\n",pContext->pBundledContext->VirtStrengthSaved);
1115
1116    LVM_ControlParams_t     ActiveParams;                           /* Current control Parameters */
1117    LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;                /* Function call status */
1118
1119    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1120
1121    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "VirtualizerGetStrength")
1122    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
1123
1124    //ALOGV("\tVirtualizerGetStrength Succesfully returned from LVM_GetControlParameters\n");
1125    //ALOGV("\tVirtualizerGetStrength() (0-100)   -> %d\n", ActiveParams.VirtualizerReverbLevel*10);
1126    return pContext->pBundledContext->VirtStrengthSaved;
1127}    /* end getStrength */
1128
1129//----------------------------------------------------------------------------
1130// VirtualizerSetStrength()
1131//----------------------------------------------------------------------------
1132// Purpose:
1133// Apply the strength to the Virtualizer. Must first be converted from the range 0-1000 to 1-15
1134//
1135// Inputs:
1136//  pContext:   effect engine context
1137//  strength    strength to be applied
1138//
1139//----------------------------------------------------------------------------
1140
1141void VirtualizerSetStrength(EffectContext *pContext, uint32_t strength){
1142    //ALOGV("\tVirtualizerSetStrength(%d)", strength);
1143    LVM_ControlParams_t     ActiveParams;              /* Current control Parameters */
1144    LVM_ReturnStatus_en     LvmStatus=LVM_SUCCESS;     /* Function call status */
1145
1146    pContext->pBundledContext->VirtStrengthSaved = (int)strength;
1147
1148    /* Get the current settings */
1149    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance,&ActiveParams);
1150
1151    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "VirtualizerSetStrength")
1152    //ALOGV("\tVirtualizerSetStrength Succesfully returned from LVM_GetControlParameters\n");
1153
1154    /* Virtualizer parameters */
1155    ActiveParams.CS_EffectLevel             = (int)((strength*32767)/1000);
1156
1157    //ALOGV("\tVirtualizerSetStrength() (0-1000)   -> %d\n", strength );
1158    //ALOGV("\tVirtualizerSetStrength() (0- 100)   -> %d\n", ActiveParams.CS_EffectLevel );
1159
1160    /* Activate the initial settings */
1161    LvmStatus = LVM_SetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1162    LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "VirtualizerSetStrength")
1163    //ALOGV("\tVirtualizerSetStrength Succesfully called LVM_SetControlParameters\n\n");
1164}    /* end setStrength */
1165
1166
1167//----------------------------------------------------------------------------
1168// EqualizerLimitBandLevels()
1169//----------------------------------------------------------------------------
1170// Purpose: limit all EQ band gains to a value less than 0 dB while
1171//          preserving the relative band levels.
1172//
1173// Inputs:
1174//  pContext:   effect engine context
1175//
1176// Outputs:
1177//
1178//----------------------------------------------------------------------------
1179void EqualizerLimitBandLevels(EffectContext *pContext) {
1180    LVM_ControlParams_t     ActiveParams;              /* Current control Parameters */
1181    LVM_ReturnStatus_en     LvmStatus=LVM_SUCCESS;     /* Function call status */
1182
1183    /* Get the current settings */
1184    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1185    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "EqualizerLimitBandLevels")
1186    //ALOGV("\tEqualizerLimitBandLevels Succesfully returned from LVM_GetControlParameters\n");
1187    //ALOGV("\tEqualizerLimitBandLevels just Got -> %d\n",
1188    //          ActiveParams.pEQNB_BandDefinition[band].Gain);
1189
1190    // Apply a volume correction to avoid clipping in the EQ based on 2 factors:
1191    // - the maximum EQ band gain: the volume correction is such that the total of volume + max
1192    // band gain is <= 0 dB
1193    // - the average gain in all bands weighted by their proximity to max gain band.
1194    int maxGain = 0;
1195    int avgGain = 0;
1196    int avgCount = 0;
1197    for (int i = 0; i < FIVEBAND_NUMBANDS; i++) {
1198        if (pContext->pBundledContext->bandGaindB[i] >= maxGain) {
1199            int tmpMaxGain = pContext->pBundledContext->bandGaindB[i];
1200            int tmpAvgGain = 0;
1201            int tmpAvgCount = 0;
1202            for (int j = 0; j < FIVEBAND_NUMBANDS; j++) {
1203                int gain = pContext->pBundledContext->bandGaindB[j];
1204                // skip current band and gains < 0 dB
1205                if (j == i || gain < 0)
1206                    continue;
1207                // no need to continue if one band not processed yet has a higher gain than current
1208                // max
1209                if (gain > tmpMaxGain) {
1210                    // force skipping "if (tmpAvgGain >= avgGain)" below as tmpAvgGain is not
1211                    // meaningful in this case
1212                    tmpAvgGain = -1;
1213                    break;
1214                }
1215
1216                int weight = 1;
1217                if (j < (i + 2) && j > (i - 2))
1218                    weight = 4;
1219                tmpAvgGain += weight * gain;
1220                tmpAvgCount += weight;
1221            }
1222            if (tmpAvgGain >= avgGain) {
1223                maxGain = tmpMaxGain;
1224                avgGain = tmpAvgGain;
1225                avgCount = tmpAvgCount;
1226            }
1227        }
1228        ActiveParams.pEQNB_BandDefinition[i].Frequency = EQNB_5BandPresetsFrequencies[i];
1229        ActiveParams.pEQNB_BandDefinition[i].QFactor   = EQNB_5BandPresetsQFactors[i];
1230        ActiveParams.pEQNB_BandDefinition[i].Gain = pContext->pBundledContext->bandGaindB[i];
1231    }
1232
1233    int gainCorrection = 0;
1234    if (maxGain + pContext->pBundledContext->volume > 0) {
1235        gainCorrection = maxGain + pContext->pBundledContext->volume;
1236    }
1237    if (avgCount) {
1238        gainCorrection += avgGain/avgCount;
1239    }
1240
1241    ALOGV("EqualizerLimitBandLevels() gainCorrection %d maxGain %d avgGain %d avgCount %d",
1242            gainCorrection, maxGain, avgGain, avgCount);
1243
1244    ActiveParams.VC_EffectLevel  = pContext->pBundledContext->volume - gainCorrection;
1245    if (ActiveParams.VC_EffectLevel < -96) {
1246        ActiveParams.VC_EffectLevel = -96;
1247    }
1248
1249    /* Activate the initial settings */
1250    LvmStatus = LVM_SetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1251    LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "EqualizerLimitBandLevels")
1252    //ALOGV("\tEqualizerLimitBandLevels just Set -> %d\n",
1253    //          ActiveParams.pEQNB_BandDefinition[band].Gain);
1254
1255    //ALOGV("\tEqualizerLimitBandLevels just set (-96dB -> 0dB)   -> %d\n",ActiveParams.VC_EffectLevel );
1256    if(pContext->pBundledContext->firstVolume == LVM_TRUE){
1257        LvmStatus = LVM_SetVolumeNoSmoothing(pContext->pBundledContext->hInstance, &ActiveParams);
1258        LVM_ERROR_CHECK(LvmStatus, "LVM_SetVolumeNoSmoothing", "LvmBundle_process")
1259        ALOGV("\tLVM_VOLUME: Disabling Smoothing for first volume change to remove spikes/clicks");
1260        pContext->pBundledContext->firstVolume = LVM_FALSE;
1261    }
1262}
1263
1264
1265//----------------------------------------------------------------------------
1266// EqualizerGetBandLevel()
1267//----------------------------------------------------------------------------
1268// Purpose: Retrieve the gain currently being used for the band passed in
1269//
1270// Inputs:
1271//  band:       band number
1272//  pContext:   effect engine context
1273//
1274// Outputs:
1275//
1276//----------------------------------------------------------------------------
1277int32_t EqualizerGetBandLevel(EffectContext *pContext, int32_t band){
1278    //ALOGV("\tEqualizerGetBandLevel -> %d\n", pContext->pBundledContext->bandGaindB[band] );
1279    return pContext->pBundledContext->bandGaindB[band] * 100;
1280}
1281
1282//----------------------------------------------------------------------------
1283// EqualizerSetBandLevel()
1284//----------------------------------------------------------------------------
1285// Purpose:
1286//  Sets gain value for the given band.
1287//
1288// Inputs:
1289//  band:       band number
1290//  Gain:       Gain to be applied in millibels
1291//  pContext:   effect engine context
1292//
1293// Outputs:
1294//
1295//---------------------------------------------------------------------------
1296void EqualizerSetBandLevel(EffectContext *pContext, int band, short Gain){
1297    int gainRounded;
1298    if(Gain > 0){
1299        gainRounded = (int)((Gain+50)/100);
1300    }else{
1301        gainRounded = (int)((Gain-50)/100);
1302    }
1303    //ALOGV("\tEqualizerSetBandLevel(%d)->(%d)", Gain, gainRounded);
1304    pContext->pBundledContext->bandGaindB[band] = gainRounded;
1305    pContext->pBundledContext->CurPreset = PRESET_CUSTOM;
1306
1307    EqualizerLimitBandLevels(pContext);
1308}
1309
1310//----------------------------------------------------------------------------
1311// EqualizerGetCentreFrequency()
1312//----------------------------------------------------------------------------
1313// Purpose: Retrieve the frequency being used for the band passed in
1314//
1315// Inputs:
1316//  band:       band number
1317//  pContext:   effect engine context
1318//
1319// Outputs:
1320//
1321//----------------------------------------------------------------------------
1322int32_t EqualizerGetCentreFrequency(EffectContext *pContext, int32_t band){
1323    int32_t Frequency =0;
1324
1325    LVM_ControlParams_t     ActiveParams;                           /* Current control Parameters */
1326    LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;                /* Function call status */
1327    LVM_EQNB_BandDef_t      *BandDef;
1328    /* Get the current settings */
1329    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance,
1330                                         &ActiveParams);
1331
1332    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "EqualizerGetCentreFrequency")
1333
1334    BandDef   = ActiveParams.pEQNB_BandDefinition;
1335    Frequency = (int32_t)BandDef[band].Frequency*1000;     // Convert to millibels
1336
1337    //ALOGV("\tEqualizerGetCentreFrequency -> %d\n", Frequency );
1338    //ALOGV("\tEqualizerGetCentreFrequency Succesfully returned from LVM_GetControlParameters\n");
1339    return Frequency;
1340}
1341
1342//----------------------------------------------------------------------------
1343// EqualizerGetBandFreqRange(
1344//----------------------------------------------------------------------------
1345// Purpose:
1346//
1347// Gets lower and upper boundaries of a band.
1348// For the high shelf, the low bound is the band frequency and the high
1349// bound is Nyquist.
1350// For the peaking filters, they are the gain[dB]/2 points.
1351//
1352// Inputs:
1353//  band:       band number
1354//  pContext:   effect engine context
1355//
1356// Outputs:
1357//  pLow:       lower band range
1358//  pLow:       upper band range
1359//----------------------------------------------------------------------------
1360int32_t EqualizerGetBandFreqRange(EffectContext *pContext, int32_t band, uint32_t *pLow,
1361                                  uint32_t *pHi){
1362    *pLow = bandFreqRange[band][0];
1363    *pHi  = bandFreqRange[band][1];
1364    return 0;
1365}
1366
1367//----------------------------------------------------------------------------
1368// EqualizerGetBand(
1369//----------------------------------------------------------------------------
1370// Purpose:
1371//
1372// Returns the band with the maximum influence on a given frequency.
1373// Result is unaffected by whether EQ is enabled or not, or by whether
1374// changes have been committed or not.
1375//
1376// Inputs:
1377//  targetFreq   The target frequency, in millihertz.
1378//  pContext:    effect engine context
1379//
1380// Outputs:
1381//  pLow:       lower band range
1382//  pLow:       upper band range
1383//----------------------------------------------------------------------------
1384int32_t EqualizerGetBand(EffectContext *pContext, uint32_t targetFreq){
1385    int band = 0;
1386
1387    if(targetFreq < bandFreqRange[0][0]){
1388        return -EINVAL;
1389    }else if(targetFreq == bandFreqRange[0][0]){
1390        return 0;
1391    }
1392    for(int i=0; i<FIVEBAND_NUMBANDS;i++){
1393        if((targetFreq > bandFreqRange[i][0])&&(targetFreq <= bandFreqRange[i][1])){
1394            band = i;
1395        }
1396    }
1397    return band;
1398}
1399
1400//----------------------------------------------------------------------------
1401// EqualizerGetPreset(
1402//----------------------------------------------------------------------------
1403// Purpose:
1404//
1405// Gets the currently set preset ID.
1406// Will return PRESET_CUSTOM in case the EQ parameters have been modified
1407// manually since a preset was set.
1408//
1409// Inputs:
1410//  pContext:    effect engine context
1411//
1412//----------------------------------------------------------------------------
1413int32_t EqualizerGetPreset(EffectContext *pContext){
1414    return pContext->pBundledContext->CurPreset;
1415}
1416
1417//----------------------------------------------------------------------------
1418// EqualizerSetPreset(
1419//----------------------------------------------------------------------------
1420// Purpose:
1421//
1422// Sets the current preset by ID.
1423// All the band parameters will be overridden.
1424//
1425// Inputs:
1426//  pContext:    effect engine context
1427//  preset       The preset ID.
1428//
1429//----------------------------------------------------------------------------
1430void EqualizerSetPreset(EffectContext *pContext, int preset){
1431
1432    //ALOGV("\tEqualizerSetPreset(%d)", preset);
1433    pContext->pBundledContext->CurPreset = preset;
1434
1435    //ActiveParams.pEQNB_BandDefinition = &BandDefs[0];
1436    for (int i=0; i<FIVEBAND_NUMBANDS; i++)
1437    {
1438        pContext->pBundledContext->bandGaindB[i] =
1439                EQNB_5BandSoftPresets[i + preset * FIVEBAND_NUMBANDS];
1440    }
1441
1442    EqualizerLimitBandLevels(pContext);
1443
1444    //ALOGV("\tEqualizerSetPreset Succesfully called LVM_SetControlParameters\n");
1445    return;
1446}
1447
1448int32_t EqualizerGetNumPresets(){
1449    return sizeof(gEqualizerPresets) / sizeof(PresetConfig);
1450}
1451
1452//----------------------------------------------------------------------------
1453// EqualizerGetPresetName(
1454//----------------------------------------------------------------------------
1455// Purpose:
1456// Gets a human-readable name for a preset ID. Will return "Custom" if
1457// PRESET_CUSTOM is passed.
1458//
1459// Inputs:
1460// preset       The preset ID. Must be less than number of presets.
1461//
1462//-------------------------------------------------------------------------
1463const char * EqualizerGetPresetName(int32_t preset){
1464    //ALOGV("\tEqualizerGetPresetName start(%d)", preset);
1465    if (preset == PRESET_CUSTOM) {
1466        return "Custom";
1467    } else {
1468        return gEqualizerPresets[preset].name;
1469    }
1470    //ALOGV("\tEqualizerGetPresetName end(%d)", preset);
1471    return 0;
1472}
1473
1474//----------------------------------------------------------------------------
1475// VolumeSetVolumeLevel()
1476//----------------------------------------------------------------------------
1477// Purpose:
1478//
1479// Inputs:
1480//  pContext:   effect engine context
1481//  level       level to be applied
1482//
1483//----------------------------------------------------------------------------
1484
1485int VolumeSetVolumeLevel(EffectContext *pContext, int16_t level){
1486
1487    if (level > 0 || level < -9600) {
1488        return -EINVAL;
1489    }
1490
1491    if (pContext->pBundledContext->bMuteEnabled == LVM_TRUE) {
1492        pContext->pBundledContext->levelSaved = level / 100;
1493    } else {
1494        pContext->pBundledContext->volume = level / 100;
1495    }
1496
1497    EqualizerLimitBandLevels(pContext);
1498
1499    return 0;
1500}    /* end VolumeSetVolumeLevel */
1501
1502//----------------------------------------------------------------------------
1503// VolumeGetVolumeLevel()
1504//----------------------------------------------------------------------------
1505// Purpose:
1506//
1507// Inputs:
1508//  pContext:   effect engine context
1509//
1510//----------------------------------------------------------------------------
1511
1512int VolumeGetVolumeLevel(EffectContext *pContext, int16_t *level){
1513
1514    if (pContext->pBundledContext->bMuteEnabled == LVM_TRUE) {
1515        *level = pContext->pBundledContext->levelSaved * 100;
1516    } else {
1517        *level = pContext->pBundledContext->volume * 100;
1518    }
1519    return 0;
1520}    /* end VolumeGetVolumeLevel */
1521
1522//----------------------------------------------------------------------------
1523// VolumeSetMute()
1524//----------------------------------------------------------------------------
1525// Purpose:
1526//
1527// Inputs:
1528//  pContext:   effect engine context
1529//  mute:       enable/disable flag
1530//
1531//----------------------------------------------------------------------------
1532
1533int32_t VolumeSetMute(EffectContext *pContext, uint32_t mute){
1534    //ALOGV("\tVolumeSetMute start(%d)", mute);
1535
1536    pContext->pBundledContext->bMuteEnabled = mute;
1537
1538    /* Set appropriate volume level */
1539    if(pContext->pBundledContext->bMuteEnabled == LVM_TRUE){
1540        pContext->pBundledContext->levelSaved = pContext->pBundledContext->volume;
1541        pContext->pBundledContext->volume = -96;
1542    }else{
1543        pContext->pBundledContext->volume = pContext->pBundledContext->levelSaved;
1544    }
1545
1546    EqualizerLimitBandLevels(pContext);
1547
1548    return 0;
1549}    /* end setMute */
1550
1551//----------------------------------------------------------------------------
1552// VolumeGetMute()
1553//----------------------------------------------------------------------------
1554// Purpose:
1555//
1556// Inputs:
1557//  pContext:   effect engine context
1558//
1559// Ourputs:
1560//  mute:       enable/disable flag
1561//----------------------------------------------------------------------------
1562
1563int32_t VolumeGetMute(EffectContext *pContext, uint32_t *mute){
1564    //ALOGV("\tVolumeGetMute start");
1565    if((pContext->pBundledContext->bMuteEnabled == LVM_FALSE)||
1566       (pContext->pBundledContext->bMuteEnabled == LVM_TRUE)){
1567        *mute = pContext->pBundledContext->bMuteEnabled;
1568        return 0;
1569    }else{
1570        ALOGV("\tLVM_ERROR : VolumeGetMute read an invalid value from context %d",
1571              pContext->pBundledContext->bMuteEnabled);
1572        return -EINVAL;
1573    }
1574    //ALOGV("\tVolumeGetMute end");
1575}    /* end getMute */
1576
1577int16_t VolumeConvertStereoPosition(int16_t position){
1578    int16_t convertedPosition = 0;
1579
1580    convertedPosition = (int16_t)(((float)position/1000)*96);
1581    return convertedPosition;
1582
1583}
1584
1585//----------------------------------------------------------------------------
1586// VolumeSetStereoPosition()
1587//----------------------------------------------------------------------------
1588// Purpose:
1589//
1590// Inputs:
1591//  pContext:       effect engine context
1592//  position:       stereo position
1593//
1594// Outputs:
1595//----------------------------------------------------------------------------
1596
1597int VolumeSetStereoPosition(EffectContext *pContext, int16_t position){
1598
1599    LVM_ControlParams_t     ActiveParams;              /* Current control Parameters */
1600    LVM_ReturnStatus_en     LvmStatus=LVM_SUCCESS;     /* Function call status */
1601    LVM_INT16               Balance = 0;
1602
1603
1604
1605    pContext->pBundledContext->positionSaved = position;
1606    Balance = VolumeConvertStereoPosition(pContext->pBundledContext->positionSaved);
1607
1608    //ALOGV("\tVolumeSetStereoPosition start pContext->pBundledContext->positionSaved = %d",
1609    //pContext->pBundledContext->positionSaved);
1610
1611    if(pContext->pBundledContext->bStereoPositionEnabled == LVM_TRUE){
1612
1613        //ALOGV("\tVolumeSetStereoPosition Position to be set is %d %d\n", position, Balance);
1614        pContext->pBundledContext->positionSaved = position;
1615        /* Get the current settings */
1616        LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1617        LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "VolumeSetStereoPosition")
1618        if(LvmStatus != LVM_SUCCESS) return -EINVAL;
1619        //ALOGV("\tVolumeSetStereoPosition Succesfully returned from LVM_GetControlParameters got:"
1620        //     " %d\n", ActiveParams.VC_Balance);
1621
1622        /* Volume parameters */
1623        ActiveParams.VC_Balance  = Balance;
1624        //ALOGV("\tVolumeSetStereoPosition() (-96dB -> +96dB)   -> %d\n", ActiveParams.VC_Balance );
1625
1626        /* Activate the initial settings */
1627        LvmStatus = LVM_SetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1628        LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "VolumeSetStereoPosition")
1629        if(LvmStatus != LVM_SUCCESS) return -EINVAL;
1630
1631        //ALOGV("\tVolumeSetStereoPosition Succesfully called LVM_SetControlParameters\n");
1632
1633        /* Get the current settings */
1634        LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1635        LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "VolumeSetStereoPosition")
1636        if(LvmStatus != LVM_SUCCESS) return -EINVAL;
1637        //ALOGV("\tVolumeSetStereoPosition Succesfully returned from LVM_GetControlParameters got: "
1638        //     "%d\n", ActiveParams.VC_Balance);
1639    }
1640    else{
1641        //ALOGV("\tVolumeSetStereoPosition Position attempting to set, but not enabled %d %d\n",
1642        //position, Balance);
1643    }
1644    //ALOGV("\tVolumeSetStereoPosition end pContext->pBundledContext->positionSaved = %d\n",
1645    //pContext->pBundledContext->positionSaved);
1646    return 0;
1647}    /* end VolumeSetStereoPosition */
1648
1649
1650//----------------------------------------------------------------------------
1651// VolumeGetStereoPosition()
1652//----------------------------------------------------------------------------
1653// Purpose:
1654//
1655// Inputs:
1656//  pContext:       effect engine context
1657//
1658// Outputs:
1659//  position:       stereo position
1660//----------------------------------------------------------------------------
1661
1662int32_t VolumeGetStereoPosition(EffectContext *pContext, int16_t *position){
1663    //ALOGV("\tVolumeGetStereoPosition start");
1664
1665    LVM_ControlParams_t     ActiveParams;                           /* Current control Parameters */
1666    LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;                /* Function call status */
1667    LVM_INT16               balance;
1668
1669    //ALOGV("\tVolumeGetStereoPosition start pContext->pBundledContext->positionSaved = %d",
1670    //pContext->pBundledContext->positionSaved);
1671
1672    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1673    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "VolumeGetStereoPosition")
1674    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
1675
1676    //ALOGV("\tVolumeGetStereoPosition -> %d\n", ActiveParams.VC_Balance);
1677    //ALOGV("\tVolumeGetStereoPosition Succesfully returned from LVM_GetControlParameters\n");
1678
1679    balance = VolumeConvertStereoPosition(pContext->pBundledContext->positionSaved);
1680
1681    if(pContext->pBundledContext->bStereoPositionEnabled == LVM_TRUE){
1682        if(balance != ActiveParams.VC_Balance){
1683            return -EINVAL;
1684        }
1685    }
1686    *position = (LVM_INT16)pContext->pBundledContext->positionSaved;     // Convert dB to millibels
1687    //ALOGV("\tVolumeGetStereoPosition end returning pContext->pBundledContext->positionSaved =%d\n",
1688    //pContext->pBundledContext->positionSaved);
1689    return 0;
1690}    /* end VolumeGetStereoPosition */
1691
1692//----------------------------------------------------------------------------
1693// VolumeEnableStereoPosition()
1694//----------------------------------------------------------------------------
1695// Purpose:
1696//
1697// Inputs:
1698//  pContext:   effect engine context
1699//  mute:       enable/disable flag
1700//
1701//----------------------------------------------------------------------------
1702
1703int32_t VolumeEnableStereoPosition(EffectContext *pContext, uint32_t enabled){
1704    //ALOGV("\tVolumeEnableStereoPosition start()");
1705
1706    pContext->pBundledContext->bStereoPositionEnabled = enabled;
1707
1708    LVM_ControlParams_t     ActiveParams;              /* Current control Parameters */
1709    LVM_ReturnStatus_en     LvmStatus=LVM_SUCCESS;     /* Function call status */
1710
1711    /* Get the current settings */
1712    LvmStatus = LVM_GetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1713    LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "VolumeEnableStereoPosition")
1714    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
1715
1716    //ALOGV("\tVolumeEnableStereoPosition Succesfully returned from LVM_GetControlParameters\n");
1717    //ALOGV("\tVolumeEnableStereoPosition to %d, position was %d\n",
1718    //     enabled, ActiveParams.VC_Balance );
1719
1720    /* Set appropriate stereo position */
1721    if(pContext->pBundledContext->bStereoPositionEnabled == LVM_FALSE){
1722        ActiveParams.VC_Balance = 0;
1723    }else{
1724        ActiveParams.VC_Balance  =
1725                            VolumeConvertStereoPosition(pContext->pBundledContext->positionSaved);
1726    }
1727
1728    /* Activate the initial settings */
1729    LvmStatus = LVM_SetControlParameters(pContext->pBundledContext->hInstance, &ActiveParams);
1730    LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "VolumeEnableStereoPosition")
1731    if(LvmStatus != LVM_SUCCESS) return -EINVAL;
1732
1733    //ALOGV("\tVolumeEnableStereoPosition Succesfully called LVM_SetControlParameters\n");
1734    //ALOGV("\tVolumeEnableStereoPosition end()\n");
1735    return 0;
1736}    /* end VolumeEnableStereoPosition */
1737
1738//----------------------------------------------------------------------------
1739// BassBoost_getParameter()
1740//----------------------------------------------------------------------------
1741// Purpose:
1742// Get a BassBoost parameter
1743//
1744// Inputs:
1745//  pBassBoost       - handle to instance data
1746//  pParam           - pointer to parameter
1747//  pValue           - pointer to variable to hold retrieved value
1748//  pValueSize       - pointer to value size: maximum size as input
1749//
1750// Outputs:
1751//  *pValue updated with parameter value
1752//  *pValueSize updated with actual value size
1753//
1754//
1755// Side Effects:
1756//
1757//----------------------------------------------------------------------------
1758
1759int BassBoost_getParameter(EffectContext     *pContext,
1760                           void              *pParam,
1761                           size_t            *pValueSize,
1762                           void              *pValue){
1763    int status = 0;
1764    int32_t *pParamTemp = (int32_t *)pParam;
1765    int32_t param = *pParamTemp++;
1766    int32_t param2;
1767    char *name;
1768
1769    //ALOGV("\tBassBoost_getParameter start");
1770
1771    switch (param){
1772        case BASSBOOST_PARAM_STRENGTH_SUPPORTED:
1773            if (*pValueSize != sizeof(uint32_t)){
1774                ALOGV("\tLVM_ERROR : BassBoost_getParameter() invalid pValueSize1 %d", *pValueSize);
1775                return -EINVAL;
1776            }
1777            *pValueSize = sizeof(uint32_t);
1778            break;
1779        case BASSBOOST_PARAM_STRENGTH:
1780            if (*pValueSize != sizeof(int16_t)){
1781                ALOGV("\tLVM_ERROR : BassBoost_getParameter() invalid pValueSize2 %d", *pValueSize);
1782                return -EINVAL;
1783            }
1784            *pValueSize = sizeof(int16_t);
1785            break;
1786
1787        default:
1788            ALOGV("\tLVM_ERROR : BassBoost_getParameter() invalid param %d", param);
1789            return -EINVAL;
1790    }
1791
1792    switch (param){
1793        case BASSBOOST_PARAM_STRENGTH_SUPPORTED:
1794            *(uint32_t *)pValue = 1;
1795
1796            //ALOGV("\tBassBoost_getParameter() BASSBOOST_PARAM_STRENGTH_SUPPORTED Value is %d",
1797            //        *(uint32_t *)pValue);
1798            break;
1799
1800        case BASSBOOST_PARAM_STRENGTH:
1801            *(int16_t *)pValue = BassGetStrength(pContext);
1802
1803            //ALOGV("\tBassBoost_getParameter() BASSBOOST_PARAM_STRENGTH Value is %d",
1804            //        *(int16_t *)pValue);
1805            break;
1806
1807        default:
1808            ALOGV("\tLVM_ERROR : BassBoost_getParameter() invalid param %d", param);
1809            status = -EINVAL;
1810            break;
1811    }
1812
1813    //ALOGV("\tBassBoost_getParameter end");
1814    return status;
1815} /* end BassBoost_getParameter */
1816
1817//----------------------------------------------------------------------------
1818// BassBoost_setParameter()
1819//----------------------------------------------------------------------------
1820// Purpose:
1821// Set a BassBoost parameter
1822//
1823// Inputs:
1824//  pBassBoost       - handle to instance data
1825//  pParam           - pointer to parameter
1826//  pValue           - pointer to value
1827//
1828// Outputs:
1829//
1830//----------------------------------------------------------------------------
1831
1832int BassBoost_setParameter (EffectContext *pContext, void *pParam, void *pValue){
1833    int status = 0;
1834    int16_t strength;
1835    int32_t *pParamTemp = (int32_t *)pParam;
1836
1837    //ALOGV("\tBassBoost_setParameter start");
1838
1839    switch (*pParamTemp){
1840        case BASSBOOST_PARAM_STRENGTH:
1841            strength = *(int16_t *)pValue;
1842            //ALOGV("\tBassBoost_setParameter() BASSBOOST_PARAM_STRENGTH value is %d", strength);
1843            //ALOGV("\tBassBoost_setParameter() Calling pBassBoost->BassSetStrength");
1844            BassSetStrength(pContext, (int32_t)strength);
1845            //ALOGV("\tBassBoost_setParameter() Called pBassBoost->BassSetStrength");
1846           break;
1847        default:
1848            ALOGV("\tLVM_ERROR : BassBoost_setParameter() invalid param %d", *pParamTemp);
1849            break;
1850    }
1851
1852    //ALOGV("\tBassBoost_setParameter end");
1853    return status;
1854} /* end BassBoost_setParameter */
1855
1856//----------------------------------------------------------------------------
1857// Virtualizer_getParameter()
1858//----------------------------------------------------------------------------
1859// Purpose:
1860// Get a Virtualizer parameter
1861//
1862// Inputs:
1863//  pVirtualizer     - handle to instance data
1864//  pParam           - pointer to parameter
1865//  pValue           - pointer to variable to hold retrieved value
1866//  pValueSize       - pointer to value size: maximum size as input
1867//
1868// Outputs:
1869//  *pValue updated with parameter value
1870//  *pValueSize updated with actual value size
1871//
1872//
1873// Side Effects:
1874//
1875//----------------------------------------------------------------------------
1876
1877int Virtualizer_getParameter(EffectContext        *pContext,
1878                             void                 *pParam,
1879                             size_t               *pValueSize,
1880                             void                 *pValue){
1881    int status = 0;
1882    int32_t *pParamTemp = (int32_t *)pParam;
1883    int32_t param = *pParamTemp++;
1884    int32_t param2;
1885    char *name;
1886
1887    //ALOGV("\tVirtualizer_getParameter start");
1888
1889    switch (param){
1890        case VIRTUALIZER_PARAM_STRENGTH_SUPPORTED:
1891            if (*pValueSize != sizeof(uint32_t)){
1892                ALOGV("\tLVM_ERROR : Virtualizer_getParameter() invalid pValueSize %d",*pValueSize);
1893                return -EINVAL;
1894            }
1895            *pValueSize = sizeof(uint32_t);
1896            break;
1897        case VIRTUALIZER_PARAM_STRENGTH:
1898            if (*pValueSize != sizeof(int16_t)){
1899                ALOGV("\tLVM_ERROR : Virtualizer_getParameter() invalid pValueSize2 %d",*pValueSize);
1900                return -EINVAL;
1901            }
1902            *pValueSize = sizeof(int16_t);
1903            break;
1904
1905        default:
1906            ALOGV("\tLVM_ERROR : Virtualizer_getParameter() invalid param %d", param);
1907            return -EINVAL;
1908    }
1909
1910    switch (param){
1911        case VIRTUALIZER_PARAM_STRENGTH_SUPPORTED:
1912            *(uint32_t *)pValue = 1;
1913
1914            //ALOGV("\tVirtualizer_getParameter() VIRTUALIZER_PARAM_STRENGTH_SUPPORTED Value is %d",
1915            //        *(uint32_t *)pValue);
1916            break;
1917
1918        case VIRTUALIZER_PARAM_STRENGTH:
1919            *(int16_t *)pValue = VirtualizerGetStrength(pContext);
1920
1921            //ALOGV("\tVirtualizer_getParameter() VIRTUALIZER_PARAM_STRENGTH Value is %d",
1922            //        *(int16_t *)pValue);
1923            break;
1924
1925        default:
1926            ALOGV("\tLVM_ERROR : Virtualizer_getParameter() invalid param %d", param);
1927            status = -EINVAL;
1928            break;
1929    }
1930
1931    //ALOGV("\tVirtualizer_getParameter end");
1932    return status;
1933} /* end Virtualizer_getParameter */
1934
1935//----------------------------------------------------------------------------
1936// Virtualizer_setParameter()
1937//----------------------------------------------------------------------------
1938// Purpose:
1939// Set a Virtualizer parameter
1940//
1941// Inputs:
1942//  pVirtualizer     - handle to instance data
1943//  pParam           - pointer to parameter
1944//  pValue           - pointer to value
1945//
1946// Outputs:
1947//
1948//----------------------------------------------------------------------------
1949
1950int Virtualizer_setParameter (EffectContext *pContext, void *pParam, void *pValue){
1951    int status = 0;
1952    int16_t strength;
1953    int32_t *pParamTemp = (int32_t *)pParam;
1954    int32_t param = *pParamTemp++;
1955
1956    //ALOGV("\tVirtualizer_setParameter start");
1957
1958    switch (param){
1959        case VIRTUALIZER_PARAM_STRENGTH:
1960            strength = *(int16_t *)pValue;
1961            //ALOGV("\tVirtualizer_setParameter() VIRTUALIZER_PARAM_STRENGTH value is %d", strength);
1962            //ALOGV("\tVirtualizer_setParameter() Calling pVirtualizer->setStrength");
1963            VirtualizerSetStrength(pContext, (int32_t)strength);
1964            //ALOGV("\tVirtualizer_setParameter() Called pVirtualizer->setStrength");
1965           break;
1966        default:
1967            ALOGV("\tLVM_ERROR : Virtualizer_setParameter() invalid param %d", param);
1968            break;
1969    }
1970
1971    //ALOGV("\tVirtualizer_setParameter end");
1972    return status;
1973} /* end Virtualizer_setParameter */
1974
1975//----------------------------------------------------------------------------
1976// Equalizer_getParameter()
1977//----------------------------------------------------------------------------
1978// Purpose:
1979// Get a Equalizer parameter
1980//
1981// Inputs:
1982//  pEqualizer       - handle to instance data
1983//  pParam           - pointer to parameter
1984//  pValue           - pointer to variable to hold retrieved value
1985//  pValueSize       - pointer to value size: maximum size as input
1986//
1987// Outputs:
1988//  *pValue updated with parameter value
1989//  *pValueSize updated with actual value size
1990//
1991//
1992// Side Effects:
1993//
1994//----------------------------------------------------------------------------
1995int Equalizer_getParameter(EffectContext     *pContext,
1996                           void              *pParam,
1997                           size_t            *pValueSize,
1998                           void              *pValue){
1999    int status = 0;
2000    int bMute = 0;
2001    int32_t *pParamTemp = (int32_t *)pParam;
2002    int32_t param = *pParamTemp++;
2003    int32_t param2;
2004    char *name;
2005
2006    //ALOGV("\tEqualizer_getParameter start");
2007
2008    switch (param) {
2009    case EQ_PARAM_NUM_BANDS:
2010    case EQ_PARAM_CUR_PRESET:
2011    case EQ_PARAM_GET_NUM_OF_PRESETS:
2012    case EQ_PARAM_BAND_LEVEL:
2013    case EQ_PARAM_GET_BAND:
2014        if (*pValueSize < sizeof(int16_t)) {
2015            ALOGV("\tLVM_ERROR : Equalizer_getParameter() invalid pValueSize 1  %d", *pValueSize);
2016            return -EINVAL;
2017        }
2018        *pValueSize = sizeof(int16_t);
2019        break;
2020
2021    case EQ_PARAM_LEVEL_RANGE:
2022        if (*pValueSize < 2 * sizeof(int16_t)) {
2023            ALOGV("\tLVM_ERROR : Equalizer_getParameter() invalid pValueSize 2  %d", *pValueSize);
2024            return -EINVAL;
2025        }
2026        *pValueSize = 2 * sizeof(int16_t);
2027        break;
2028    case EQ_PARAM_BAND_FREQ_RANGE:
2029        if (*pValueSize < 2 * sizeof(int32_t)) {
2030            ALOGV("\tLVM_ERROR : Equalizer_getParameter() invalid pValueSize 3  %d", *pValueSize);
2031            return -EINVAL;
2032        }
2033        *pValueSize = 2 * sizeof(int32_t);
2034        break;
2035
2036    case EQ_PARAM_CENTER_FREQ:
2037        if (*pValueSize < sizeof(int32_t)) {
2038            ALOGV("\tLVM_ERROR : Equalizer_getParameter() invalid pValueSize 5  %d", *pValueSize);
2039            return -EINVAL;
2040        }
2041        *pValueSize = sizeof(int32_t);
2042        break;
2043
2044    case EQ_PARAM_GET_PRESET_NAME:
2045        break;
2046
2047    case EQ_PARAM_PROPERTIES:
2048        if (*pValueSize < (2 + FIVEBAND_NUMBANDS) * sizeof(uint16_t)) {
2049            ALOGV("\tLVM_ERROR : Equalizer_getParameter() invalid pValueSize 1  %d", *pValueSize);
2050            return -EINVAL;
2051        }
2052        *pValueSize = (2 + FIVEBAND_NUMBANDS) * sizeof(uint16_t);
2053        break;
2054
2055    default:
2056        ALOGV("\tLVM_ERROR : Equalizer_getParameter unknown param %d", param);
2057        return -EINVAL;
2058    }
2059
2060    switch (param) {
2061    case EQ_PARAM_NUM_BANDS:
2062        *(uint16_t *)pValue = (uint16_t)FIVEBAND_NUMBANDS;
2063        //ALOGV("\tEqualizer_getParameter() EQ_PARAM_NUM_BANDS %d", *(int16_t *)pValue);
2064        break;
2065
2066    case EQ_PARAM_LEVEL_RANGE:
2067        *(int16_t *)pValue = -1500;
2068        *((int16_t *)pValue + 1) = 1500;
2069        //ALOGV("\tEqualizer_getParameter() EQ_PARAM_LEVEL_RANGE min %d, max %d",
2070        //      *(int16_t *)pValue, *((int16_t *)pValue + 1));
2071        break;
2072
2073    case EQ_PARAM_BAND_LEVEL:
2074        param2 = *pParamTemp;
2075        if (param2 >= FIVEBAND_NUMBANDS) {
2076            status = -EINVAL;
2077            break;
2078        }
2079        *(int16_t *)pValue = (int16_t)EqualizerGetBandLevel(pContext, param2);
2080        //ALOGV("\tEqualizer_getParameter() EQ_PARAM_BAND_LEVEL band %d, level %d",
2081        //      param2, *(int32_t *)pValue);
2082        break;
2083
2084    case EQ_PARAM_CENTER_FREQ:
2085        param2 = *pParamTemp;
2086        if (param2 >= FIVEBAND_NUMBANDS) {
2087            status = -EINVAL;
2088            break;
2089        }
2090        *(int32_t *)pValue = EqualizerGetCentreFrequency(pContext, param2);
2091        //ALOGV("\tEqualizer_getParameter() EQ_PARAM_CENTER_FREQ band %d, frequency %d",
2092        //      param2, *(int32_t *)pValue);
2093        break;
2094
2095    case EQ_PARAM_BAND_FREQ_RANGE:
2096        param2 = *pParamTemp;
2097        if (param2 >= FIVEBAND_NUMBANDS) {
2098            status = -EINVAL;
2099            break;
2100        }
2101        EqualizerGetBandFreqRange(pContext, param2, (uint32_t *)pValue, ((uint32_t *)pValue + 1));
2102        //ALOGV("\tEqualizer_getParameter() EQ_PARAM_BAND_FREQ_RANGE band %d, min %d, max %d",
2103        //      param2, *(int32_t *)pValue, *((int32_t *)pValue + 1));
2104        break;
2105
2106    case EQ_PARAM_GET_BAND:
2107        param2 = *pParamTemp;
2108        *(uint16_t *)pValue = (uint16_t)EqualizerGetBand(pContext, param2);
2109        //ALOGV("\tEqualizer_getParameter() EQ_PARAM_GET_BAND frequency %d, band %d",
2110        //      param2, *(uint16_t *)pValue);
2111        break;
2112
2113    case EQ_PARAM_CUR_PRESET:
2114        *(uint16_t *)pValue = (uint16_t)EqualizerGetPreset(pContext);
2115        //ALOGV("\tEqualizer_getParameter() EQ_PARAM_CUR_PRESET %d", *(int32_t *)pValue);
2116        break;
2117
2118    case EQ_PARAM_GET_NUM_OF_PRESETS:
2119        *(uint16_t *)pValue = (uint16_t)EqualizerGetNumPresets();
2120        //ALOGV("\tEqualizer_getParameter() EQ_PARAM_GET_NUM_OF_PRESETS %d", *(int16_t *)pValue);
2121        break;
2122
2123    case EQ_PARAM_GET_PRESET_NAME:
2124        param2 = *pParamTemp;
2125        if (param2 >= EqualizerGetNumPresets()) {
2126        //if (param2 >= 20) {     // AGO FIX
2127            status = -EINVAL;
2128            break;
2129        }
2130        name = (char *)pValue;
2131        strncpy(name, EqualizerGetPresetName(param2), *pValueSize - 1);
2132        name[*pValueSize - 1] = 0;
2133        *pValueSize = strlen(name) + 1;
2134        //ALOGV("\tEqualizer_getParameter() EQ_PARAM_GET_PRESET_NAME preset %d, name %s len %d",
2135        //      param2, gEqualizerPresets[param2].name, *pValueSize);
2136        break;
2137
2138    case EQ_PARAM_PROPERTIES: {
2139        int16_t *p = (int16_t *)pValue;
2140        ALOGV("\tEqualizer_getParameter() EQ_PARAM_PROPERTIES");
2141        p[0] = (int16_t)EqualizerGetPreset(pContext);
2142        p[1] = (int16_t)FIVEBAND_NUMBANDS;
2143        for (int i = 0; i < FIVEBAND_NUMBANDS; i++) {
2144            p[2 + i] = (int16_t)EqualizerGetBandLevel(pContext, i);
2145        }
2146    } break;
2147
2148    default:
2149        ALOGV("\tLVM_ERROR : Equalizer_getParameter() invalid param %d", param);
2150        status = -EINVAL;
2151        break;
2152    }
2153
2154    //GV("\tEqualizer_getParameter end\n");
2155    return status;
2156} /* end Equalizer_getParameter */
2157
2158//----------------------------------------------------------------------------
2159// Equalizer_setParameter()
2160//----------------------------------------------------------------------------
2161// Purpose:
2162// Set a Equalizer parameter
2163//
2164// Inputs:
2165//  pEqualizer    - handle to instance data
2166//  pParam        - pointer to parameter
2167//  pValue        - pointer to value
2168//
2169// Outputs:
2170//
2171//----------------------------------------------------------------------------
2172int Equalizer_setParameter (EffectContext *pContext, void *pParam, void *pValue){
2173    int status = 0;
2174    int32_t preset;
2175    int32_t band;
2176    int32_t level;
2177    int32_t *pParamTemp = (int32_t *)pParam;
2178    int32_t param = *pParamTemp++;
2179
2180
2181    //ALOGV("\tEqualizer_setParameter start");
2182    switch (param) {
2183    case EQ_PARAM_CUR_PRESET:
2184        preset = (int32_t)(*(uint16_t *)pValue);
2185
2186        //ALOGV("\tEqualizer_setParameter() EQ_PARAM_CUR_PRESET %d", preset);
2187        if ((preset >= EqualizerGetNumPresets())||(preset < 0)) {
2188            status = -EINVAL;
2189            break;
2190        }
2191        EqualizerSetPreset(pContext, preset);
2192        break;
2193    case EQ_PARAM_BAND_LEVEL:
2194        band =  *pParamTemp;
2195        level = (int32_t)(*(int16_t *)pValue);
2196        //ALOGV("\tEqualizer_setParameter() EQ_PARAM_BAND_LEVEL band %d, level %d", band, level);
2197        if (band >= FIVEBAND_NUMBANDS) {
2198            status = -EINVAL;
2199            break;
2200        }
2201        EqualizerSetBandLevel(pContext, band, level);
2202        break;
2203    case EQ_PARAM_PROPERTIES: {
2204        //ALOGV("\tEqualizer_setParameter() EQ_PARAM_PROPERTIES");
2205        int16_t *p = (int16_t *)pValue;
2206        if ((int)p[0] >= EqualizerGetNumPresets()) {
2207            status = -EINVAL;
2208            break;
2209        }
2210        if (p[0] >= 0) {
2211            EqualizerSetPreset(pContext, (int)p[0]);
2212        } else {
2213            if ((int)p[1] != FIVEBAND_NUMBANDS) {
2214                status = -EINVAL;
2215                break;
2216            }
2217            for (int i = 0; i < FIVEBAND_NUMBANDS; i++) {
2218                EqualizerSetBandLevel(pContext, i, (int)p[2 + i]);
2219            }
2220        }
2221    } break;
2222    default:
2223        ALOGV("\tLVM_ERROR : Equalizer_setParameter() invalid param %d", param);
2224        status = -EINVAL;
2225        break;
2226    }
2227
2228    //ALOGV("\tEqualizer_setParameter end");
2229    return status;
2230} /* end Equalizer_setParameter */
2231
2232//----------------------------------------------------------------------------
2233// Volume_getParameter()
2234//----------------------------------------------------------------------------
2235// Purpose:
2236// Get a Volume parameter
2237//
2238// Inputs:
2239//  pVolume          - handle to instance data
2240//  pParam           - pointer to parameter
2241//  pValue           - pointer to variable to hold retrieved value
2242//  pValueSize       - pointer to value size: maximum size as input
2243//
2244// Outputs:
2245//  *pValue updated with parameter value
2246//  *pValueSize updated with actual value size
2247//
2248//
2249// Side Effects:
2250//
2251//----------------------------------------------------------------------------
2252
2253int Volume_getParameter(EffectContext     *pContext,
2254                        void              *pParam,
2255                        size_t            *pValueSize,
2256                        void              *pValue){
2257    int status = 0;
2258    int bMute = 0;
2259    int32_t *pParamTemp = (int32_t *)pParam;
2260    int32_t param = *pParamTemp++;;
2261    char *name;
2262
2263    //ALOGV("\tVolume_getParameter start");
2264
2265    switch (param){
2266        case VOLUME_PARAM_LEVEL:
2267        case VOLUME_PARAM_MAXLEVEL:
2268        case VOLUME_PARAM_STEREOPOSITION:
2269            if (*pValueSize != sizeof(int16_t)){
2270                ALOGV("\tLVM_ERROR : Volume_getParameter() invalid pValueSize 1  %d", *pValueSize);
2271                return -EINVAL;
2272            }
2273            *pValueSize = sizeof(int16_t);
2274            break;
2275
2276        case VOLUME_PARAM_MUTE:
2277        case VOLUME_PARAM_ENABLESTEREOPOSITION:
2278            if (*pValueSize < sizeof(int32_t)){
2279                ALOGV("\tLVM_ERROR : Volume_getParameter() invalid pValueSize 2  %d", *pValueSize);
2280                return -EINVAL;
2281            }
2282            *pValueSize = sizeof(int32_t);
2283            break;
2284
2285        default:
2286            ALOGV("\tLVM_ERROR : Volume_getParameter unknown param %d", param);
2287            return -EINVAL;
2288    }
2289
2290    switch (param){
2291        case VOLUME_PARAM_LEVEL:
2292            status = VolumeGetVolumeLevel(pContext, (int16_t *)(pValue));
2293            //ALOGV("\tVolume_getParameter() VOLUME_PARAM_LEVEL Value is %d",
2294            //        *(int16_t *)pValue);
2295            break;
2296
2297        case VOLUME_PARAM_MAXLEVEL:
2298            *(int16_t *)pValue = 0;
2299            //ALOGV("\tVolume_getParameter() VOLUME_PARAM_MAXLEVEL Value is %d",
2300            //        *(int16_t *)pValue);
2301            break;
2302
2303        case VOLUME_PARAM_STEREOPOSITION:
2304            VolumeGetStereoPosition(pContext, (int16_t *)pValue);
2305            //ALOGV("\tVolume_getParameter() VOLUME_PARAM_STEREOPOSITION Value is %d",
2306            //        *(int16_t *)pValue);
2307            break;
2308
2309        case VOLUME_PARAM_MUTE:
2310            status = VolumeGetMute(pContext, (uint32_t *)pValue);
2311            ALOGV("\tVolume_getParameter() VOLUME_PARAM_MUTE Value is %d",
2312                    *(uint32_t *)pValue);
2313            break;
2314
2315        case VOLUME_PARAM_ENABLESTEREOPOSITION:
2316            *(int32_t *)pValue = pContext->pBundledContext->bStereoPositionEnabled;
2317            //ALOGV("\tVolume_getParameter() VOLUME_PARAM_ENABLESTEREOPOSITION Value is %d",
2318            //        *(uint32_t *)pValue);
2319            break;
2320
2321        default:
2322            ALOGV("\tLVM_ERROR : Volume_getParameter() invalid param %d", param);
2323            status = -EINVAL;
2324            break;
2325    }
2326
2327    //ALOGV("\tVolume_getParameter end");
2328    return status;
2329} /* end Volume_getParameter */
2330
2331
2332//----------------------------------------------------------------------------
2333// Volume_setParameter()
2334//----------------------------------------------------------------------------
2335// Purpose:
2336// Set a Volume parameter
2337//
2338// Inputs:
2339//  pVolume       - handle to instance data
2340//  pParam        - pointer to parameter
2341//  pValue        - pointer to value
2342//
2343// Outputs:
2344//
2345//----------------------------------------------------------------------------
2346
2347int Volume_setParameter (EffectContext *pContext, void *pParam, void *pValue){
2348    int      status = 0;
2349    int16_t  level;
2350    int16_t  position;
2351    uint32_t mute;
2352    uint32_t positionEnabled;
2353    int32_t *pParamTemp = (int32_t *)pParam;
2354    int32_t param = *pParamTemp++;
2355
2356    //ALOGV("\tVolume_setParameter start");
2357
2358    switch (param){
2359        case VOLUME_PARAM_LEVEL:
2360            level = *(int16_t *)pValue;
2361            //ALOGV("\tVolume_setParameter() VOLUME_PARAM_LEVEL value is %d", level);
2362            //ALOGV("\tVolume_setParameter() Calling pVolume->setVolumeLevel");
2363            status = VolumeSetVolumeLevel(pContext, (int16_t)level);
2364            //ALOGV("\tVolume_setParameter() Called pVolume->setVolumeLevel");
2365            break;
2366
2367        case VOLUME_PARAM_MUTE:
2368            mute = *(uint32_t *)pValue;
2369            //ALOGV("\tVolume_setParameter() Calling pVolume->setMute, mute is %d", mute);
2370            //ALOGV("\tVolume_setParameter() Calling pVolume->setMute");
2371            status = VolumeSetMute(pContext, mute);
2372            //ALOGV("\tVolume_setParameter() Called pVolume->setMute");
2373            break;
2374
2375        case VOLUME_PARAM_ENABLESTEREOPOSITION:
2376            positionEnabled = *(uint32_t *)pValue;
2377            status = VolumeEnableStereoPosition(pContext, positionEnabled);
2378            status = VolumeSetStereoPosition(pContext, pContext->pBundledContext->positionSaved);
2379            //ALOGV("\tVolume_setParameter() VOLUME_PARAM_ENABLESTEREOPOSITION called");
2380            break;
2381
2382        case VOLUME_PARAM_STEREOPOSITION:
2383            position = *(int16_t *)pValue;
2384            //ALOGV("\tVolume_setParameter() VOLUME_PARAM_STEREOPOSITION value is %d", position);
2385            //ALOGV("\tVolume_setParameter() Calling pVolume->VolumeSetStereoPosition");
2386            status = VolumeSetStereoPosition(pContext, (int16_t)position);
2387            //ALOGV("\tVolume_setParameter() Called pVolume->VolumeSetStereoPosition");
2388            break;
2389
2390        default:
2391            ALOGV("\tLVM_ERROR : Volume_setParameter() invalid param %d", param);
2392            break;
2393    }
2394
2395    //ALOGV("\tVolume_setParameter end");
2396    return status;
2397} /* end Volume_setParameter */
2398
2399/****************************************************************************************
2400 * Name : LVC_ToDB_s32Tos16()
2401 *  Input       : Signed 32-bit integer
2402 *  Output      : Signed 16-bit integer
2403 *                  MSB (16) = sign bit
2404 *                  (15->05) = integer part
2405 *                  (04->01) = decimal part
2406 *  Returns     : Db value with respect to full scale
2407 *  Description :
2408 *  Remarks     :
2409 ****************************************************************************************/
2410
2411LVM_INT16 LVC_ToDB_s32Tos16(LVM_INT32 Lin_fix)
2412{
2413    LVM_INT16   db_fix;
2414    LVM_INT16   Shift;
2415    LVM_INT16   SmallRemainder;
2416    LVM_UINT32  Remainder = (LVM_UINT32)Lin_fix;
2417
2418    /* Count leading bits, 1 cycle in assembly*/
2419    for (Shift = 0; Shift<32; Shift++)
2420    {
2421        if ((Remainder & 0x80000000U)!=0)
2422        {
2423            break;
2424        }
2425        Remainder = Remainder << 1;
2426    }
2427
2428    /*
2429     * Based on the approximation equation (for Q11.4 format):
2430     *
2431     * dB = -96 * Shift + 16 * (8 * Remainder - 2 * Remainder^2)
2432     */
2433    db_fix    = (LVM_INT16)(-96 * Shift);               /* Six dB steps in Q11.4 format*/
2434    SmallRemainder = (LVM_INT16)((Remainder & 0x7fffffff) >> 24);
2435    db_fix = (LVM_INT16)(db_fix + SmallRemainder );
2436    SmallRemainder = (LVM_INT16)(SmallRemainder * SmallRemainder);
2437    db_fix = (LVM_INT16)(db_fix - (LVM_INT16)((LVM_UINT16)SmallRemainder >> 9));
2438
2439    /* Correct for small offset */
2440    db_fix = (LVM_INT16)(db_fix - 5);
2441
2442    return db_fix;
2443}
2444
2445//----------------------------------------------------------------------------
2446// Effect_setEnabled()
2447//----------------------------------------------------------------------------
2448// Purpose:
2449// Enable or disable effect
2450//
2451// Inputs:
2452//  pContext      - pointer to effect context
2453//  enabled       - true if enabling the effect, false otherwise
2454//
2455// Outputs:
2456//
2457//----------------------------------------------------------------------------
2458
2459int Effect_setEnabled(EffectContext *pContext, bool enabled)
2460{
2461    ALOGV("\tEffect_setEnabled() type %d, enabled %d", pContext->EffectType, enabled);
2462
2463    if (enabled) {
2464        // Bass boost or Virtualizer can be temporarily disabled if playing over device speaker due
2465        // to their nature.
2466        bool tempDisabled = false;
2467        switch (pContext->EffectType) {
2468            case LVM_BASS_BOOST:
2469                if (pContext->pBundledContext->bBassEnabled == LVM_TRUE) {
2470                     ALOGV("\tEffect_setEnabled() LVM_BASS_BOOST is already enabled");
2471                     return -EINVAL;
2472                }
2473                if(pContext->pBundledContext->SamplesToExitCountBb <= 0){
2474                    pContext->pBundledContext->NumberEffectsEnabled++;
2475                }
2476                pContext->pBundledContext->SamplesToExitCountBb =
2477                     (LVM_INT32)(pContext->pBundledContext->SamplesPerSecond*0.1);
2478                pContext->pBundledContext->bBassEnabled = LVM_TRUE;
2479                tempDisabled = pContext->pBundledContext->bBassTempDisabled;
2480                break;
2481            case LVM_EQUALIZER:
2482                if (pContext->pBundledContext->bEqualizerEnabled == LVM_TRUE) {
2483                    ALOGV("\tEffect_setEnabled() LVM_EQUALIZER is already enabled");
2484                    return -EINVAL;
2485                }
2486                if(pContext->pBundledContext->SamplesToExitCountEq <= 0){
2487                    pContext->pBundledContext->NumberEffectsEnabled++;
2488                }
2489                pContext->pBundledContext->SamplesToExitCountEq =
2490                     (LVM_INT32)(pContext->pBundledContext->SamplesPerSecond*0.1);
2491                pContext->pBundledContext->bEqualizerEnabled = LVM_TRUE;
2492                break;
2493            case LVM_VIRTUALIZER:
2494                if (pContext->pBundledContext->bVirtualizerEnabled == LVM_TRUE) {
2495                    ALOGV("\tEffect_setEnabled() LVM_VIRTUALIZER is already enabled");
2496                    return -EINVAL;
2497                }
2498                if(pContext->pBundledContext->SamplesToExitCountVirt <= 0){
2499                    pContext->pBundledContext->NumberEffectsEnabled++;
2500                }
2501                pContext->pBundledContext->SamplesToExitCountVirt =
2502                     (LVM_INT32)(pContext->pBundledContext->SamplesPerSecond*0.1);
2503                pContext->pBundledContext->bVirtualizerEnabled = LVM_TRUE;
2504                tempDisabled = pContext->pBundledContext->bVirtualizerTempDisabled;
2505                break;
2506            case LVM_VOLUME:
2507                if (pContext->pBundledContext->bVolumeEnabled == LVM_TRUE) {
2508                    ALOGV("\tEffect_setEnabled() LVM_VOLUME is already enabled");
2509                    return -EINVAL;
2510                }
2511                pContext->pBundledContext->NumberEffectsEnabled++;
2512                pContext->pBundledContext->bVolumeEnabled = LVM_TRUE;
2513                break;
2514            default:
2515                ALOGV("\tEffect_setEnabled() invalid effect type");
2516                return -EINVAL;
2517        }
2518        if (!tempDisabled) {
2519            LvmEffect_enable(pContext);
2520        }
2521    } else {
2522        switch (pContext->EffectType) {
2523            case LVM_BASS_BOOST:
2524                if (pContext->pBundledContext->bBassEnabled == LVM_FALSE) {
2525                    ALOGV("\tEffect_setEnabled() LVM_BASS_BOOST is already disabled");
2526                    return -EINVAL;
2527                }
2528                pContext->pBundledContext->bBassEnabled = LVM_FALSE;
2529                break;
2530            case LVM_EQUALIZER:
2531                if (pContext->pBundledContext->bEqualizerEnabled == LVM_FALSE) {
2532                    ALOGV("\tEffect_setEnabled() LVM_EQUALIZER is already disabled");
2533                    return -EINVAL;
2534                }
2535                pContext->pBundledContext->bEqualizerEnabled = LVM_FALSE;
2536                break;
2537            case LVM_VIRTUALIZER:
2538                if (pContext->pBundledContext->bVirtualizerEnabled == LVM_FALSE) {
2539                    ALOGV("\tEffect_setEnabled() LVM_VIRTUALIZER is already disabled");
2540                    return -EINVAL;
2541                }
2542                pContext->pBundledContext->bVirtualizerEnabled = LVM_FALSE;
2543                break;
2544            case LVM_VOLUME:
2545                if (pContext->pBundledContext->bVolumeEnabled == LVM_FALSE) {
2546                    ALOGV("\tEffect_setEnabled() LVM_VOLUME is already disabled");
2547                    return -EINVAL;
2548                }
2549                pContext->pBundledContext->bVolumeEnabled = LVM_FALSE;
2550                break;
2551            default:
2552                ALOGV("\tEffect_setEnabled() invalid effect type");
2553                return -EINVAL;
2554        }
2555        LvmEffect_disable(pContext);
2556    }
2557
2558    return 0;
2559}
2560
2561//----------------------------------------------------------------------------
2562// LVC_Convert_VolToDb()
2563//----------------------------------------------------------------------------
2564// Purpose:
2565// Convery volume in Q24 to dB
2566//
2567// Inputs:
2568//  vol:   Q.24 volume dB
2569//
2570//-----------------------------------------------------------------------
2571
2572int16_t LVC_Convert_VolToDb(uint32_t vol){
2573    int16_t  dB;
2574
2575    dB = LVC_ToDB_s32Tos16(vol <<7);
2576    dB = (dB +8)>>4;
2577    dB = (dB <-96) ? -96 : dB ;
2578
2579    return dB;
2580}
2581
2582} // namespace
2583} // namespace
2584
2585extern "C" {
2586/* Effect Control Interface Implementation: Process */
2587int Effect_process(effect_handle_t     self,
2588                              audio_buffer_t         *inBuffer,
2589                              audio_buffer_t         *outBuffer){
2590    EffectContext * pContext = (EffectContext *) self;
2591    LVM_ReturnStatus_en     LvmStatus = LVM_SUCCESS;                /* Function call status */
2592    int    status = 0;
2593    int    lvmStatus = 0;
2594    LVM_INT16   *in  = (LVM_INT16 *)inBuffer->raw;
2595    LVM_INT16   *out = (LVM_INT16 *)outBuffer->raw;
2596
2597//ALOGV("\tEffect_process Start : Enabled = %d     Called = %d (%8d %8d %8d)",
2598//pContext->pBundledContext->NumberEffectsEnabled,pContext->pBundledContext->NumberEffectsCalled,
2599//    pContext->pBundledContext->SamplesToExitCountBb,
2600//    pContext->pBundledContext->SamplesToExitCountVirt,
2601//    pContext->pBundledContext->SamplesToExitCountEq);
2602
2603    if (pContext == NULL){
2604        ALOGV("\tLVM_ERROR : Effect_process() ERROR pContext == NULL");
2605        return -EINVAL;
2606    }
2607
2608    //if(pContext->EffectType == LVM_BASS_BOOST){
2609    //  ALOGV("\tEffect_process: Effect type is BASS_BOOST");
2610    //}else if(pContext->EffectType == LVM_EQUALIZER){
2611    //  ALOGV("\tEffect_process: Effect type is LVM_EQUALIZER");
2612    //}else if(pContext->EffectType == LVM_VIRTUALIZER){
2613    //  ALOGV("\tEffect_process: Effect type is LVM_VIRTUALIZER");
2614    //}
2615
2616    if (inBuffer == NULL  || inBuffer->raw == NULL  ||
2617            outBuffer == NULL || outBuffer->raw == NULL ||
2618            inBuffer->frameCount != outBuffer->frameCount){
2619        ALOGV("\tLVM_ERROR : Effect_process() ERROR NULL INPUT POINTER OR FRAME COUNT IS WRONG");
2620        return -EINVAL;
2621    }
2622    if ((pContext->pBundledContext->bBassEnabled == LVM_FALSE)&&
2623        (pContext->EffectType == LVM_BASS_BOOST)){
2624        //ALOGV("\tEffect_process() LVM_BASS_BOOST Effect is not enabled");
2625        if(pContext->pBundledContext->SamplesToExitCountBb > 0){
2626            pContext->pBundledContext->SamplesToExitCountBb -= outBuffer->frameCount * 2; // STEREO
2627            //ALOGV("\tEffect_process: Waiting to turn off BASS_BOOST, %d samples left",
2628            //    pContext->pBundledContext->SamplesToExitCountBb);
2629        }
2630        if(pContext->pBundledContext->SamplesToExitCountBb <= 0) {
2631            status = -ENODATA;
2632            pContext->pBundledContext->NumberEffectsEnabled--;
2633            ALOGV("\tEffect_process() this is the last frame for LVM_BASS_BOOST");
2634        }
2635    }
2636    if ((pContext->pBundledContext->bVolumeEnabled == LVM_FALSE)&&
2637        (pContext->EffectType == LVM_VOLUME)){
2638        //ALOGV("\tEffect_process() LVM_VOLUME Effect is not enabled");
2639        status = -ENODATA;
2640        pContext->pBundledContext->NumberEffectsEnabled--;
2641    }
2642    if ((pContext->pBundledContext->bEqualizerEnabled == LVM_FALSE)&&
2643        (pContext->EffectType == LVM_EQUALIZER)){
2644        //ALOGV("\tEffect_process() LVM_EQUALIZER Effect is not enabled");
2645        if(pContext->pBundledContext->SamplesToExitCountEq > 0){
2646            pContext->pBundledContext->SamplesToExitCountEq -= outBuffer->frameCount * 2; // STEREO
2647            //ALOGV("\tEffect_process: Waiting to turn off EQUALIZER, %d samples left",
2648            //    pContext->pBundledContext->SamplesToExitCountEq);
2649        }
2650        if(pContext->pBundledContext->SamplesToExitCountEq <= 0) {
2651            status = -ENODATA;
2652            pContext->pBundledContext->NumberEffectsEnabled--;
2653            ALOGV("\tEffect_process() this is the last frame for LVM_EQUALIZER");
2654        }
2655    }
2656    if ((pContext->pBundledContext->bVirtualizerEnabled == LVM_FALSE)&&
2657        (pContext->EffectType == LVM_VIRTUALIZER)){
2658        //ALOGV("\tEffect_process() LVM_VIRTUALIZER Effect is not enabled");
2659        if(pContext->pBundledContext->SamplesToExitCountVirt > 0){
2660            pContext->pBundledContext->SamplesToExitCountVirt -= outBuffer->frameCount * 2;// STEREO
2661            //ALOGV("\tEffect_process: Waiting for to turn off VIRTUALIZER, %d samples left",
2662            //    pContext->pBundledContext->SamplesToExitCountVirt);
2663        }
2664        if(pContext->pBundledContext->SamplesToExitCountVirt <= 0) {
2665            status = -ENODATA;
2666            pContext->pBundledContext->NumberEffectsEnabled--;
2667            ALOGV("\tEffect_process() this is the last frame for LVM_VIRTUALIZER");
2668        }
2669    }
2670
2671    if(status != -ENODATA){
2672        pContext->pBundledContext->NumberEffectsCalled++;
2673    }
2674
2675    if(pContext->pBundledContext->NumberEffectsCalled ==
2676       pContext->pBundledContext->NumberEffectsEnabled){
2677        //ALOGV("\tEffect_process     Calling process with %d effects enabled, %d called: Effect %d",
2678        //pContext->pBundledContext->NumberEffectsEnabled,
2679        //pContext->pBundledContext->NumberEffectsCalled, pContext->EffectType);
2680
2681        if(status == -ENODATA){
2682            ALOGV("\tEffect_process() processing last frame");
2683        }
2684        pContext->pBundledContext->NumberEffectsCalled = 0;
2685        /* Process all the available frames, block processing is
2686           handled internalLY by the LVM bundle */
2687        lvmStatus = android::LvmBundle_process(    (LVM_INT16 *)inBuffer->raw,
2688                                                (LVM_INT16 *)outBuffer->raw,
2689                                                outBuffer->frameCount,
2690                                                pContext);
2691        if(lvmStatus != LVM_SUCCESS){
2692            ALOGV("\tLVM_ERROR : LvmBundle_process returned error %d", lvmStatus);
2693            return lvmStatus;
2694        }
2695    } else {
2696        //ALOGV("\tEffect_process Not Calling process with %d effects enabled, %d called: Effect %d",
2697        //pContext->pBundledContext->NumberEffectsEnabled,
2698        //pContext->pBundledContext->NumberEffectsCalled, pContext->EffectType);
2699        // 2 is for stereo input
2700        if (pContext->config.outputCfg.accessMode == EFFECT_BUFFER_ACCESS_ACCUMULATE) {
2701            for (size_t i=0; i < outBuffer->frameCount*2; i++){
2702                outBuffer->s16[i] =
2703                        clamp16((LVM_INT32)outBuffer->s16[i] + (LVM_INT32)inBuffer->s16[i]);
2704            }
2705        } else if (outBuffer->raw != inBuffer->raw) {
2706            memcpy(outBuffer->raw, inBuffer->raw, outBuffer->frameCount*sizeof(LVM_INT16)*2);
2707        }
2708    }
2709
2710    return status;
2711}   /* end Effect_process */
2712
2713/* Effect Control Interface Implementation: Command */
2714int Effect_command(effect_handle_t  self,
2715                              uint32_t            cmdCode,
2716                              uint32_t            cmdSize,
2717                              void                *pCmdData,
2718                              uint32_t            *replySize,
2719                              void                *pReplyData){
2720    EffectContext * pContext = (EffectContext *) self;
2721    int retsize;
2722
2723    //ALOGV("\t\nEffect_command start");
2724
2725    if(pContext->EffectType == LVM_BASS_BOOST){
2726        //ALOGV("\tEffect_command setting command for LVM_BASS_BOOST");
2727    }
2728    if(pContext->EffectType == LVM_VIRTUALIZER){
2729        //ALOGV("\tEffect_command setting command for LVM_VIRTUALIZER");
2730    }
2731    if(pContext->EffectType == LVM_EQUALIZER){
2732        //ALOGV("\tEffect_command setting command for LVM_EQUALIZER");
2733    }
2734    if(pContext->EffectType == LVM_VOLUME){
2735        //ALOGV("\tEffect_command setting command for LVM_VOLUME");
2736    }
2737
2738    if (pContext == NULL){
2739        ALOGV("\tLVM_ERROR : Effect_command ERROR pContext == NULL");
2740        return -EINVAL;
2741    }
2742
2743    //ALOGV("\tEffect_command INPUTS are: command %d cmdSize %d",cmdCode, cmdSize);
2744
2745    // Incase we disable an effect, next time process is
2746    // called the number of effect called could be greater
2747    // pContext->pBundledContext->NumberEffectsCalled = 0;
2748
2749    //ALOGV("\tEffect_command NumberEffectsCalled = %d, NumberEffectsEnabled = %d",
2750    //        pContext->pBundledContext->NumberEffectsCalled,
2751    //        pContext->pBundledContext->NumberEffectsEnabled);
2752
2753    switch (cmdCode){
2754        case EFFECT_CMD_INIT:
2755            if (pReplyData == NULL || replySize == NULL || *replySize != sizeof(int)){
2756                ALOGV("\tLVM_ERROR, EFFECT_CMD_INIT: ERROR for effect type %d",
2757                        pContext->EffectType);
2758                return -EINVAL;
2759            }
2760            *(int *) pReplyData = 0;
2761            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_INIT start");
2762            if(pContext->EffectType == LVM_BASS_BOOST){
2763                //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_INIT for LVM_BASS_BOOST");
2764                android::BassSetStrength(pContext, 0);
2765            }
2766            if(pContext->EffectType == LVM_VIRTUALIZER){
2767                //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_INIT for LVM_VIRTUALIZER");
2768                android::VirtualizerSetStrength(pContext, 0);
2769            }
2770            if(pContext->EffectType == LVM_EQUALIZER){
2771                //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_INIT for LVM_EQUALIZER");
2772                android::EqualizerSetPreset(pContext, 0);
2773            }
2774            if(pContext->EffectType == LVM_VOLUME){
2775                //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_INIT for LVM_VOLUME");
2776                *(int *) pReplyData = android::VolumeSetVolumeLevel(pContext, 0);
2777            }
2778            break;
2779
2780        case EFFECT_CMD_SET_CONFIG:
2781            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_SET_CONFIG start");
2782            if (pCmdData    == NULL || cmdSize     != sizeof(effect_config_t) ||
2783                    pReplyData  == NULL || replySize == NULL || *replySize  != sizeof(int)) {
2784                ALOGV("\tLVM_ERROR : Effect_command cmdCode Case: "
2785                        "EFFECT_CMD_SET_CONFIG: ERROR");
2786                return -EINVAL;
2787            }
2788            *(int *) pReplyData = android::Effect_setConfig(pContext, (effect_config_t *) pCmdData);
2789            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_SET_CONFIG end");
2790            break;
2791
2792        case EFFECT_CMD_GET_CONFIG:
2793            if (pReplyData == NULL || replySize == NULL || *replySize != sizeof(effect_config_t)) {
2794                ALOGV("\tLVM_ERROR : Effect_command cmdCode Case: "
2795                        "EFFECT_CMD_GET_CONFIG: ERROR");
2796                return -EINVAL;
2797            }
2798
2799            android::Effect_getConfig(pContext, (effect_config_t *)pReplyData);
2800            break;
2801
2802        case EFFECT_CMD_RESET:
2803            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_RESET start");
2804            android::Effect_setConfig(pContext, &pContext->config);
2805            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_RESET end");
2806            break;
2807
2808        case EFFECT_CMD_GET_PARAM:{
2809            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_GET_PARAM start");
2810
2811            effect_param_t *p = (effect_param_t *)pCmdData;
2812
2813            if (pCmdData == NULL || cmdSize < sizeof(effect_param_t) ||
2814                    cmdSize < (sizeof(effect_param_t) + p->psize) ||
2815                    pReplyData == NULL || replySize == NULL ||
2816                    *replySize < (sizeof(effect_param_t) + p->psize)) {
2817                ALOGV("\tLVM_ERROR : EFFECT_CMD_GET_PARAM: ERROR");
2818                return -EINVAL;
2819            }
2820
2821            memcpy(pReplyData, pCmdData, sizeof(effect_param_t) + p->psize);
2822
2823            p = (effect_param_t *)pReplyData;
2824
2825            int voffset = ((p->psize - 1) / sizeof(int32_t) + 1) * sizeof(int32_t);
2826
2827            if(pContext->EffectType == LVM_BASS_BOOST){
2828                p->status = android::BassBoost_getParameter(pContext,
2829                                                            p->data,
2830                                                            (size_t  *)&p->vsize,
2831                                                            p->data + voffset);
2832                //ALOGV("\tBassBoost_command EFFECT_CMD_GET_PARAM "
2833                //        "*pCmdData %d, *replySize %d, *pReplyData %d ",
2834                //        *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)),
2835                //        *replySize,
2836                //        *(int16_t *)((char *)pReplyData + sizeof(effect_param_t) + voffset));
2837            }
2838
2839            if(pContext->EffectType == LVM_VIRTUALIZER){
2840                p->status = android::Virtualizer_getParameter(pContext,
2841                                                             (void *)p->data,
2842                                                             (size_t  *)&p->vsize,
2843                                                              p->data + voffset);
2844
2845                //ALOGV("\tVirtualizer_command EFFECT_CMD_GET_PARAM "
2846                //        "*pCmdData %d, *replySize %d, *pReplyData %d ",
2847                //        *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)),
2848                //        *replySize,
2849                //        *(int16_t *)((char *)pReplyData + sizeof(effect_param_t) + voffset));
2850            }
2851            if(pContext->EffectType == LVM_EQUALIZER){
2852                //ALOGV("\tEqualizer_command cmdCode Case: "
2853                //        "EFFECT_CMD_GET_PARAM start");
2854                p->status = android::Equalizer_getParameter(pContext,
2855                                                            p->data,
2856                                                            &p->vsize,
2857                                                            p->data + voffset);
2858
2859                //ALOGV("\tEqualizer_command EFFECT_CMD_GET_PARAM *pCmdData %d, *replySize %d, "
2860                //       "*pReplyData %08x %08x",
2861                //        *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)), *replySize,
2862                //        *(int32_t *)((char *)pReplyData + sizeof(effect_param_t) + voffset),
2863                //        *(int32_t *)((char *)pReplyData + sizeof(effect_param_t) + voffset +
2864                //        sizeof(int32_t)));
2865            }
2866            if(pContext->EffectType == LVM_VOLUME){
2867                //ALOGV("\tVolume_command cmdCode Case: EFFECT_CMD_GET_PARAM start");
2868                p->status = android::Volume_getParameter(pContext,
2869                                                         (void *)p->data,
2870                                                         (size_t  *)&p->vsize,
2871                                                         p->data + voffset);
2872
2873                //ALOGV("\tVolume_command EFFECT_CMD_GET_PARAM "
2874                //        "*pCmdData %d, *replySize %d, *pReplyData %d ",
2875                //        *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)),
2876                //        *replySize,
2877                //        *(int16_t *)((char *)pReplyData + sizeof(effect_param_t) + voffset));
2878            }
2879            *replySize = sizeof(effect_param_t) + voffset + p->vsize;
2880
2881            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_GET_PARAM end");
2882        } break;
2883        case EFFECT_CMD_SET_PARAM:{
2884            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_SET_PARAM start");
2885            if(pContext->EffectType == LVM_BASS_BOOST){
2886                //ALOGV("\tBassBoost_command EFFECT_CMD_SET_PARAM param %d, *replySize %d, value %d",
2887                //       *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)),
2888                //       *replySize,
2889                //       *(int16_t *)((char *)pCmdData + sizeof(effect_param_t) + sizeof(int32_t)));
2890
2891                if (pCmdData   == NULL ||
2892                        cmdSize    != (sizeof(effect_param_t) + sizeof(int32_t) +sizeof(int16_t)) ||
2893                        pReplyData == NULL || replySize == NULL || *replySize != sizeof(int32_t)) {
2894                    ALOGV("\tLVM_ERROR : BassBoost_command cmdCode Case: "
2895                            "EFFECT_CMD_SET_PARAM: ERROR");
2896                    return -EINVAL;
2897                }
2898                effect_param_t *p = (effect_param_t *) pCmdData;
2899
2900                if (p->psize != sizeof(int32_t)){
2901                    ALOGV("\tLVM_ERROR : BassBoost_command cmdCode Case: "
2902                            "EFFECT_CMD_SET_PARAM: ERROR, psize is not sizeof(int32_t)");
2903                    return -EINVAL;
2904                }
2905
2906                //ALOGV("\tnBassBoost_command cmdSize is %d\n"
2907                //        "\tsizeof(effect_param_t) is  %d\n"
2908                //        "\tp->psize is %d\n"
2909                //        "\tp->vsize is %d"
2910                //        "\n",
2911                //        cmdSize, sizeof(effect_param_t), p->psize, p->vsize );
2912
2913                *(int *)pReplyData = android::BassBoost_setParameter(pContext,
2914                                                                    (void *)p->data,
2915                                                                    p->data + p->psize);
2916            }
2917            if(pContext->EffectType == LVM_VIRTUALIZER){
2918              //ALOGV("\tVirtualizer_command EFFECT_CMD_SET_PARAM param %d, *replySize %d, value %d",
2919              //        *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)),
2920              //        *replySize,
2921              //        *(int16_t *)((char *)pCmdData + sizeof(effect_param_t) + sizeof(int32_t)));
2922
2923                if (pCmdData   == NULL ||
2924                        // legal parameters are int16_t or int32_t
2925                        cmdSize    > (sizeof(effect_param_t) + sizeof(int32_t) +sizeof(int32_t)) ||
2926                        cmdSize    < (sizeof(effect_param_t) + sizeof(int32_t) +sizeof(int16_t)) ||
2927                        pReplyData == NULL || replySize == NULL || *replySize != sizeof(int32_t)) {
2928                    ALOGV("\tLVM_ERROR : Virtualizer_command cmdCode Case: "
2929                            "EFFECT_CMD_SET_PARAM: ERROR");
2930                    return -EINVAL;
2931                }
2932                effect_param_t *p = (effect_param_t *) pCmdData;
2933
2934                if (p->psize != sizeof(int32_t)){
2935                    ALOGV("\tLVM_ERROR : Virtualizer_command cmdCode Case: "
2936                            "EFFECT_CMD_SET_PARAM: ERROR, psize is not sizeof(int32_t)");
2937                    return -EINVAL;
2938                }
2939
2940                //ALOGV("\tnVirtualizer_command cmdSize is %d\n"
2941                //        "\tsizeof(effect_param_t) is  %d\n"
2942                //        "\tp->psize is %d\n"
2943                //        "\tp->vsize is %d"
2944                //        "\n",
2945                //        cmdSize, sizeof(effect_param_t), p->psize, p->vsize );
2946
2947                *(int *)pReplyData = android::Virtualizer_setParameter(pContext,
2948                                                                      (void *)p->data,
2949                                                                       p->data + p->psize);
2950            }
2951            if(pContext->EffectType == LVM_EQUALIZER){
2952               //ALOGV("\tEqualizer_command cmdCode Case: "
2953               //        "EFFECT_CMD_SET_PARAM start");
2954               //ALOGV("\tEqualizer_command EFFECT_CMD_SET_PARAM param %d, *replySize %d, value %d ",
2955               //        *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)),
2956               //        *replySize,
2957               //        *(int16_t *)((char *)pCmdData + sizeof(effect_param_t) + sizeof(int32_t)));
2958
2959                if (pCmdData == NULL || cmdSize < (sizeof(effect_param_t) + sizeof(int32_t)) ||
2960                        pReplyData == NULL || replySize == NULL || *replySize != sizeof(int32_t)) {
2961                    ALOGV("\tLVM_ERROR : Equalizer_command cmdCode Case: "
2962                            "EFFECT_CMD_SET_PARAM: ERROR");
2963                    return -EINVAL;
2964                }
2965                effect_param_t *p = (effect_param_t *) pCmdData;
2966
2967                *(int *)pReplyData = android::Equalizer_setParameter(pContext,
2968                                                                    (void *)p->data,
2969                                                                     p->data + p->psize);
2970            }
2971            if(pContext->EffectType == LVM_VOLUME){
2972                //ALOGV("\tVolume_command cmdCode Case: EFFECT_CMD_SET_PARAM start");
2973                //ALOGV("\tVolume_command EFFECT_CMD_SET_PARAM param %d, *replySize %d, value %d ",
2974                //        *(int32_t *)((char *)pCmdData + sizeof(effect_param_t)),
2975                //        *replySize,
2976                //        *(int16_t *)((char *)pCmdData + sizeof(effect_param_t) +sizeof(int32_t)));
2977
2978                if (pCmdData   == NULL ||
2979                        cmdSize    < (sizeof(effect_param_t) + sizeof(int32_t)) ||
2980                        pReplyData == NULL || replySize == NULL ||
2981                        *replySize != sizeof(int32_t)) {
2982                    ALOGV("\tLVM_ERROR : Volume_command cmdCode Case: "
2983                            "EFFECT_CMD_SET_PARAM: ERROR");
2984                    return -EINVAL;
2985                }
2986                effect_param_t *p = (effect_param_t *) pCmdData;
2987
2988                *(int *)pReplyData = android::Volume_setParameter(pContext,
2989                                                                 (void *)p->data,
2990                                                                 p->data + p->psize);
2991            }
2992            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_SET_PARAM end");
2993        } break;
2994
2995        case EFFECT_CMD_ENABLE:
2996            ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_ENABLE start");
2997            if (pReplyData == NULL || replySize == NULL || *replySize != sizeof(int)) {
2998                ALOGV("\tLVM_ERROR : Effect_command cmdCode Case: EFFECT_CMD_ENABLE: ERROR");
2999                return -EINVAL;
3000            }
3001
3002            *(int *)pReplyData = android::Effect_setEnabled(pContext, LVM_TRUE);
3003            break;
3004
3005        case EFFECT_CMD_DISABLE:
3006            //ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_DISABLE start");
3007            if (pReplyData == NULL || replySize == NULL || *replySize != sizeof(int)) {
3008                ALOGV("\tLVM_ERROR : Effect_command cmdCode Case: EFFECT_CMD_DISABLE: ERROR");
3009                return -EINVAL;
3010            }
3011            *(int *)pReplyData = android::Effect_setEnabled(pContext, LVM_FALSE);
3012            break;
3013
3014        case EFFECT_CMD_SET_DEVICE:
3015        {
3016            ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_SET_DEVICE start");
3017            if (pCmdData   == NULL){
3018                ALOGV("\tLVM_ERROR : Effect_command cmdCode Case: EFFECT_CMD_SET_DEVICE: ERROR");
3019                return -EINVAL;
3020            }
3021
3022            uint32_t device = *(uint32_t *)pCmdData;
3023
3024            if (pContext->EffectType == LVM_BASS_BOOST) {
3025                if((device == AUDIO_DEVICE_OUT_SPEAKER) ||
3026                        (device == AUDIO_DEVICE_OUT_BLUETOOTH_SCO_CARKIT) ||
3027                        (device == AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_SPEAKER)){
3028                    ALOGV("\tEFFECT_CMD_SET_DEVICE device is invalid for LVM_BASS_BOOST %d",
3029                          *(int32_t *)pCmdData);
3030                    ALOGV("\tEFFECT_CMD_SET_DEVICE temporary disable LVM_BAS_BOOST");
3031
3032                    // If a device doesnt support bassboost the effect must be temporarily disabled
3033                    // the effect must still report its original state as this can only be changed
3034                    // by the ENABLE/DISABLE command
3035
3036                    if (pContext->pBundledContext->bBassEnabled == LVM_TRUE) {
3037                        ALOGV("\tEFFECT_CMD_SET_DEVICE disable LVM_BASS_BOOST %d",
3038                             *(int32_t *)pCmdData);
3039                        android::LvmEffect_disable(pContext);
3040                    }
3041                    pContext->pBundledContext->bBassTempDisabled = LVM_TRUE;
3042                } else {
3043                    ALOGV("\tEFFECT_CMD_SET_DEVICE device is valid for LVM_BASS_BOOST %d",
3044                         *(int32_t *)pCmdData);
3045
3046                    // If a device supports bassboost and the effect has been temporarily disabled
3047                    // previously then re-enable it
3048
3049                    if (pContext->pBundledContext->bBassEnabled == LVM_TRUE) {
3050                        ALOGV("\tEFFECT_CMD_SET_DEVICE re-enable LVM_BASS_BOOST %d",
3051                             *(int32_t *)pCmdData);
3052                        android::LvmEffect_enable(pContext);
3053                    }
3054                    pContext->pBundledContext->bBassTempDisabled = LVM_FALSE;
3055                }
3056            }
3057            if (pContext->EffectType == LVM_VIRTUALIZER) {
3058                if((device == AUDIO_DEVICE_OUT_SPEAKER)||
3059                        (device == AUDIO_DEVICE_OUT_BLUETOOTH_SCO_CARKIT)||
3060                        (device == AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_SPEAKER)){
3061                    ALOGV("\tEFFECT_CMD_SET_DEVICE device is invalid for LVM_VIRTUALIZER %d",
3062                          *(int32_t *)pCmdData);
3063                    ALOGV("\tEFFECT_CMD_SET_DEVICE temporary disable LVM_VIRTUALIZER");
3064
3065                    //If a device doesnt support virtualizer the effect must be temporarily disabled
3066                    // the effect must still report its original state as this can only be changed
3067                    // by the ENABLE/DISABLE command
3068
3069                    if (pContext->pBundledContext->bVirtualizerEnabled == LVM_TRUE) {
3070                        ALOGV("\tEFFECT_CMD_SET_DEVICE disable LVM_VIRTUALIZER %d",
3071                              *(int32_t *)pCmdData);
3072                        android::LvmEffect_disable(pContext);
3073                    }
3074                    pContext->pBundledContext->bVirtualizerTempDisabled = LVM_TRUE;
3075                } else {
3076                    ALOGV("\tEFFECT_CMD_SET_DEVICE device is valid for LVM_VIRTUALIZER %d",
3077                          *(int32_t *)pCmdData);
3078
3079                    // If a device supports virtualizer and the effect has been temporarily disabled
3080                    // previously then re-enable it
3081
3082                    if(pContext->pBundledContext->bVirtualizerEnabled == LVM_TRUE){
3083                        ALOGV("\tEFFECT_CMD_SET_DEVICE re-enable LVM_VIRTUALIZER %d",
3084                              *(int32_t *)pCmdData);
3085                        android::LvmEffect_enable(pContext);
3086                    }
3087                    pContext->pBundledContext->bVirtualizerTempDisabled = LVM_FALSE;
3088                }
3089            }
3090            ALOGV("\tEffect_command cmdCode Case: EFFECT_CMD_SET_DEVICE end");
3091            break;
3092        }
3093        case EFFECT_CMD_SET_VOLUME:
3094        {
3095            uint32_t leftVolume, rightVolume;
3096            int16_t  leftdB, rightdB;
3097            int16_t  maxdB, pandB;
3098            int32_t  vol_ret[2] = {1<<24,1<<24}; // Apply no volume
3099            int      status = 0;
3100            LVM_ControlParams_t     ActiveParams;           /* Current control Parameters */
3101            LVM_ReturnStatus_en     LvmStatus=LVM_SUCCESS;  /* Function call status */
3102
3103            // if pReplyData is NULL, VOL_CTRL is delegated to another effect
3104            if(pReplyData == LVM_NULL){
3105                break;
3106            }
3107
3108            if (pCmdData == NULL || cmdSize != 2 * sizeof(uint32_t) || pReplyData == NULL ||
3109                    replySize == NULL || *replySize < 2*sizeof(int32_t)) {
3110                ALOGV("\tLVM_ERROR : Effect_command cmdCode Case: "
3111                        "EFFECT_CMD_SET_VOLUME: ERROR");
3112                return -EINVAL;
3113            }
3114
3115            leftVolume  = ((*(uint32_t *)pCmdData));
3116            rightVolume = ((*((uint32_t *)pCmdData + 1)));
3117
3118            if(leftVolume == 0x1000000){
3119                leftVolume -= 1;
3120            }
3121            if(rightVolume == 0x1000000){
3122                rightVolume -= 1;
3123            }
3124
3125            // Convert volume to dB
3126            leftdB  = android::LVC_Convert_VolToDb(leftVolume);
3127            rightdB = android::LVC_Convert_VolToDb(rightVolume);
3128
3129            pandB = rightdB - leftdB;
3130
3131            // Calculate max volume in dB
3132            maxdB = leftdB;
3133            if(rightdB > maxdB){
3134                maxdB = rightdB;
3135            }
3136            //ALOGV("\tEFFECT_CMD_SET_VOLUME Session: %d, SessionID: %d VOLUME is %d dB (%d), "
3137            //      "effect is %d",
3138            //pContext->pBundledContext->SessionNo, pContext->pBundledContext->SessionId,
3139            //(int32_t)maxdB, maxVol<<7, pContext->EffectType);
3140            //ALOGV("\tEFFECT_CMD_SET_VOLUME: Left is %d, Right is %d", leftVolume, rightVolume);
3141            //ALOGV("\tEFFECT_CMD_SET_VOLUME: Left %ddB, Right %ddB, Position %ddB",
3142            //        leftdB, rightdB, pandB);
3143
3144            memcpy(pReplyData, vol_ret, sizeof(int32_t)*2);
3145            android::VolumeSetVolumeLevel(pContext, (int16_t)(maxdB*100));
3146
3147            /* Get the current settings */
3148            LvmStatus =LVM_GetControlParameters(pContext->pBundledContext->hInstance,&ActiveParams);
3149            LVM_ERROR_CHECK(LvmStatus, "LVM_GetControlParameters", "VolumeSetStereoPosition")
3150            if(LvmStatus != LVM_SUCCESS) return -EINVAL;
3151
3152            /* Volume parameters */
3153            ActiveParams.VC_Balance  = pandB;
3154            ALOGV("\t\tVolumeSetStereoPosition() (-96dB -> +96dB)-> %d\n", ActiveParams.VC_Balance );
3155
3156            /* Activate the initial settings */
3157            LvmStatus =LVM_SetControlParameters(pContext->pBundledContext->hInstance,&ActiveParams);
3158            LVM_ERROR_CHECK(LvmStatus, "LVM_SetControlParameters", "VolumeSetStereoPosition")
3159            if(LvmStatus != LVM_SUCCESS) return -EINVAL;
3160            break;
3161         }
3162        case EFFECT_CMD_SET_AUDIO_MODE:
3163            break;
3164        default:
3165            return -EINVAL;
3166    }
3167
3168    //ALOGV("\tEffect_command end...\n\n");
3169    return 0;
3170}    /* end Effect_command */
3171
3172/* Effect Control Interface Implementation: get_descriptor */
3173int Effect_getDescriptor(effect_handle_t   self,
3174                                    effect_descriptor_t *pDescriptor)
3175{
3176    EffectContext * pContext = (EffectContext *) self;
3177    const effect_descriptor_t *desc;
3178
3179    if (pContext == NULL || pDescriptor == NULL) {
3180        ALOGV("Effect_getDescriptor() invalid param");
3181        return -EINVAL;
3182    }
3183
3184    switch(pContext->EffectType) {
3185        case LVM_BASS_BOOST:
3186            desc = &android::gBassBoostDescriptor;
3187            break;
3188        case LVM_VIRTUALIZER:
3189            desc = &android::gVirtualizerDescriptor;
3190            break;
3191        case LVM_EQUALIZER:
3192            desc = &android::gEqualizerDescriptor;
3193            break;
3194        case LVM_VOLUME:
3195            desc = &android::gVolumeDescriptor;
3196            break;
3197        default:
3198            return -EINVAL;
3199    }
3200
3201    *pDescriptor = *desc;
3202
3203    return 0;
3204}   /* end Effect_getDescriptor */
3205
3206// effect_handle_t interface implementation for effect
3207const struct effect_interface_s gLvmEffectInterface = {
3208    Effect_process,
3209    Effect_command,
3210    Effect_getDescriptor,
3211    NULL,
3212};    /* end gLvmEffectInterface */
3213
3214// This is the only symbol that needs to be exported
3215__attribute__ ((visibility ("default")))
3216audio_effect_library_t AUDIO_EFFECT_LIBRARY_INFO_SYM = {
3217    tag : AUDIO_EFFECT_LIBRARY_TAG,
3218    version : EFFECT_LIBRARY_API_VERSION,
3219    name : "Effect Bundle Library",
3220    implementor : "NXP Software Ltd.",
3221    create_effect : android::EffectCreate,
3222    release_effect : android::EffectRelease,
3223    get_descriptor : android::EffectGetDescriptor,
3224};
3225
3226}
3227