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